Merge remote-tracking branch 'upstream/main' into aeisenberg/qlconfig-in-cli

This commit is contained in:
Andrew Eisenberg
2023-02-09 09:47:43 -08:00
31 changed files with 57 additions and 479 deletions

View File

@@ -143,7 +143,6 @@ async function installIntoToolcache({
apiDetails,
tmpDir,
util.GitHubVariant.GHES,
false,
cliVersion !== undefined
? { cliVersion, tagName, variant: util.GitHubVariant.GHES }
: SAMPLE_DEFAULT_CLI_VERSION,
@@ -205,7 +204,6 @@ test("downloads and caches explicitly requested bundles that aren't in the toolc
sampleApiDetails,
tmpDir,
util.GitHubVariant.DOTCOM,
false,
SAMPLE_DEFAULT_CLI_VERSION,
getRunnerLogger(true),
false
@@ -239,7 +237,6 @@ test("downloads an explicitly requested bundle even if a different version is ca
sampleApiDetails,
tmpDir,
util.GitHubVariant.DOTCOM,
false,
SAMPLE_DEFAULT_CLI_VERSION,
getRunnerLogger(true),
false
@@ -290,7 +287,6 @@ for (const {
sampleApiDetails,
tmpDir,
util.GitHubVariant.DOTCOM,
false,
SAMPLE_DEFAULT_CLI_VERSION,
getRunnerLogger(true),
false
@@ -358,7 +354,6 @@ for (const { githubReleases, toolcacheVersion } of [
sampleApiDetails,
tmpDir,
util.GitHubVariant.DOTCOM,
false,
SAMPLE_DEFAULT_CLI_VERSION,
getRunnerLogger(true),
false
@@ -387,7 +382,6 @@ for (const variant of [util.GitHubVariant.GHAE, util.GitHubVariant.GHES]) {
sampleApiDetails,
tmpDir,
variant,
false,
{
cliVersion: defaults.cliVersion,
tagName: defaults.bundleVersion,
@@ -423,7 +417,6 @@ for (const variant of [util.GitHubVariant.GHAE, util.GitHubVariant.GHES]) {
sampleApiDetails,
tmpDir,
variant,
false,
{
cliVersion: defaults.cliVersion,
tagName: defaults.bundleVersion,
@@ -460,7 +453,6 @@ test('downloads bundle if "latest" tools specified but not cached', async (t) =>
sampleApiDetails,
tmpDir,
util.GitHubVariant.DOTCOM,
false,
SAMPLE_DEFAULT_CLI_VERSION,
getRunnerLogger(true),
false
@@ -533,7 +525,6 @@ for (const isBundleVersionInUrl of [true, false]) {
sampleGHAEApiDetails,
tmpDir,
util.GitHubVariant.GHAE,
false,
{
cliVersion: defaults.cliVersion,
tagName: defaults.bundleVersion,
@@ -573,7 +564,6 @@ test("bundle URL from another repo is cached as 0.0.0-bundleVersion", async (t)
sampleApiDetails,
tmpDir,
util.GitHubVariant.DOTCOM,
false,
SAMPLE_DEFAULT_CLI_VERSION,
getRunnerLogger(true),
false

View File

@@ -296,7 +296,6 @@ export const CODEQL_VERSION_INIT_WITH_QLCONFIG = "2.12.3";
* @param apiDetails
* @param tempDir
* @param variant
* @param bypassToolcache
* @param defaultCliVersion
* @param logger
* @param checkVersion Whether to check that CodeQL CLI meets the minimum
@@ -308,7 +307,6 @@ export async function setupCodeQL(
apiDetails: api.GitHubApiDetails,
tempDir: string,
variant: util.GitHubVariant,
bypassToolcache: boolean,
defaultCliVersion: CodeQLDefaultVersionInfo,
logger: Logger,
checkVersion: boolean
@@ -325,7 +323,6 @@ export async function setupCodeQL(
apiDetails,
tempDir,
variant,
bypassToolcache,
defaultCliVersion,
logger
);

View File

@@ -34,8 +34,6 @@ export interface FeatureEnablement {
}
export enum Feature {
BypassToolcacheEnabled = "bypass_toolcache_enabled",
BypassToolcacheKotlinSwiftEnabled = "bypass_toolcache_kotlin_swift_enabled",
CliConfigFileEnabled = "cli_config_file_enabled",
DisableKotlinAnalysisEnabled = "disable_kotlin_analysis_enabled",
MlPoweredQueriesEnabled = "ml_powered_queries_enabled",
@@ -47,18 +45,6 @@ export const featureConfig: Record<
Feature,
{ envVar: string; minimumVersion: string | undefined }
> = {
[Feature.BypassToolcacheEnabled]: {
envVar: "CODEQL_BYPASS_TOOLCACHE",
// Cannot specify a minimum version because this flag is checked before we have
// access to the CodeQL instance.
minimumVersion: undefined,
},
[Feature.BypassToolcacheKotlinSwiftEnabled]: {
envVar: "CODEQL_BYPASS_TOOLCACHE_KOTLIN_SWIFT",
// Cannot specify a minimum version because this flag is checked before we have
// access to the CodeQL instance.
minimumVersion: undefined,
},
[Feature.DisableKotlinAnalysisEnabled]: {
envVar: "CODEQL_DISABLE_KOTLIN_ANALYSIS",
minimumVersion: undefined,
@@ -138,11 +124,6 @@ export class Features implements FeatureEnablement {
);
}
// Bypassing the toolcache is disabled in test mode.
if (feature === Feature.BypassToolcacheEnabled && util.isInTestMode()) {
return false;
}
const envVar = (
process.env[featureConfig[feature].envVar] || ""
).toLocaleLowerCase();

View File

@@ -43,7 +43,6 @@ import {
GitHubVariant,
initializeEnvironment,
isHostedRunner,
shouldBypassToolcache,
} from "./util";
import { validateWorkflow } from "./workflow";
@@ -239,13 +238,6 @@ async function run() {
apiDetails,
getTemporaryDirectory(),
gitHubVersion.type,
await shouldBypassToolcache(
features,
getOptionalInput("tools"),
getOptionalInput("languages"),
repositoryNwo,
logger
),
codeQLDefaultVersionInfo,
logger
);

View File

@@ -27,7 +27,6 @@ export async function initCodeQL(
apiDetails: GitHubApiDetails,
tempDir: string,
variant: util.GitHubVariant,
bypassToolcache: boolean,
defaultCliVersion: CodeQLDefaultVersionInfo,
logger: Logger
): Promise<{
@@ -43,7 +42,6 @@ export async function initCodeQL(
apiDetails,
tempDir,
variant,
bypassToolcache,
defaultCliVersion,
logger,
true

View File

@@ -21,8 +21,6 @@ export const LANGUAGE_ALIASES: { [lang: string]: Language } = {
export type LanguageOrAlias = Language | keyof typeof LANGUAGE_ALIASES;
export const KOTLIN_SWIFT_BYPASS = ["kotlin", "swift"];
export function resolveAlias(lang: LanguageOrAlias): Language {
return LANGUAGE_ALIASES[lang] || lang;
}

View File

@@ -354,7 +354,6 @@ async function findOverridingToolsInCache(
export async function getCodeQLSource(
toolsInput: string | undefined,
bypassToolcache: boolean,
defaultCliVersion: CodeQLDefaultVersionInfo,
apiDetails: api.GitHubApiDetails,
variant: util.GitHubVariant,
@@ -368,25 +367,18 @@ export async function getCodeQLSource(
};
}
/** The reason why the tools shipped with the Action have been forced. */
const forceShippedToolsReason =
// We use the special value of 'latest' to prioritize the version in the
// defaults over any pinned cached version.
toolsInput === "latest"
? '"tools: latest" was requested'
: // If the user hasn't requested a particular CodeQL version, then bypass
// the toolcache when the appropriate feature is enabled. This
// allows us to quickly rollback a broken bundle that has made its way
// into the toolcache.
toolsInput === undefined && bypassToolcache
? "a specific version of the CodeQL tools was not requested and the bypass toolcache feature is enabled"
: undefined;
/** Whether the tools shipped with the Action, i.e. those in `defaults.json`, have been forced. */
const forceShippedTools = forceShippedToolsReason !== undefined;
/**
* Whether the tools shipped with the Action, i.e. those in `defaults.json`, have been forced.
*
* We use the special value of 'latest' to prioritize the version in `defaults.json` over the
* version specified by the feature flags on Dotcom and over any pinned cached version on
* Enterprise Server.
*/
const forceShippedTools = toolsInput === "latest";
if (forceShippedTools) {
logger.info(
"Overriding the version of the CodeQL tools by the version shipped with the Action since " +
`${forceShippedToolsReason}.`
`"tools: latest" was requested.`
);
}
@@ -714,7 +706,6 @@ export function getCodeQLURLVersion(url: string): string {
* @param apiDetails
* @param tempDir
* @param variant
* @param bypassToolcache
* @param defaultCliVersion
* @param logger
* @param checkVersion Whether to check that CodeQL CLI meets the minimum
@@ -726,7 +717,6 @@ export async function setupCodeQLBundle(
apiDetails: api.GitHubApiDetails,
tempDir: string,
variant: util.GitHubVariant,
bypassToolcache: boolean,
defaultCliVersion: CodeQLDefaultVersionInfo,
logger: Logger
): Promise<{
@@ -737,7 +727,6 @@ export async function setupCodeQLBundle(
}> {
const source = await getCodeQLSource(
toolsInput,
bypassToolcache,
defaultCliVersion,
apiDetails,
variant,

View File

@@ -8,14 +8,8 @@ import * as sinon from "sinon";
import * as api from "./api-client";
import { Config } from "./config-utils";
import { Feature } from "./feature-flags";
import { getRunnerLogger } from "./logging";
import { parseRepositoryNwo } from "./repository";
import {
createFeatures,
mockLanguagesInRepo,
setupTests,
} from "./testing-utils";
import { setupTests } from "./testing-utils";
import * as util from "./util";
setupTests(test);
@@ -398,123 +392,3 @@ test("withTimeout doesn't call callback if promise resolves", async (t) => {
t.deepEqual(shortTaskTimedOut, false);
t.deepEqual(result, 99);
});
const mockRepositoryNwo = parseRepositoryNwo("owner/repo");
// eslint-disable-next-line github/array-foreach
[
{
name: "disabled",
features: [],
hasCustomCodeQL: false,
languagesInput: undefined,
languagesInRepository: [],
expected: false,
expectedApiCall: false,
},
{
name: "disabled even though swift kotlin bypassed",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: undefined,
languagesInRepository: [],
expected: false,
expectedApiCall: true,
},
{
name: "disabled even though swift kotlin analyzed",
features: [],
hasCustomCodeQL: false,
languagesInput: " sWiFt , KoTlIn ",
languagesInRepository: [],
expected: false,
expectedApiCall: false,
},
{
name: "toolcache bypass all",
features: [Feature.BypassToolcacheEnabled],
hasCustomCodeQL: false,
languagesInput: undefined,
languagesInRepository: [],
expected: true,
expectedApiCall: false,
},
{
name: "custom CodeQL",
features: [],
hasCustomCodeQL: true,
languagesInput: undefined,
languagesInRepository: [],
expected: true,
expectedApiCall: false,
},
{
name: "bypass swift",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: " sWiFt ,other",
languagesInRepository: [],
expected: true,
expectedApiCall: false,
},
{
name: "bypass kotlin",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: "other, KoTlIn ",
languagesInRepository: [],
expected: true,
expectedApiCall: false,
},
{
name: "bypass kotlin language from repository",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: "",
languagesInRepository: ["KoTlIn", "other"],
expected: true,
expectedApiCall: true,
},
{
name: "bypass swift language from repository",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: "",
languagesInRepository: ["SwiFt", "other"],
expected: true,
expectedApiCall: true,
},
{
name: "bypass java from input if there is kotlin in repository",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: "java",
languagesInRepository: ["kotlin", "other"],
expected: true,
expectedApiCall: true,
},
{
name: "don't bypass java from input if there is no kotlin in repository",
features: [Feature.BypassToolcacheKotlinSwiftEnabled],
hasCustomCodeQL: false,
languagesInput: "java",
languagesInRepository: ["java", "other"],
expected: false,
expectedApiCall: true,
},
].forEach((args) => {
test(`shouldBypassToolcache: ${args.name}`, async (t) => {
const mockRequest = mockLanguagesInRepo(args.languagesInRepository);
const mockLogger = getRunnerLogger(true);
const featureEnablement = createFeatures(args.features);
const codeqlUrl = args.hasCustomCodeQL ? "custom-codeql-url" : undefined;
const actual = await util.shouldBypassToolcache(
featureEnablement,
codeqlUrl,
args.languagesInput,
mockRepositoryNwo,
mockLogger
);
t.deepEqual(actual, args.expected);
t.deepEqual(mockRequest.called, args.expectedApiCall);
});
});

View File

@@ -13,15 +13,12 @@ import * as apiCompatibility from "./api-compatibility.json";
import { CodeQL, CODEQL_VERSION_NEW_TRACING } from "./codeql";
import {
Config,
getLanguagesInRepo,
getRawLanguages,
parsePacksSpecification,
prettyPrintPack,
} from "./config-utils";
import { Feature, FeatureEnablement } from "./feature-flags";
import { KOTLIN_SWIFT_BYPASS, Language } from "./languages";
import { Language } from "./languages";
import { Logger } from "./logging";
import { RepositoryNwo } from "./repository";
import { CODEQL_ACTION_TEST_MODE } from "./shared-environment";
/**
@@ -802,64 +799,6 @@ export function isHostedRunner() {
);
}
/**
*
* @param featuresEnablement The features enabled for the current run
* @param languagesInput Languages input from the workflow
* @param repository The owner/name of the repository
* @param logger A logger
* @returns A boolean indicating whether or not the toolcache should be bypassed
* and the latest codeql should be downloaded.
*/
export async function shouldBypassToolcache(
featuresEnablement: FeatureEnablement,
codeqlUrl: string | undefined,
languagesInput: string | undefined,
repository: RepositoryNwo,
logger: Logger
): Promise<boolean> {
// An explicit codeql url is specified, that means the toolcache will not be used.
if (codeqlUrl) {
return true;
}
// Check if the toolcache is disabled for all languages
if (await featuresEnablement.getValue(Feature.BypassToolcacheEnabled)) {
return true;
}
// Check if the toolcache is disabled for kotlin and swift.
if (
!(await featuresEnablement.getValue(
Feature.BypassToolcacheKotlinSwiftEnabled
))
) {
return false;
}
// Now check to see if kotlin or swift is one of the languages being analyzed.
const { rawLanguages, autodetected } = await getRawLanguages(
languagesInput,
repository,
logger
);
let bypass = rawLanguages.some((lang) => KOTLIN_SWIFT_BYPASS.includes(lang));
if (bypass) {
logger.info(
`Bypassing toolcache for kotlin or swift. Languages: ${rawLanguages}`
);
} else if (!autodetected && rawLanguages.includes(Language.java)) {
// special case: java was explicitly specified, but there might be
// some kotlin in the repository, so we need to make a request for that.
const langsInRepo = await getLanguagesInRepo(repository, logger);
if (langsInRepo.includes("kotlin")) {
logger.info(`Bypassing toolcache for kotlin.`);
bypass = true;
}
}
return bypass;
}
export function parseMatrixInput(
matrixInput: string | undefined
): { [key: string]: string } | undefined {