Merge branch 'main' into update-bundle/codeql-bundle-v2.16.2

This commit is contained in:
Dave Bartolomeo 2024-02-12 09:34:51 -08:00 committed by GitHub
commit b0346e4adb
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
98 changed files with 1222 additions and 667 deletions

88
.github/workflows/__build-mode-autobuild.yml generated vendored Normal file
View file

@ -0,0 +1,88 @@
# Warning: This file is generated automatically, and should not be modified.
# Instead, please modify the template in the pr-checks directory and run:
# (cd pr-checks; pip install ruamel.yaml@0.17.31 && python3 sync.py)
# to regenerate this file.
name: PR Check - Build mode autobuild
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
GO111MODULE: auto
CODEQL_EXTRACTOR_JAVA_AGENT_DISABLE_KOTLIN: 'true'
on:
push:
branches:
- main
- releases/v*
pull_request:
types:
- opened
- synchronize
- reopened
- ready_for_review
workflow_dispatch: {}
jobs:
build-mode-autobuild:
strategy:
matrix:
include:
- os: ubuntu-latest
version: nightly-latest
name: Build mode autobuild
permissions:
contents: read
security-events: write
timeout-minutes: 45
runs-on: ${{ matrix.os }}
steps:
- name: Setup Python on MacOS
uses: actions/setup-python@v5
if: >-
matrix.os == 'macos-latest' && (
matrix.version == 'stable-20221211' ||
matrix.version == 'stable-20230418' ||
matrix.version == 'stable-v2.13.5' ||
matrix.version == 'stable-v2.14.6')
with:
python-version: '3.11'
- name: Check out repository
uses: actions/checkout@v4
- name: Prepare test
id: prepare-test
uses: ./.github/actions/prepare-test
with:
version: ${{ matrix.version }}
use-all-platform-bundle: 'false'
- name: Set environment variable for Swift enablement
if: runner.os != 'Windows' && matrix.version == '20221211'
shell: bash
run: echo "CODEQL_ENABLE_EXPERIMENTAL_FEATURES_SWIFT=true" >> $GITHUB_ENV
- name: Set up Java test repo configuration
run: |
mv * .github ../action/tests/multi-language-repo/
mv ../action/tests/multi-language-repo/.github/workflows .github
mv ../action/tests/java-repo/* .
- uses: ./../action/init
id: init
with:
build-mode: autobuild
db-location: ${{ runner.temp }}/customDbLocation
languages: java
tools: ${{ steps.prepare-test.outputs.tools-url }}
- name: Validate database build mode
run: |
metadata_path="$RUNNER_TEMP/customDbLocation/java/codeql-database.yml"
build_mode=$(yq eval '.buildMode' "$metadata_path")
if [[ "$build_mode" != "autobuild" ]]; then
echo "Expected build mode to be 'autobuild' but was $build_mode"
exit 1
fi
- uses: ./../action/analyze
env:
CODEQL_ACTION_TEST_MODE: true

90
.github/workflows/__build-mode-manual.yml generated vendored Normal file
View file

@ -0,0 +1,90 @@
# Warning: This file is generated automatically, and should not be modified.
# Instead, please modify the template in the pr-checks directory and run:
# (cd pr-checks; pip install ruamel.yaml@0.17.31 && python3 sync.py)
# to regenerate this file.
name: PR Check - Build mode manual
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
GO111MODULE: auto
CODEQL_EXTRACTOR_JAVA_AGENT_DISABLE_KOTLIN: 'true'
on:
push:
branches:
- main
- releases/v*
pull_request:
types:
- opened
- synchronize
- reopened
- ready_for_review
workflow_dispatch: {}
jobs:
build-mode-manual:
strategy:
matrix:
include:
- os: ubuntu-latest
version: nightly-latest
name: Build mode manual
permissions:
contents: read
security-events: write
timeout-minutes: 45
runs-on: ${{ matrix.os }}
steps:
- name: Setup Python on MacOS
uses: actions/setup-python@v5
if: >-
matrix.os == 'macos-latest' && (
matrix.version == 'stable-20221211' ||
matrix.version == 'stable-20230418' ||
matrix.version == 'stable-v2.13.5' ||
matrix.version == 'stable-v2.14.6')
with:
python-version: '3.11'
- name: Check out repository
uses: actions/checkout@v4
- name: Prepare test
id: prepare-test
uses: ./.github/actions/prepare-test
with:
version: ${{ matrix.version }}
use-all-platform-bundle: 'false'
- name: Set environment variable for Swift enablement
if: runner.os != 'Windows' && matrix.version == '20221211'
shell: bash
run: echo "CODEQL_ENABLE_EXPERIMENTAL_FEATURES_SWIFT=true" >> $GITHUB_ENV
- uses: ./../action/init
id: init
with:
build-mode: manual
db-location: ${{ runner.temp }}/customDbLocation
languages: java
tools: ${{ steps.prepare-test.outputs.tools-url }}
- name: Validate database build mode
run: |
metadata_path="$RUNNER_TEMP/customDbLocation/java/codeql-database.yml"
build_mode=$(yq eval '.buildMode' "$metadata_path")
if [[ "$build_mode" != "manual" ]]; then
echo "Expected build mode to be 'manual' but was $build_mode"
exit 1
fi
- uses: ./../action/.github/actions/setup-swift
with:
codeql-path: ${{ steps.init.outputs.codeql-path }}
- name: Build code
shell: bash
run: ./build.sh
- uses: ./../action/analyze
env:
CODEQL_ACTION_TEST_MODE: true

View file

@ -79,7 +79,10 @@ jobs:
exit 1 exit 1
fi fi
# The latest nightly supports omitting the autobuild Action when the build mode is specified.
- uses: ./../action/autobuild - uses: ./../action/autobuild
if: matrix.version != 'nightly-latest'
- uses: ./../action/analyze - uses: ./../action/analyze
env: env:
CODEQL_ACTION_TEST_MODE: true CODEQL_ACTION_TEST_MODE: true

View file

@ -101,13 +101,13 @@ jobs:
core.setFailed('`codeqlConfigSummary` property not found in the SARIF run property bag.'); core.setFailed('`codeqlConfigSummary` property not found in the SARIF run property bag.');
} }
if (configSummary.disableDefaultQueries !== false) { if (configSummary.disableDefaultQueries !== false) {
core.setFailed('`disableDefaultQueries` property incorrect: expected false, got ' + core.setFailed('`disableDefaultQueries` property incorrect: expected false, got ' +
`${JSON.stringify(configSummary.disableDefaultQueries)}.`); `${JSON.stringify(configSummary.disableDefaultQueries)}.`);
} }
const expectedQueries = [{ type: 'builtinSuite', uses: 'security-extended' }]; const expectedQueries = [{ type: 'builtinSuite', uses: 'security-extended' }];
// Use JSON.stringify to deep-equal the arrays. // Use JSON.stringify to deep-equal the arrays.
if (JSON.stringify(configSummary.queries) !== JSON.stringify(expectedQueries)) { if (JSON.stringify(configSummary.queries) !== JSON.stringify(expectedQueries)) {
core.setFailed(`\`queries\` property incorrect: expected ${JSON.stringify(expectedQueries)}, got ` + core.setFailed(`\`queries\` property incorrect: expected ${JSON.stringify(expectedQueries)}, got ` +
`${JSON.stringify(configSummary.queries)}.`); `${JSON.stringify(configSummary.queries)}.`);
} }
core.info('Finished config export tests.'); core.info('Finished config export tests.');

View file

@ -136,7 +136,7 @@ jobs:
core.setFailed( core.setFailed(
'Expected exactly one status page reporting descriptor for this diagnostic in the ' + 'Expected exactly one status page reporting descriptor for this diagnostic in the ' +
`'runs[].invocations[].toolExecutionNotifications[]' SARIF property, but found ` + `'runs[].invocations[].toolExecutionNotifications[]' SARIF property, but found ` +
`${statusPageNotifications.length}. All notification reporting descriptors: ` + `${statusPageNotifications.length}. All notification reporting descriptors: ` +
`${JSON.stringify(toolExecutionNotifications)}.` `${JSON.stringify(toolExecutionNotifications)}.`
); );
} }

View file

@ -146,7 +146,7 @@ jobs:
- name: Check language autodetect for Swift - name: Check language autodetect for Swift
if: >- if: >-
env.CODEQL_ENABLE_EXPERIMENTAL_FEATURES_SWIFT == 'true' || env.CODEQL_ENABLE_EXPERIMENTAL_FEATURES_SWIFT == 'true' ||
(runner.os != 'Windows' && matrix.version == 'nightly-latest') (runner.os != 'Windows' && matrix.version == 'nightly-latest')
shell: bash shell: bash
run: | run: |

View file

@ -20,15 +20,12 @@ on:
workflow_dispatch: {} workflow_dispatch: {}
jobs: jobs:
upload-artifacts: upload-artifacts:
strategy:
matrix:
os: [ubuntu-latest, macos-latest]
name: Upload debug artifacts after failure in analyze name: Upload debug artifacts after failure in analyze
continue-on-error: true continue-on-error: true
env: env:
CODEQL_ACTION_TEST_MODE: true CODEQL_ACTION_TEST_MODE: true
timeout-minutes: 45 timeout-minutes: 45
runs-on: ${{ matrix.os }} runs-on: ubuntu-latest
steps: steps:
- name: Dump GitHub event - name: Dump GitHub event
run: cat "${GITHUB_EVENT_PATH}" run: cat "${GITHUB_EVENT_PATH}"
@ -67,27 +64,24 @@ jobs:
- name: Check expected artifacts exist - name: Check expected artifacts exist
shell: bash shell: bash
run: | run: |
OPERATING_SYSTEMS="ubuntu-latest macos-latest"
LANGUAGES="cpp csharp go java javascript python" LANGUAGES="cpp csharp go java javascript python"
for os in $OPERATING_SYSTEMS; do pushd "./my-debug-artifacts"
pushd "./my-debug-artifacts-$os" echo "Artifacts from run:"
echo "Artifacts from run on $os:" for language in $LANGUAGES; do
for language in $LANGUAGES; do echo "- Checking $language"
echo "- Checking $language" if [[ ! -f "my-db-$language-partial.zip" ]] ; then
if [[ ! -f "my-db-$language-partial.zip" ]] ; then echo "Missing a partial database bundle for $language"
echo "Missing a partial database bundle for $language" exit 1
exit 1 fi
fi if [[ ! -d "log" ]] ; then
if [[ ! -d "log" ]] ; then echo "Missing database initialization logs"
echo "Missing database initialization logs" exit 1
exit 1 fi
fi if [[ ! "$language" == "go" ]] && [[ ! -d "$language/log" ]] ; then
if [[ ! "$language" == "go" ]] && [[ ! -d "$language/log" ]] ; then echo "Missing logs for $language"
echo "Missing logs for $language" exit 1
exit 1 fi
fi
done
popd
done done
popd
env: env:
GO111MODULE: auto GO111MODULE: auto

View file

@ -21,9 +21,6 @@ jobs:
upload-artifacts: upload-artifacts:
strategy: strategy:
matrix: matrix:
os:
- ubuntu-latest
- macos-latest
version: version:
- stable-20221211 - stable-20221211
- stable-20230418 - stable-20230418
@ -36,7 +33,7 @@ jobs:
env: env:
CODEQL_ACTION_TEST_MODE: true CODEQL_ACTION_TEST_MODE: true
timeout-minutes: 45 timeout-minutes: 45
runs-on: ${{ matrix.os }} runs-on: ubuntu-latest
steps: steps:
- name: Check out repository - name: Check out repository
uses: actions/checkout@v4 uses: actions/checkout@v4
@ -48,16 +45,6 @@ jobs:
- uses: actions/setup-go@v5 - uses: actions/setup-go@v5
with: with:
go-version: ^1.13.1 go-version: ^1.13.1
- name: Setup Python on MacOS
uses: actions/setup-python@v5
if: |
matrix.os == 'macos-latest' && (
matrix.version == 'stable-20221211' ||
matrix.version == 'stable-20230418' ||
matrix.version == 'stable-v2.13.5' ||
matrix.version == 'stable-v2.14.6')
with:
python-version: '3.11'
- uses: ./../action/init - uses: ./../action/init
id: init id: init
with: with:
@ -87,26 +74,24 @@ jobs:
VERSIONS="stable-20221211 stable-20230418 stable-v2.13.5 stable-v2.14.6 default latest nightly-latest" VERSIONS="stable-20221211 stable-20230418 stable-v2.13.5 stable-v2.14.6 default latest nightly-latest"
LANGUAGES="cpp csharp go java javascript python" LANGUAGES="cpp csharp go java javascript python"
for version in $VERSIONS; do for version in $VERSIONS; do
for os in ubuntu-latest macos-latest; do pushd "./my-debug-artifacts-${version//./}"
pushd "./my-debug-artifacts-$os-${version//./}" echo "Artifacts from version $version:"
echo "Artifacts from version $version on $os:" for language in $LANGUAGES; do
for language in $LANGUAGES; do echo "- Checking $language"
echo "- Checking $language" if [[ ! -f "$language.sarif" ]] ; then
if [[ ! -f "$language.sarif" ]] ; then echo "Missing a SARIF file for $language"
echo "Missing a SARIF file for $language" exit 1
exit 1 fi
fi if [[ ! -f "my-db-$language.zip" ]] ; then
if [[ ! -f "my-db-$language.zip" ]] ; then echo "Missing a database bundle for $language"
echo "Missing a database bundle for $language" exit 1
exit 1 fi
fi if [[ ! -d "$language/log" ]] ; then
if [[ ! -d "$language/log" ]] ; then echo "Missing logs for $language"
echo "Missing logs for $language" exit 1
exit 1 fi
fi
done
popd
done done
popd
done done
env: env:
GO111MODULE: auto GO111MODULE: auto

View file

@ -69,6 +69,8 @@ inputs:
required: true required: true
default: "true" default: "true"
token: token:
description: "GitHub token to use for authenticating with this instance of GitHub. The token needs the `security-events: write` permission."
required: false
default: ${{ github.token }} default: ${{ github.token }}
matrix: matrix:
default: ${{ toJson(matrix) }} default: ${{ toJson(matrix) }}

View file

@ -3,6 +3,8 @@ description: 'Attempt to automatically build code'
author: 'GitHub' author: 'GitHub'
inputs: inputs:
token: token:
description: "GitHub token to use for authenticating with this instance of GitHub. The token needs the `security-events: write` permission."
required: false
default: ${{ github.token }} default: ${{ github.token }}
matrix: matrix:
default: ${{ toJson(matrix) }} default: ${{ toJson(matrix) }}

4
lib/actions-util.js generated
View file

@ -41,7 +41,7 @@ const pkg = require("../package.json");
const getRequiredInput = function (name) { const getRequiredInput = function (name) {
const value = core.getInput(name); const value = core.getInput(name);
if (!value) { if (!value) {
throw new util_1.UserError(`Input required and not supplied: ${name}`); throw new util_1.ConfigurationError(`Input required and not supplied: ${name}`);
} }
return value; return value;
}; };
@ -177,7 +177,7 @@ async function getRef() {
const hasShaInput = !!shaInput; const hasShaInput = !!shaInput;
// If one of 'ref' or 'sha' are provided, both are required // If one of 'ref' or 'sha' are provided, both are required
if ((hasRefInput || hasShaInput) && !(hasRefInput && hasShaInput)) { if ((hasRefInput || hasShaInput) && !(hasRefInput && hasShaInput)) {
throw new util_1.UserError("Both 'ref' and 'sha' are required if one of them is provided."); throw new util_1.ConfigurationError("Both 'ref' and 'sha' are required if one of them is provided.");
} }
const ref = refInput || getRefFromEnv(); const ref = refInput || getRefFromEnv();
const sha = shaInput || (0, util_1.getRequiredEnvParam)("GITHUB_SHA"); const sha = shaInput || (0, util_1.getRequiredEnvParam)("GITHUB_SHA");

File diff suppressed because one or more lines are too long

36
lib/analyze-action.js generated
View file

@ -31,7 +31,6 @@ const fs = __importStar(require("fs"));
const path_1 = __importDefault(require("path")); const path_1 = __importDefault(require("path"));
const perf_hooks_1 = require("perf_hooks"); const perf_hooks_1 = require("perf_hooks");
const core = __importStar(require("@actions/core")); const core = __importStar(require("@actions/core"));
const safe_which_1 = require("@chrisgavin/safe-which");
const actionsUtil = __importStar(require("./actions-util")); const actionsUtil = __importStar(require("./actions-util"));
const analyze_1 = require("./analyze"); const analyze_1 = require("./analyze");
const api_client_1 = require("./api-client"); const api_client_1 = require("./api-client");
@ -39,7 +38,6 @@ const autobuild_1 = require("./autobuild");
const codeql_1 = require("./codeql"); const codeql_1 = require("./codeql");
const config_utils_1 = require("./config-utils"); const config_utils_1 = require("./config-utils");
const database_upload_1 = require("./database-upload"); const database_upload_1 = require("./database-upload");
const diagnostics_1 = require("./diagnostics");
const environment_1 = require("./environment"); const environment_1 = require("./environment");
const feature_flags_1 = require("./feature-flags"); const feature_flags_1 = require("./feature-flags");
const languages_1 = require("./languages"); const languages_1 = require("./languages");
@ -111,6 +109,10 @@ async function runAutobuildIfLegacyGoWorkflow(config, logger) {
if (!config.languages.includes(languages_1.Language.go)) { if (!config.languages.includes(languages_1.Language.go)) {
return; return;
} }
if (config.buildMode) {
logger.debug("Skipping legacy Go autobuild since a build mode has been specified.");
return;
}
if (process.env[environment_1.EnvVar.DID_AUTOBUILD_GOLANG] === "true") { if (process.env[environment_1.EnvVar.DID_AUTOBUILD_GOLANG] === "true") {
logger.debug("Won't run Go autobuild since it has already been run."); logger.debug("Won't run Go autobuild since it has already been run.");
return; return;
@ -151,7 +153,7 @@ async function run() {
throw new Error("Config file could not be found at expected location. Has the 'init' action been called?"); throw new Error("Config file could not be found at expected location. Has the 'init' action been called?");
} }
if (hasBadExpectErrorInput()) { if (hasBadExpectErrorInput()) {
throw new util.UserError("`expect-error` input parameter is for internal use only. It should only be set by codeql-action or a fork."); throw new util.ConfigurationError("`expect-error` input parameter is for internal use only. It should only be set by codeql-action or a fork.");
} }
const apiDetails = (0, api_client_1.getApiDetails)(); const apiDetails = (0, api_client_1.getApiDetails)();
const outputDir = actionsUtil.getRequiredInput("output"); const outputDir = actionsUtil.getRequiredInput("output");
@ -161,29 +163,7 @@ async function run() {
util.checkActionVersion(actionsUtil.getActionVersion(), gitHubVersion); util.checkActionVersion(actionsUtil.getActionVersion(), gitHubVersion);
const features = new feature_flags_1.Features(gitHubVersion, repositoryNwo, actionsUtil.getTemporaryDirectory(), logger); const features = new feature_flags_1.Features(gitHubVersion, repositoryNwo, actionsUtil.getTemporaryDirectory(), logger);
const memory = util.getMemoryFlag(actionsUtil.getOptionalInput("ram") || process.env["CODEQL_RAM"], logger); const memory = util.getMemoryFlag(actionsUtil.getOptionalInput("ram") || process.env["CODEQL_RAM"], logger);
// Check that `which go` still points at the same path it did when the `init` Action ran to ensure that no steps await (0, analyze_1.warnIfGoInstalledAfterInit)(config, logger);
// in-between performed any setup. We encourage users to perform all setup tasks before initializing CodeQL so that
// the setup tasks do not interfere with our analysis.
// Furthermore, if we installed a wrapper script in the `init` Action, we need to ensure that there isn't a step
// in the workflow after the `init` step which installs a different version of Go and takes precedence in the PATH,
// thus potentially circumventing our workaround that allows tracing to work.
const goInitPath = process.env[environment_1.EnvVar.GO_BINARY_LOCATION];
if (process.env[environment_1.EnvVar.DID_AUTOBUILD_GOLANG] !== "true" &&
goInitPath !== undefined) {
const goBinaryPath = await (0, safe_which_1.safeWhich)("go");
if (goInitPath !== goBinaryPath) {
core.warning(`Expected \`which go\` to return ${goInitPath}, but got ${goBinaryPath}: please ensure that the correct version of Go is installed before the \`codeql-action/init\` Action is used.`);
(0, diagnostics_1.addDiagnostic)(config, languages_1.Language.go, (0, diagnostics_1.makeDiagnostic)("go/workflow/go-installed-after-codeql-init", "Go was installed after the `codeql-action/init` Action was run", {
markdownMessage: "To avoid interfering with the CodeQL analysis, perform all installation steps before calling the `github/codeql-action/init` Action.",
visibility: {
statusPage: true,
telemetry: true,
cliSummaryTable: true,
},
severity: "warning",
}));
}
}
await runAutobuildIfLegacyGoWorkflow(config, logger); await runAutobuildIfLegacyGoWorkflow(config, logger);
dbCreationTimings = await (0, analyze_1.runFinalize)(outputDir, threads, memory, config, logger, features); dbCreationTimings = await (0, analyze_1.runFinalize)(outputDir, threads, memory, config, logger, features);
if (actionsUtil.getRequiredInput("skip-queries") !== "true") { if (actionsUtil.getRequiredInput("skip-queries") !== "true") {
@ -200,7 +180,7 @@ async function run() {
core.setOutput("sarif-output", path_1.default.resolve(outputDir)); core.setOutput("sarif-output", path_1.default.resolve(outputDir));
const uploadInput = actionsUtil.getOptionalInput("upload"); const uploadInput = actionsUtil.getOptionalInput("upload");
if (runStats && actionsUtil.getUploadValue(uploadInput) === "always") { if (runStats && actionsUtil.getUploadValue(uploadInput) === "always") {
uploadResult = await uploadLib.uploadFromActions(outputDir, actionsUtil.getRequiredInput("checkout_path"), actionsUtil.getOptionalInput("category"), logger, { considerInvalidRequestUserError: false }); uploadResult = await uploadLib.uploadFromActions(outputDir, actionsUtil.getRequiredInput("checkout_path"), actionsUtil.getOptionalInput("category"), logger, { considerInvalidRequestConfigError: false });
core.setOutput("sarif-id", uploadResult.sarifID); core.setOutput("sarif-id", uploadResult.sarifID);
} }
else { else {
@ -215,7 +195,7 @@ async function run() {
trapCacheUploadTime = perf_hooks_1.performance.now() - trapCacheUploadStartTime; trapCacheUploadTime = perf_hooks_1.performance.now() - trapCacheUploadStartTime;
// We don't upload results in test mode, so don't wait for processing // We don't upload results in test mode, so don't wait for processing
if (util.isInTestMode()) { if (util.isInTestMode()) {
core.debug("In test mode. Waiting for processing is disabled."); logger.debug("In test mode. Waiting for processing is disabled.");
} }
else if (uploadResult !== undefined && else if (uploadResult !== undefined &&
actionsUtil.getRequiredInput("wait-for-processing") === "true") { actionsUtil.getRequiredInput("wait-for-processing") === "true") {

File diff suppressed because one or more lines are too long

60
lib/analyze.js generated
View file

@ -26,16 +26,21 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod }; return (mod && mod.__esModule) ? mod : { "default": mod };
}; };
Object.defineProperty(exports, "__esModule", { value: true }); Object.defineProperty(exports, "__esModule", { value: true });
exports.runCleanup = exports.runFinalize = exports.runQueries = exports.dbIsFinalized = exports.createdDBForScannedLanguages = exports.CodeQLAnalysisError = void 0; exports.runCleanup = exports.warnIfGoInstalledAfterInit = exports.runFinalize = exports.runQueries = exports.dbIsFinalized = exports.runExtraction = exports.CodeQLAnalysisError = void 0;
const fs = __importStar(require("fs")); const fs = __importStar(require("fs"));
const path = __importStar(require("path")); const path = __importStar(require("path"));
const perf_hooks_1 = require("perf_hooks"); const perf_hooks_1 = require("perf_hooks");
const toolrunner = __importStar(require("@actions/exec/lib/toolrunner")); const toolrunner = __importStar(require("@actions/exec/lib/toolrunner"));
const safe_which_1 = require("@chrisgavin/safe-which");
const del_1 = __importDefault(require("del")); const del_1 = __importDefault(require("del"));
const yaml = __importStar(require("js-yaml")); const yaml = __importStar(require("js-yaml"));
const codeql_1 = require("./codeql"); const codeql_1 = require("./codeql");
const config_utils_1 = require("./config-utils");
const diagnostics_1 = require("./diagnostics");
const environment_1 = require("./environment");
const feature_flags_1 = require("./feature-flags"); const feature_flags_1 = require("./feature-flags");
const languages_1 = require("./languages"); const languages_1 = require("./languages");
const tools_features_1 = require("./tools-features");
const tracer_config_1 = require("./tracer-config"); const tracer_config_1 = require("./tracer-config");
const upload_lib_1 = require("./upload-lib"); const upload_lib_1 = require("./upload-lib");
const util = __importStar(require("./util")); const util = __importStar(require("./util"));
@ -75,20 +80,35 @@ async function setupPythonExtractor(logger, features, codeql) {
logger.info(`Setting LGTM_PYTHON_SETUP_VERSION=${output}`); logger.info(`Setting LGTM_PYTHON_SETUP_VERSION=${output}`);
process.env["LGTM_PYTHON_SETUP_VERSION"] = output; process.env["LGTM_PYTHON_SETUP_VERSION"] = output;
} }
async function createdDBForScannedLanguages(codeql, config, logger, features) { async function runExtraction(codeql, config, logger, features) {
for (const language of config.languages) { for (const language of config.languages) {
if ((0, languages_1.isScannedLanguage)(language) && if (dbIsFinalized(config, language, logger)) {
!dbIsFinalized(config, language, logger)) { logger.debug(`Database for ${language} has already been finalized, skipping extraction.`);
continue;
}
if (shouldExtractLanguage(config, language)) {
logger.startGroup(`Extracting ${language}`); logger.startGroup(`Extracting ${language}`);
if (language === languages_1.Language.python) { if (language === languages_1.Language.python) {
await setupPythonExtractor(logger, features, codeql); await setupPythonExtractor(logger, features, codeql);
} }
await codeql.extractScannedLanguage(config, language); if (config.buildMode &&
(await codeql.supportsFeature(tools_features_1.ToolsFeature.TraceCommandUseBuildMode))) {
await codeql.extractUsingBuildMode(config, language);
}
else {
await codeql.extractScannedLanguage(config, language);
}
logger.endGroup(); logger.endGroup();
} }
} }
} }
exports.createdDBForScannedLanguages = createdDBForScannedLanguages; exports.runExtraction = runExtraction;
function shouldExtractLanguage(config, language) {
return (config.buildMode === config_utils_1.BuildMode.None ||
(config.buildMode === config_utils_1.BuildMode.Autobuild &&
process.env[environment_1.EnvVar.AUTOBUILD_DID_COMPLETE_SUCCESSFULLY] !== "true") ||
(!config.buildMode && (0, languages_1.isScannedLanguage)(language)));
}
function dbIsFinalized(config, language, logger) { function dbIsFinalized(config, language, logger) {
const dbPath = util.getCodeQLDatabasePath(config, language); const dbPath = util.getCodeQLDatabasePath(config, language);
try { try {
@ -104,7 +124,7 @@ exports.dbIsFinalized = dbIsFinalized;
async function finalizeDatabaseCreation(config, threadsFlag, memoryFlag, logger, features) { async function finalizeDatabaseCreation(config, threadsFlag, memoryFlag, logger, features) {
const codeql = await (0, codeql_1.getCodeQL)(config.codeQLCmd); const codeql = await (0, codeql_1.getCodeQL)(config.codeQLCmd);
const extractionStart = perf_hooks_1.performance.now(); const extractionStart = perf_hooks_1.performance.now();
await createdDBForScannedLanguages(codeql, config, logger, features); await runExtraction(codeql, config, logger, features);
const extractionTime = perf_hooks_1.performance.now() - extractionStart; const extractionTime = perf_hooks_1.performance.now() - extractionStart;
const trapImportStart = perf_hooks_1.performance.now(); const trapImportStart = perf_hooks_1.performance.now();
for (const language of config.languages) { for (const language of config.languages) {
@ -230,6 +250,32 @@ async function runFinalize(outputDir, threadsFlag, memoryFlag, config, logger, f
return timings; return timings;
} }
exports.runFinalize = runFinalize; exports.runFinalize = runFinalize;
async function warnIfGoInstalledAfterInit(config, logger) {
// Check that `which go` still points at the same path it did when the `init` Action ran to ensure that no steps
// in-between performed any setup. We encourage users to perform all setup tasks before initializing CodeQL so that
// the setup tasks do not interfere with our analysis.
// Furthermore, if we installed a wrapper script in the `init` Action, we need to ensure that there isn't a step
// in the workflow after the `init` step which installs a different version of Go and takes precedence in the PATH,
// thus potentially circumventing our workaround that allows tracing to work.
const goInitPath = process.env[environment_1.EnvVar.GO_BINARY_LOCATION];
if (process.env[environment_1.EnvVar.DID_AUTOBUILD_GOLANG] !== "true" &&
goInitPath !== undefined) {
const goBinaryPath = await (0, safe_which_1.safeWhich)("go");
if (goInitPath !== goBinaryPath) {
logger.warning(`Expected \`which go\` to return ${goInitPath}, but got ${goBinaryPath}: please ensure that the correct version of Go is installed before the \`codeql-action/init\` Action is used.`);
(0, diagnostics_1.addDiagnostic)(config, languages_1.Language.go, (0, diagnostics_1.makeDiagnostic)("go/workflow/go-installed-after-codeql-init", "Go was installed after the `codeql-action/init` Action was run", {
markdownMessage: "To avoid interfering with the CodeQL analysis, perform all installation steps before calling the `github/codeql-action/init` Action.",
visibility: {
statusPage: true,
telemetry: true,
cliSummaryTable: true,
},
severity: "warning",
}));
}
}
}
exports.warnIfGoInstalledAfterInit = warnIfGoInstalledAfterInit;
async function runCleanup(config, cleanupLevel, logger) { async function runCleanup(config, cleanupLevel, logger) {
logger.startGroup("Cleaning up databases"); logger.startGroup("Cleaning up databases");
for (const language of config.languages) { for (const language of config.languages) {

File diff suppressed because one or more lines are too long

View file

@ -27,7 +27,9 @@ const core = __importStar(require("@actions/core"));
const actions_util_1 = require("./actions-util"); const actions_util_1 = require("./actions-util");
const api_client_1 = require("./api-client"); const api_client_1 = require("./api-client");
const autobuild_1 = require("./autobuild"); const autobuild_1 = require("./autobuild");
const codeql_1 = require("./codeql");
const configUtils = __importStar(require("./config-utils")); const configUtils = __importStar(require("./config-utils"));
const environment_1 = require("./environment");
const logging_1 = require("./logging"); const logging_1 = require("./logging");
const status_report_1 = require("./status-report"); const status_report_1 = require("./status-report");
const util_1 = require("./util"); const util_1 = require("./util");
@ -58,7 +60,8 @@ async function run() {
if (config === undefined) { if (config === undefined) {
throw new Error("Config file could not be found at expected location. Has the 'init' action been called?"); throw new Error("Config file could not be found at expected location. Has the 'init' action been called?");
} }
languages = await (0, autobuild_1.determineAutobuildLanguages)(config, logger); const codeql = await (0, codeql_1.getCodeQL)(config.codeQLCmd);
languages = await (0, autobuild_1.determineAutobuildLanguages)(codeql, config, logger);
if (languages !== undefined) { if (languages !== undefined) {
const workingDirectory = (0, actions_util_1.getOptionalInput)("working-directory"); const workingDirectory = (0, actions_util_1.getOptionalInput)("working-directory");
if (workingDirectory) { if (workingDirectory) {
@ -77,6 +80,7 @@ async function run() {
await sendCompletedStatusReport(logger, startedAt, languages ?? [], currentLanguage, error); await sendCompletedStatusReport(logger, startedAt, languages ?? [], currentLanguage, error);
return; return;
} }
core.exportVariable(environment_1.EnvVar.AUTOBUILD_DID_COMPLETE_SUCCESSFULLY, "true");
await sendCompletedStatusReport(logger, startedAt, languages ?? []); await sendCompletedStatusReport(logger, startedAt, languages ?? []);
} }
async function runWrapper() { async function runWrapper() {

View file

@ -1 +1 @@
{"version":3,"file":"autobuild-action.js","sourceRoot":"","sources":["../src/autobuild-action.ts"],"names":[],"mappings":"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"} {"version":3,"file":"autobuild-action.js","sourceRoot":"","sources":["../src/autobuild-action.ts"],"names":[],"mappings":"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"}

10
lib/autobuild.js generated
View file

@ -28,12 +28,20 @@ const core = __importStar(require("@actions/core"));
const actions_util_1 = require("./actions-util"); const actions_util_1 = require("./actions-util");
const api_client_1 = require("./api-client"); const api_client_1 = require("./api-client");
const codeql_1 = require("./codeql"); const codeql_1 = require("./codeql");
const config_utils_1 = require("./config-utils");
const environment_1 = require("./environment"); const environment_1 = require("./environment");
const feature_flags_1 = require("./feature-flags"); const feature_flags_1 = require("./feature-flags");
const languages_1 = require("./languages"); const languages_1 = require("./languages");
const repository_1 = require("./repository"); const repository_1 = require("./repository");
const tools_features_1 = require("./tools-features");
const util_1 = require("./util"); const util_1 = require("./util");
async function determineAutobuildLanguages(config, logger) { async function determineAutobuildLanguages(codeql, config, logger) {
if ((config.buildMode === config_utils_1.BuildMode.None &&
(await codeql.supportsFeature(tools_features_1.ToolsFeature.TraceCommandUseBuildMode))) ||
config.buildMode === config_utils_1.BuildMode.Manual) {
logger.info(`Using ${config.buildMode} build mode, nothing to autobuild.`);
return undefined;
}
// Attempt to find a language to autobuild // Attempt to find a language to autobuild
// We want pick the dominant language in the repo from the ones we're able to build // We want pick the dominant language in the repo from the ones we're able to build
// The languages are sorted in order specified by user or by lines of code if we got // The languages are sorted in order specified by user or by lines of code if we got

View file

@ -1 +1 @@
{"version":3,"file":"autobuild.js","sourceRoot":"","sources":["../src/autobuild.ts"],"names":[],"mappings":"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"} {"version":3,"file":"autobuild.js","sourceRoot":"","sources":["../src/autobuild.ts"],"names":[],"mappings":"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"}

179
lib/cli-errors.js generated Normal file
View file

@ -0,0 +1,179 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.wrapCliConfigurationError = exports.getCliConfigCategoryIfExists = exports.cliErrorsConfig = exports.CliConfigErrorCategory = exports.CommandInvocationError = void 0;
const util_1 = require("./util");
/**
* A class of Error that we can classify as an error stemming from a CLI
* invocation, with associated exit code, stderr,etc.
*/
class CommandInvocationError extends Error {
constructor(cmd, args, exitCode, stderr, stdout) {
const prettyCommand = [cmd, ...args]
.map((x) => (x.includes(" ") ? `'${x}'` : x))
.join(" ");
const fatalErrors = extractFatalErrors(stderr);
const lastLine = stderr.trim().split("\n").pop()?.trim();
let error = fatalErrors
? ` and error was: ${fatalErrors.trim()}`
: lastLine
? ` and last log line was: ${lastLine}`
: "";
if (error[error.length - 1] !== ".") {
error += ".";
}
super(`Encountered a fatal error while running "${prettyCommand}". ` +
`Exit code was ${exitCode}${error} See the logs for more details.`);
this.exitCode = exitCode;
this.stderr = stderr;
this.stdout = stdout;
}
}
exports.CommandInvocationError = CommandInvocationError;
/**
* Provide a better error message from the stderr of a CLI invocation that failed with a fatal
* error.
*
* - If the CLI invocation failed with a fatal error, this returns that fatal error, followed by
* any fatal errors that occurred in plumbing commands.
* - If the CLI invocation did not fail with a fatal error, this returns `undefined`.
*
* ### Example
*
* ```
* Running TRAP import for CodeQL database at /home/runner/work/_temp/codeql_databases/javascript...
* A fatal error occurred: Evaluator heap must be at least 384.00 MiB
* A fatal error occurred: Dataset import for
* /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2
* ```
*
* becomes
*
* ```
* Encountered a fatal error while running "codeql-for-testing database finalize --finalize-dataset
* --threads=2 --ram=2048 db". Exit code was 32 and error was: A fatal error occurred: Dataset
* import for /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2.
* Context: A fatal error occurred: Evaluator heap must be at least 384.00 MiB.
* ```
*
* Where possible, this tries to summarize the error into a single line, as this displays better in
* the Actions UI.
*/
function extractFatalErrors(error) {
const fatalErrorRegex = /.*fatal error occurred:/gi;
let fatalErrors = [];
let lastFatalErrorIndex;
let match;
while ((match = fatalErrorRegex.exec(error)) !== null) {
if (lastFatalErrorIndex !== undefined) {
fatalErrors.push(error.slice(lastFatalErrorIndex, match.index).trim());
}
lastFatalErrorIndex = match.index;
}
if (lastFatalErrorIndex !== undefined) {
const lastError = error.slice(lastFatalErrorIndex).trim();
if (fatalErrors.length === 0) {
// No other errors
return lastError;
}
const isOneLiner = !fatalErrors.some((e) => e.includes("\n"));
if (isOneLiner) {
fatalErrors = fatalErrors.map(ensureEndsInPeriod);
}
return [
ensureEndsInPeriod(lastError),
"Context:",
...fatalErrors.reverse(),
].join(isOneLiner ? " " : "\n");
}
return undefined;
}
function ensureEndsInPeriod(text) {
return text[text.length - 1] === "." ? text : `${text}.`;
}
/** Error messages from the CLI that we consider configuration errors and handle specially. */
var CliConfigErrorCategory;
(function (CliConfigErrorCategory) {
CliConfigErrorCategory["IncompatibleWithActionVersion"] = "IncompatibleWithActionVersion";
CliConfigErrorCategory["InitCalledTwice"] = "InitCalledTwice";
CliConfigErrorCategory["InvalidSourceRoot"] = "InvalidSourceRoot";
CliConfigErrorCategory["NoJavaScriptTypeScriptCodeFound"] = "NoJavaScriptTypeScriptCodeFound";
})(CliConfigErrorCategory || (exports.CliConfigErrorCategory = CliConfigErrorCategory = {}));
/**
* All of our caught CLI error messages that we handle specially: ie. if we
* would like to categorize an error as a configuration error or not.
*/
exports.cliErrorsConfig = {
// Version of CodeQL CLI is incompatible with this version of the CodeQL Action
[CliConfigErrorCategory.IncompatibleWithActionVersion]: {
cliErrorMessageSnippets: ["is not compatible with this CodeQL CLI"],
},
[CliConfigErrorCategory.InitCalledTwice]: {
cliErrorMessageSnippets: [
"Refusing to create databases",
"exists and is not an empty directory",
],
additionalErrorMessageToPrepend: `Is the "init" action called twice in the same job?`,
},
// Expected source location for database creation does not exist
[CliConfigErrorCategory.InvalidSourceRoot]: {
cliErrorMessageSnippets: ["Invalid source root"],
},
/**
* Earlier versions of the JavaScript extractor (pre-CodeQL 2.12.0) extract externs even if no
* source code was found. This means that we don't get the no code found error from
* `codeql database finalize`. To ensure users get a good error message, we detect this manually
* here, and upon detection override the error message.
*
* This can be removed once support for CodeQL 2.11.6 is removed.
*/
[CliConfigErrorCategory.NoJavaScriptTypeScriptCodeFound]: {
exitCode: 32,
cliErrorMessageSnippets: ["No JavaScript or TypeScript code found."],
additionalErrorMessageToPrepend: "No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build.",
},
};
// Check if the given CLI error or exit code, if applicable, apply to any known
// CLI errors in the configuration record. If either the CLI error message matches all of
// the error messages in the config record, or the exit codes match, return the error category;
// if not, return undefined.
function getCliConfigCategoryIfExists(cliError) {
for (const [category, configuration] of Object.entries(exports.cliErrorsConfig)) {
if (cliError.exitCode !== undefined &&
configuration.exitCode !== undefined &&
cliError.exitCode === configuration.exitCode) {
return category;
}
let allMessageSnippetsFound = true;
for (const e of configuration.cliErrorMessageSnippets) {
if (!cliError.message.includes(e) && !cliError.stderr.includes(e)) {
allMessageSnippetsFound = false;
}
}
if (allMessageSnippetsFound === true) {
return category;
}
}
return undefined;
}
exports.getCliConfigCategoryIfExists = getCliConfigCategoryIfExists;
/**
* Changes an error received from the CLI to a ConfigurationError with optionally an extra
* error message prepended, if it exists in a known set of configuration errors. Otherwise,
* simply returns the original error.
*/
function wrapCliConfigurationError(cliError) {
if (!(cliError instanceof CommandInvocationError)) {
return cliError;
}
const cliConfigErrorCategory = getCliConfigCategoryIfExists(cliError);
if (cliConfigErrorCategory === undefined) {
return cliError;
}
const errorMessageWrapperIfExists = exports.cliErrorsConfig[cliConfigErrorCategory].additionalErrorMessageToPrepend;
return errorMessageWrapperIfExists
? new util_1.ConfigurationError(`${errorMessageWrapperIfExists} ${cliError.message}`)
: new util_1.ConfigurationError(cliError.message);
}
exports.wrapCliConfigurationError = wrapCliConfigurationError;
//# sourceMappingURL=cli-errors.js.map

