diff --git a/lib/start-proxy-action.js b/lib/start-proxy-action.js index 404675104..def58d827 100644 --- a/lib/start-proxy-action.js +++ b/lib/start-proxy-action.js @@ -118928,7 +118928,7 @@ function getActionsLogger() { } // src/start-proxy.ts -var core7 = __toESM(require_core()); +var core10 = __toESM(require_core()); // src/artifact-scanner.ts var exec = __toESM(require_exec()); @@ -118992,164 +118992,9 @@ var KnownLanguage = /* @__PURE__ */ ((KnownLanguage2) => { return KnownLanguage2; })(KnownLanguage || {}); -// src/start-proxy.ts -var UPDATEJOB_PROXY = "update-job-proxy"; -var UPDATEJOB_PROXY_VERSION = "v2.0.20250624110901"; -var UPDATEJOB_PROXY_URL_PREFIX = "https://github.com/github/codeql-action/releases/download/codeql-bundle-v2.22.0/"; -var LANGUAGE_ALIASES = { - c: "cpp" /* cpp */, - "c++": "cpp" /* cpp */, - "c#": "csharp" /* csharp */, - kotlin: "java" /* java */, - typescript: "javascript" /* javascript */, - "javascript-typescript": "javascript" /* javascript */, - "java-kotlin": "java" /* java */ -}; -function parseLanguage(language) { - language = language.trim().toLowerCase(); - if (language in KnownLanguage) { - return language; - } - if (language in LANGUAGE_ALIASES) { - return LANGUAGE_ALIASES[language]; - } - return void 0; -} -function isPAT(value) { - return isAuthToken(value, [ - GITHUB_PAT_CLASSIC_PATTERN, - GITHUB_PAT_FINE_GRAINED_PATTERN - ]); -} -var LANGUAGE_TO_REGISTRY_TYPE = { - java: ["maven_repository"], - csharp: ["nuget_feed"], - javascript: ["npm_registry"], - python: ["python_index"], - ruby: ["rubygems_server"], - rust: ["cargo_registry"], - go: ["goproxy_server", "git_source"] -}; -function getCredentials(logger, registrySecrets, registriesCredentials, language) { - const registryTypeForLanguage = language ? LANGUAGE_TO_REGISTRY_TYPE[language] : void 0; - let credentialsStr; - if (registriesCredentials !== void 0) { - logger.info(`Using registries_credentials input.`); - credentialsStr = Buffer.from(registriesCredentials, "base64").toString(); - } else if (registrySecrets !== void 0) { - logger.info(`Using registry_secrets input.`); - credentialsStr = registrySecrets; - } else { - logger.info(`No credentials defined.`); - return []; - } - let parsed; - try { - parsed = JSON.parse(credentialsStr); - } catch { - logger.error("Failed to parse the credentials data."); - throw new ConfigurationError("Invalid credentials format."); - } - if (!Array.isArray(parsed)) { - throw new ConfigurationError( - "Expected credentials data to be an array of configurations, but it is not." - ); - } - const out = []; - for (const e of parsed) { - if (e === null || typeof e !== "object") { - throw new ConfigurationError("Invalid credentials - must be an object"); - } - if (isDefined2(e.password)) { - core7.setSecret(e.password); - } - if (isDefined2(e.token)) { - core7.setSecret(e.token); - } - if (!isDefined2(e.url) && !isDefined2(e.host)) { - throw new ConfigurationError( - "Invalid credentials - must specify host or url" - ); - } - if (registryTypeForLanguage && !registryTypeForLanguage.some((t) => t === e.type)) { - continue; - } - const isPrintable2 = (str2) => { - return str2 ? /^[\x20-\x7E]*$/.test(str2) : true; - }; - if (!isPrintable2(e.type) || !isPrintable2(e.host) || !isPrintable2(e.url) || !isPrintable2(e.username) || !isPrintable2(e.password) || !isPrintable2(e.token)) { - throw new ConfigurationError( - "Invalid credentials - fields must contain only printable characters" - ); - } - if (!isDefined2(e.username) && (isDefined2(e.password) && isPAT(e.password) || isDefined2(e.token) && isPAT(e.token))) { - logger.warning( - `A ${e.type} private registry is configured for ${e.host || e.url} using a GitHub Personal Access Token (PAT), but no username was provided. This may not work correctly. When configuring a private registry using a PAT, select "Username and password" and enter the username of the user who generated the PAT.` - ); - } - out.push({ - type: e.type, - host: e.host, - url: e.url, - username: e.username, - password: e.password, - token: e.token - }); - } - return out; -} -function getProxyPackage() { - const platform = process.platform === "win32" ? "win64" : process.platform === "darwin" ? "osx64" : "linux64"; - return `${UPDATEJOB_PROXY}-${platform}.tar.gz`; -} -function getFallbackUrl(proxyPackage) { - return `${UPDATEJOB_PROXY_URL_PREFIX}${proxyPackage}`; -} -async function getLinkedRelease() { - return getApiClient().rest.repos.getReleaseByTag({ - owner: "github", - repo: "codeql-action", - tag: bundleVersion - }); -} -async function getDownloadUrl(logger) { - const proxyPackage = getProxyPackage(); - try { - const cliRelease = await getLinkedRelease(); - for (const asset of cliRelease.data.assets) { - if (asset.name === proxyPackage) { - logger.info( - `Found '${proxyPackage}' in release '${bundleVersion}' at '${asset.url}'` - ); - return { - url: asset.url, - // The `update-job-proxy` doesn't have a version as such. Since we now bundle it - // with CodeQL CLI bundle releases, we use the corresponding CLI version to - // differentiate between (potentially) different versions of `update-job-proxy`. - version: cliVersion - }; - } - } - } catch (ex) { - logger.warning( - `Failed to retrieve information about the linked release: ${getErrorMessage(ex)}` - ); - } - logger.info( - `Did not find '${proxyPackage}' in the linked release, falling back to hard-coded version.` - ); - return { - url: getFallbackUrl(proxyPackage), - version: UPDATEJOB_PROXY_VERSION - }; -} -function credentialToStr(c) { - return `Type: ${c.type}; Host: ${c.host}; Url: ${c.url} Username: ${c.username}; Password: ${c.password !== void 0}; Token: ${c.token !== void 0}`; -} - // src/status-report.ts var os = __toESM(require("os")); -var core10 = __toESM(require_core()); +var core9 = __toESM(require_core()); // src/analyses.ts var AnalysisKind = /* @__PURE__ */ ((AnalysisKind2) => { @@ -119160,7 +119005,7 @@ var AnalysisKind = /* @__PURE__ */ ((AnalysisKind2) => { var supportedAnalysisKinds = new Set(Object.values(AnalysisKind)); // src/caching-utils.ts -var core8 = __toESM(require_core()); +var core7 = __toESM(require_core()); // src/config/db-config.ts var jsonschema = __toESM(require_lib3()); @@ -119179,14 +119024,14 @@ var semver5 = __toESM(require_semver2()); var actionsCache = __toESM(require_cache5()); // src/git-utils.ts -var core9 = __toESM(require_core()); +var core8 = __toESM(require_core()); var toolrunner2 = __toESM(require_toolrunner()); var io3 = __toESM(require_io()); var semver3 = __toESM(require_semver2()); var runGitCommand = async function(workingDirectory, args, customErrorMessage, options) { let stdout = ""; let stderr = ""; - core9.debug(`Running git command: git ${args.join(" ")}`); + core8.debug(`Running git command: git ${args.join(" ")}`); try { await new toolrunner2.ToolRunner(await io3.which("git", true), args, { silent: true, @@ -119207,7 +119052,7 @@ var runGitCommand = async function(workingDirectory, args, customErrorMessage, o if (stderr.includes("not a git repository")) { reason = "The checkout path provided to the action does not appear to be a git repository."; } - core9.info(`git call failed. ${customErrorMessage} Error: ${reason}`); + core8.info(`git call failed. ${customErrorMessage} Error: ${reason}`); throw error3; } }; @@ -119263,7 +119108,7 @@ async function getRef() { ) !== head; if (hasChangedRef) { const newRef = ref.replace(pull_ref_regex, "refs/pull/$1/head"); - core9.debug( + core8.debug( `No longer on merge commit, rewriting ref from ${ref} to ${newRef}.` ); return newRef; @@ -119538,12 +119383,12 @@ function getActionsStatus(error3, otherFailureCause) { } function setJobStatusIfUnsuccessful(actionStatus) { if (actionStatus === "user-error") { - core10.exportVariable( + core9.exportVariable( "CODEQL_ACTION_JOB_STATUS" /* JOB_STATUS */, process.env["CODEQL_ACTION_JOB_STATUS" /* JOB_STATUS */] ?? "JOB_STATUS_CONFIGURATION_ERROR" /* ConfigErrorStatus */ ); } else if (actionStatus === "failure" || actionStatus === "aborted") { - core10.exportVariable( + core9.exportVariable( "CODEQL_ACTION_JOB_STATUS" /* JOB_STATUS */, process.env["CODEQL_ACTION_JOB_STATUS" /* JOB_STATUS */] ?? "JOB_STATUS_FAILURE" /* FailureStatus */ ); @@ -119562,14 +119407,14 @@ async function createStatusReportBase(actionName, status, actionStartedAt, confi let workflowStartedAt = process.env["CODEQL_WORKFLOW_STARTED_AT" /* WORKFLOW_STARTED_AT */]; if (workflowStartedAt === void 0) { workflowStartedAt = actionStartedAt.toISOString(); - core10.exportVariable("CODEQL_WORKFLOW_STARTED_AT" /* WORKFLOW_STARTED_AT */, workflowStartedAt); + core9.exportVariable("CODEQL_WORKFLOW_STARTED_AT" /* WORKFLOW_STARTED_AT */, workflowStartedAt); } const runnerOs = getRequiredEnvParam("RUNNER_OS"); const codeQlCliVersion = getCachedCodeQlVersion(); const actionRef = process.env["GITHUB_ACTION_REF"] || ""; const testingEnvironment = getTestingEnvironment(); if (testingEnvironment) { - core10.exportVariable("CODEQL_ACTION_TESTING_ENVIRONMENT" /* TESTING_ENVIRONMENT */, testingEnvironment); + core9.exportVariable("CODEQL_ACTION_TESTING_ENVIRONMENT" /* TESTING_ENVIRONMENT */, testingEnvironment); } const isSteadyStateDefaultSetupRun = process.env["CODE_SCANNING_IS_STEADY_STATE_DEFAULT_SETUP"] === "true"; const statusReport = { @@ -119652,9 +119497,9 @@ var INCOMPATIBLE_MSG = "CodeQL Action version is incompatible with the API endpo async function sendStatusReport(statusReport) { setJobStatusIfUnsuccessful(statusReport.status); const statusReportJSON = JSON.stringify(statusReport); - core10.debug(`Sending status report: ${statusReportJSON}`); + core9.debug(`Sending status report: ${statusReportJSON}`); if (isInTestMode()) { - core10.debug("In test mode. Status reports are not uploaded."); + core9.debug("In test mode. Status reports are not uploaded."); return; } const nwo = getRepositoryNwo(); @@ -119674,28 +119519,28 @@ async function sendStatusReport(statusReport) { switch (httpError.status) { case 403: if (getWorkflowEventName() === "push" && process.env["GITHUB_ACTOR"] === "dependabot[bot]") { - core10.warning( + core9.warning( `Workflows triggered by Dependabot on the "push" event run with read-only access. Uploading CodeQL results requires write access. To use CodeQL with Dependabot, please ensure you are using the "pull_request" event for this workflow and avoid triggering on the "push" event for Dependabot branches. See ${"https://docs.github.com/en/code-security/code-scanning/creating-an-advanced-setup-for-code-scanning/customizing-your-advanced-setup-for-code-scanning#scanning-on-push" /* SCANNING_ON_PUSH */} for more information on how to configure these events.` ); } else { - core10.warning( + core9.warning( `This run of the CodeQL Action does not have permission to access the CodeQL Action API endpoints. This could be because the Action is running on a pull request from a fork. If not, please ensure the workflow has at least the 'security-events: read' permission. Details: ${httpError.message}` ); } return; case 404: - core10.warning(httpError.message); + core9.warning(httpError.message); return; case 422: if (getRequiredEnvParam("GITHUB_SERVER_URL") !== GITHUB_DOTCOM_URL) { - core10.debug(INCOMPATIBLE_MSG); + core9.debug(INCOMPATIBLE_MSG); } else { - core10.debug(OUT_OF_DATE_MSG); + core9.debug(OUT_OF_DATE_MSG); } return; } } - core10.warning( + core9.warning( `An unexpected error occurred when sending a status report: ${getErrorMessage( e )}` @@ -119727,6 +119572,178 @@ async function sendUnhandledErrorStatusReport(actionName, actionStartedAt, error } } +// src/start-proxy.ts +async function sendSuccessStatusReport(startedAt, config, registry_types, logger) { + const statusReportBase = await createStatusReportBase( + "start-proxy" /* StartProxy */, + "success", + startedAt, + config, + await checkDiskUsage(logger), + logger + ); + if (statusReportBase !== void 0) { + const statusReport = { + ...statusReportBase, + registry_types: registry_types.join(",") + }; + await sendStatusReport(statusReport); + } +} +var UPDATEJOB_PROXY = "update-job-proxy"; +var UPDATEJOB_PROXY_VERSION = "v2.0.20250624110901"; +var UPDATEJOB_PROXY_URL_PREFIX = "https://github.com/github/codeql-action/releases/download/codeql-bundle-v2.22.0/"; +var LANGUAGE_ALIASES = { + c: "cpp" /* cpp */, + "c++": "cpp" /* cpp */, + "c#": "csharp" /* csharp */, + kotlin: "java" /* java */, + typescript: "javascript" /* javascript */, + "javascript-typescript": "javascript" /* javascript */, + "java-kotlin": "java" /* java */ +}; +function parseLanguage(language) { + language = language.trim().toLowerCase(); + if (language in KnownLanguage) { + return language; + } + if (language in LANGUAGE_ALIASES) { + return LANGUAGE_ALIASES[language]; + } + return void 0; +} +function isPAT(value) { + return isAuthToken(value, [ + GITHUB_PAT_CLASSIC_PATTERN, + GITHUB_PAT_FINE_GRAINED_PATTERN + ]); +} +var LANGUAGE_TO_REGISTRY_TYPE = { + java: ["maven_repository"], + csharp: ["nuget_feed"], + javascript: ["npm_registry"], + python: ["python_index"], + ruby: ["rubygems_server"], + rust: ["cargo_registry"], + go: ["goproxy_server", "git_source"] +}; +function getCredentials(logger, registrySecrets, registriesCredentials, language) { + const registryTypeForLanguage = language ? LANGUAGE_TO_REGISTRY_TYPE[language] : void 0; + let credentialsStr; + if (registriesCredentials !== void 0) { + logger.info(`Using registries_credentials input.`); + credentialsStr = Buffer.from(registriesCredentials, "base64").toString(); + } else if (registrySecrets !== void 0) { + logger.info(`Using registry_secrets input.`); + credentialsStr = registrySecrets; + } else { + logger.info(`No credentials defined.`); + return []; + } + let parsed; + try { + parsed = JSON.parse(credentialsStr); + } catch { + logger.error("Failed to parse the credentials data."); + throw new ConfigurationError("Invalid credentials format."); + } + if (!Array.isArray(parsed)) { + throw new ConfigurationError( + "Expected credentials data to be an array of configurations, but it is not." + ); + } + const out = []; + for (const e of parsed) { + if (e === null || typeof e !== "object") { + throw new ConfigurationError("Invalid credentials - must be an object"); + } + if (isDefined2(e.password)) { + core10.setSecret(e.password); + } + if (isDefined2(e.token)) { + core10.setSecret(e.token); + } + if (!isDefined2(e.url) && !isDefined2(e.host)) { + throw new ConfigurationError( + "Invalid credentials - must specify host or url" + ); + } + if (registryTypeForLanguage && !registryTypeForLanguage.some((t) => t === e.type)) { + continue; + } + const isPrintable2 = (str2) => { + return str2 ? /^[\x20-\x7E]*$/.test(str2) : true; + }; + if (!isPrintable2(e.type) || !isPrintable2(e.host) || !isPrintable2(e.url) || !isPrintable2(e.username) || !isPrintable2(e.password) || !isPrintable2(e.token)) { + throw new ConfigurationError( + "Invalid credentials - fields must contain only printable characters" + ); + } + if (!isDefined2(e.username) && (isDefined2(e.password) && isPAT(e.password) || isDefined2(e.token) && isPAT(e.token))) { + logger.warning( + `A ${e.type} private registry is configured for ${e.host || e.url} using a GitHub Personal Access Token (PAT), but no username was provided. This may not work correctly. When configuring a private registry using a PAT, select "Username and password" and enter the username of the user who generated the PAT.` + ); + } + out.push({ + type: e.type, + host: e.host, + url: e.url, + username: e.username, + password: e.password, + token: e.token + }); + } + return out; +} +function getProxyPackage() { + const platform = process.platform === "win32" ? "win64" : process.platform === "darwin" ? "osx64" : "linux64"; + return `${UPDATEJOB_PROXY}-${platform}.tar.gz`; +} +function getFallbackUrl(proxyPackage) { + return `${UPDATEJOB_PROXY_URL_PREFIX}${proxyPackage}`; +} +async function getLinkedRelease() { + return getApiClient().rest.repos.getReleaseByTag({ + owner: "github", + repo: "codeql-action", + tag: bundleVersion + }); +} +async function getDownloadUrl(logger) { + const proxyPackage = getProxyPackage(); + try { + const cliRelease = await getLinkedRelease(); + for (const asset of cliRelease.data.assets) { + if (asset.name === proxyPackage) { + logger.info( + `Found '${proxyPackage}' in release '${bundleVersion}' at '${asset.url}'` + ); + return { + url: asset.url, + // The `update-job-proxy` doesn't have a version as such. Since we now bundle it + // with CodeQL CLI bundle releases, we use the corresponding CLI version to + // differentiate between (potentially) different versions of `update-job-proxy`. + version: cliVersion + }; + } + } + } catch (ex) { + logger.warning( + `Failed to retrieve information about the linked release: ${getErrorMessage(ex)}` + ); + } + logger.info( + `Did not find '${proxyPackage}' in the linked release, falling back to hard-coded version.` + ); + return { + url: getFallbackUrl(proxyPackage), + version: UPDATEJOB_PROXY_VERSION + }; +} +function credentialToStr(c) { + return `Type: ${c.type}; Host: ${c.host}; Url: ${c.url} Username: ${c.username}; Password: ${c.password !== void 0}; Token: ${c.token !== void 0}`; +} + // src/start-proxy-action.ts var KEY_SIZE = 2048; var KEY_EXPIRY_YEARS = 2; @@ -119774,23 +119791,6 @@ function generateCertificateAuthority() { const key = import_node_forge.pki.privateKeyToPem(keys.privateKey); return { cert: pem, key }; } -async function sendSuccessStatusReport(startedAt, config, registry_types, logger) { - const statusReportBase = await createStatusReportBase( - "start-proxy" /* StartProxy */, - "success", - startedAt, - config, - await checkDiskUsage(logger), - logger - ); - if (statusReportBase !== void 0) { - const statusReport = { - ...statusReportBase, - registry_types: registry_types.join(",") - }; - await sendStatusReport(statusReport); - } -} async function run(startedAt) { const logger = getActionsLogger(); let language; diff --git a/src/start-proxy-action.ts b/src/start-proxy-action.ts index 8110d8581..439e730f6 100644 --- a/src/start-proxy-action.ts +++ b/src/start-proxy-action.ts @@ -7,7 +7,6 @@ import { pki } from "node-forge"; import * as actionsUtil from "./actions-util"; import { getApiDetails, getAuthorizationHeaderFor } from "./api-client"; -import { Config } from "./config-utils"; import { KnownLanguage } from "./languages"; import { getActionsLogger, Logger } from "./logging"; import { @@ -16,6 +15,7 @@ import { getCredentials, getDownloadUrl, parseLanguage, + sendSuccessStatusReport, UPDATEJOB_PROXY, } from "./start-proxy"; import { @@ -24,7 +24,6 @@ import { getActionsStatus, sendStatusReport, sendUnhandledErrorStatusReport, - StatusReportBase, } from "./status-report"; import * as util from "./util"; @@ -95,35 +94,6 @@ function generateCertificateAuthority(): CertificateAuthority { return { cert: pem, key }; } -interface StartProxyStatus extends StatusReportBase { - // A comma-separated list of registry types which are configured for CodeQL. - // This only includes registry types we support, not all that are configured. - registry_types: string; -} - -async function sendSuccessStatusReport( - startedAt: Date, - config: Partial, - registry_types: string[], - logger: Logger, -) { - const statusReportBase = await createStatusReportBase( - ActionName.StartProxy, - "success", - startedAt, - config, - await util.checkDiskUsage(logger), - logger, - ); - if (statusReportBase !== undefined) { - const statusReport: StartProxyStatus = { - ...statusReportBase, - registry_types: registry_types.join(","), - }; - await sendStatusReport(statusReport); - } -} - async function run(startedAt: Date) { // To capture errors appropriately, keep as much code within the try-catch as // possible, and only use safe functions outside. diff --git a/src/start-proxy.ts b/src/start-proxy.ts index 1079bf6cb..32b8389bd 100644 --- a/src/start-proxy.ts +++ b/src/start-proxy.ts @@ -2,11 +2,56 @@ import * as core from "@actions/core"; import { getApiClient } from "./api-client"; import * as artifactScanner from "./artifact-scanner"; +import { Config } from "./config-utils"; import * as defaults from "./defaults.json"; import { KnownLanguage } from "./languages"; import { Logger } from "./logging"; +import { + ActionName, + createStatusReportBase, + sendStatusReport, + StatusReportBase, +} from "./status-report"; +import * as util from "./util"; import { ConfigurationError, getErrorMessage, isDefined } from "./util"; +interface StartProxyStatus extends StatusReportBase { + // A comma-separated list of registry types which are configured for CodeQL. + // This only includes registry types we support, not all that are configured. + registry_types: string; +} + +/** + * Sends a status report for the `start-proxy` action indicating a successful outcome. + * + * @param startedAt When the action was started. + * @param config The configuration used. + * @param registry_types The types of registries that are configured. + * @param logger The logger to use. + */ +export async function sendSuccessStatusReport( + startedAt: Date, + config: Partial, + registry_types: string[], + logger: Logger, +) { + const statusReportBase = await createStatusReportBase( + ActionName.StartProxy, + "success", + startedAt, + config, + await util.checkDiskUsage(logger), + logger, + ); + if (statusReportBase !== undefined) { + const statusReport: StartProxyStatus = { + ...statusReportBase, + registry_types: registry_types.join(","), + }; + await sendStatusReport(statusReport); + } +} + export const UPDATEJOB_PROXY = "update-job-proxy"; export const UPDATEJOB_PROXY_VERSION = "v2.0.20250624110901"; const UPDATEJOB_PROXY_URL_PREFIX =