Skip to content
This repository has been archived by the owner on Mar 31, 2024. It is now read-only.

Commit

Permalink
[kbn/optimizer] include bootstrap cache key in optimizer cache key (e…
Browse files Browse the repository at this point in the history
…lastic#58176)

* [kbn/optimizer] include bootstrap cache key in optimizer cache key

* remove cache buster

* update cache keys tests

* move mocks
  • Loading branch information
Spencer authored and spalger committed Feb 21, 2020
1 parent d07f36a commit b342d6b
Show file tree
Hide file tree
Showing 3 changed files with 75 additions and 21 deletions.
1 change: 0 additions & 1 deletion packages/kbn-optimizer/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@
* under the License.
*/

// cache buster - https://github.com/elastic/kibana/issues/58077 - 1
export { OptimizerConfig } from './optimizer';
export * from './run_optimizer';
export * from './log_optimizer_state';
52 changes: 40 additions & 12 deletions packages/kbn-optimizer/src/optimizer/cache_keys.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,35 @@
* under the License.
*/

import Path from 'path';

import jestDiff from 'jest-diff';
import { REPO_ROOT, createAbsolutePathSerializer } from '@kbn/dev-utils';

import { reformatJestDiff, getOptimizerCacheKey, diffCacheKey } from './cache_keys';
import { OptimizerConfig } from './optimizer_config';

jest.mock('./get_changes.ts');
jest.mock('./get_changes.ts', () => ({
getChanges: async () =>
new Map([
['/foo/bar/a', 'modified'],
['/foo/bar/b', 'modified'],
['/foo/bar/c', 'deleted'],
]),
}));

jest.mock('./get_mtimes.ts', () => ({
getMtimes: async (paths: string[]) => new Map(paths.map(path => [path, 12345])),
}));

jest.mock('execa');

jest.mock('fs', () => {
const realFs = jest.requireActual('fs');
jest.spyOn(realFs, 'readFile');
return realFs;
});

expect.addSnapshotSerializer(createAbsolutePathSerializer());

jest.requireMock('execa').mockImplementation(async (cmd: string, args: string[], opts: object) => {
Expand All @@ -46,28 +67,35 @@ jest.requireMock('execa').mockImplementation(async (cmd: string, args: string[],
};
});

jest.requireMock('./get_changes.ts').getChanges.mockImplementation(
async () =>
new Map([
['/foo/bar/a', 'modified'],
['/foo/bar/b', 'modified'],
['/foo/bar/c', 'deleted'],
])
);

describe('getOptimizerCacheKey()', () => {
it('uses latest commit and changes files to create unique value', async () => {
it('uses latest commit, bootstrap cache, and changed files to create unique value', async () => {
jest
.requireMock('fs')
.readFile.mockImplementation(
(path: string, enc: string, cb: (err: null, file: string) => void) => {
expect(path).toBe(
Path.resolve(REPO_ROOT, 'packages/kbn-optimizer/target/.bootstrap-cache')
);
expect(enc).toBe('utf8');
cb(null, '<bootstrap cache>');
}
);

const config = OptimizerConfig.create({
repoRoot: REPO_ROOT,
});

await expect(getOptimizerCacheKey(config)).resolves.toMatchInlineSnapshot(`
Object {
"bootstrap": "<bootstrap cache>",
"deletedPaths": Array [
"/foo/bar/c",
],
"lastCommit": "<last commit sha>",
"modifiedPaths": Object {},
"modifiedTimes": Object {
"/foo/bar/a": 12345,
"/foo/bar/b": 12345,
},
"workerConfig": Object {
"browserslistEnv": "dev",
"cache": true,
Expand Down
43 changes: 35 additions & 8 deletions packages/kbn-optimizer/src/optimizer/cache_keys.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@
*/

import Path from 'path';
import Fs from 'fs';
import { promisify } from 'util';

import Chalk from 'chalk';
import execa from 'execa';
Expand Down Expand Up @@ -116,9 +118,10 @@ export function reformatJestDiff(diff: string | null) {

export interface OptimizerCacheKey {
readonly lastCommit: string | undefined;
readonly bootstrap: string | undefined;
readonly workerConfig: WorkerConfig;
readonly deletedPaths: string[];
readonly modifiedPaths: Record<string, number>;
readonly modifiedTimes: Record<string, number>;
}

async function getLastCommit() {
Expand All @@ -133,21 +136,45 @@ async function getLastCommit() {
return stdout.trim() || undefined;
}

async function getBootstrapCacheKey() {
try {
return await promisify(Fs.readFile)(
Path.resolve(OPTIMIZER_DIR, 'target/.bootstrap-cache'),
'utf8'
);
} catch (error) {
if (error?.code !== 'ENOENT') {
throw error;
}
return undefined;
}
}

export async function getOptimizerCacheKey(config: OptimizerConfig) {
const changes = Array.from((await getChanges(OPTIMIZER_DIR)).entries());
const [changes, lastCommit, bootstrap] = await Promise.all([
getChanges(OPTIMIZER_DIR),
getLastCommit(),
getBootstrapCacheKey(),
] as const);

const deletedPaths: string[] = [];
const modifiedPaths: string[] = [];
for (const [path, type] of changes) {
(type === 'deleted' ? deletedPaths : modifiedPaths).push(path);
}

const cacheKeys: OptimizerCacheKey = {
lastCommit: await getLastCommit(),
workerConfig: config.getWorkerConfig('♻'),
deletedPaths: changes.filter(e => e[1] === 'deleted').map(e => e[0]),
modifiedPaths: {} as Record<string, number>,
lastCommit,
bootstrap,
deletedPaths,
modifiedTimes: {} as Record<string, number>,
};

const modified = changes.filter(e => e[1] === 'modified').map(e => e[0]);
const mtimes = await getMtimes(modified);
const mtimes = await getMtimes(modifiedPaths);
for (const [path, mtime] of Array.from(mtimes.entries()).sort(ascending(e => e[0]))) {
if (typeof mtime === 'number') {
cacheKeys.modifiedPaths[path] = mtime;
cacheKeys.modifiedTimes[path] = mtime;
}
}

Expand Down

0 comments on commit b342d6b

Please sign in to comment.