1
lib/cli-errors.js.map Normal file
View file

@ -0,0 +1 @@
{"version":3,"file":"cli-errors.js","sourceRoot":"","sources":["../src/cli-errors.ts"],"names":[],"mappings":"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"}

152
lib/codeql.js generated
View file

@ -23,7 +23,7 @@ var __importStar = (this && this.__importStar) || function (mod) {
return result; return result;
}; };
Object.defineProperty(exports, "__esModule", { value: true }); Object.defineProperty(exports, "__esModule", { value: true });
exports.getGeneratedCodeScanningConfigPath = exports.getTrapCachingExtractorConfigArgsForLang = exports.getTrapCachingExtractorConfigArgs = exports.getExtraOptions = exports.getCodeQLForCmd = exports.getCodeQLForTesting = exports.getCachedCodeQL = exports.setCodeQL = exports.getCodeQL = exports.setupCodeQL = exports.CODEQL_VERSION_SUBLANGUAGE_FILE_COVERAGE = exports.CODEQL_VERSION_ANALYSIS_SUMMARY_V2 = exports.CODEQL_VERSION_LANGUAGE_ALIASING = exports.CODEQL_VERSION_LANGUAGE_BASELINE_CONFIG = exports.CODEQL_VERSION_RESOLVE_ENVIRONMENT = exports.CODEQL_VERSION_DIAGNOSTICS_EXPORT_FIXED = exports.CODEQL_VERSION_BETTER_NO_CODE_ERROR_MESSAGE = exports.CODEQL_VERSION_INIT_WITH_QLCONFIG = exports.CODEQL_VERSION_EXPORT_CODE_SCANNING_CONFIG = exports.CODEQL_VERSION_SECURITY_EXPERIMENTAL_SUITE = exports.CommandInvocationError = void 0; exports.getGeneratedCodeScanningConfigPath = exports.getTrapCachingExtractorConfigArgsForLang = exports.getTrapCachingExtractorConfigArgs = exports.getExtraOptions = exports.getCodeQLForCmd = exports.getCodeQLForTesting = exports.getCachedCodeQL = exports.setCodeQL = exports.getCodeQL = exports.setupCodeQL = exports.CODEQL_VERSION_SUBLANGUAGE_FILE_COVERAGE = exports.CODEQL_VERSION_ANALYSIS_SUMMARY_V2 = exports.CODEQL_VERSION_LANGUAGE_ALIASING = exports.CODEQL_VERSION_LANGUAGE_BASELINE_CONFIG = exports.CODEQL_VERSION_RESOLVE_ENVIRONMENT = exports.CODEQL_VERSION_DIAGNOSTICS_EXPORT_FIXED = exports.CODEQL_VERSION_BETTER_NO_CODE_ERROR_MESSAGE = exports.CODEQL_VERSION_INIT_WITH_QLCONFIG = exports.CODEQL_VERSION_EXPORT_CODE_SCANNING_CONFIG = exports.CODEQL_VERSION_SECURITY_EXPERIMENTAL_SUITE = void 0;
const fs = __importStar(require("fs")); const fs = __importStar(require("fs"));
const path = __importStar(require("path")); const path = __importStar(require("path"));
const core = __importStar(require("@actions/core")); const core = __importStar(require("@actions/core"));
@ -31,6 +31,7 @@ const toolrunner = __importStar(require("@actions/exec/lib/toolrunner"));
const yaml = __importStar(require("js-yaml")); const yaml = __importStar(require("js-yaml"));
const semver = __importStar(require("semver")); const semver = __importStar(require("semver"));
const actions_util_1 = require("./actions-util"); const actions_util_1 = require("./actions-util");
const cli_errors_1 = require("./cli-errors");
const environment_1 = require("./environment"); const environment_1 = require("./environment");
const feature_flags_1 = require("./feature-flags"); const feature_flags_1 = require("./feature-flags");
const languages_1 = require("./languages"); const languages_1 = require("./languages");
@ -38,29 +39,6 @@ const setupCodeql = __importStar(require("./setup-codeql"));
const tools_features_1 = require("./tools-features"); const tools_features_1 = require("./tools-features");
const util = __importStar(require("./util")); const util = __importStar(require("./util"));
const util_1 = require("./util"); const util_1 = require("./util");
class CommandInvocationError extends Error {
constructor(cmd, args, exitCode, stderr, stdout) {
const prettyCommand = [cmd, ...args]
.map((x) => (x.includes(" ") ? `'${x}'` : x))
.join(" ");
const fatalErrors = extractFatalErrors(stderr);
const lastLine = stderr.trim().split("\n").pop()?.trim();
let error = fatalErrors
? ` and error was: ${fatalErrors.trim()}`
: lastLine
? ` and last log line was: ${lastLine}`
: "";
if (error[error.length - 1] !== ".") {
error += ".";
}
super(`Encountered a fatal error while running "${prettyCommand}". ` +
`Exit code was ${exitCode}${error} See the logs for more details.`);
this.exitCode = exitCode;
this.stderr = stderr;
this.stdout = stdout;
}
}
exports.CommandInvocationError = CommandInvocationError;
/** /**
* Stores the CodeQL object, and is populated by `setupCodeQL` or `getCodeQL`. * Stores the CodeQL object, and is populated by `setupCodeQL` or `getCodeQL`.
* Can be overridden in tests using `setCodeQL`. * Can be overridden in tests using `setCodeQL`.
@ -156,7 +134,7 @@ async function setupCodeQL(toolsInput, apiDetails, tempDir, variant, defaultCliV
codeqlCmd += ".exe"; codeqlCmd += ".exe";
} }
else if (process.platform !== "linux" && process.platform !== "darwin") { else if (process.platform !== "linux" && process.platform !== "darwin") {
throw new util.UserError(`Unsupported platform: ${process.platform}`); throw new util.ConfigurationError(`Unsupported platform: ${process.platform}`);
} }
cachedCodeQL = await getCodeQLForCmd(codeqlCmd, checkVersion); cachedCodeQL = await getCodeQLForCmd(codeqlCmd, checkVersion);
return { return {
@ -211,6 +189,7 @@ function setCodeQL(partialCodeql) {
databaseInitCluster: resolveFunction(partialCodeql, "databaseInitCluster"), databaseInitCluster: resolveFunction(partialCodeql, "databaseInitCluster"),
runAutobuild: resolveFunction(partialCodeql, "runAutobuild"), runAutobuild: resolveFunction(partialCodeql, "runAutobuild"),
extractScannedLanguage: resolveFunction(partialCodeql, "extractScannedLanguage"), extractScannedLanguage: resolveFunction(partialCodeql, "extractScannedLanguage"),
extractUsingBuildMode: resolveFunction(partialCodeql, "extractUsingBuildMode"),
finalizeDatabase: resolveFunction(partialCodeql, "finalizeDatabase"), finalizeDatabase: resolveFunction(partialCodeql, "finalizeDatabase"),
resolveLanguages: resolveFunction(partialCodeql, "resolveLanguages"), resolveLanguages: resolveFunction(partialCodeql, "resolveLanguages"),
betterResolveLanguages: resolveFunction(partialCodeql, "betterResolveLanguages"), betterResolveLanguages: resolveFunction(partialCodeql, "betterResolveLanguages"),
@ -315,16 +294,24 @@ async function getCodeQLForCmd(cmd, checkVersion) {
else if (await util.codeQlVersionAbove(this, exports.CODEQL_VERSION_SUBLANGUAGE_FILE_COVERAGE)) { else if (await util.codeQlVersionAbove(this, exports.CODEQL_VERSION_SUBLANGUAGE_FILE_COVERAGE)) {
extraArgs.push("--no-sublanguage-file-coverage"); extraArgs.push("--no-sublanguage-file-coverage");
} }
await runTool(cmd, [ try {
"database", await runTool(cmd, [
"init", "database",
"--db-cluster", "init",
config.dbLocation, "--db-cluster",
`--source-root=${sourceRoot}`, config.dbLocation,
...(await getLanguageAliasingArguments(this)), `--source-root=${sourceRoot}`,
...extraArgs, ...(await getLanguageAliasingArguments(this)),
...getExtraOptionsFromEnv(["database", "init"]), ...extraArgs,
], { stdin: externalRepositoryToken }); ...getExtraOptionsFromEnv(["database", "init"]),
], { stdin: externalRepositoryToken });
}
catch (e) {
if (e instanceof Error) {
throw (0, cli_errors_1.wrapCliConfigurationError)(e);
}
throw e;
}
}, },
async runAutobuild(language) { async runAutobuild(language) {
const autobuildCmd = path.join(await this.resolveExtractor(language), "tools", process.platform === "win32" ? "autobuild.cmd" : "autobuild.sh"); const autobuildCmd = path.join(await this.resolveExtractor(language), "tools", process.platform === "win32" ? "autobuild.cmd" : "autobuild.sh");
@ -364,6 +351,16 @@ async function getCodeQLForCmd(cmd, checkVersion) {
util.getCodeQLDatabasePath(config, language), util.getCodeQLDatabasePath(config, language),
]); ]);
}, },
async extractUsingBuildMode(config, language) {
await runTool(cmd, [
"database",
"trace-command",
"--use-build-mode",
...(await getTrapCachingExtractorConfigArgsForLang(config, language)),
...getExtraOptionsFromEnv(["database", "trace-command"]),
util.getCodeQLDatabasePath(config, language),
]);
},
async finalizeDatabase(databasePath, threadsFlag, memoryFlag) { async finalizeDatabase(databasePath, threadsFlag, memoryFlag) {
const args = [ const args = [
"database", "database",
@ -378,11 +375,9 @@ async function getCodeQLForCmd(cmd, checkVersion) {
await runTool(cmd, args); await runTool(cmd, args);
} }
catch (e) { catch (e) {
if (e instanceof CommandInvocationError && if (e instanceof Error &&
!(await util.codeQlVersionAbove(this, exports.CODEQL_VERSION_BETTER_NO_CODE_ERROR_MESSAGE)) && !(await util.codeQlVersionAbove(this, exports.CODEQL_VERSION_BETTER_NO_CODE_ERROR_MESSAGE))) {
isNoCodeFoundError(e)) { throw (0, cli_errors_1.wrapCliConfigurationError)(e);
throw new util.UserError("No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build");
} }
throw e; throw e;
} }
@ -689,7 +684,7 @@ async function getCodeQLForCmd(cmd, checkVersion) {
// CodeQL object is created. // CodeQL object is created.
if (checkVersion && if (checkVersion &&
!(await util.codeQlVersionAbove(codeql, CODEQL_MINIMUM_VERSION))) { !(await util.codeQlVersionAbove(codeql, CODEQL_MINIMUM_VERSION))) {
throw new util.UserError(`Expected a CodeQL CLI with version at least ${CODEQL_MINIMUM_VERSION} but got version ${(await codeql.getVersion()).version}`); throw new util.ConfigurationError(`Expected a CodeQL CLI with version at least ${CODEQL_MINIMUM_VERSION} but got version ${(await codeql.getVersion()).version}`);
} }
else if (checkVersion && else if (checkVersion &&
process.env[environment_1.EnvVar.SUPPRESS_DEPRECATED_SOON_WARNING] !== "true" && process.env[environment_1.EnvVar.SUPPRESS_DEPRECATED_SOON_WARNING] !== "true" &&
@ -794,71 +789,10 @@ async function runTool(cmd, args = [], opts = {}) {
...(opts.stdin ? { input: Buffer.from(opts.stdin || "") } : {}), ...(opts.stdin ? { input: Buffer.from(opts.stdin || "") } : {}),
}).exec(); }).exec();
if (exitCode !== 0) { if (exitCode !== 0) {
throw new CommandInvocationError(cmd, args, exitCode, error, output); throw new cli_errors_1.CommandInvocationError(cmd, args, exitCode, error, output);
} }
return output; return output;
} }
/**
* Provide a better error message from the stderr of a CLI invocation that failed with a fatal
* error.
*
* - If the CLI invocation failed with a fatal error, this returns that fatal error, followed by
* any fatal errors that occurred in plumbing commands.
* - If the CLI invocation did not fail with a fatal error, this returns `undefined`.
*
* ### Example
*
* ```
* Running TRAP import for CodeQL database at /home/runner/work/_temp/codeql_databases/javascript...
* A fatal error occurred: Evaluator heap must be at least 384.00 MiB
* A fatal error occurred: Dataset import for
* /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2
* ```
*
* becomes
*
* ```
* Encountered a fatal error while running "codeql-for-testing database finalize --finalize-dataset
* --threads=2 --ram=2048 db". Exit code was 32 and error was: A fatal error occurred: Dataset
* import for /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2.
* Context: A fatal error occurred: Evaluator heap must be at least 384.00 MiB.
* ```
*
* Where possible, this tries to summarize the error into a single line, as this displays better in
* the Actions UI.
*/
function extractFatalErrors(error) {
const fatalErrorRegex = /.*fatal error occurred:/gi;
let fatalErrors = [];
let lastFatalErrorIndex;
let match;
while ((match = fatalErrorRegex.exec(error)) !== null) {
if (lastFatalErrorIndex !== undefined) {
fatalErrors.push(error.slice(lastFatalErrorIndex, match.index).trim());
}
lastFatalErrorIndex = match.index;
}
if (lastFatalErrorIndex !== undefined) {
const lastError = error.slice(lastFatalErrorIndex).trim();
if (fatalErrors.length === 0) {
// No other errors
return lastError;
}
const isOneLiner = !fatalErrors.some((e) => e.includes("\n"));
if (isOneLiner) {
fatalErrors = fatalErrors.map(ensureEndsInPeriod);
}
return [
ensureEndsInPeriod(lastError),
"Context:",
...fatalErrors.reverse(),
].join(isOneLiner ? " " : "\n");
}
return undefined;
}
function ensureEndsInPeriod(text) {
return text[text.length - 1] === "." ? text : `${text}.`;
}
/** /**
* Generates a code scanning configuration that is to be used for a scan. * Generates a code scanning configuration that is to be used for a scan.
* *
@ -960,18 +894,6 @@ function getGeneratedCodeScanningConfigPath(config) {
return path.resolve(config.tempDir, "user-config.yaml"); return path.resolve(config.tempDir, "user-config.yaml");
} }
exports.getGeneratedCodeScanningConfigPath = getGeneratedCodeScanningConfigPath; exports.getGeneratedCodeScanningConfigPath = getGeneratedCodeScanningConfigPath;
function isNoCodeFoundError(e) {
/**
* Earlier versions of the JavaScript extractor (pre-CodeQL 2.12.0) extract externs even if no
* source code was found. This means that we don't get the no code found error from
* `codeql database finalize`. To ensure users get a good error message, we detect this manually
* here, and upon detection override the error message.
*
* This can be removed once support for CodeQL 2.11.6 is removed.
*/
const javascriptNoCodeFoundWarning = "No JavaScript or TypeScript code found.";
return e.exitCode === 32 || e.stderr.includes(javascriptNoCodeFoundWarning);
}
async function isDiagnosticsExportInvalidSarifFixed(codeql) { async function isDiagnosticsExportInvalidSarifFixed(codeql) {
return await util.codeQlVersionAbove(codeql, exports.CODEQL_VERSION_DIAGNOSTICS_EXPORT_FIXED); return await util.codeQlVersionAbove(codeql, exports.CODEQL_VERSION_DIAGNOSTICS_EXPORT_FIXED);
} }

