Add logic to download codeql platform-language pkg

* Add `bundleName` argument to `getCodeQLBundleDownloadURL`
* Add `languages` argument to `setupCodeQL`.

The logic now tries to find the platform-language pkg before defaulting
to the full bundle. We keep the toolcache clean by adding the pl version
to the tool version.
This commit is contained in:
Marco Gario
2020-09-09 13:53:11 +02:00
parent d3d7dd4600
commit 57b0b7fd1d
4 changed files with 80 additions and 23 deletions
+58 -10
View File
@@ -10,20 +10,21 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const github = __importStar(require("@actions/github"));
const toolcache = __importStar(require("@actions/tool-cache"));
const ava_1 = __importDefault(require("ava"));
const nock_1 = __importDefault(require("nock"));
const path = __importStar(require("path"));
const sinon_1 = __importDefault(require("sinon"));
const api = __importStar(require("./api-client"));
const github = __importStar(require("@actions/github"));
const codeql = __importStar(require("./codeql"));
const defaults = __importStar(require("./defaults.json")); // Referenced from codeql-action-sync-tool!
const languages_1 = require("./languages");
const logging_1 = require("./logging");
const testing_utils_1 = require("./testing-utils");
const util = __importStar(require("./util"));
testing_utils_1.setupTests(ava_1.default);
ava_1.default('download codeql bundle cache', async (t) => {
ava_1.default('download and populate codeql bundle cache', async (t) => {
await util.withTmpDir(async (tmpDir) => {
const versions = ['20200601', '20200610'];
const languages = [
@@ -37,21 +38,66 @@ ava_1.default('download codeql bundle cache', async (t) => {
for (let j = 0; j < languages.length; j++) {
const version = versions[i];
const plVersion = (languages[j].length === 1) ? `${platform}-${languages[j][0]}` : undefined;
const pkg = plVersion ? `codeql-${plVersion}.tar.gz` : `codeql-bundle.tar.gz`;
nock_1.default('https://example.com')
.get(`/download/codeql-bundle-${version}/${pkg}`)
.get(`/download/codeql-bundle-${version}/codeql-bundle.tar.gz`)
.replyWithFile(200, path.join(__dirname, `/../src/testdata/codeql-bundle.tar.gz`));
await codeql.setupCodeQL(`https://example.com/download/codeql-bundle-${version}/codeql-bundle.tar.gz`, languages[j], 'token', 'https://github.example.com', tmpDir, tmpDir, 'runner', logging_1.getRunnerLogger(true));
const toolcacheVersion = plVersion ? `0.0.0-${version}-${plVersion}` : `0.0.0-${version}`;
t.assert(toolcache.find('CodeQL', toolcacheVersion), `Looking for ${toolcacheVersion} - ${plVersion}`);
t.assert(toolcache.find('CodeQL', toolcacheVersion), `Looking for ${toolcacheVersion}`);
}
}
const cachedVersions = toolcache.findAllVersions('CodeQL');
t.is(cachedVersions.length, 4);
});
});
ava_1.default('use codeql bundle cache if pl version is not available', async (t) => {
// If we look for a pl version but find in cache the bundle, we use the bundle
ava_1.default('download small codeql bundle if analyzing only one language', async (t) => {
// Note: We do not specify a codeqlURL in this test, thus testing that
// the logic for constructing the URL takes into account the
// language being analyzed
await util.withTmpDir(async (tmpDir) => {
const languages = [
[languages_1.Language.cpp],
[languages_1.Language.cpp, languages_1.Language.python] // Multi-language requires the full bundle
];
const platform = process.platform === 'win32' ? 'win64' :
process.platform === 'linux' ? 'linux64' :
process.platform === 'darwin' ? 'osx64' : undefined;
for (let i = 0; i < languages.length; i++) {
const plVersion = (languages[i].length === 1) ? `${platform}-${languages[i][0]}` : undefined;
const pkg = plVersion ? `codeql-bundle-${plVersion}.tar.gz` : 'codeql-bundle.tar.gz';
// Mock the API client
let client = new github.GitHub('123');
const response = {
data: {
'assets': [
{
'name': `codeql-bundle-${platform}-cpp.tar.gz`,
'url': `https://github.example.com/url/codeql-bundle-${platform}-cpp.tar.gz`
},
{
'name': 'codeql-bundle.tar.gz',
'url': 'https://github.example.com/url/codeql-bundle.tar.gz'
},
]
},
};
sinon_1.default.stub(client.repos, "getReleaseByTag").resolves(response);
sinon_1.default.stub(api, "getApiClient").value(() => client);
nock_1.default('https://github.example.com')
.get(`/url/${pkg}`)
.replyWithFile(200, path.join(__dirname, `/../src/testdata/codeql-bundle.tar.gz`));
await codeql.setupCodeQL(undefined, languages[i], 'token', 'https://github.example.com', tmpDir, tmpDir, 'runner', logging_1.getRunnerLogger(true));
const parsedVersion = codeql.getCodeQLURLVersion(`/${defaults.bundleVersion}/`, logging_1.getRunnerLogger(true));
const toolcacheVersion = plVersion ? `${parsedVersion}-${plVersion}` : parsedVersion;
t.assert(toolcache.find('CodeQL', toolcacheVersion), `Looking for ${toolcacheVersion} - ${plVersion}`);
}
const cachedVersions = toolcache.findAllVersions('CodeQL');
t.is(cachedVersions.length, 2);
});
});
ava_1.default('use full codeql bundle cache if smaller bundle is not available', async (t) => {
// If we look for a platform-language version but find the full bundle in the cache,
// we use the full bundle
await util.withTmpDir(async (tmpDir) => {
const version = '20200601';
nock_1.default('https://example.com')
@@ -66,13 +112,15 @@ ava_1.default('use codeql bundle cache if pl version is not available', async (t
t.is(toolcache.findAllVersions('CodeQL').length, 1);
});
});
ava_1.default('use larger bundles if smaller ones are unavailble', async (t) => {
ava_1.default('use larger bundles if smaller ones are not released', async (t) => {
// Mock the API client
let client = new github.GitHub('123');
const response = {
data: { 'assets': [
data: {
'assets': [
{ 'name': 'full-bundle', 'url': 'url/file.gz' },
] },
]
},
};
let getReleaseByTagMock = sinon_1.default.stub(client.repos, "getReleaseByTag").resolves(response);
sinon_1.default.stub(api, "getApiClient").value(() => client);