File diff suppressed because one or more lines are too long

10
lib/codeql.test.js generated
View file

@ -554,8 +554,9 @@ for (const { codeqlVersion, flagPassed, githubVersion, negativeFlagPassed, } of
// safeWhich throws because of the test CodeQL object. // safeWhich throws because of the test CodeQL object.
sinon.stub(safeWhich, "safeWhich").resolves(""); sinon.stub(safeWhich, "safeWhich").resolves("");
await t.throwsAsync(async () => await codeqlObject.finalizeDatabase("", "", ""), { await t.throwsAsync(async () => await codeqlObject.finalizeDatabase("", "", ""), {
message: "No code found during the build. Please see: " + instanceOf: util.ConfigurationError,
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build", message: new RegExp("No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build.+"),
}); });
}); });
(0, ava_1.default)("database finalize overrides no code found error on CodeQL 2.11.6", async (t) => { (0, ava_1.default)("database finalize overrides no code found error on CodeQL 2.11.6", async (t) => {
@ -565,8 +566,9 @@ for (const { codeqlVersion, flagPassed, githubVersion, negativeFlagPassed, } of
// safeWhich throws because of the test CodeQL object. // safeWhich throws because of the test CodeQL object.
sinon.stub(safeWhich, "safeWhich").resolves(""); sinon.stub(safeWhich, "safeWhich").resolves("");
await t.throwsAsync(async () => await codeqlObject.finalizeDatabase("", "", ""), { await t.throwsAsync(async () => await codeqlObject.finalizeDatabase("", "", ""), {
message: "No code found during the build. Please see: " + instanceOf: util.ConfigurationError,
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build", message: new RegExp("No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build.+"),
}); });
}); });
(0, ava_1.default)("database finalize does not override no code found error on CodeQL 2.12.4", async (t) => { (0, ava_1.default)("database finalize does not override no code found error on CodeQL 2.12.4", async (t) => {

File diff suppressed because one or more lines are too long

57
lib/config-utils.js generated
View file

@ -23,7 +23,7 @@ var __importStar = (this && this.__importStar) || function (mod) {
return result; return result;
}; };
Object.defineProperty(exports, "__esModule", { value: true }); Object.defineProperty(exports, "__esModule", { value: true });
exports.wrapEnvironment = exports.generateRegistries = exports.getConfig = exports.getPathToParsedConfigFile = exports.initConfig = exports.validatePackSpecification = exports.parsePacksSpecification = exports.parsePacksFromInput = exports.calculateAugmentation = exports.getDefaultConfig = exports.getRawLanguages = exports.getLanguageAliases = exports.getLanguages = exports.getLanguagesInRepo = exports.getUnknownLanguagesError = exports.getNoLanguagesError = exports.getConfigFileDirectoryGivenMessage = exports.getConfigFileFormatInvalidMessage = exports.getConfigFileRepoFormatInvalidMessage = exports.getConfigFileDoesNotExistErrorMessage = exports.getConfigFileOutsideWorkspaceErrorMessage = exports.getPacksStrInvalid = exports.defaultAugmentationProperties = void 0; exports.wrapEnvironment = exports.generateRegistries = exports.getConfig = exports.getPathToParsedConfigFile = exports.initConfig = exports.validatePackSpecification = exports.parsePacksSpecification = exports.parsePacksFromInput = exports.calculateAugmentation = exports.getDefaultConfig = exports.getRawLanguages = exports.getLanguageAliases = exports.getLanguages = exports.getLanguagesInRepo = exports.getUnknownLanguagesError = exports.getNoLanguagesError = exports.getConfigFileDirectoryGivenMessage = exports.getConfigFileFormatInvalidMessage = exports.getConfigFileRepoFormatInvalidMessage = exports.getConfigFileDoesNotExistErrorMessage = exports.getConfigFileOutsideWorkspaceErrorMessage = exports.getPacksStrInvalid = exports.defaultAugmentationProperties = exports.BuildMode = void 0;
const fs = __importStar(require("fs")); const fs = __importStar(require("fs"));
const path = __importStar(require("path")); const path = __importStar(require("path"));
const perf_hooks_1 = require("perf_hooks"); const perf_hooks_1 = require("perf_hooks");
@ -36,6 +36,12 @@ const trap_caching_1 = require("./trap-caching");
const util_1 = require("./util"); const util_1 = require("./util");
// Property names from the user-supplied config file. // Property names from the user-supplied config file.
const PACKS_PROPERTY = "packs"; const PACKS_PROPERTY = "packs";
var BuildMode;
(function (BuildMode) {
BuildMode["None"] = "none";
BuildMode["Autobuild"] = "autobuild";
BuildMode["Manual"] = "manual";
})(BuildMode || (exports.BuildMode = BuildMode = {}));
/** /**
* The default, empty augmentation properties. This is most useful * The default, empty augmentation properties. This is most useful
* for tests. * for tests.
@ -148,7 +154,7 @@ async function getLanguages(codeQL, languagesInput, repository, logger) {
// If the languages parameter was not given and no languages were // If the languages parameter was not given and no languages were
// detected then fail here as this is a workflow configuration error. // detected then fail here as this is a workflow configuration error.
if (languages.length === 0) { if (languages.length === 0) {
throw new util_1.UserError(getNoLanguagesError()); throw new util_1.ConfigurationError(getNoLanguagesError());
} }
// Make sure they are supported // Make sure they are supported
const parsedLanguages = []; const parsedLanguages = [];
@ -165,7 +171,7 @@ async function getLanguages(codeQL, languagesInput, repository, logger) {
// Any unknown languages here would have come directly from the input // Any unknown languages here would have come directly from the input
// since we filter unknown languages coming from the GitHub API. // since we filter unknown languages coming from the GitHub API.
if (unknownLanguages.length > 0) { if (unknownLanguages.length > 0) {
throw new util_1.UserError(getUnknownLanguagesError(unknownLanguages)); throw new util_1.ConfigurationError(getUnknownLanguagesError(unknownLanguages));
} }
return parsedLanguages; return parsedLanguages;
} }
@ -218,7 +224,7 @@ async function getDefaultConfig({ languagesInput, queriesInput, packsInput, buil
const { trapCaches, trapCacheDownloadTime } = await downloadCacheWithTime(trapCachingEnabled, codeql, languages, logger); const { trapCaches, trapCacheDownloadTime } = await downloadCacheWithTime(trapCachingEnabled, codeql, languages, logger);
return { return {
languages, languages,
buildMode: buildModeInput, buildMode: validateBuildModeInput(buildModeInput),
originalUserInput: {}, originalUserInput: {},
tempDir, tempDir,
codeQLCmd: codeql.getPath(), codeQLCmd: codeql.getPath(),
@ -261,7 +267,7 @@ async function loadConfig({ languagesInput, queriesInput, packsInput, buildModeI
const { trapCaches, trapCacheDownloadTime } = await downloadCacheWithTime(trapCachingEnabled, codeql, languages, logger); const { trapCaches, trapCacheDownloadTime } = await downloadCacheWithTime(trapCachingEnabled, codeql, languages, logger);
return { return {
languages, languages,
buildMode: buildModeInput, buildMode: validateBuildModeInput(buildModeInput),
originalUserInput: parsedYAML, originalUserInput: parsedYAML,
tempDir, tempDir,
codeQLCmd: codeql.getPath(), codeQLCmd: codeql.getPath(),
@ -315,7 +321,7 @@ function parseQueriesFromInput(rawQueriesInput, queriesInputCombines) {
? rawQueriesInput.trim().slice(1).trim() ? rawQueriesInput.trim().slice(1).trim()
: rawQueriesInput?.trim() ?? ""; : rawQueriesInput?.trim() ?? "";
if (queriesInputCombines && trimmedInput.length === 0) { if (queriesInputCombines && trimmedInput.length === 0) {
throw new util_1.UserError(getConfigFilePropertyError(undefined, "queries", "A '+' was used in the 'queries' input to specify that you wished to add some packs to your CodeQL analysis. However, no packs were specified. Please either remove the '+' or specify some packs.")); throw new util_1.ConfigurationError(getConfigFilePropertyError(undefined, "queries", "A '+' was used in the 'queries' input to specify that you wished to add some packs to your CodeQL analysis. However, no packs were specified. Please either remove the '+' or specify some packs."));
} }
return trimmedInput.split(",").map((query) => ({ uses: query.trim() })); return trimmedInput.split(",").map((query) => ({ uses: query.trim() }));
} }
@ -335,16 +341,16 @@ function parsePacksFromInput(rawPacksInput, languages, packsInputCombines) {
return undefined; return undefined;
} }
if (languages.length > 1) { if (languages.length > 1) {
throw new util_1.UserError("Cannot specify a 'packs' input in a multi-language analysis. Use a codeql-config.yml file instead and specify packs by language."); throw new util_1.ConfigurationError("Cannot specify a 'packs' input in a multi-language analysis. Use a codeql-config.yml file instead and specify packs by language.");
} }
else if (languages.length === 0) { else if (languages.length === 0) {
throw new util_1.UserError("No languages specified. Cannot process the packs input."); throw new util_1.ConfigurationError("No languages specified. Cannot process the packs input.");
} }
rawPacksInput = rawPacksInput.trim(); rawPacksInput = rawPacksInput.trim();
if (packsInputCombines) { if (packsInputCombines) {
rawPacksInput = rawPacksInput.trim().substring(1).trim(); rawPacksInput = rawPacksInput.trim().substring(1).trim();
if (!rawPacksInput) { if (!rawPacksInput) {
throw new util_1.UserError(getConfigFilePropertyError(undefined, "packs", "A '+' was used in the 'packs' input to specify that you wished to add some packs to your CodeQL analysis. However, no packs were specified. Please either remove the '+' or specify some packs.")); throw new util_1.ConfigurationError(getConfigFilePropertyError(undefined, "packs", "A '+' was used in the 'packs' input to specify that you wished to add some packs to your CodeQL analysis. However, no packs were specified. Please either remove the '+' or specify some packs."));
} }
} }
return { return {
@ -375,7 +381,7 @@ exports.parsePacksFromInput = parsePacksFromInput;
*/ */
function parsePacksSpecification(packStr) { function parsePacksSpecification(packStr) {
if (typeof packStr !== "string") { if (typeof packStr !== "string") {
throw new util_1.UserError(getPacksStrInvalid(packStr)); throw new util_1.ConfigurationError(getPacksStrInvalid(packStr));
} }
packStr = packStr.trim(); packStr = packStr.trim();
const atIndex = packStr.indexOf("@"); const atIndex = packStr.indexOf("@");
@ -396,7 +402,7 @@ function parsePacksSpecification(packStr) {
? packStr.slice(pathStart, pathEnd).trim() ? packStr.slice(pathStart, pathEnd).trim()
: undefined; : undefined;
if (!PACK_IDENTIFIER_PATTERN.test(packName)) { if (!PACK_IDENTIFIER_PATTERN.test(packName)) {
throw new util_1.UserError(getPacksStrInvalid(packStr)); throw new util_1.ConfigurationError(getPacksStrInvalid(packStr));
} }
if (version) { if (version) {
try { try {
@ -404,7 +410,7 @@ function parsePacksSpecification(packStr) {
} }
catch (e) { catch (e) {
// The range string is invalid. OK to ignore the caught error // The range string is invalid. OK to ignore the caught error
throw new util_1.UserError(getPacksStrInvalid(packStr)); throw new util_1.ConfigurationError(getPacksStrInvalid(packStr));
} }
} }
if (packPath && if (packPath &&
@ -415,11 +421,11 @@ function parsePacksSpecification(packStr) {
// which seems more awkward. // which seems more awkward.
path.normalize(packPath).split(path.sep).join("/") !== path.normalize(packPath).split(path.sep).join("/") !==
packPath.split(path.sep).join("/"))) { packPath.split(path.sep).join("/"))) {
throw new util_1.UserError(getPacksStrInvalid(packStr)); throw new util_1.ConfigurationError(getPacksStrInvalid(packStr));
} }
if (!packPath && pathStart) { if (!packPath && pathStart) {
// 0 length path // 0 length path
throw new util_1.UserError(getPacksStrInvalid(packStr)); throw new util_1.ConfigurationError(getPacksStrInvalid(packStr));
} }
return { return {
name: packName, name: packName,
@ -487,7 +493,7 @@ function parseRegistries(registriesInput) {
: undefined; : undefined;
} }
catch (e) { catch (e) {
throw new util_1.UserError("Invalid registries input. Must be a YAML string."); throw new util_1.ConfigurationError("Invalid registries input. Must be a YAML string.");
} }
} }
function isLocal(configPath) { function isLocal(configPath) {
@ -500,11 +506,11 @@ function isLocal(configPath) {
function getLocalConfig(configFile, workspacePath) { function getLocalConfig(configFile, workspacePath) {
// Error if the config file is now outside of the workspace // Error if the config file is now outside of the workspace
if (!(configFile + path.sep).startsWith(workspacePath + path.sep)) { if (!(configFile + path.sep).startsWith(workspacePath + path.sep)) {
throw new util_1.UserError(getConfigFileOutsideWorkspaceErrorMessage(configFile)); throw new util_1.ConfigurationError(getConfigFileOutsideWorkspaceErrorMessage(configFile));
} }
// Error if the file does not exist // Error if the file does not exist
if (!fs.existsSync(configFile)) { if (!fs.existsSync(configFile)) {
throw new util_1.UserError(getConfigFileDoesNotExistErrorMessage(configFile)); throw new util_1.ConfigurationError(getConfigFileDoesNotExistErrorMessage(configFile));
} }
return yaml.load(fs.readFileSync(configFile, "utf8")); return yaml.load(fs.readFileSync(configFile, "utf8"));
} }
@ -514,7 +520,7 @@ async function getRemoteConfig(configFile, apiDetails) {
const pieces = format.exec(configFile); const pieces = format.exec(configFile);
// 5 = 4 groups + the whole expression // 5 = 4 groups + the whole expression
if (pieces === null || pieces.groups === undefined || pieces.length < 5) { if (pieces === null || pieces.groups === undefined || pieces.length < 5) {
throw new util_1.UserError(getConfigFileRepoFormatInvalidMessage(configFile)); throw new util_1.ConfigurationError(getConfigFileRepoFormatInvalidMessage(configFile));
} }
const response = await api const response = await api
.getApiClientWithExternalAuth(apiDetails) .getApiClientWithExternalAuth(apiDetails)
@ -529,10 +535,10 @@ async function getRemoteConfig(configFile, apiDetails) {
fileContents = response.data.content; fileContents = response.data.content;
} }
else if (Array.isArray(response.data)) { else if (Array.isArray(response.data)) {
throw new util_1.UserError(getConfigFileDirectoryGivenMessage(configFile)); throw new util_1.ConfigurationError(getConfigFileDirectoryGivenMessage(configFile));
} }
else { else {
throw new util_1.UserError(getConfigFileFormatInvalidMessage(configFile)); throw new util_1.ConfigurationError(getConfigFileFormatInvalidMessage(configFile));
} }
return yaml.load(Buffer.from(fileContents, "base64").toString("binary")); return yaml.load(Buffer.from(fileContents, "base64").toString("binary"));
} }
@ -611,7 +617,7 @@ exports.generateRegistries = generateRegistries;
function createRegistriesBlock(registries) { function createRegistriesBlock(registries) {
if (!Array.isArray(registries) || if (!Array.isArray(registries) ||
registries.some((r) => !r.url || !r.packages)) { registries.some((r) => !r.url || !r.packages)) {
throw new util_1.UserError("Invalid 'registries' input. Must be an array of objects with 'url' and 'packages' properties."); throw new util_1.ConfigurationError("Invalid 'registries' input. Must be an array of objects with 'url' and 'packages' properties.");
} }
// be sure to remove the `token` field from the registry before writing it to disk. // be sure to remove the `token` field from the registry before writing it to disk.
const safeRegistries = registries.map((registry) => ({ const safeRegistries = registries.map((registry) => ({
@ -658,4 +664,13 @@ async function wrapEnvironment(env, operation) {
} }
} }
exports.wrapEnvironment = wrapEnvironment; exports.wrapEnvironment = wrapEnvironment;
function validateBuildModeInput(buildModeInput) {
if (buildModeInput === undefined) {
return undefined;
}
if (!Object.values(BuildMode).includes(buildModeInput)) {
throw new util_1.ConfigurationError(`Invalid build mode: '${buildModeInput}'. Supported build modes are: ${Object.values(BuildMode).join(", ")}.`);
}
return buildModeInput;
}
//# sourceMappingURL=config-utils.js.map //# sourceMappingURL=config-utils.js.map

File diff suppressed because one or more lines are too long

View file

@ -35,6 +35,7 @@ const sinon = __importStar(require("sinon"));
const api = __importStar(require("./api-client")); const api = __importStar(require("./api-client"));
const codeql_1 = require("./codeql"); const codeql_1 = require("./codeql");
const configUtils = __importStar(require("./config-utils")); const configUtils = __importStar(require("./config-utils"));
const config_utils_1 = require("./config-utils");
const languages_1 = require("./languages"); const languages_1 = require("./languages");
const logging_1 = require("./logging"); const logging_1 = require("./logging");
const repository_1 = require("./repository"); const repository_1 = require("./repository");
@ -190,7 +191,7 @@ function mockListLanguages(languages) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getConfigFileOutsideWorkspaceErrorMessage(path.join(tempDir, "../input")))); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getConfigFileOutsideWorkspaceErrorMessage(path.join(tempDir, "../input"))));
} }
}); });
}); });
@ -208,7 +209,7 @@ function mockListLanguages(languages) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getConfigFileRepoFormatInvalidMessage("octo-org/codeql-config@main"))); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getConfigFileRepoFormatInvalidMessage("octo-org/codeql-config@main")));
} }
}); });
}); });
@ -228,7 +229,7 @@ function mockListLanguages(languages) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getConfigFileDoesNotExistErrorMessage(path.join(tempDir, "input")))); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getConfigFileDoesNotExistErrorMessage(path.join(tempDir, "input"))));
} }
}); });
}); });
@ -266,7 +267,7 @@ function mockListLanguages(languages) {
// And the config we expect it to parse to // And the config we expect it to parse to
const expectedConfig = { const expectedConfig = {
languages: [languages_1.Language.javascript], languages: [languages_1.Language.javascript],
buildMode: "none", buildMode: config_utils_1.BuildMode.None,
originalUserInput: { originalUserInput: {
name: "my config", name: "my config",
"disable-default-queries": true, "disable-default-queries": true,
@ -425,7 +426,7 @@ function queriesToResolvedQueryForm(queries) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getConfigFileDirectoryGivenMessage(repoReference))); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getConfigFileDirectoryGivenMessage(repoReference)));
} }
}); });
}); });
@ -446,7 +447,7 @@ function queriesToResolvedQueryForm(queries) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getConfigFileFormatInvalidMessage(repoReference))); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getConfigFileFormatInvalidMessage(repoReference)));
} }
}); });
}); });
@ -470,7 +471,7 @@ function queriesToResolvedQueryForm(queries) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getNoLanguagesError())); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getNoLanguagesError()));
} }
}); });
}); });
@ -487,7 +488,7 @@ function queriesToResolvedQueryForm(queries) {
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} }
catch (err) { catch (err) {
t.deepEqual(err, new util_1.UserError(configUtils.getUnknownLanguagesError(["rubbish", "english"]))); t.deepEqual(err, new util_1.ConfigurationError(configUtils.getUnknownLanguagesError(["rubbish", "english"])));
} }
}); });
}); });

File diff suppressed because one or more lines are too long

2
lib/environment.js generated
View file

@ -11,6 +11,8 @@ var EnvVar;
(function (EnvVar) { (function (EnvVar) {
/** Whether the `analyze` Action completes successfully. */ /** Whether the `analyze` Action completes successfully. */
EnvVar["ANALYZE_DID_COMPLETE_SUCCESSFULLY"] = "CODEQL_ACTION_ANALYZE_DID_COMPLETE_SUCCESSFULLY"; EnvVar["ANALYZE_DID_COMPLETE_SUCCESSFULLY"] = "CODEQL_ACTION_ANALYZE_DID_COMPLETE_SUCCESSFULLY";
/** Whether the `autobuild` Action completes successfully. */
EnvVar["AUTOBUILD_DID_COMPLETE_SUCCESSFULLY"] = "CODEQL_ACTION_AUTOBUILD_DID_COMPLETE_SUCCESSFULLY";
/** Whether the CodeQL Action has invoked the Go autobuilder. */ /** Whether the CodeQL Action has invoked the Go autobuilder. */
EnvVar["DID_AUTOBUILD_GOLANG"] = "CODEQL_ACTION_DID_AUTOBUILD_GOLANG"; EnvVar["DID_AUTOBUILD_GOLANG"] = "CODEQL_ACTION_DID_AUTOBUILD_GOLANG";
/** /**

View file

@ -1 +1 @@
{"version":3,"file":"environment.js","sourceRoot":"","sources":["../src/environment.ts"],"names":[],"mappings":";;;AAAA;;;;;GAKG;AACH,IAAY,MAyEX;AAzED,WAAY,MAAM;IAChB,2DAA2D;IAC3D,+FAAqF,CAAA;IAErF,gEAAgE;IAChE,qEAA2D,CAAA;IAE3D;;;OAGG;IACH,yFAA+E,CAAA;IAE/E;;;OAGG;IACH,yEAA+D,CAAA;IAE/D,gFAAgF;IAChF,6DAAmD,CAAA;IAEnD;;;OAGG;IACH,uEAA6D,CAAA;IAE7D,gEAAgE;IAChE,mEAAyD,CAAA;IAEzD,kFAAkF;IAClF,mFAAyE,CAAA;IAEzE,6CAA6C;IAC7C,uCAA6B,CAAA;IAE7B,+EAA+E;IAC/E,iDAAuC,CAAA;IAEvC,mEAAyD,CAAA;IAEzD;;;OAGG;IACH,2FAAiF,CAAA;IAEjF,mFAAmF;IACnF,6FAAmF,CAAA;IAEnF,qFAAqF;IACrF,+CAAqC,CAAA;IAErC,mEAAyD,CAAA;IAEzD,kEAAkE;IAClE,2CAAiC,CAAA;IAEjC;;;;;;OAMG;IACH,4DAAkD,CAAA;IAElD;;;OAGG;IACH,wDAA8C,CAAA;AAChD,CAAC,EAzEW,MAAM,sBAAN,MAAM,QAyEjB"} {"version":3,"file":"environment.js","sourceRoot":"","sources":["../src/environment.ts"],"names":[],"mappings":";;;AAAA;;;;;GAKG;AACH,IAAY,MA4EX;AA5ED,WAAY,MAAM;IAChB,2DAA2D;IAC3D,+FAAqF,CAAA;IAErF,6DAA6D;IAC7D,mGAAyF,CAAA;IAEzF,gEAAgE;IAChE,qEAA2D,CAAA;IAE3D;;;OAGG;IACH,yFAA+E,CAAA;IAE/E;;;OAGG;IACH,yEAA+D,CAAA;IAE/D,gFAAgF;IAChF,6DAAmD,CAAA;IAEnD;;;OAGG;IACH,uEAA6D,CAAA;IAE7D,gEAAgE;IAChE,mEAAyD,CAAA;IAEzD,kFAAkF;IAClF,mFAAyE,CAAA;IAEzE,6CAA6C;IAC7C,uCAA6B,CAAA;IAE7B,+EAA+E;IAC/E,iDAAuC,CAAA;IAEvC,mEAAyD,CAAA;IAEzD;;;OAGG;IACH,2FAAiF,CAAA;IAEjF,mFAAmF;IACnF,6FAAmF,CAAA;IAEnF,qFAAqF;IACrF,+CAAqC,CAAA;IAErC,mEAAyD,CAAA;IAEzD,kEAAkE;IAClE,2CAAiC,CAAA;IAEjC;;;;;;OAMG;IACH,4DAAkD,CAAA;IAElD;;;OAGG;IACH,wDAA8C,CAAA;AAChD,CAAC,EA5EW,MAAM,sBAAN,MAAM,QA4EjB"}

View file

@ -75,7 +75,7 @@ async function maybeUploadFailedSarif(config, repositoryNwo, features, logger) {
await codeql.databaseExportDiagnostics(databasePath, sarifFile, category, config.tempDir, logger); await codeql.databaseExportDiagnostics(databasePath, sarifFile, category, config.tempDir, logger);
} }
logger.info(`Uploading failed SARIF file ${sarifFile}`); logger.info(`Uploading failed SARIF file ${sarifFile}`);
const uploadResult = await uploadLib.uploadFromActions(sarifFile, checkoutPath, category, logger, { considerInvalidRequestUserError: false }); const uploadResult = await uploadLib.uploadFromActions(sarifFile, checkoutPath, category, logger, { considerInvalidRequestConfigError: false });
await uploadLib.waitForProcessing(repositoryNwo, uploadResult.sarifID, logger, { isUnsuccessfulExecution: true }); await uploadLib.waitForProcessing(repositoryNwo, uploadResult.sarifID, logger, { isUnsuccessfulExecution: true });
return uploadResult return uploadResult
? { ...uploadResult.statusReport, sarifID: uploadResult.sarifID } ? { ...uploadResult.statusReport, sarifID: uploadResult.sarifID }
@ -88,7 +88,7 @@ async function tryUploadSarifIfRunFailed(config, repositoryNwo, features, logger
// means that something along the way failed in a step that is not // means that something along the way failed in a step that is not
// owned by the Action, for example a manual build step. We // owned by the Action, for example a manual build step. We
// consider this a configuration error. // consider this a configuration error.
core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? status_report_1.JobStatus.ConfigurationError); core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? status_report_1.JobStatus.ConfigErrorStatus);
try { try {
return await maybeUploadFailedSarif(config, repositoryNwo, features, logger); return await maybeUploadFailedSarif(config, repositoryNwo, features, logger);
} }
@ -98,7 +98,7 @@ async function tryUploadSarifIfRunFailed(config, repositoryNwo, features, logger
} }
} }
else { else {
core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? status_report_1.JobStatus.Success); core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? status_report_1.JobStatus.SuccessStatus);
return { return {
upload_failed_run_skipped_because: "Analyze Action completed successfully", upload_failed_run_skipped_because: "Analyze Action completed successfully",
}; };
@ -204,7 +204,7 @@ function getFinalJobStatus() {
const jobStatusFromEnvironment = process.env[environment_1.EnvVar.JOB_STATUS]; const jobStatusFromEnvironment = process.env[environment_1.EnvVar.JOB_STATUS];
if (!jobStatusFromEnvironment || if (!jobStatusFromEnvironment ||
!Object.values(status_report_1.JobStatus).includes(jobStatusFromEnvironment)) { !Object.values(status_report_1.JobStatus).includes(jobStatusFromEnvironment)) {
return status_report_1.JobStatus.Unknown; return status_report_1.JobStatus.UnknownStatus;
} }
return jobStatusFromEnvironment; return jobStatusFromEnvironment;
} }

File diff suppressed because one or more lines are too long

2
lib/init-action.js generated
View file

@ -181,7 +181,7 @@ async function run() {
catch (unwrappedError) { catch (unwrappedError) {
const error = (0, util_1.wrapError)(unwrappedError); const error = (0, util_1.wrapError)(unwrappedError);
core.setFailed(error.message); core.setFailed(error.message);
await (0, status_report_1.sendStatusReport)(await (0, status_report_1.createStatusReportBase)("init", error instanceof util_1.UserError ? "user-error" : "aborted", startedAt, await (0, util_1.checkDiskUsage)(), error.message, error.stack)); await (0, status_report_1.sendStatusReport)(await (0, status_report_1.createStatusReportBase)("init", error instanceof util_1.ConfigurationError ? "user-error" : "aborted", startedAt, await (0, util_1.checkDiskUsage)(), error.message, error.stack));
return; return;
} }
try { try {

File diff suppressed because one or more lines are too long

48
lib/init.js generated
View file

@ -32,7 +32,6 @@ const codeql_1 = require("./codeql");
const configUtils = __importStar(require("./config-utils")); const configUtils = __importStar(require("./config-utils"));
const languages_1 = require("./languages"); const languages_1 = require("./languages");
const tracer_config_1 = require("./tracer-config"); const tracer_config_1 = require("./tracer-config");
const util = __importStar(require("./util"));
async function initCodeQL(toolsInput, apiDetails, tempDir, variant, defaultCliVersion, logger) { async function initCodeQL(toolsInput, apiDetails, tempDir, variant, defaultCliVersion, logger) {
logger.startGroup("Setup CodeQL tools"); logger.startGroup("Setup CodeQL tools");
const { codeql, toolsDownloadDurationMs, toolsSource, toolsVersion } = await (0, codeql_1.setupCodeQL)(toolsInput, apiDetails, tempDir, variant, defaultCliVersion, logger, true); const { codeql, toolsDownloadDurationMs, toolsSource, toolsVersion } = await (0, codeql_1.setupCodeQL)(toolsInput, apiDetails, tempDir, variant, defaultCliVersion, logger, true);
@ -52,18 +51,13 @@ async function initConfig(inputs) {
exports.initConfig = initConfig; exports.initConfig = initConfig;
async function runInit(codeql, config, sourceRoot, processName, registriesInput, apiDetails, logger) { async function runInit(codeql, config, sourceRoot, processName, registriesInput, apiDetails, logger) {
fs.mkdirSync(config.dbLocation, { recursive: true }); fs.mkdirSync(config.dbLocation, { recursive: true });
try { const { registriesAuthTokens, qlconfigFile } = await configUtils.generateRegistries(registriesInput, config.tempDir, logger);
const { registriesAuthTokens, qlconfigFile } = await configUtils.generateRegistries(registriesInput, config.tempDir, logger); await configUtils.wrapEnvironment({
await configUtils.wrapEnvironment({ GITHUB_TOKEN: apiDetails.auth,
GITHUB_TOKEN: apiDetails.auth, CODEQL_REGISTRIES_AUTH: registriesAuthTokens,
CODEQL_REGISTRIES_AUTH: registriesAuthTokens, },
}, // Init a database cluster
// Init a database cluster async () => await codeql.databaseInitCluster(config, sourceRoot, processName, qlconfigFile, logger));
async () => await codeql.databaseInitCluster(config, sourceRoot, processName, qlconfigFile, logger));
}
catch (e) {
throw processError(e);
}
return await (0, tracer_config_1.getCombinedTracerConfig)(codeql, config); return await (0, tracer_config_1.getCombinedTracerConfig)(codeql, config);
} }
exports.runInit = runInit; exports.runInit = runInit;
@ -77,34 +71,6 @@ function printPathFiltersWarning(config, logger) {
} }
} }
exports.printPathFiltersWarning = printPathFiltersWarning; exports.printPathFiltersWarning = printPathFiltersWarning;
/**
* Possibly convert this error into a UserError in order to avoid
* counting this error towards our internal error budget.
*
* @param e The error to possibly convert to a UserError.
*
* @returns A UserError if the error is a known error that can be
* attributed to the user, otherwise the original error.
*/
function processError(e) {
if (!(e instanceof Error)) {
return e;
}
if (
// Init action called twice
e.message?.includes("Refusing to create databases") &&
e.message?.includes("exists and is not an empty directory.")) {
return new util.UserError(`Is the "init" action called twice in the same job? ${e.message}`);
}
if (
// Version of CodeQL CLI is incompatible with this version of the CodeQL Action
e.message?.includes("is not compatible with this CodeQL CLI") ||
// Expected source location for database creation does not exist
e.message?.includes("Invalid source root")) {
return new util.UserError(e.message);
}
return e;
}
/** /**
* If we are running python 3.12+ on windows, we need to switch to python 3.11. * If we are running python 3.12+ on windows, we need to switch to python 3.11.
* This check happens in a powershell script. * This check happens in a powershell script.

View file

@ -1 +1 @@
{"version":3,"file":"init.js","sourceRoot":"","sources":["../src/init.ts"],"names":[],"mappings":"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"} {"version":3,"file":"init.js","sourceRoot":"","sources":["../src/init.ts"],"names":[],"mappings":"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"}

2
lib/repository.js generated
View file

@ -5,7 +5,7 @@ const util_1 = require("./util");
function parseRepositoryNwo(input) { function parseRepositoryNwo(input) {
const parts = input.split("/"); const parts = input.split("/");
if (parts.length !== 2) { if (parts.length !== 2) {
throw new util_1.UserError(`"${input}" is not a valid repository name`); throw new util_1.ConfigurationError(`"${input}" is not a valid repository name`);
} }
return { return {
owner: parts[0], owner: parts[0],

View file

@ -1 +1 @@
{"version":3,"file":"repository.js","sourceRoot":"","sources":["../src/repository.ts"],"names":[],"mappings":";;;AAAA,iCAAmC;AAQnC,SAAgB,kBAAkB,CAAC,KAAa;IAC9C,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC/B,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACvB,MAAM,IAAI,gBAAS,CAAC,IAAI,KAAK,kCAAkC,CAAC,CAAC;IACnE,CAAC;IACD,OAAO;QACL,KAAK,EAAE,KAAK,CAAC,CAAC,CAAC;QACf,IAAI,EAAE,KAAK,CAAC,CAAC,CAAC;KACf,CAAC;AACJ,CAAC;AATD,gDASC"} {"version":3,"file":"repository.js","sourceRoot":"","sources":["../src/repository.ts"],"names":[],"mappings":";;;AAAA,iCAA4C;AAQ5C,SAAgB,kBAAkB,CAAC,KAAa;IAC9C,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC/B,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACvB,MAAM,IAAI,yBAAkB,CAAC,IAAI,KAAK,kCAAkC,CAAC,CAAC;IAC5E,CAAC;IACD,OAAO;QACL,KAAK,EAAE,KAAK,CAAC,CAAC,CAAC;QACf,IAAI,EAAE,KAAK,CAAC,CAAC,CAAC;KACf,CAAC;AACJ,CAAC;AATD,gDASC"}

View file

@ -26,7 +26,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
const core = __importStar(require("@actions/core")); const core = __importStar(require("@actions/core"));
const actions_util_1 = require("./actions-util"); const actions_util_1 = require("./actions-util");
const api_client_1 = require("./api-client"); const api_client_1 = require("./api-client");
const codeql_1 = require("./codeql"); const cli_errors_1 = require("./cli-errors");
const configUtils = __importStar(require("./config-utils")); const configUtils = __importStar(require("./config-utils"));
const logging_1 = require("./logging"); const logging_1 = require("./logging");
const resolve_environment_1 = require("./resolve-environment"); const resolve_environment_1 = require("./resolve-environment");
@ -54,7 +54,7 @@ async function run() {
} }
catch (unwrappedError) { catch (unwrappedError) {
const error = (0, util_1.wrapError)(unwrappedError); const error = (0, util_1.wrapError)(unwrappedError);
if (error instanceof codeql_1.CommandInvocationError) { if (error instanceof cli_errors_1.CommandInvocationError) {
// If the CLI failed to run successfully for whatever reason, // If the CLI failed to run successfully for whatever reason,
// we just return an empty JSON object and proceed with the workflow. // we just return an empty JSON object and proceed with the workflow.
core.setOutput(ENVIRONMENT_OUTPUT_NAME, {}); core.setOutput(ENVIRONMENT_OUTPUT_NAME, {});

View file

@ -1 +1 @@
{"version":3,"file":"resolve-environment-action.js","sourceRoot":"","sources":["../src/resolve-environment-action.ts"],"names":[],"mappings":"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"} {"version":3,"file":"resolve-environment-action.js","sourceRoot":"","sources":["../src/resolve-environment-action.ts"],"names":[],"mappings":"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"}

View file

@ -36,7 +36,7 @@ async function runResolveBuildEnvironment(cmd, logger, workingDir, languageInput
if (!(await util.codeQlVersionAbove(codeql, codeql_1.CODEQL_VERSION_LANGUAGE_ALIASING))) { if (!(await util.codeQlVersionAbove(codeql, codeql_1.CODEQL_VERSION_LANGUAGE_ALIASING))) {
const parsedLanguage = (0, languages_1.parseLanguage)(languageInput)?.toString(); const parsedLanguage = (0, languages_1.parseLanguage)(languageInput)?.toString();
if (parsedLanguage === undefined) { if (parsedLanguage === undefined) {
throw new util.UserError(`Did not recognize the language '${languageInput}'.`); throw new util.ConfigurationError(`Did not recognize the language '${languageInput}'.`);
} }
language = parsedLanguage; language = parsedLanguage;
} }

View file

@ -1 +1 @@
{"version":3,"file":"resolve-environment.js","sourceRoot":"","sources":["../src/resolve-environment.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,qCAIkB;AAClB,2CAA4C;AAE5C,6CAA+B;AAExB,KAAK,UAAU,0BAA0B,CAC9C,GAAW,EACX,MAAc,EACd,UAA8B,EAC9B,aAAqB;IAErB,MAAM,CAAC,UAAU,CACf,+CAA+C,aAAa,EAAE,CAC/D,CAAC;IAEF,MAAM,MAAM,GAAG,MAAM,IAAA,kBAAS,EAAC,GAAG,CAAC,CAAC;IAEpC,IAAI,QAAQ,GAAG,aAAa,CAAC;IAC7B,6FAA6F;IAC7F,mFAAmF;IACnF,IACE,CAAC,CAAC,MAAM,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,yCAAgC,CAAC,CAAC,EAC1E,CAAC;QACD,MAAM,cAAc,GAAG,IAAA,yBAAa,EAAC,aAAa,CAAC,EAAE,QAAQ,EAAE,CAAC;QAChE,IAAI,cAAc,KAAK,SAAS,EAAE,CAAC;YACjC,MAAM,IAAI,IAAI,CAAC,SAAS,CACtB,mCAAmC,aAAa,IAAI,CACrD,CAAC;QACJ,CAAC;QACD,QAAQ,GAAG,cAAc,CAAC;IAC5B,CAAC;IAED,IAAI,MAAM,GAAG,EAAE,CAAC;IAEhB,gFAAgF;IAChF,yEAAyE;IACzE,IACE,CAAC,CAAC,MAAM,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,2CAAkC,CAAC,CAAC,EAC5E,CAAC;QACD,MAAM,CAAC,OAAO,CACZ,0EAA0E;YACxE,mCAAmC,CACtC,CAAC;IACJ,CAAC;SAAM,CAAC;QACN,IAAI,UAAU,KAAK,SAAS,EAAE,CAAC;YAC7B,MAAM,CAAC,IAAI,CAAC,SAAS,UAAU,4BAA4B,CAAC,CAAC;QAC/D,CAAC;QAED,MAAM,GAAG,MAAM,MAAM,CAAC,uBAAuB,CAAC,UAAU,EAAE,QAAQ,CAAC,CAAC;IACtE,CAAC;IAED,MAAM,CAAC,QAAQ,EAAE,CAAC;IAClB,OAAO,MAAM,CAAC;AAChB,CAAC;AAhDD,gEAgDC"} {"version":3,"file":"resolve-environment.js","sourceRoot":"","sources":["../src/resolve-environment.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,qCAIkB;AAClB,2CAA4C;AAE5C,6CAA+B;AAExB,KAAK,UAAU,0BAA0B,CAC9C,GAAW,EACX,MAAc,EACd,UAA8B,EAC9B,aAAqB;IAErB,MAAM,CAAC,UAAU,CACf,+CAA+C,aAAa,EAAE,CAC/D,CAAC;IAEF,MAAM,MAAM,GAAG,MAAM,IAAA,kBAAS,EAAC,GAAG,CAAC,CAAC;IAEpC,IAAI,QAAQ,GAAG,aAAa,CAAC;IAC7B,6FAA6F;IAC7F,mFAAmF;IACnF,IACE,CAAC,CAAC,MAAM,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,yCAAgC,CAAC,CAAC,EAC1E,CAAC;QACD,MAAM,cAAc,GAAG,IAAA,yBAAa,EAAC,aAAa,CAAC,EAAE,QAAQ,EAAE,CAAC;QAChE,IAAI,cAAc,KAAK,SAAS,EAAE,CAAC;YACjC,MAAM,IAAI,IAAI,CAAC,kBAAkB,CAC/B,mCAAmC,aAAa,IAAI,CACrD,CAAC;QACJ,CAAC;QACD,QAAQ,GAAG,cAAc,CAAC;IAC5B,CAAC;IAED,IAAI,MAAM,GAAG,EAAE,CAAC;IAEhB,gFAAgF;IAChF,yEAAyE;IACzE,IACE,CAAC,CAAC,MAAM,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,2CAAkC,CAAC,CAAC,EAC5E,CAAC;QACD,MAAM,CAAC,OAAO,CACZ,0EAA0E;YACxE,mCAAmC,CACtC,CAAC;IACJ,CAAC;SAAM,CAAC;QACN,IAAI,UAAU,KAAK,SAAS,EAAE,CAAC;YAC7B,MAAM,CAAC,IAAI,CAAC,SAAS,UAAU,4BAA4B,CAAC,CAAC;QAC/D,CAAC;QAED,MAAM,GAAG,MAAM,MAAM,CAAC,uBAAuB,CAAC,UAAU,EAAE,QAAQ,CAAC,CAAC;IACtE,CAAC;IAED,MAAM,CAAC,QAAQ,EAAE,CAAC;IAClB,OAAO,MAAM,CAAC;AAChB,CAAC;AAhDD,gEAgDC"}

2
lib/setup-codeql.js generated
View file

@ -441,7 +441,7 @@ exports.downloadCodeQL = downloadCodeQL;
function getCodeQLURLVersion(url) { function getCodeQLURLVersion(url) {
const match = url.match(/\/codeql-bundle-(.*)\//); const match = url.match(/\/codeql-bundle-(.*)\//);
if (match === null || match.length < 2) { if (match === null || match.length < 2) {
throw new util.UserError(`Malformed tools url: ${url}. Version could not be inferred`); throw new util.ConfigurationError(`Malformed tools url: ${url}. Version could not be inferred`);
} }
return match[1]; return match[1];
} }

File diff suppressed because one or more lines are too long

14
lib/status-report.js generated
View file

@ -33,14 +33,14 @@ const util_1 = require("./util");
/** Overall status of the entire job. String values match the Hydro schema. */ /** Overall status of the entire job. String values match the Hydro schema. */
var JobStatus; var JobStatus;
(function (JobStatus) { (function (JobStatus) {
JobStatus["Unknown"] = "JOB_STATUS_UNKNOWN"; JobStatus["UnknownStatus"] = "JOB_STATUS_UNKNOWN";
JobStatus["Success"] = "JOB_STATUS_SUCCESS"; JobStatus["SuccessStatus"] = "JOB_STATUS_SUCCESS";
JobStatus["Failure"] = "JOB_STATUS_FAILURE"; JobStatus["FailureStatus"] = "JOB_STATUS_FAILURE";
JobStatus["ConfigurationError"] = "JOB_STATUS_CONFIGURATION_ERROR"; JobStatus["ConfigErrorStatus"] = "JOB_STATUS_CONFIGURATION_ERROR";
})(JobStatus || (exports.JobStatus = JobStatus = {})); })(JobStatus || (exports.JobStatus = JobStatus = {}));
function getActionsStatus(error, otherFailureCause) { function getActionsStatus(error, otherFailureCause) {
if (error || otherFailureCause) { if (error || otherFailureCause) {
return error instanceof util_1.UserError ? "user-error" : "failure"; return error instanceof util_1.ConfigurationError ? "user-error" : "failure";
} }
else { else {
return "success"; return "success";
@ -54,10 +54,10 @@ exports.getActionsStatus = getActionsStatus;
*/ */
function setJobStatusIfUnsuccessful(actionStatus) { function setJobStatusIfUnsuccessful(actionStatus) {
if (actionStatus === "user-error") { if (actionStatus === "user-error") {
core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? JobStatus.ConfigurationError); core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? JobStatus.ConfigErrorStatus);
} }
else if (actionStatus === "failure" || actionStatus === "aborted") { else if (actionStatus === "failure" || actionStatus === "aborted") {
core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? JobStatus.Failure); core.exportVariable(environment_1.EnvVar.JOB_STATUS, process.env[environment_1.EnvVar.JOB_STATUS] ?? JobStatus.FailureStatus);
} }
} }
/** /**

File diff suppressed because one or more lines are too long

1
lib/tools-features.js generated
View file

@ -6,6 +6,7 @@ var ToolsFeature;
ToolsFeature["BuildModeOption"] = "buildModeOption"; ToolsFeature["BuildModeOption"] = "buildModeOption";
ToolsFeature["IndirectTracingSupportsStaticBinaries"] = "indirectTracingSupportsStaticBinaries"; ToolsFeature["IndirectTracingSupportsStaticBinaries"] = "indirectTracingSupportsStaticBinaries";
ToolsFeature["SetsCodeqlRunnerEnvVar"] = "setsCodeqlRunnerEnvVar"; ToolsFeature["SetsCodeqlRunnerEnvVar"] = "setsCodeqlRunnerEnvVar";
ToolsFeature["TraceCommandUseBuildMode"] = "traceCommandUseBuildMode";
})(ToolsFeature || (exports.ToolsFeature = ToolsFeature = {})); })(ToolsFeature || (exports.ToolsFeature = ToolsFeature = {}));
/** /**
* Determines if the given feature is supported by the CLI. * Determines if the given feature is supported by the CLI.

View file

@ -1 +1 @@
{"version":3,"file":"tools-features.js","sourceRoot":"","sources":["../src/tools-features.ts"],"names":[],"mappings":";;;AAEA,IAAY,YAIX;AAJD,WAAY,YAAY;IACtB,mDAAmC,CAAA;IACnC,+FAA+E,CAAA;IAC/E,iEAAiD,CAAA;AACnD,CAAC,EAJW,YAAY,4BAAZ,YAAY,QAIvB;AAED;;;;;;GAMG;AACH,SAAgB,uBAAuB,CACrC,WAAwB,EACxB,OAAqB;IAErB,OAAO,CAAC,CAAC,WAAW,CAAC,QAAQ,IAAI,WAAW,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;AACjE,CAAC;AALD,0DAKC"} {"version":3,"file":"tools-features.js","sourceRoot":"","sources":["../src/tools-features.ts"],"names":[],"mappings":";;;AAEA,IAAY,YAKX;AALD,WAAY,YAAY;IACtB,mDAAmC,CAAA;IACnC,+FAA+E,CAAA;IAC/E,iEAAiD,CAAA;IACjD,qEAAqD,CAAA;AACvD,CAAC,EALW,YAAY,4BAAZ,YAAY,QAKvB;AAED;;;;;;GAMG;AACH,SAAgB,uBAAuB,CACrC,WAAwB,EACxB,OAAqB;IAErB,OAAO,CAAC,CAAC,WAAW,CAAC,QAAQ,IAAI,WAAW,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;AACjE,CAAC;AALD,0DAKC"}

14
lib/upload-lib.js generated
View file

@ -132,17 +132,17 @@ exports.findSarifFilesInDir = findSarifFilesInDir;
* Uploads a single SARIF file or a directory of SARIF files depending on what `sarifPath` refers * Uploads a single SARIF file or a directory of SARIF files depending on what `sarifPath` refers
* to. * to.
* *
* @param considerInvalidRequestUserError Whether an invalid request, for example one with a * @param considerInvalidRequestConfigError Whether an invalid request, for example one with a
* `sarifPath` that does not exist, should be considered a * `sarifPath` that does not exist, should be considered a
* user error. * user error.
*/ */
async function uploadFromActions(sarifPath, checkoutPath, category, logger, { considerInvalidRequestUserError, }) { async function uploadFromActions(sarifPath, checkoutPath, category, logger, { considerInvalidRequestConfigError: considerInvalidRequestConfigError, }) {
try { try {
return await uploadFiles(getSarifFilePaths(sarifPath), (0, repository_1.parseRepositoryNwo)(util.getRequiredEnvParam("GITHUB_REPOSITORY")), await actionsUtil.getCommitOid(checkoutPath), await actionsUtil.getRef(), await api.getAnalysisKey(), category, util.getRequiredEnvParam("GITHUB_WORKFLOW"), actionsUtil.getWorkflowRunID(), actionsUtil.getWorkflowRunAttempt(), checkoutPath, actionsUtil.getRequiredInput("matrix"), logger); return await uploadFiles(getSarifFilePaths(sarifPath), (0, repository_1.parseRepositoryNwo)(util.getRequiredEnvParam("GITHUB_REPOSITORY")), await actionsUtil.getCommitOid(checkoutPath), await actionsUtil.getRef(), await api.getAnalysisKey(), category, util.getRequiredEnvParam("GITHUB_WORKFLOW"), actionsUtil.getWorkflowRunID(), actionsUtil.getWorkflowRunAttempt(), checkoutPath, actionsUtil.getRequiredInput("matrix"), logger);
} }
catch (e) { catch (e) {
if (e instanceof InvalidRequestError && considerInvalidRequestUserError) { if (e instanceof InvalidRequestError && considerInvalidRequestConfigError) {
throw new util_1.UserError(e.message); throw new util_1.ConfigurationError(e.message);
} }
throw e; throw e;
} }
@ -343,8 +343,8 @@ async function waitForProcessing(repositoryNwo, sarifID, logger, options = {
} }
else if (status === "failed") { else if (status === "failed") {
const message = `Code Scanning could not process the submitted SARIF file:\n${response.data.errors}`; const message = `Code Scanning could not process the submitted SARIF file:\n${response.data.errors}`;
throw shouldConsiderAsUserError(response.data.errors) throw shouldConsiderConfigurationError(response.data.errors)
? new util_1.UserError(message) ? new util_1.ConfigurationError(message)
: new InvalidRequestError(message); : new InvalidRequestError(message);
} }
else { else {
@ -363,7 +363,7 @@ exports.waitForProcessing = waitForProcessing;
/** /**
* Returns whether the provided processing errors should be considered a user error. * Returns whether the provided processing errors should be considered a user error.
*/ */
function shouldConsiderAsUserError(processingErrors) { function shouldConsiderConfigurationError(processingErrors) {
return (processingErrors.length === 1 && return (processingErrors.length === 1 &&
processingErrors[0] === processingErrors[0] ===
"CodeQL analyses from advanced configurations cannot be processed when the default setup is enabled"); "CodeQL analyses from advanced configurations cannot be processed when the default setup is enabled");

File diff suppressed because one or more lines are too long

View file

@ -50,7 +50,7 @@ async function run() {
return; return;
} }
try { try {
const uploadResult = await upload_lib.uploadFromActions(actionsUtil.getRequiredInput("sarif_file"), actionsUtil.getRequiredInput("checkout_path"), actionsUtil.getOptionalInput("category"), logger, { considerInvalidRequestUserError: true }); const uploadResult = await upload_lib.uploadFromActions(actionsUtil.getRequiredInput("sarif_file"), actionsUtil.getRequiredInput("checkout_path"), actionsUtil.getOptionalInput("category"), logger, { considerInvalidRequestConfigError: true });
core.setOutput("sarif-id", uploadResult.sarifID); core.setOutput("sarif-id", uploadResult.sarifID);
// We don't upload results in test mode, so don't wait for processing // We don't upload results in test mode, so don't wait for processing
if ((0, util_1.isInTestMode)()) { if ((0, util_1.isInTestMode)()) {

View file

@ -1 +1 @@
{"version":3,"file":"upload-sarif-action.js","sourceRoot":"","sources":["../src/upload-sarif-action.ts"],"names":[],"mappings":"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"} {"version":3,"file":"upload-sarif-action.js","sourceRoot":"","sources":["../src/upload-sarif-action.ts"],"names":[],"mappings":"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"}

16
lib/util.js generated
View file

@ -26,7 +26,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod }; return (mod && mod.__esModule) ? mod : { "default": mod };
}; };
Object.defineProperty(exports, "__esModule", { value: true }); Object.defineProperty(exports, "__esModule", { value: true });
exports.checkActionVersion = exports.checkDiskUsage = exports.prettyPrintPack = exports.getErrorMessage = exports.wrapError = exports.fixInvalidNotificationsInFile = exports.fixInvalidNotifications = exports.parseMatrixInput = exports.isHostedRunner = exports.checkForTimeout = exports.withTimeout = exports.tryGetFolderBytes = exports.listFolder = exports.doesDirectoryExist = exports.isInTestMode = exports.supportExpectDiscardedCache = exports.isGoodVersion = exports.delay = exports.bundleDb = exports.codeQlVersionAbove = exports.getCachedCodeQlVersion = exports.cacheCodeQlVersion = exports.isHTTPError = exports.UserError = exports.HTTPError = exports.getRequiredEnvParam = exports.initializeEnvironment = exports.assertNever = exports.apiVersionInRange = exports.DisallowedAPIVersionReason = exports.checkGitHubVersionInRange = exports.GitHubVariant = exports.parseGitHubUrl = exports.getCodeQLDatabasePath = exports.getThreadsFlag = exports.getThreadsFlagValue = exports.getAddSnippetsFlag = exports.getMemoryFlag = exports.getMemoryFlagValue = exports.getMemoryFlagValueForPlatform = exports.withTmpDir = exports.getToolNames = exports.getExtraOptionsEnvParam = exports.DEFAULT_DEBUG_DATABASE_NAME = exports.DEFAULT_DEBUG_ARTIFACT_NAME = exports.GITHUB_DOTCOM_URL = void 0; exports.checkActionVersion = exports.checkDiskUsage = exports.prettyPrintPack = exports.getErrorMessage = exports.wrapError = exports.fixInvalidNotificationsInFile = exports.fixInvalidNotifications = exports.parseMatrixInput = exports.isHostedRunner = exports.checkForTimeout = exports.withTimeout = exports.tryGetFolderBytes = exports.listFolder = exports.doesDirectoryExist = exports.isInTestMode = exports.supportExpectDiscardedCache = exports.isGoodVersion = exports.delay = exports.bundleDb = exports.codeQlVersionAbove = exports.getCachedCodeQlVersion = exports.cacheCodeQlVersion = exports.isHTTPError = exports.ConfigurationError = exports.HTTPError = exports.getRequiredEnvParam = exports.initializeEnvironment = exports.assertNever = exports.apiVersionInRange = exports.DisallowedAPIVersionReason = exports.checkGitHubVersionInRange = exports.GitHubVariant = exports.parseGitHubUrl = exports.getCodeQLDatabasePath = exports.getThreadsFlag = exports.getThreadsFlagValue = exports.getAddSnippetsFlag = exports.getMemoryFlag = exports.getMemoryFlagValue = exports.getMemoryFlagValueForPlatform = exports.withTmpDir = exports.getToolNames = exports.getExtraOptionsEnvParam = exports.DEFAULT_DEBUG_DATABASE_NAME = exports.DEFAULT_DEBUG_ARTIFACT_NAME = exports.GITHUB_DOTCOM_URL = void 0;
const fs = __importStar(require("fs")); const fs = __importStar(require("fs"));
const os = __importStar(require("os")); const os = __importStar(require("os"));
const path = __importStar(require("path")); const path = __importStar(require("path"));
@ -78,7 +78,7 @@ function getExtraOptionsEnvParam() {
} }
catch (unwrappedError) { catch (unwrappedError) {
const error = wrapError(unwrappedError); const error = wrapError(unwrappedError);
throw new UserError(`${varName} environment variable is set, but does not contain valid JSON: ${error.message}`); throw new ConfigurationError(`${varName} environment variable is set, but does not contain valid JSON: ${error.message}`);
} }
} }
exports.getExtraOptionsEnvParam = getExtraOptionsEnvParam; exports.getExtraOptionsEnvParam = getExtraOptionsEnvParam;
@ -142,7 +142,7 @@ function getMemoryFlagValueForPlatform(userInput, totalMemoryBytes, platform) {
if (userInput) { if (userInput) {
memoryToUseMegaBytes = Number(userInput); memoryToUseMegaBytes = Number(userInput);
if (Number.isNaN(memoryToUseMegaBytes) || memoryToUseMegaBytes <= 0) { if (Number.isNaN(memoryToUseMegaBytes) || memoryToUseMegaBytes <= 0) {
throw new UserError(`Invalid RAM setting "${userInput}", specified.`); throw new ConfigurationError(`Invalid RAM setting "${userInput}", specified.`);
} }
} }
else { else {
@ -262,7 +262,7 @@ function getThreadsFlagValue(userInput, logger) {
if (userInput) { if (userInput) {
numThreads = Number(userInput); numThreads = Number(userInput);
if (Number.isNaN(numThreads)) { if (Number.isNaN(numThreads)) {
throw new UserError(`Invalid threads setting "${userInput}", specified.`); throw new ConfigurationError(`Invalid threads setting "${userInput}", specified.`);
} }
if (numThreads > maxThreads) { if (numThreads > maxThreads) {
logger.info(`Clamping desired number of threads (${numThreads}) to max available (${maxThreads}).`); logger.info(`Clamping desired number of threads (${numThreads}) to max available (${maxThreads}).`);
@ -360,14 +360,14 @@ function parseGitHubUrl(inputUrl) {
inputUrl = `https://${inputUrl}`; inputUrl = `https://${inputUrl}`;
} }
if (!inputUrl.startsWith("http://") && !inputUrl.startsWith("https://")) { if (!inputUrl.startsWith("http://") && !inputUrl.startsWith("https://")) {
throw new UserError(`"${originalUrl}" is not a http or https URL`); throw new ConfigurationError(`"${originalUrl}" is not a http or https URL`);
} }
let url; let url;
try { try {
url = new URL(inputUrl); url = new URL(inputUrl);
} }
catch (e) { catch (e) {
throw new UserError(`"${originalUrl}" is not a valid URL`); throw new ConfigurationError(`"${originalUrl}" is not a valid URL`);
} }
// If we detect this is trying to be to github.com // If we detect this is trying to be to github.com
// then return with a fixed canonical URL. // then return with a fixed canonical URL.
@ -478,12 +478,12 @@ exports.HTTPError = HTTPError;
* An Error class that indicates an error that occurred due to * An Error class that indicates an error that occurred due to
* a misconfiguration of the action or the CodeQL CLI. * a misconfiguration of the action or the CodeQL CLI.
*/ */
class UserError extends Error { class ConfigurationError extends Error {
constructor(message) { constructor(message) {
super(message); super(message);
} }
} }
exports.UserError = UserError; exports.ConfigurationError = ConfigurationError;
function isHTTPError(arg) { function isHTTPError(arg) {
return arg?.status !== undefined && Number.isInteger(arg.status); return arg?.status !== undefined && Number.isInteger(arg.status);
} }

File diff suppressed because one or more lines are too long

View file

@ -0,0 +1,29 @@
name: "Build mode autobuild"
description: "An end-to-end integration test of a Java repository built using 'build-mode: autobuild'"
operatingSystems: ["ubuntu"]
versions: ["nightly-latest"]
steps:
- name: Set up Java test repo configuration
run: |
mv * .github ../action/tests/multi-language-repo/
mv ../action/tests/multi-language-repo/.github/workflows .github
mv ../action/tests/java-repo/* .
- uses: ./../action/init
id: init
with:
build-mode: autobuild
db-location: "${{ runner.temp }}/customDbLocation"
languages: java
tools: ${{ steps.prepare-test.outputs.tools-url }}
- name: Validate database build mode
run: |
metadata_path="$RUNNER_TEMP/customDbLocation/java/codeql-database.yml"
build_mode=$(yq eval '.buildMode' "$metadata_path")
if [[ "$build_mode" != "autobuild" ]]; then
echo "Expected build mode to be 'autobuild' but was $build_mode"
exit 1
fi
- uses: ./../action/analyze

View file

@ -0,0 +1,31 @@
name: "Build mode manual"
description: "An end-to-end integration test of a Java repository built using 'build-mode: manual'"
operatingSystems: ["ubuntu"]
versions: ["nightly-latest"]
steps:
- uses: ./../action/init
id: init
with:
build-mode: manual
db-location: "${{ runner.temp }}/customDbLocation"
languages: java
tools: ${{ steps.prepare-test.outputs.tools-url }}
- name: Validate database build mode
run: |
metadata_path="$RUNNER_TEMP/customDbLocation/java/codeql-database.yml"
build_mode=$(yq eval '.buildMode' "$metadata_path")
if [[ "$build_mode" != "manual" ]]; then
echo "Expected build mode to be 'manual' but was $build_mode"
exit 1
fi
- uses: ./../action/.github/actions/setup-swift
with:
codeql-path: ${{ steps.init.outputs.codeql-path }}
- name: Build code
shell: bash
run: ./build.sh
- uses: ./../action/analyze

View file

@ -20,5 +20,8 @@ steps:
exit 1 exit 1
fi fi
# The latest nightly supports omitting the autobuild Action when the build mode is specified.
- uses: ./../action/autobuild - uses: ./../action/autobuild
if: matrix.version != 'nightly-latest'
- uses: ./../action/analyze - uses: ./../action/analyze

View file

@ -33,13 +33,13 @@ steps:
core.setFailed('`codeqlConfigSummary` property not found in the SARIF run property bag.'); core.setFailed('`codeqlConfigSummary` property not found in the SARIF run property bag.');
} }
if (configSummary.disableDefaultQueries !== false) { if (configSummary.disableDefaultQueries !== false) {
core.setFailed('`disableDefaultQueries` property incorrect: expected false, got ' + core.setFailed('`disableDefaultQueries` property incorrect: expected false, got ' +
`${JSON.stringify(configSummary.disableDefaultQueries)}.`); `${JSON.stringify(configSummary.disableDefaultQueries)}.`);
} }
const expectedQueries = [{ type: 'builtinSuite', uses: 'security-extended' }]; const expectedQueries = [{ type: 'builtinSuite', uses: 'security-extended' }];
// Use JSON.stringify to deep-equal the arrays. // Use JSON.stringify to deep-equal the arrays.
if (JSON.stringify(configSummary.queries) !== JSON.stringify(expectedQueries)) { if (JSON.stringify(configSummary.queries) !== JSON.stringify(expectedQueries)) {
core.setFailed(`\`queries\` property incorrect: expected ${JSON.stringify(expectedQueries)}, got ` + core.setFailed(`\`queries\` property incorrect: expected ${JSON.stringify(expectedQueries)}, got ` +
`${JSON.stringify(configSummary.queries)}.`); `${JSON.stringify(configSummary.queries)}.`);
} }
core.info('Finished config export tests.'); core.info('Finished config export tests.');

View file

@ -66,7 +66,7 @@ steps:
core.setFailed( core.setFailed(
'Expected exactly one status page reporting descriptor for this diagnostic in the ' + 'Expected exactly one status page reporting descriptor for this diagnostic in the ' +
`'runs[].invocations[].toolExecutionNotifications[]' SARIF property, but found ` + `'runs[].invocations[].toolExecutionNotifications[]' SARIF property, but found ` +
`${statusPageNotifications.length}. All notification reporting descriptors: ` + `${statusPageNotifications.length}. All notification reporting descriptors: ` +
`${JSON.stringify(toolExecutionNotifications)}.` `${JSON.stringify(toolExecutionNotifications)}.`
); );
} }

View file

@ -61,8 +61,8 @@ steps:
fi fi
- name: Check language autodetect for Swift - name: Check language autodetect for Swift
if: >- if: >-
env.CODEQL_ENABLE_EXPERIMENTAL_FEATURES_SWIFT == 'true' || env.CODEQL_ENABLE_EXPERIMENTAL_FEATURES_SWIFT == 'true' ||
(runner.os != 'Windows' && matrix.version == 'nightly-latest') (runner.os != 'Windows' && matrix.version == 'nightly-latest')
shell: bash shell: bash
run: | run: |

View file

@ -3,6 +3,8 @@ description: '[Experimental] Attempt to infer a build environment suitable for a
author: 'GitHub' author: 'GitHub'
inputs: inputs:
token: token:
description: "GitHub token to use for authenticating with this instance of GitHub. The token needs the `security-events: write` permission."
required: false
default: ${{ github.token }} default: ${{ github.token }}
matrix: matrix:
default: ${{ toJson(matrix) }} default: ${{ toJson(matrix) }}

View file

@ -11,7 +11,7 @@ import {
doesDirectoryExist, doesDirectoryExist,
getCodeQLDatabasePath, getCodeQLDatabasePath,
getRequiredEnvParam, getRequiredEnvParam,
UserError, ConfigurationError,
} from "./util"; } from "./util";
// eslint-disable-next-line import/no-commonjs // eslint-disable-next-line import/no-commonjs
@ -26,7 +26,7 @@ const pkg = require("../package.json") as JSONSchemaForNPMPackageJsonFiles;
export const getRequiredInput = function (name: string): string { export const getRequiredInput = function (name: string): string {
const value = core.getInput(name); const value = core.getInput(name);
if (!value) { if (!value) {
throw new UserError(`Input required and not supplied: ${name}`); throw new ConfigurationError(`Input required and not supplied: ${name}`);
} }
return value; return value;
}; };
@ -187,7 +187,7 @@ export async function getRef(): Promise<string> {
const hasShaInput = !!shaInput; const hasShaInput = !!shaInput;
// If one of 'ref' or 'sha' are provided, both are required // If one of 'ref' or 'sha' are provided, both are required
if ((hasRefInput || hasShaInput) && !(hasRefInput && hasShaInput)) { if ((hasRefInput || hasShaInput) && !(hasRefInput && hasShaInput)) {
throw new UserError( throw new ConfigurationError(
"Both 'ref' and 'sha' are required if one of them is provided.", "Both 'ref' and 'sha' are required if one of them is provided.",
); );
} }

View file

@ -3,7 +3,6 @@ import path from "path";
import { performance } from "perf_hooks"; import { performance } from "perf_hooks";
import * as core from "@actions/core"; import * as core from "@actions/core";
import { safeWhich } from "@chrisgavin/safe-which";
import * as actionsUtil from "./actions-util"; import * as actionsUtil from "./actions-util";
import { import {
@ -13,13 +12,13 @@ import {
runCleanup, runCleanup,
runFinalize, runFinalize,
runQueries, runQueries,
warnIfGoInstalledAfterInit,
} from "./analyze"; } from "./analyze";
import { getApiDetails, getGitHubVersion } from "./api-client"; import { getApiDetails, getGitHubVersion } from "./api-client";
import { runAutobuild } from "./autobuild"; import { runAutobuild } from "./autobuild";
import { getCodeQL } from "./codeql"; import { getCodeQL } from "./codeql";
import { Config, getConfig } from "./config-utils"; import { Config, getConfig } from "./config-utils";
import { uploadDatabases } from "./database-upload"; import { uploadDatabases } from "./database-upload";
import { addDiagnostic, makeDiagnostic } from "./diagnostics";
import { EnvVar } from "./environment"; import { EnvVar } from "./environment";
import { Features } from "./feature-flags"; import { Features } from "./feature-flags";
import { Language } from "./languages"; import { Language } from "./languages";
@ -140,6 +139,12 @@ async function runAutobuildIfLegacyGoWorkflow(config: Config, logger: Logger) {
if (!config.languages.includes(Language.go)) { if (!config.languages.includes(Language.go)) {
return; return;
} }
if (config.buildMode) {
logger.debug(
"Skipping legacy Go autobuild since a build mode has been specified.",
);
return;
}
if (process.env[EnvVar.DID_AUTOBUILD_GOLANG] === "true") { if (process.env[EnvVar.DID_AUTOBUILD_GOLANG] === "true") {
logger.debug("Won't run Go autobuild since it has already been run."); logger.debug("Won't run Go autobuild since it has already been run.");
return; return;
@ -202,7 +207,7 @@ async function run() {
} }
if (hasBadExpectErrorInput()) { if (hasBadExpectErrorInput()) {
throw new util.UserError( throw new util.ConfigurationError(
"`expect-error` input parameter is for internal use only. It should only be set by codeql-action or a fork.", "`expect-error` input parameter is for internal use only. It should only be set by codeql-action or a fork.",
); );
} }
@ -234,46 +239,7 @@ async function run() {
logger, logger,
); );
// Check that `which go` still points at the same path it did when the `init` Action ran to ensure that no steps await warnIfGoInstalledAfterInit(config, logger);
// in-between performed any setup. We encourage users to perform all setup tasks before initializing CodeQL so that
// the setup tasks do not interfere with our analysis.
// Furthermore, if we installed a wrapper script in the `init` Action, we need to ensure that there isn't a step
// in the workflow after the `init` step which installs a different version of Go and takes precedence in the PATH,
// thus potentially circumventing our workaround that allows tracing to work.
const goInitPath = process.env[EnvVar.GO_BINARY_LOCATION];
if (
process.env[EnvVar.DID_AUTOBUILD_GOLANG] !== "true" &&
goInitPath !== undefined
) {
const goBinaryPath = await safeWhich("go");
if (goInitPath !== goBinaryPath) {
core.warning(
`Expected \`which go\` to return ${goInitPath}, but got ${goBinaryPath}: please ensure that the correct version of Go is installed before the \`codeql-action/init\` Action is used.`,
);
addDiagnostic(
config,
Language.go,
makeDiagnostic(
"go/workflow/go-installed-after-codeql-init",
"Go was installed after the `codeql-action/init` Action was run",
{
markdownMessage:
"To avoid interfering with the CodeQL analysis, perform all installation steps before calling the `github/codeql-action/init` Action.",
visibility: {
statusPage: true,
telemetry: true,
cliSummaryTable: true,
},
severity: "warning",
},
),
);
}
}
await runAutobuildIfLegacyGoWorkflow(config, logger); await runAutobuildIfLegacyGoWorkflow(config, logger);
dbCreationTimings = await runFinalize( dbCreationTimings = await runFinalize(
@ -319,7 +285,7 @@ async function run() {
actionsUtil.getRequiredInput("checkout_path"), actionsUtil.getRequiredInput("checkout_path"),
actionsUtil.getOptionalInput("category"), actionsUtil.getOptionalInput("category"),
logger, logger,
{ considerInvalidRequestUserError: false }, { considerInvalidRequestConfigError: false },
); );
core.setOutput("sarif-id", uploadResult.sarifID); core.setOutput("sarif-id", uploadResult.sarifID);
} else { } else {
@ -337,7 +303,7 @@ async function run() {
// We don't upload results in test mode, so don't wait for processing // We don't upload results in test mode, so don't wait for processing
if (util.isInTestMode()) { if (util.isInTestMode()) {
core.debug("In test mode. Waiting for processing is disabled."); logger.debug("In test mode. Waiting for processing is disabled.");
} else if ( } else if (
uploadResult !== undefined && uploadResult !== undefined &&
actionsUtil.getRequiredInput("wait-for-processing") === "true" actionsUtil.getRequiredInput("wait-for-processing") === "true"

View file

@ -3,6 +3,7 @@ import * as path from "path";
import { performance } from "perf_hooks"; import { performance } from "perf_hooks";
import * as toolrunner from "@actions/exec/lib/toolrunner"; import * as toolrunner from "@actions/exec/lib/toolrunner";
import { safeWhich } from "@chrisgavin/safe-which";
import del from "del"; import del from "del";
import * as yaml from "js-yaml"; import * as yaml from "js-yaml";
@ -12,6 +13,9 @@ import {
getCodeQL, getCodeQL,
} from "./codeql"; } from "./codeql";
import * as configUtils from "./config-utils"; import * as configUtils from "./config-utils";
import { BuildMode } from "./config-utils";
import { addDiagnostic, makeDiagnostic } from "./diagnostics";
import { EnvVar } from "./environment";
import { import {
FeatureEnablement, FeatureEnablement,
Feature, Feature,
@ -20,6 +24,7 @@ import {
import { isScannedLanguage, Language } from "./languages"; import { isScannedLanguage, Language } from "./languages";
import { Logger } from "./logging"; import { Logger } from "./logging";
import { DatabaseCreationTimings, EventReport } from "./status-report"; import { DatabaseCreationTimings, EventReport } from "./status-report";
import { ToolsFeature } from "./tools-features";
import { endTracingForCluster } from "./tracer-config"; import { endTracingForCluster } from "./tracer-config";
import { validateSarifFileSchema } from "./upload-lib"; import { validateSarifFileSchema } from "./upload-lib";
import * as util from "./util"; import * as util from "./util";
@ -163,29 +168,50 @@ async function setupPythonExtractor(
process.env["LGTM_PYTHON_SETUP_VERSION"] = output; process.env["LGTM_PYTHON_SETUP_VERSION"] = output;
} }
export async function createdDBForScannedLanguages( export async function runExtraction(
codeql: CodeQL, codeql: CodeQL,
config: configUtils.Config, config: configUtils.Config,
logger: Logger, logger: Logger,
features: FeatureEnablement, features: FeatureEnablement,
) { ) {
for (const language of config.languages) { for (const language of config.languages) {
if ( if (dbIsFinalized(config, language, logger)) {
isScannedLanguage(language) && logger.debug(
!dbIsFinalized(config, language, logger) `Database for ${language} has already been finalized, skipping extraction.`,
) { );
logger.startGroup(`Extracting ${language}`); continue;
}
if (shouldExtractLanguage(config, language)) {
logger.startGroup(`Extracting ${language}`);
if (language === Language.python) { if (language === Language.python) {
await setupPythonExtractor(logger, features, codeql); await setupPythonExtractor(logger, features, codeql);
} }
if (
await codeql.extractScannedLanguage(config, language); config.buildMode &&
(await codeql.supportsFeature(ToolsFeature.TraceCommandUseBuildMode))
) {
await codeql.extractUsingBuildMode(config, language);
} else {
await codeql.extractScannedLanguage(config, language);
}
logger.endGroup(); logger.endGroup();
} }
} }
} }
function shouldExtractLanguage(
config: configUtils.Config,
language: Language,
): boolean {
return (
config.buildMode === BuildMode.None ||
(config.buildMode === BuildMode.Autobuild &&
process.env[EnvVar.AUTOBUILD_DID_COMPLETE_SUCCESSFULLY] !== "true") ||
(!config.buildMode && isScannedLanguage(language))
);
}
export function dbIsFinalized( export function dbIsFinalized(
config: configUtils.Config, config: configUtils.Config,
language: Language, language: Language,
@ -215,7 +241,7 @@ async function finalizeDatabaseCreation(
const codeql = await getCodeQL(config.codeQLCmd); const codeql = await getCodeQL(config.codeQLCmd);
const extractionStart = performance.now(); const extractionStart = performance.now();
await createdDBForScannedLanguages(codeql, config, logger, features); await runExtraction(codeql, config, logger, features);
const extractionTime = performance.now() - extractionStart; const extractionTime = performance.now() - extractionStart;
const trapImportStart = performance.now(); const trapImportStart = performance.now();
@ -419,6 +445,51 @@ export async function runFinalize(
return timings; return timings;
} }
export async function warnIfGoInstalledAfterInit(
config: configUtils.Config,
logger: Logger,
) {
// Check that `which go` still points at the same path it did when the `init` Action ran to ensure that no steps
// in-between performed any setup. We encourage users to perform all setup tasks before initializing CodeQL so that
// the setup tasks do not interfere with our analysis.
// Furthermore, if we installed a wrapper script in the `init` Action, we need to ensure that there isn't a step
// in the workflow after the `init` step which installs a different version of Go and takes precedence in the PATH,
// thus potentially circumventing our workaround that allows tracing to work.
const goInitPath = process.env[EnvVar.GO_BINARY_LOCATION];
if (
process.env[EnvVar.DID_AUTOBUILD_GOLANG] !== "true" &&
goInitPath !== undefined
) {
const goBinaryPath = await safeWhich("go");
if (goInitPath !== goBinaryPath) {
logger.warning(
`Expected \`which go\` to return ${goInitPath}, but got ${goBinaryPath}: please ensure that the correct version of Go is installed before the \`codeql-action/init\` Action is used.`,
);
addDiagnostic(
config,
Language.go,
makeDiagnostic(
"go/workflow/go-installed-after-codeql-init",
"Go was installed after the `codeql-action/init` Action was run",
{
markdownMessage:
"To avoid interfering with the CodeQL analysis, perform all installation steps before calling the `github/codeql-action/init` Action.",
visibility: {
statusPage: true,
telemetry: true,
cliSummaryTable: true,
},
severity: "warning",
},
),
);
}
}
}
export async function runCleanup( export async function runCleanup(
config: configUtils.Config, config: configUtils.Config,
cleanupLevel: string, cleanupLevel: string,

View file

@ -7,7 +7,9 @@ import {
} from "./actions-util"; } from "./actions-util";
import { getGitHubVersion } from "./api-client"; import { getGitHubVersion } from "./api-client";
import { determineAutobuildLanguages, runAutobuild } from "./autobuild"; import { determineAutobuildLanguages, runAutobuild } from "./autobuild";
import { getCodeQL } from "./codeql";
import * as configUtils from "./config-utils"; import * as configUtils from "./config-utils";
import { EnvVar } from "./environment";
import { Language } from "./languages"; import { Language } from "./languages";
import { Logger, getActionsLogger } from "./logging"; import { Logger, getActionsLogger } from "./logging";
import { import {
@ -87,7 +89,9 @@ async function run() {
); );
} }
languages = await determineAutobuildLanguages(config, logger); const codeql = await getCodeQL(config.codeQLCmd);
languages = await determineAutobuildLanguages(codeql, config, logger);
if (languages !== undefined) { if (languages !== undefined) {
const workingDirectory = getOptionalInput("working-directory"); const workingDirectory = getOptionalInput("working-directory");
if (workingDirectory) { if (workingDirectory) {
@ -116,6 +120,8 @@ async function run() {
return; return;
} }
core.exportVariable(EnvVar.AUTOBUILD_DID_COMPLETE_SUCCESSFULLY, "true");
await sendCompletedStatusReport(logger, startedAt, languages ?? []); await sendCompletedStatusReport(logger, startedAt, languages ?? []);
} }

View file

@ -4,17 +4,29 @@ import { getTemporaryDirectory, getWorkflowEventName } from "./actions-util";
import { getGitHubVersion } from "./api-client"; import { getGitHubVersion } from "./api-client";
import { CodeQL, getCodeQL } from "./codeql"; import { CodeQL, getCodeQL } from "./codeql";
import * as configUtils from "./config-utils"; import * as configUtils from "./config-utils";
import { BuildMode } from "./config-utils";
import { EnvVar } from "./environment"; import { EnvVar } from "./environment";
import { Feature, featureConfig, Features } from "./feature-flags"; import { Feature, featureConfig, Features } from "./feature-flags";
import { isTracedLanguage, Language } from "./languages"; import { isTracedLanguage, Language } from "./languages";
import { Logger } from "./logging"; import { Logger } from "./logging";
import { parseRepositoryNwo } from "./repository"; import { parseRepositoryNwo } from "./repository";
import { ToolsFeature } from "./tools-features";
import { getRequiredEnvParam } from "./util"; import { getRequiredEnvParam } from "./util";
export async function determineAutobuildLanguages( export async function determineAutobuildLanguages(
codeql: CodeQL,
config: configUtils.Config, config: configUtils.Config,
logger: Logger, logger: Logger,
): Promise<Language[] | undefined> { ): Promise<Language[] | undefined> {
if (
(config.buildMode === BuildMode.None &&
(await codeql.supportsFeature(ToolsFeature.TraceCommandUseBuildMode))) ||
config.buildMode === BuildMode.Manual
) {
logger.info(`Using ${config.buildMode} build mode, nothing to autobuild.`);
return undefined;
}
// Attempt to find a language to autobuild // Attempt to find a language to autobuild
// We want pick the dominant language in the repo from the ones we're able to build // We want pick the dominant language in the repo from the ones we're able to build
// The languages are sorted in order specified by user or by lines of code if we got // The languages are sorted in order specified by user or by lines of code if we got

209
src/cli-errors.ts Normal file
View file

@ -0,0 +1,209 @@
import { ConfigurationError } from "./util";
/**
* A class of Error that we can classify as an error stemming from a CLI
* invocation, with associated exit code, stderr,etc.
*/
export class CommandInvocationError extends Error {
constructor(
cmd: string,
args: string[],
public exitCode: number,
public stderr: string,
public stdout: string,
) {
const prettyCommand = [cmd, ...args]
.map((x) => (x.includes(" ") ? `'${x}'` : x))
.join(" ");
const fatalErrors = extractFatalErrors(stderr);
const lastLine = stderr.trim().split("\n").pop()?.trim();
let error = fatalErrors
? ` and error was: ${fatalErrors.trim()}`
: lastLine
? ` and last log line was: ${lastLine}`
: "";
if (error[error.length - 1] !== ".") {
error += ".";
}
super(
`Encountered a fatal error while running "${prettyCommand}". ` +
`Exit code was ${exitCode}${error} See the logs for more details.`,
);
}
}
/**
* Provide a better error message from the stderr of a CLI invocation that failed with a fatal
* error.
*
* - If the CLI invocation failed with a fatal error, this returns that fatal error, followed by
* any fatal errors that occurred in plumbing commands.
* - If the CLI invocation did not fail with a fatal error, this returns `undefined`.
*
* ### Example
*
* ```
* Running TRAP import for CodeQL database at /home/runner/work/_temp/codeql_databases/javascript...
* A fatal error occurred: Evaluator heap must be at least 384.00 MiB
* A fatal error occurred: Dataset import for
* /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2
* ```
*
* becomes
*
* ```
* Encountered a fatal error while running "codeql-for-testing database finalize --finalize-dataset
* --threads=2 --ram=2048 db". Exit code was 32 and error was: A fatal error occurred: Dataset
* import for /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2.
* Context: A fatal error occurred: Evaluator heap must be at least 384.00 MiB.
* ```
*
* Where possible, this tries to summarize the error into a single line, as this displays better in
* the Actions UI.
*/
function extractFatalErrors(error: string): string | undefined {
const fatalErrorRegex = /.*fatal error occurred:/gi;
let fatalErrors: string[] = [];
let lastFatalErrorIndex: number | undefined;
let match: RegExpMatchArray | null;
while ((match = fatalErrorRegex.exec(error)) !== null) {
if (lastFatalErrorIndex !== undefined) {
fatalErrors.push(error.slice(lastFatalErrorIndex, match.index).trim());
}
lastFatalErrorIndex = match.index;
}
if (lastFatalErrorIndex !== undefined) {
const lastError = error.slice(lastFatalErrorIndex).trim();
if (fatalErrors.length === 0) {
// No other errors
return lastError;
}
const isOneLiner = !fatalErrors.some((e) => e.includes("\n"));
if (isOneLiner) {
fatalErrors = fatalErrors.map(ensureEndsInPeriod);
}
return [
ensureEndsInPeriod(lastError),
"Context:",
...fatalErrors.reverse(),
].join(isOneLiner ? " " : "\n");
}
return undefined;
}
function ensureEndsInPeriod(text: string): string {
return text[text.length - 1] === "." ? text : `${text}.`;
}
/** Error messages from the CLI that we consider configuration errors and handle specially. */
export enum CliConfigErrorCategory {
IncompatibleWithActionVersion = "IncompatibleWithActionVersion",
InitCalledTwice = "InitCalledTwice",
InvalidSourceRoot = "InvalidSourceRoot",
NoJavaScriptTypeScriptCodeFound = "NoJavaScriptTypeScriptCodeFound",
}
type CliErrorConfiguration = {
cliErrorMessageSnippets: string[];
exitCode?: number;
// Error message to prepend for this type of CLI error.
// If undefined, use original CLI error message.
additionalErrorMessageToPrepend?: string;
};
/**
* All of our caught CLI error messages that we handle specially: ie. if we
* would like to categorize an error as a configuration error or not.
*/
export const cliErrorsConfig: Record<
CliConfigErrorCategory,
CliErrorConfiguration
> = {
// Version of CodeQL CLI is incompatible with this version of the CodeQL Action
[CliConfigErrorCategory.IncompatibleWithActionVersion]: {
cliErrorMessageSnippets: ["is not compatible with this CodeQL CLI"],
},
[CliConfigErrorCategory.InitCalledTwice]: {
cliErrorMessageSnippets: [
"Refusing to create databases",
"exists and is not an empty directory",
],
additionalErrorMessageToPrepend: `Is the "init" action called twice in the same job?`,
},
// Expected source location for database creation does not exist
[CliConfigErrorCategory.InvalidSourceRoot]: {
cliErrorMessageSnippets: ["Invalid source root"],
},
/**
* Earlier versions of the JavaScript extractor (pre-CodeQL 2.12.0) extract externs even if no
* source code was found. This means that we don't get the no code found error from
* `codeql database finalize`. To ensure users get a good error message, we detect this manually
* here, and upon detection override the error message.
*
* This can be removed once support for CodeQL 2.11.6 is removed.
*/
[CliConfigErrorCategory.NoJavaScriptTypeScriptCodeFound]: {
exitCode: 32,
cliErrorMessageSnippets: ["No JavaScript or TypeScript code found."],
additionalErrorMessageToPrepend:
"No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build.",
},
};
// Check if the given CLI error or exit code, if applicable, apply to any known
// CLI errors in the configuration record. If either the CLI error message matches all of
// the error messages in the config record, or the exit codes match, return the error category;
// if not, return undefined.
export function getCliConfigCategoryIfExists(
cliError: CommandInvocationError,
): CliConfigErrorCategory | undefined {
for (const [category, configuration] of Object.entries(cliErrorsConfig)) {
if (
cliError.exitCode !== undefined &&
configuration.exitCode !== undefined &&
cliError.exitCode === configuration.exitCode
) {
return category as CliConfigErrorCategory;
}
let allMessageSnippetsFound: boolean = true;
for (const e of configuration.cliErrorMessageSnippets) {
if (!cliError.message.includes(e) && !cliError.stderr.includes(e)) {
allMessageSnippetsFound = false;
}
}
if (allMessageSnippetsFound === true) {
return category as CliConfigErrorCategory;
}
}
return undefined;
}
/**
* Changes an error received from the CLI to a ConfigurationError with optionally an extra
* error message prepended, if it exists in a known set of configuration errors. Otherwise,
* simply returns the original error.
*/
export function wrapCliConfigurationError(cliError: Error): Error {
if (!(cliError instanceof CommandInvocationError)) {
return cliError;
}
const cliConfigErrorCategory = getCliConfigCategoryIfExists(cliError);
if (cliConfigErrorCategory === undefined) {
return cliError;
}
const errorMessageWrapperIfExists =
cliErrorsConfig[cliConfigErrorCategory].additionalErrorMessageToPrepend;
return errorMessageWrapperIfExists
? new ConfigurationError(
`${errorMessageWrapperIfExists} ${cliError.message}`,
)
: new ConfigurationError(cliError.message);
}

View file

@ -875,9 +875,11 @@ test("database finalize recognises JavaScript no code found error on CodeQL 2.11
await t.throwsAsync( await t.throwsAsync(
async () => await codeqlObject.finalizeDatabase("", "", ""), async () => await codeqlObject.finalizeDatabase("", "", ""),
{ {
message: instanceOf: util.ConfigurationError,
message: new RegExp(
"No code found during the build. Please see: " + "No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build", "https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build.+",
),
}, },
); );
}); });
@ -892,9 +894,11 @@ test("database finalize overrides no code found error on CodeQL 2.11.6", async (
await t.throwsAsync( await t.throwsAsync(
async () => await codeqlObject.finalizeDatabase("", "", ""), async () => await codeqlObject.finalizeDatabase("", "", ""),
{ {
message: instanceOf: util.ConfigurationError,
message: new RegExp(
"No code found during the build. Please see: " + "No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build", "https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build.+",
),
}, },
); );
}); });

View file

@ -12,6 +12,10 @@ import {
isAnalyzingDefaultBranch, isAnalyzingDefaultBranch,
} from "./actions-util"; } from "./actions-util";
import * as api from "./api-client"; import * as api from "./api-client";
import {
CommandInvocationError,
wrapCliConfigurationError,
} from "./cli-errors";
import type { Config } from "./config-utils"; import type { Config } from "./config-utils";
import { EnvVar } from "./environment"; import { EnvVar } from "./environment";
import { import {
@ -48,36 +52,6 @@ interface ExtraOptions {
}; };
} }
export class CommandInvocationError extends Error {
constructor(
cmd: string,
args: string[],
public exitCode: number,
public stderr: string,
public stdout: string,
) {
const prettyCommand = [cmd, ...args]
.map((x) => (x.includes(" ") ? `'${x}'` : x))
.join(" ");
const fatalErrors = extractFatalErrors(stderr);
const lastLine = stderr.trim().split("\n").pop()?.trim();
let error = fatalErrors
? ` and error was: ${fatalErrors.trim()}`
: lastLine
? ` and last log line was: ${lastLine}`
: "";
if (error[error.length - 1] !== ".") {
error += ".";
}
super(
`Encountered a fatal error while running "${prettyCommand}". ` +
`Exit code was ${exitCode}${error} See the logs for more details.`,
);
}
}
export interface CodeQL { export interface CodeQL {
/** /**
* Get the path of the CodeQL executable. * Get the path of the CodeQL executable.
@ -114,6 +88,11 @@ export interface CodeQL {
* and running the language extractor. * and running the language extractor.
*/ */
extractScannedLanguage(config: Config, language: Language): Promise<void>; extractScannedLanguage(config: Config, language: Language): Promise<void>;
/**
* Extract code with 'codeql database trace-command --use-build-mode'. This can only be used when
* the database specifies a build mode. This requires the `traceCommandUseBuildMode` tool feature.
*/
extractUsingBuildMode(config: Config, language: Language): Promise<void>;
/** /**
* Finalize a database using 'codeql database finalize'. * Finalize a database using 'codeql database finalize'.
*/ */
@ -404,7 +383,9 @@ export async function setupCodeQL(
if (process.platform === "win32") { if (process.platform === "win32") {
codeqlCmd += ".exe"; codeqlCmd += ".exe";
} else if (process.platform !== "linux" && process.platform !== "darwin") { } else if (process.platform !== "linux" && process.platform !== "darwin") {
throw new util.UserError(`Unsupported platform: ${process.platform}`); throw new util.ConfigurationError(
`Unsupported platform: ${process.platform}`,
);
} }
cachedCodeQL = await getCodeQLForCmd(codeqlCmd, checkVersion); cachedCodeQL = await getCodeQLForCmd(codeqlCmd, checkVersion);
@ -474,6 +455,10 @@ export function setCodeQL(partialCodeql: Partial<CodeQL>): CodeQL {
partialCodeql, partialCodeql,
"extractScannedLanguage", "extractScannedLanguage",
), ),
extractUsingBuildMode: resolveFunction(
partialCodeql,
"extractUsingBuildMode",
),
finalizeDatabase: resolveFunction(partialCodeql, "finalizeDatabase"), finalizeDatabase: resolveFunction(partialCodeql, "finalizeDatabase"),
resolveLanguages: resolveFunction(partialCodeql, "resolveLanguages"), resolveLanguages: resolveFunction(partialCodeql, "resolveLanguages"),
betterResolveLanguages: resolveFunction( betterResolveLanguages: resolveFunction(
@ -630,20 +615,27 @@ export async function getCodeQLForCmd(
extraArgs.push("--no-sublanguage-file-coverage"); extraArgs.push("--no-sublanguage-file-coverage");
} }
await runTool( try {
cmd, await runTool(
[ cmd,
"database", [
"init", "database",
"--db-cluster", "init",
config.dbLocation, "--db-cluster",
`--source-root=${sourceRoot}`, config.dbLocation,
...(await getLanguageAliasingArguments(this)), `--source-root=${sourceRoot}`,
...extraArgs, ...(await getLanguageAliasingArguments(this)),
...getExtraOptionsFromEnv(["database", "init"]), ...extraArgs,
], ...getExtraOptionsFromEnv(["database", "init"]),
{ stdin: externalRepositoryToken }, ],
); { stdin: externalRepositoryToken },
);
} catch (e) {
if (e instanceof Error) {
throw wrapCliConfigurationError(e);
}
throw e;
}
}, },
async runAutobuild(language: Language) { async runAutobuild(language: Language) {
const autobuildCmd = path.join( const autobuildCmd = path.join(
@ -690,6 +682,16 @@ export async function getCodeQLForCmd(
util.getCodeQLDatabasePath(config, language), util.getCodeQLDatabasePath(config, language),
]); ]);
}, },
async extractUsingBuildMode(config: Config, language: Language) {
await runTool(cmd, [
"database",
"trace-command",
"--use-build-mode",
...(await getTrapCachingExtractorConfigArgsForLang(config, language)),
...getExtraOptionsFromEnv(["database", "trace-command"]),
util.getCodeQLDatabasePath(config, language),
]);
},
async finalizeDatabase( async finalizeDatabase(
databasePath: string, databasePath: string,
threadsFlag: string, threadsFlag: string,
@ -708,17 +710,13 @@ export async function getCodeQLForCmd(
await runTool(cmd, args); await runTool(cmd, args);
} catch (e) { } catch (e) {
if ( if (
e instanceof CommandInvocationError && e instanceof Error &&
!(await util.codeQlVersionAbove( !(await util.codeQlVersionAbove(
this, this,
CODEQL_VERSION_BETTER_NO_CODE_ERROR_MESSAGE, CODEQL_VERSION_BETTER_NO_CODE_ERROR_MESSAGE,
)) && ))
isNoCodeFoundError(e)
) { ) {
throw new util.UserError( throw wrapCliConfigurationError(e);
"No code found during the build. Please see: " +
"https://gh.io/troubleshooting-code-scanning/no-source-code-seen-during-build",
);
} }
throw e; throw e;
} }
@ -1109,7 +1107,7 @@ export async function getCodeQLForCmd(
checkVersion && checkVersion &&
!(await util.codeQlVersionAbove(codeql, CODEQL_MINIMUM_VERSION)) !(await util.codeQlVersionAbove(codeql, CODEQL_MINIMUM_VERSION))
) { ) {
throw new util.UserError( throw new util.ConfigurationError(
`Expected a CodeQL CLI with version at least ${CODEQL_MINIMUM_VERSION} but got version ${ `Expected a CodeQL CLI with version at least ${CODEQL_MINIMUM_VERSION} but got version ${
(await codeql.getVersion()).version (await codeql.getVersion()).version
}`, }`,
@ -1246,69 +1244,6 @@ async function runTool(
return output; return output;
} }
/**
* Provide a better error message from the stderr of a CLI invocation that failed with a fatal
* error.
*
* - If the CLI invocation failed with a fatal error, this returns that fatal error, followed by
* any fatal errors that occurred in plumbing commands.
* - If the CLI invocation did not fail with a fatal error, this returns `undefined`.
*
* ### Example
*
* ```
* Running TRAP import for CodeQL database at /home/runner/work/_temp/codeql_databases/javascript...
* A fatal error occurred: Evaluator heap must be at least 384.00 MiB
* A fatal error occurred: Dataset import for
* /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2
* ```
*
* becomes
*
* ```
* Encountered a fatal error while running "codeql-for-testing database finalize --finalize-dataset
* --threads=2 --ram=2048 db". Exit code was 32 and error was: A fatal error occurred: Dataset
* import for /home/runner/work/_temp/codeql_databases/javascript/db-javascript failed with code 2.
* Context: A fatal error occurred: Evaluator heap must be at least 384.00 MiB.
* ```
*
* Where possible, this tries to summarize the error into a single line, as this displays better in
* the Actions UI.
*/
function extractFatalErrors(error: string): string | undefined {
const fatalErrorRegex = /.*fatal error occurred:/gi;
let fatalErrors: string[] = [];
let lastFatalErrorIndex: number | undefined;
let match: RegExpMatchArray | null;
while ((match = fatalErrorRegex.exec(error)) !== null) {
if (lastFatalErrorIndex !== undefined) {
fatalErrors.push(error.slice(lastFatalErrorIndex, match.index).trim());
}
lastFatalErrorIndex = match.index;
}
if (lastFatalErrorIndex !== undefined) {
const lastError = error.slice(lastFatalErrorIndex).trim();
if (fatalErrors.length === 0) {
// No other errors
return lastError;
}
const isOneLiner = !fatalErrors.some((e) => e.includes("\n"));
if (isOneLiner) {
fatalErrors = fatalErrors.map(ensureEndsInPeriod);
}
return [
ensureEndsInPeriod(lastError),
"Context:",
...fatalErrors.reverse(),
].join(isOneLiner ? " " : "\n");
}
return undefined;
}
function ensureEndsInPeriod(text: string): string {
return text[text.length - 1] === "." ? text : `${text}.`;
}
/** /**
* Generates a code scanning configuration that is to be used for a scan. * Generates a code scanning configuration that is to be used for a scan.
* *
@ -1439,20 +1374,6 @@ export function getGeneratedCodeScanningConfigPath(config: Config): string {
return path.resolve(config.tempDir, "user-config.yaml"); return path.resolve(config.tempDir, "user-config.yaml");
} }
function isNoCodeFoundError(e: CommandInvocationError): boolean {
/**
* Earlier versions of the JavaScript extractor (pre-CodeQL 2.12.0) extract externs even if no
* source code was found. This means that we don't get the no code found error from
* `codeql database finalize`. To ensure users get a good error message, we detect this manually
* here, and upon detection override the error message.
*
* This can be removed once support for CodeQL 2.11.6 is removed.
*/
const javascriptNoCodeFoundWarning =
"No JavaScript or TypeScript code found.";
return e.exitCode === 32 || e.stderr.includes(javascriptNoCodeFoundWarning);
}
async function isDiagnosticsExportInvalidSarifFixed( async function isDiagnosticsExportInvalidSarifFixed(
codeql: CodeQL, codeql: CodeQL,
): Promise<boolean> { ): Promise<boolean> {

View file

@ -14,6 +14,7 @@ import {
setCodeQL, setCodeQL,
} from "./codeql"; } from "./codeql";
import * as configUtils from "./config-utils"; import * as configUtils from "./config-utils";
import { BuildMode } from "./config-utils";
import { Language } from "./languages"; import { Language } from "./languages";
import { getRunnerLogger } from "./logging"; import { getRunnerLogger } from "./logging";
import { parseRepositoryNwo } from "./repository"; import { parseRepositoryNwo } from "./repository";
@ -25,7 +26,7 @@ import {
GitHubVariant, GitHubVariant,
GitHubVersion, GitHubVersion,
prettyPrintPack, prettyPrintPack,
UserError, ConfigurationError,
withTmpDir, withTmpDir,
} from "./util"; } from "./util";
@ -218,7 +219,7 @@ test("load input outside of workspace", async (t) => {
} catch (err) { } catch (err) {
t.deepEqual( t.deepEqual(
err, err,
new UserError( new ConfigurationError(
configUtils.getConfigFileOutsideWorkspaceErrorMessage( configUtils.getConfigFileOutsideWorkspaceErrorMessage(
path.join(tempDir, "../input"), path.join(tempDir, "../input"),
), ),
@ -246,7 +247,7 @@ test("load non-local input with invalid repo syntax", async (t) => {
} catch (err) { } catch (err) {
t.deepEqual( t.deepEqual(
err, err,
new UserError( new ConfigurationError(
configUtils.getConfigFileRepoFormatInvalidMessage( configUtils.getConfigFileRepoFormatInvalidMessage(
"octo-org/codeql-config@main", "octo-org/codeql-config@main",
), ),
@ -276,7 +277,7 @@ test("load non-existent input", async (t) => {
} catch (err) { } catch (err) {
t.deepEqual( t.deepEqual(
err, err,
new UserError( new ConfigurationError(
configUtils.getConfigFileDoesNotExistErrorMessage( configUtils.getConfigFileDoesNotExistErrorMessage(
path.join(tempDir, "input"), path.join(tempDir, "input"),
), ),
@ -323,7 +324,7 @@ test("load non-empty input", async (t) => {
// And the config we expect it to parse to // And the config we expect it to parse to
const expectedConfig: configUtils.Config = { const expectedConfig: configUtils.Config = {
languages: [Language.javascript], languages: [Language.javascript],
buildMode: "none", buildMode: BuildMode.None,
originalUserInput: { originalUserInput: {
name: "my config", name: "my config",
"disable-default-queries": true, "disable-default-queries": true,
@ -516,7 +517,7 @@ test("Remote config handles the case where a directory is provided", async (t) =
} catch (err) { } catch (err) {
t.deepEqual( t.deepEqual(
err, err,
new UserError( new ConfigurationError(
configUtils.getConfigFileDirectoryGivenMessage(repoReference), configUtils.getConfigFileDirectoryGivenMessage(repoReference),
), ),
); );
@ -545,7 +546,7 @@ test("Invalid format of remote config handled correctly", async (t) => {
} catch (err) { } catch (err) {
t.deepEqual( t.deepEqual(
err, err,
new UserError( new ConfigurationError(
configUtils.getConfigFileFormatInvalidMessage(repoReference), configUtils.getConfigFileFormatInvalidMessage(repoReference),
), ),
); );
@ -575,7 +576,10 @@ test("No detected languages", async (t) => {
); );
throw new Error("initConfig did not throw error"); throw new Error("initConfig did not throw error");
} catch (err) { } catch (err) {
t.deepEqual(err, new UserError(configUtils.getNoLanguagesError())); t.deepEqual(
err,
new ConfigurationError(configUtils.getNoLanguagesError()),
);
} }
}); });
}); });
@ -597,7 +601,7 @@ test("Unknown languages", async (t) => {
} catch (err) { } catch (err) {
t.deepEqual( t.deepEqual(
err, err,
new UserError( new ConfigurationError(
configUtils.getUnknownLanguagesError(["rubbish", "english"]), configUtils.getUnknownLanguagesError(["rubbish", "english"]),
), ),
); );

View file

@ -15,7 +15,7 @@ import {
codeQlVersionAbove, codeQlVersionAbove,
GitHubVersion, GitHubVersion,
prettyPrintPack, prettyPrintPack,
UserError, ConfigurationError,
} from "./util"; } from "./util";
// Property names from the user-supplied config file. // Property names from the user-supplied config file.
@ -72,6 +72,12 @@ interface IncludeQueryFilter {
include: Record<string, string[] | string>; include: Record<string, string[] | string>;
} }
export enum BuildMode {
None = "none",
Autobuild = "autobuild",
Manual = "manual",
}
/** /**
* Format of the parsed config file. * Format of the parsed config file.
*/ */
@ -83,7 +89,7 @@ export interface Config {
/** /**
* Build mode, if set. Currently only a single build mode is supported per job. * Build mode, if set. Currently only a single build mode is supported per job.
*/ */
buildMode: string | undefined; buildMode: BuildMode | undefined;
/** /**
* A unaltered copy of the original user input. * A unaltered copy of the original user input.
* Mainly intended to be used for status reporting. * Mainly intended to be used for status reporting.
@ -326,7 +332,7 @@ export async function getLanguages(
// If the languages parameter was not given and no languages were // If the languages parameter was not given and no languages were
// detected then fail here as this is a workflow configuration error. // detected then fail here as this is a workflow configuration error.
if (languages.length === 0) { if (languages.length === 0) {
throw new UserError(getNoLanguagesError()); throw new ConfigurationError(getNoLanguagesError());
} }
// Make sure they are supported // Make sure they are supported
@ -344,7 +350,7 @@ export async function getLanguages(
// Any unknown languages here would have come directly from the input // Any unknown languages here would have come directly from the input
// since we filter unknown languages coming from the GitHub API. // since we filter unknown languages coming from the GitHub API.
if (unknownLanguages.length > 0) { if (unknownLanguages.length > 0) {
throw new UserError(getUnknownLanguagesError(unknownLanguages)); throw new ConfigurationError(getUnknownLanguagesError(unknownLanguages));
} }
return parsedLanguages; return parsedLanguages;
@ -466,7 +472,7 @@ export async function getDefaultConfig({
return { return {
languages, languages,
buildMode: buildModeInput, buildMode: validateBuildModeInput(buildModeInput),
originalUserInput: {}, originalUserInput: {},
tempDir, tempDir,
codeQLCmd: codeql.getPath(), codeQLCmd: codeql.getPath(),
@ -554,7 +560,7 @@ async function loadConfig({
return { return {
languages, languages,
buildMode: buildModeInput, buildMode: validateBuildModeInput(buildModeInput),
originalUserInput: parsedYAML, originalUserInput: parsedYAML,
tempDir, tempDir,
codeQLCmd: codeql.getPath(), codeQLCmd: codeql.getPath(),
@ -625,7 +631,7 @@ function parseQueriesFromInput(
? rawQueriesInput.trim().slice(1).trim() ? rawQueriesInput.trim().slice(1).trim()
: rawQueriesInput?.trim() ?? ""; : rawQueriesInput?.trim() ?? "";
if (queriesInputCombines && trimmedInput.length === 0) { if (queriesInputCombines && trimmedInput.length === 0) {
throw new UserError( throw new ConfigurationError(
getConfigFilePropertyError( getConfigFilePropertyError(
undefined, undefined,
"queries", "queries",
@ -658,11 +664,11 @@ export function parsePacksFromInput(
} }
if (languages.length > 1) { if (languages.length > 1) {
throw new UserError( throw new ConfigurationError(
"Cannot specify a 'packs' input in a multi-language analysis. Use a codeql-config.yml file instead and specify packs by language.", "Cannot specify a 'packs' input in a multi-language analysis. Use a codeql-config.yml file instead and specify packs by language.",
); );
} else if (languages.length === 0) { } else if (languages.length === 0) {
throw new UserError( throw new ConfigurationError(
"No languages specified. Cannot process the packs input.", "No languages specified. Cannot process the packs input.",
); );
} }
@ -671,7 +677,7 @@ export function parsePacksFromInput(
if (packsInputCombines) { if (packsInputCombines) {
rawPacksInput = rawPacksInput.trim().substring(1).trim(); rawPacksInput = rawPacksInput.trim().substring(1).trim();
if (!rawPacksInput) { if (!rawPacksInput) {
throw new UserError( throw new ConfigurationError(
getConfigFilePropertyError( getConfigFilePropertyError(
undefined, undefined,
"packs", "packs",
@ -709,7 +715,7 @@ export function parsePacksFromInput(
*/ */
export function parsePacksSpecification(packStr: string): Pack { export function parsePacksSpecification(packStr: string): Pack {
if (typeof packStr !== "string") { if (typeof packStr !== "string") {
throw new UserError(getPacksStrInvalid(packStr)); throw new ConfigurationError(getPacksStrInvalid(packStr));
} }
packStr = packStr.trim(); packStr = packStr.trim();
@ -737,14 +743,14 @@ export function parsePacksSpecification(packStr: string): Pack {
: undefined; : undefined;
if (!PACK_IDENTIFIER_PATTERN.test(packName)) { if (!PACK_IDENTIFIER_PATTERN.test(packName)) {
throw new UserError(getPacksStrInvalid(packStr)); throw new ConfigurationError(getPacksStrInvalid(packStr));
} }
if (version) { if (version) {
try { try {
new semver.Range(version); new semver.Range(version);
} catch (e) { } catch (e) {
// The range string is invalid. OK to ignore the caught error // The range string is invalid. OK to ignore the caught error
throw new UserError(getPacksStrInvalid(packStr)); throw new ConfigurationError(getPacksStrInvalid(packStr));
} }
} }
@ -758,12 +764,12 @@ export function parsePacksSpecification(packStr: string): Pack {
path.normalize(packPath).split(path.sep).join("/") !== path.normalize(packPath).split(path.sep).join("/") !==
packPath.split(path.sep).join("/")) packPath.split(path.sep).join("/"))
) { ) {
throw new UserError(getPacksStrInvalid(packStr)); throw new ConfigurationError(getPacksStrInvalid(packStr));
} }
if (!packPath && pathStart) { if (!packPath && pathStart) {
// 0 length path // 0 length path
throw new UserError(getPacksStrInvalid(packStr)); throw new ConfigurationError(getPacksStrInvalid(packStr));
} }
return { return {
@ -846,7 +852,9 @@ function parseRegistries(
? (yaml.load(registriesInput) as RegistryConfigWithCredentials[]) ? (yaml.load(registriesInput) as RegistryConfigWithCredentials[])
: undefined; : undefined;
} catch (e) { } catch (e) {
throw new UserError("Invalid registries input. Must be a YAML string."); throw new ConfigurationError(
"Invalid registries input. Must be a YAML string.",
);
} }
} }
@ -862,12 +870,16 @@ function isLocal(configPath: string): boolean {
function getLocalConfig(configFile: string, workspacePath: string): UserConfig { function getLocalConfig(configFile: string, workspacePath: string): UserConfig {
// Error if the config file is now outside of the workspace // Error if the config file is now outside of the workspace
if (!(configFile + path.sep).startsWith(workspacePath + path.sep)) { if (!(configFile + path.sep).startsWith(workspacePath + path.sep)) {
throw new UserError(getConfigFileOutsideWorkspaceErrorMessage(configFile)); throw new ConfigurationError(
getConfigFileOutsideWorkspaceErrorMessage(configFile),
);
} }
// Error if the file does not exist // Error if the file does not exist
if (!fs.existsSync(configFile)) { if (!fs.existsSync(configFile)) {
throw new UserError(getConfigFileDoesNotExistErrorMessage(configFile)); throw new ConfigurationError(
getConfigFileDoesNotExistErrorMessage(configFile),
);
} }
return yaml.load(fs.readFileSync(configFile, "utf8")) as UserConfig; return yaml.load(fs.readFileSync(configFile, "utf8")) as UserConfig;
@ -884,7 +896,9 @@ async function getRemoteConfig(
const pieces = format.exec(configFile); const pieces = format.exec(configFile);
// 5 = 4 groups + the whole expression // 5 = 4 groups + the whole expression
if (pieces === null || pieces.groups === undefined || pieces.length < 5) { if (pieces === null || pieces.groups === undefined || pieces.length < 5) {
throw new UserError(getConfigFileRepoFormatInvalidMessage(configFile)); throw new ConfigurationError(
getConfigFileRepoFormatInvalidMessage(configFile),
);
} }
const response = await api const response = await api
@ -900,9 +914,11 @@ async function getRemoteConfig(
if ("content" in response.data && response.data.content !== undefined) { if ("content" in response.data && response.data.content !== undefined) {
fileContents = response.data.content; fileContents = response.data.content;
} else if (Array.isArray(response.data)) { } else if (Array.isArray(response.data)) {
throw new UserError(getConfigFileDirectoryGivenMessage(configFile)); throw new ConfigurationError(
getConfigFileDirectoryGivenMessage(configFile),
);
} else { } else {
throw new UserError(getConfigFileFormatInvalidMessage(configFile)); throw new ConfigurationError(getConfigFileFormatInvalidMessage(configFile));
} }
return yaml.load( return yaml.load(
@ -1002,7 +1018,7 @@ function createRegistriesBlock(registries: RegistryConfigWithCredentials[]): {
!Array.isArray(registries) || !Array.isArray(registries) ||
registries.some((r) => !r.url || !r.packages) registries.some((r) => !r.url || !r.packages)
) { ) {
throw new UserError( throw new ConfigurationError(
"Invalid 'registries' input. Must be an array of objects with 'url' and 'packages' properties.", "Invalid 'registries' input. Must be an array of objects with 'url' and 'packages' properties.",
); );
} }
@ -1056,3 +1072,20 @@ export async function wrapEnvironment(
} }
} }
} }
function validateBuildModeInput(
buildModeInput: string | undefined,
): BuildMode | undefined {
if (buildModeInput === undefined) {
return undefined;
}
if (!Object.values(BuildMode).includes(buildModeInput as BuildMode)) {
throw new ConfigurationError(
`Invalid build mode: '${buildModeInput}'. Supported build modes are: ${Object.values(
BuildMode,
).join(", ")}.`,
);
}
return buildModeInput as BuildMode;
}

View file

@ -8,6 +8,9 @@ export enum EnvVar {
/** Whether the `analyze` Action completes successfully. */ /** Whether the `analyze` Action completes successfully. */
ANALYZE_DID_COMPLETE_SUCCESSFULLY = "CODEQL_ACTION_ANALYZE_DID_COMPLETE_SUCCESSFULLY", ANALYZE_DID_COMPLETE_SUCCESSFULLY = "CODEQL_ACTION_ANALYZE_DID_COMPLETE_SUCCESSFULLY",
/** Whether the `autobuild` Action completes successfully. */
AUTOBUILD_DID_COMPLETE_SUCCESSFULLY = "CODEQL_ACTION_AUTOBUILD_DID_COMPLETE_SUCCESSFULLY",
/** Whether the CodeQL Action has invoked the Go autobuilder. */ /** Whether the CodeQL Action has invoked the Go autobuilder. */
DID_AUTOBUILD_GOLANG = "CODEQL_ACTION_DID_AUTOBUILD_GOLANG", DID_AUTOBUILD_GOLANG = "CODEQL_ACTION_DID_AUTOBUILD_GOLANG",

View file

@ -107,7 +107,7 @@ async function maybeUploadFailedSarif(
checkoutPath, checkoutPath,
category, category,
logger, logger,
{ considerInvalidRequestUserError: false }, { considerInvalidRequestConfigError: false },
); );
await uploadLib.waitForProcessing( await uploadLib.waitForProcessing(
repositoryNwo, repositoryNwo,
@ -134,7 +134,7 @@ export async function tryUploadSarifIfRunFailed(
// consider this a configuration error. // consider this a configuration error.
core.exportVariable( core.exportVariable(
EnvVar.JOB_STATUS, EnvVar.JOB_STATUS,
process.env[EnvVar.JOB_STATUS] ?? JobStatus.ConfigurationError, process.env[EnvVar.JOB_STATUS] ?? JobStatus.ConfigErrorStatus,
); );
try { try {
return await maybeUploadFailedSarif( return await maybeUploadFailedSarif(
@ -152,7 +152,7 @@ export async function tryUploadSarifIfRunFailed(
} else { } else {
core.exportVariable( core.exportVariable(
EnvVar.JOB_STATUS, EnvVar.JOB_STATUS,
process.env[EnvVar.JOB_STATUS] ?? JobStatus.Success, process.env[EnvVar.JOB_STATUS] ?? JobStatus.SuccessStatus,
); );
return { return {
upload_failed_run_skipped_because: upload_failed_run_skipped_because:
@ -314,7 +314,7 @@ export function getFinalJobStatus(): JobStatus {
!jobStatusFromEnvironment || !jobStatusFromEnvironment ||
!Object.values(JobStatus).includes(jobStatusFromEnvironment as JobStatus) !Object.values(JobStatus).includes(jobStatusFromEnvironment as JobStatus)
) { ) {
return JobStatus.Unknown; return JobStatus.UnknownStatus;
} }
return jobStatusFromEnvironment as JobStatus; return jobStatusFromEnvironment as JobStatus;
} }

View file

@ -52,7 +52,7 @@ import {
getThreadsFlagValue, getThreadsFlagValue,
initializeEnvironment, initializeEnvironment,
isHostedRunner, isHostedRunner,
UserError, ConfigurationError,
wrapError, wrapError,
checkActionVersion, checkActionVersion,
} from "./util"; } from "./util";
@ -317,7 +317,7 @@ async function run() {
await sendStatusReport( await sendStatusReport(
await createStatusReportBase( await createStatusReportBase(
"init", "init",
error instanceof UserError ? "user-error" : "aborted", error instanceof ConfigurationError ? "user-error" : "aborted",
startedAt, startedAt,
await checkDiskUsage(), await checkDiskUsage(),
error.message, error.message,

View file

@ -64,32 +64,29 @@ export async function runInit(
logger: Logger, logger: Logger,
): Promise<TracerConfig | undefined> { ): Promise<TracerConfig | undefined> {
fs.mkdirSync(config.dbLocation, { recursive: true }); fs.mkdirSync(config.dbLocation, { recursive: true });
try {
const { registriesAuthTokens, qlconfigFile } =
await configUtils.generateRegistries(
registriesInput,
config.tempDir,
logger,
);
await configUtils.wrapEnvironment(
{
GITHUB_TOKEN: apiDetails.auth,
CODEQL_REGISTRIES_AUTH: registriesAuthTokens,
},
// Init a database cluster const { registriesAuthTokens, qlconfigFile } =
async () => await configUtils.generateRegistries(
await codeql.databaseInitCluster( registriesInput,
config, config.tempDir,
sourceRoot, logger,
processName,
qlconfigFile,
logger,
),
); );
} catch (e) { await configUtils.wrapEnvironment(
throw processError(e); {
} GITHUB_TOKEN: apiDetails.auth,
CODEQL_REGISTRIES_AUTH: registriesAuthTokens,
},
// Init a database cluster
async () =>
await codeql.databaseInitCluster(
config,
sourceRoot,
processName,
qlconfigFile,
logger,
),
);
return await getCombinedTracerConfig(codeql, config); return await getCombinedTracerConfig(codeql, config);
} }
@ -110,42 +107,6 @@ export function printPathFiltersWarning(
} }
} }
/**
* Possibly convert this error into a UserError in order to avoid
* counting this error towards our internal error budget.
*
* @param e The error to possibly convert to a UserError.
*
* @returns A UserError if the error is a known error that can be
* attributed to the user, otherwise the original error.
*/
function processError(e: any): Error {
if (!(e instanceof Error)) {
return e;
}
if (
// Init action called twice
e.message?.includes("Refusing to create databases") &&
e.message?.includes("exists and is not an empty directory.")
) {
return new util.UserError(
`Is the "init" action called twice in the same job? ${e.message}`,
);
}
if (
// Version of CodeQL CLI is incompatible with this version of the CodeQL Action
e.message?.includes("is not compatible with this CodeQL CLI") ||
// Expected source location for database creation does not exist
e.message?.includes("Invalid source root")
) {
return new util.UserError(e.message);
}
return e;
}
/** /**
* If we are running python 3.12+ on windows, we need to switch to python 3.11. * If we are running python 3.12+ on windows, we need to switch to python 3.11.
* This check happens in a powershell script. * This check happens in a powershell script.

View file

@ -1,4 +1,4 @@
import { UserError } from "./util"; import { ConfigurationError } from "./util";
// A repository name with owner, parsed into its two parts // A repository name with owner, parsed into its two parts
export interface RepositoryNwo { export interface RepositoryNwo {
@ -9,7 +9,7 @@ export interface RepositoryNwo {
export function parseRepositoryNwo(input: string): RepositoryNwo { export function parseRepositoryNwo(input: string): RepositoryNwo {
const parts = input.split("/"); const parts = input.split("/");
if (parts.length !== 2) { if (parts.length !== 2) {
throw new UserError(`"${input}" is not a valid repository name`); throw new ConfigurationError(`"${input}" is not a valid repository name`);
} }
return { return {
owner: parts[0], owner: parts[0],

View file

@ -7,7 +7,7 @@ import {
getTemporaryDirectory, getTemporaryDirectory,
} from "./actions-util"; } from "./actions-util";
import { getGitHubVersion } from "./api-client"; import { getGitHubVersion } from "./api-client";
import { CommandInvocationError } from "./codeql"; import { CommandInvocationError } from "./cli-errors";
import * as configUtils from "./config-utils"; import * as configUtils from "./config-utils";
import { getActionsLogger } from "./logging"; import { getActionsLogger } from "./logging";
import { runResolveBuildEnvironment } from "./resolve-environment"; import { runResolveBuildEnvironment } from "./resolve-environment";

View file

@ -27,7 +27,7 @@ export async function runResolveBuildEnvironment(
) { ) {
const parsedLanguage = parseLanguage(languageInput)?.toString(); const parsedLanguage = parseLanguage(languageInput)?.toString();
if (parsedLanguage === undefined) { if (parsedLanguage === undefined) {
throw new util.UserError( throw new util.ConfigurationError(
`Did not recognize the language '${languageInput}'.`, `Did not recognize the language '${languageInput}'.`,
); );
} }

View file

@ -608,7 +608,7 @@ export async function downloadCodeQL(
export function getCodeQLURLVersion(url: string): string { export function getCodeQLURLVersion(url: string): string {
const match = url.match(/\/codeql-bundle-(.*)\//); const match = url.match(/\/codeql-bundle-(.*)\//);
if (match === null || match.length < 2) { if (match === null || match.length < 2) {
throw new util.UserError( throw new util.ConfigurationError(
`Malformed tools url: ${url}. Version could not be inferred`, `Malformed tools url: ${url}. Version could not be inferred`,
); );
} }

View file

@ -14,7 +14,7 @@ import {
import { getAnalysisKey, getApiClient } from "./api-client"; import { getAnalysisKey, getApiClient } from "./api-client";
import { EnvVar } from "./environment"; import { EnvVar } from "./environment";
import { import {
UserError, ConfigurationError,
isHTTPError, isHTTPError,
getRequiredEnvParam, getRequiredEnvParam,
getCachedCodeQlVersion, getCachedCodeQlVersion,
@ -40,10 +40,10 @@ export type ActionStatus =
/** Overall status of the entire job. String values match the Hydro schema. */ /** Overall status of the entire job. String values match the Hydro schema. */
export enum JobStatus { export enum JobStatus {
Unknown = "JOB_STATUS_UNKNOWN", UnknownStatus = "JOB_STATUS_UNKNOWN",
Success = "JOB_STATUS_SUCCESS", SuccessStatus = "JOB_STATUS_SUCCESS",
Failure = "JOB_STATUS_FAILURE", FailureStatus = "JOB_STATUS_FAILURE",
ConfigurationError = "JOB_STATUS_CONFIGURATION_ERROR", ConfigErrorStatus = "JOB_STATUS_CONFIGURATION_ERROR",
} }
export interface StatusReportBase { export interface StatusReportBase {
@ -135,7 +135,7 @@ export function getActionsStatus(
otherFailureCause?: string, otherFailureCause?: string,
): ActionStatus { ): ActionStatus {
if (error || otherFailureCause) { if (error || otherFailureCause) {
return error instanceof UserError ? "user-error" : "failure"; return error instanceof ConfigurationError ? "user-error" : "failure";
} else { } else {
return "success"; return "success";
} }
@ -150,12 +150,12 @@ function setJobStatusIfUnsuccessful(actionStatus: ActionStatus) {
if (actionStatus === "user-error") { if (actionStatus === "user-error") {
core.exportVariable( core.exportVariable(
EnvVar.JOB_STATUS, EnvVar.JOB_STATUS,
process.env[EnvVar.JOB_STATUS] ?? JobStatus.ConfigurationError, process.env[EnvVar.JOB_STATUS] ?? JobStatus.ConfigErrorStatus,
); );
} else if (actionStatus === "failure" || actionStatus === "aborted") { } else if (actionStatus === "failure" || actionStatus === "aborted") {
core.exportVariable( core.exportVariable(
EnvVar.JOB_STATUS, EnvVar.JOB_STATUS,
process.env[EnvVar.JOB_STATUS] ?? JobStatus.Failure, process.env[EnvVar.JOB_STATUS] ?? JobStatus.FailureStatus,
); );
} }
} }

View file

@ -4,6 +4,7 @@ export enum ToolsFeature {
BuildModeOption = "buildModeOption", BuildModeOption = "buildModeOption",
IndirectTracingSupportsStaticBinaries = "indirectTracingSupportsStaticBinaries", IndirectTracingSupportsStaticBinaries = "indirectTracingSupportsStaticBinaries",
SetsCodeqlRunnerEnvVar = "setsCodeqlRunnerEnvVar", SetsCodeqlRunnerEnvVar = "setsCodeqlRunnerEnvVar",
TraceCommandUseBuildMode = "traceCommandUseBuildMode",
} }
/** /**

View file

@ -14,7 +14,7 @@ import * as fingerprints from "./fingerprints";
import { Logger } from "./logging"; import { Logger } from "./logging";
import { parseRepositoryNwo, RepositoryNwo } from "./repository"; import { parseRepositoryNwo, RepositoryNwo } from "./repository";
import * as util from "./util"; import * as util from "./util";
import { SarifFile, UserError, wrapError } from "./util"; import { SarifFile, ConfigurationError, wrapError } from "./util";
// Takes a list of paths to sarif files and combines them together, // Takes a list of paths to sarif files and combines them together,
// returning the contents of the combined sarif file. // returning the contents of the combined sarif file.
@ -158,7 +158,7 @@ export function findSarifFilesInDir(sarifPath: string): string[] {
* Uploads a single SARIF file or a directory of SARIF files depending on what `sarifPath` refers * Uploads a single SARIF file or a directory of SARIF files depending on what `sarifPath` refers
* to. * to.
* *
* @param considerInvalidRequestUserError Whether an invalid request, for example one with a * @param considerInvalidRequestConfigError Whether an invalid request, for example one with a
* `sarifPath` that does not exist, should be considered a * `sarifPath` that does not exist, should be considered a
* user error. * user error.
*/ */
@ -168,8 +168,8 @@ export async function uploadFromActions(
category: string | undefined, category: string | undefined,
logger: Logger, logger: Logger,
{ {
considerInvalidRequestUserError, considerInvalidRequestConfigError: considerInvalidRequestConfigError,
}: { considerInvalidRequestUserError: boolean }, }: { considerInvalidRequestConfigError: boolean },
): Promise<UploadResult> { ): Promise<UploadResult> {
try { try {
return await uploadFiles( return await uploadFiles(
@ -187,8 +187,8 @@ export async function uploadFromActions(
logger, logger,
); );
} catch (e) { } catch (e) {
if (e instanceof InvalidRequestError && considerInvalidRequestUserError) { if (e instanceof InvalidRequestError && considerInvalidRequestConfigError) {
throw new UserError(e.message); throw new ConfigurationError(e.message);
} }
throw e; throw e;
} }
@ -489,8 +489,8 @@ export async function waitForProcessing(
break; break;
} else if (status === "failed") { } else if (status === "failed") {
const message = `Code Scanning could not process the submitted SARIF file:\n${response.data.errors}`; const message = `Code Scanning could not process the submitted SARIF file:\n${response.data.errors}`;
throw shouldConsiderAsUserError(response.data.errors as string[]) throw shouldConsiderConfigurationError(response.data.errors as string[])
? new UserError(message) ? new ConfigurationError(message)
: new InvalidRequestError(message); : new InvalidRequestError(message);
} else { } else {
util.assertNever(status); util.assertNever(status);
@ -508,7 +508,7 @@ export async function waitForProcessing(
/** /**
* Returns whether the provided processing errors should be considered a user error. * Returns whether the provided processing errors should be considered a user error.
*/ */
function shouldConsiderAsUserError(processingErrors: string[]): boolean { function shouldConsiderConfigurationError(processingErrors: string[]): boolean {
return ( return (
processingErrors.length === 1 && processingErrors.length === 1 &&
processingErrors[0] === processingErrors[0] ===

View file

@ -69,7 +69,7 @@ async function run() {
actionsUtil.getRequiredInput("checkout_path"), actionsUtil.getRequiredInput("checkout_path"),
actionsUtil.getOptionalInput("category"), actionsUtil.getOptionalInput("category"),
logger, logger,
{ considerInvalidRequestUserError: true }, { considerInvalidRequestConfigError: true },
); );
core.setOutput("sarif-id", uploadResult.sarifID); core.setOutput("sarif-id", uploadResult.sarifID);

View file

@ -120,7 +120,7 @@ export function getExtraOptionsEnvParam(): object {
return JSON.parse(raw); return JSON.parse(raw);
} catch (unwrappedError) { } catch (unwrappedError) {
const error = wrapError(unwrappedError); const error = wrapError(unwrappedError);
throw new UserError( throw new ConfigurationError(
`${varName} environment variable is set, but does not contain valid JSON: ${error.message}`, `${varName} environment variable is set, but does not contain valid JSON: ${error.message}`,
); );
} }
@ -204,7 +204,9 @@ export function getMemoryFlagValueForPlatform(
if (userInput) { if (userInput) {
memoryToUseMegaBytes = Number(userInput); memoryToUseMegaBytes = Number(userInput);
if (Number.isNaN(memoryToUseMegaBytes) || memoryToUseMegaBytes <= 0) { if (Number.isNaN(memoryToUseMegaBytes) || memoryToUseMegaBytes <= 0) {
throw new UserError(`Invalid RAM setting "${userInput}", specified.`); throw new ConfigurationError(
`Invalid RAM setting "${userInput}", specified.`,
);
} }
} else { } else {
const totalMemoryMegaBytes = totalMemoryBytes / (1024 * 1024); const totalMemoryMegaBytes = totalMemoryBytes / (1024 * 1024);
@ -373,7 +375,9 @@ export function getThreadsFlagValue(
if (userInput) { if (userInput) {
numThreads = Number(userInput); numThreads = Number(userInput);
if (Number.isNaN(numThreads)) { if (Number.isNaN(numThreads)) {
throw new UserError(`Invalid threads setting "${userInput}", specified.`); throw new ConfigurationError(
`Invalid threads setting "${userInput}", specified.`,
);
} }
if (numThreads > maxThreads) { if (numThreads > maxThreads) {
logger.info( logger.info(
@ -500,14 +504,14 @@ export function parseGitHubUrl(inputUrl: string): string {
inputUrl = `https://${inputUrl}`; inputUrl = `https://${inputUrl}`;
} }
if (!inputUrl.startsWith("http://") && !inputUrl.startsWith("https://")) { if (!inputUrl.startsWith("http://") && !inputUrl.startsWith("https://")) {
throw new UserError(`"${originalUrl}" is not a http or https URL`); throw new ConfigurationError(`"${originalUrl}" is not a http or https URL`);
} }
let url: URL; let url: URL;
try { try {
url = new URL(inputUrl); url = new URL(inputUrl);
} catch (e) { } catch (e) {
throw new UserError(`"${originalUrl}" is not a valid URL`); throw new ConfigurationError(`"${originalUrl}" is not a valid URL`);
} }
// If we detect this is trying to be to github.com // If we detect this is trying to be to github.com
@ -652,7 +656,7 @@ export class HTTPError extends Error {
* An Error class that indicates an error that occurred due to * An Error class that indicates an error that occurred due to
* a misconfiguration of the action or the CodeQL CLI. * a misconfiguration of the action or the CodeQL CLI.
*/ */
export class UserError extends Error { export class ConfigurationError extends Error {
constructor(message: string) { constructor(message: string) {
super(message); super(message);
} }

Binary file not shown.

View file

@ -0,0 +1,2 @@
#Thu Feb 08 15:11:31 GMT 2024
gradle.version=8.1.1

Binary file not shown.

View file

@ -20,6 +20,8 @@ inputs:
description: "The sha of the HEAD of the ref where results will be uploaded. If not provided, the Action will use the GITHUB_SHA environment variable. If provided, the ref input must be provided as well. This input is ignored for pull requests from forks." description: "The sha of the HEAD of the ref where results will be uploaded. If not provided, the Action will use the GITHUB_SHA environment variable. If provided, the ref input must be provided as well. This input is ignored for pull requests from forks."
required: false required: false
token: token:
description: "GitHub token to use for authenticating with this instance of GitHub. The token needs the `security-events: write` permission."
required: false
default: ${{ github.token }} default: ${{ github.token }}
matrix: matrix:
default: ${{ toJson(matrix) }} default: ${{ toJson(matrix) }}