apify-test-tools 0.10.2-beta.4 → 0.10.2-beta.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.github/cli/apify-test-tools.mjs +125 -127
- package/.github/scripts/run-with-apify-tokens.mjs +1 -1
- package/CHANGELOG.md +5 -0
- package/CONTRIBUTING.md +4 -1
- package/README.md +69 -71
- package/bin/affected-actors.ts +132 -91
- package/bin/build.ts +0 -2
- package/bin/diff-changes.ts +7 -6
- package/bin/diff-json-schema.ts +5 -6
- package/bin/git.ts +21 -55
- package/bin/main.ts +7 -97
- package/bin/slack.ts +14 -27
- package/bin/types.ts +6 -0
- package/dist/bin/affected-actors.d.ts +23 -22
- package/dist/bin/affected-actors.d.ts.map +1 -1
- package/dist/bin/affected-actors.js +108 -60
- package/dist/bin/affected-actors.js.map +1 -1
- package/dist/bin/build.d.ts +0 -1
- package/dist/bin/build.d.ts.map +1 -1
- package/dist/bin/build.js +0 -2
- package/dist/bin/build.js.map +1 -1
- package/dist/bin/diff-changes.d.ts +4 -3
- package/dist/bin/diff-changes.d.ts.map +1 -1
- package/dist/bin/diff-changes.js +4 -4
- package/dist/bin/diff-changes.js.map +1 -1
- package/dist/bin/diff-json-schema.d.ts +2 -2
- package/dist/bin/diff-json-schema.d.ts.map +1 -1
- package/dist/bin/diff-json-schema.js +1 -4
- package/dist/bin/diff-json-schema.js.map +1 -1
- package/dist/bin/git.d.ts +6 -9
- package/dist/bin/git.d.ts.map +1 -1
- package/dist/bin/git.js +20 -48
- package/dist/bin/git.js.map +1 -1
- package/dist/bin/main.js +7 -77
- package/dist/bin/main.js.map +1 -1
- package/dist/bin/slack.d.ts +2 -7
- package/dist/bin/slack.d.ts.map +1 -1
- package/dist/bin/slack.js +12 -18
- package/dist/bin/slack.js.map +1 -1
- package/dist/bin/types.d.ts +5 -0
- package/dist/bin/types.d.ts.map +1 -1
- package/dist/test/bundle/cli-bundle.test.js +14 -16
- package/dist/test/bundle/cli-bundle.test.js.map +1 -1
- package/dist/test/e2e/cli-bundle.e2e.test.js +22 -63
- package/dist/test/e2e/cli-bundle.e2e.test.js.map +1 -1
- package/dist/test/e2e/git-build-release.e2e.test.d.ts +2 -0
- package/dist/test/e2e/git-build-release.e2e.test.d.ts.map +1 -0
- package/dist/test/e2e/git-build-release.e2e.test.js +87 -0
- package/dist/test/e2e/git-build-release.e2e.test.js.map +1 -0
- package/dist/test/e2e/helpers.d.ts +37 -0
- package/dist/test/e2e/helpers.d.ts.map +1 -0
- package/dist/test/e2e/helpers.js +57 -0
- package/dist/test/e2e/helpers.js.map +1 -0
- package/dist/test/unit/bin/affected-actors-cli.test.d.ts +2 -0
- package/dist/test/unit/bin/affected-actors-cli.test.d.ts.map +1 -0
- package/dist/test/unit/bin/affected-actors-cli.test.js +161 -0
- package/dist/test/unit/bin/affected-actors-cli.test.js.map +1 -0
- package/dist/test/unit/bin/affected-actors.test.js +65 -78
- package/dist/test/unit/bin/affected-actors.test.js.map +1 -1
- package/dist/test/unit/bin/build-cli.test.js +5 -13
- package/dist/test/unit/bin/build-cli.test.js.map +1 -1
- package/dist/test/unit/bin/compiled-cli.d.ts +6 -0
- package/dist/test/unit/bin/compiled-cli.d.ts.map +1 -0
- package/dist/test/unit/bin/compiled-cli.js +16 -0
- package/dist/test/unit/bin/compiled-cli.js.map +1 -0
- package/dist/test/unit/bin/diff-changes.test.js +55 -55
- package/dist/test/unit/bin/diff-changes.test.js.map +1 -1
- package/dist/test/unit/bin/diff.test.js +25 -28
- package/dist/test/unit/bin/diff.test.js.map +1 -1
- package/dist/test/unit/bin/git.test.js +29 -97
- package/dist/test/unit/bin/git.test.js.map +1 -1
- package/dist/test/unit/bin/slack.test.js +6 -27
- package/dist/test/unit/bin/slack.test.js.map +1 -1
- package/dist/test/unit/should-built-and-test.test.js +18 -21
- package/dist/test/unit/should-built-and-test.test.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +1 -1
- package/test/bundle/cli-bundle.test.ts +14 -24
- package/test/e2e/cli-bundle.e2e.test.ts +39 -84
- package/test/e2e/git-build-release.e2e.test.ts +113 -0
- package/test/e2e/helpers.ts +82 -0
- package/test/unit/bin/affected-actors-cli.test.ts +193 -0
- package/test/unit/bin/affected-actors.test.ts +83 -85
- package/test/unit/bin/build-cli.test.ts +6 -12
- package/test/unit/bin/compiled-cli.ts +17 -0
- package/test/unit/bin/diff-changes.test.ts +55 -55
- package/test/unit/bin/diff.test.ts +25 -28
- package/test/unit/bin/git.test.ts +37 -120
- package/test/unit/bin/slack.test.ts +6 -30
- package/test/unit/should-built-and-test.test.ts +19 -22
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { MockInstance } from 'vitest';
|
|
2
2
|
import { beforeEach, describe, expect, it, vi } from 'vitest';
|
|
3
3
|
|
|
4
|
-
import { getAffectedActors
|
|
4
|
+
import { getAffectedActors } from '../../../bin/affected-actors.js';
|
|
5
5
|
import * as DiffChanges from '../../../bin/diff-changes.js';
|
|
6
6
|
import * as Git from '../../../bin/git.js';
|
|
7
7
|
import type { ActorConfig, Commit } from '../../../bin/types.js';
|
|
@@ -40,84 +40,113 @@ describe('getAffectedActors', () => {
|
|
|
40
40
|
});
|
|
41
41
|
|
|
42
42
|
describe('with --base', () => {
|
|
43
|
-
|
|
43
|
+
const mergeBaseSha = 'b'.repeat(40);
|
|
44
|
+
let commitsBetweenSpy: MockInstance;
|
|
44
45
|
|
|
45
46
|
beforeEach(() => {
|
|
46
|
-
vi.spyOn(Git, '
|
|
47
|
-
|
|
47
|
+
vi.spyOn(Git, 'getMergeBase').mockResolvedValue(mergeBaseSha);
|
|
48
|
+
commitsBetweenSpy = vi.spyOn(Git, 'getCommitsBetween').mockResolvedValue(commits);
|
|
48
49
|
});
|
|
49
50
|
|
|
50
|
-
it(
|
|
51
|
-
const
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
...selection,
|
|
55
|
-
});
|
|
51
|
+
it("inspects the branch's own changes, from where it forked from or last merged --base", async () => {
|
|
52
|
+
const findCommitSpy = vi.spyOn(Git, 'findCommitSha');
|
|
53
|
+
|
|
54
|
+
const result = await getAffectedActors({ base: 'origin/master', ...selection });
|
|
56
55
|
|
|
57
56
|
expect(result).toStrictEqual({
|
|
58
|
-
|
|
57
|
+
version: 1,
|
|
58
|
+
head: headSha,
|
|
59
59
|
commits,
|
|
60
60
|
changedFiles,
|
|
61
61
|
changelog: '- Added foo',
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
expect(getCommitsSpy).toHaveBeenCalledWith({
|
|
66
|
-
sourceBranch: 'HEAD',
|
|
67
|
-
targetBranch: 'origin/master',
|
|
68
|
-
baseCommit: sinceSha,
|
|
62
|
+
// Only the names, the config file stays the source of truth for the rest
|
|
63
|
+
functionallyChangedActors: [{ actorFullName: 'owner/a' }],
|
|
64
|
+
cosmeticallyChangedActors: [{ actorFullName: 'owner/b' }],
|
|
69
65
|
});
|
|
70
|
-
|
|
71
|
-
expect(Git.getChangedFilesBetween).toHaveBeenCalledWith(
|
|
72
|
-
expect(Git.getChangelogAdditions).toHaveBeenCalledWith(
|
|
66
|
+
expect(Git.getMergeBase).toHaveBeenCalledWith('origin/master', 'HEAD');
|
|
67
|
+
expect(Git.getChangedFilesBetween).toHaveBeenCalledWith(mergeBaseSha, headSha);
|
|
68
|
+
expect(Git.getChangelogAdditions).toHaveBeenCalledWith(mergeBaseSha, headSha, changedFiles);
|
|
69
|
+
expect(commitsBetweenSpy).toHaveBeenCalledWith(mergeBaseSha, headSha);
|
|
73
70
|
expect(changedActorsSpy).toHaveBeenCalledWith({
|
|
74
71
|
filepathsChanged: changedFiles,
|
|
75
72
|
actorConfigs: [actorA, actorB],
|
|
76
|
-
|
|
73
|
+
range: { fromRef: mergeBaseSha, toRef: headSha },
|
|
77
74
|
});
|
|
75
|
+
expect(findCommitSpy).not.toHaveBeenCalled();
|
|
78
76
|
});
|
|
79
77
|
|
|
80
|
-
describe('
|
|
78
|
+
describe('and --since', () => {
|
|
79
|
+
const sinceFiles = ['README.md'];
|
|
80
|
+
|
|
81
81
|
beforeEach(() => {
|
|
82
|
-
vi.spyOn(Git, '
|
|
83
|
-
vi.spyOn(Git, '
|
|
82
|
+
vi.spyOn(Git, 'findCommitSha').mockResolvedValue(sinceSha);
|
|
83
|
+
vi.spyOn(Git, 'getChangedFilesBetween').mockImplementation(async (fromRef) =>
|
|
84
|
+
fromRef === sinceSha ? sinceFiles : changedFiles,
|
|
85
|
+
);
|
|
84
86
|
});
|
|
85
87
|
|
|
86
|
-
const
|
|
87
|
-
|
|
88
|
-
|
|
88
|
+
const getNarrowed = async (
|
|
89
|
+
branch: DiffChanges.ChangedActors,
|
|
90
|
+
sinceValidated: DiffChanges.ChangedActors,
|
|
91
|
+
) => {
|
|
92
|
+
changedActorsSpy.mockImplementation(async ({ range }) =>
|
|
93
|
+
range.fromRef === sinceSha ? sinceValidated : branch,
|
|
89
94
|
);
|
|
90
|
-
|
|
95
|
+
const result = await getAffectedActors({ base: 'origin/master', since: sinceSha, ...selection });
|
|
96
|
+
return {
|
|
97
|
+
functional: result.functionallyChangedActors.map(({ actorFullName }) => actorFullName),
|
|
98
|
+
cosmetic: result.cosmeticallyChangedActors.map(({ actorFullName }) => actorFullName),
|
|
99
|
+
};
|
|
91
100
|
};
|
|
92
101
|
|
|
93
|
-
it(
|
|
94
|
-
await
|
|
102
|
+
it('classifies the changes since --since separately', async () => {
|
|
103
|
+
await getNarrowed({ functional: [actorA], cosmetic: [] }, { functional: [actorA], cosmetic: [] });
|
|
95
104
|
expect(changedActorsSpy).toHaveBeenCalledWith({
|
|
96
|
-
filepathsChanged:
|
|
105
|
+
filepathsChanged: sinceFiles,
|
|
97
106
|
actorConfigs: [actorA, actorB],
|
|
98
|
-
|
|
107
|
+
range: { fromRef: sinceSha, toRef: headSha },
|
|
99
108
|
});
|
|
100
|
-
expect(getCommitsSpy).toHaveBeenCalledWith({ sourceBranch: 'HEAD', targetBranch: 'master' });
|
|
101
109
|
});
|
|
102
110
|
|
|
103
|
-
it('
|
|
104
|
-
const result = await
|
|
105
|
-
expect(result.
|
|
106
|
-
expect(result.
|
|
111
|
+
it('still describes the whole branch', async () => {
|
|
112
|
+
const result = await getAffectedActors({ base: 'origin/master', since: sinceSha, ...selection });
|
|
113
|
+
expect(result.commits).toStrictEqual(commits);
|
|
114
|
+
expect(result.changedFiles).toStrictEqual(changedFiles);
|
|
115
|
+
});
|
|
116
|
+
|
|
117
|
+
it('retests an Actor whose validated change meets a new functional change', async () => {
|
|
118
|
+
await expect(
|
|
119
|
+
getNarrowed({ functional: [actorA], cosmetic: [] }, { functional: [actorA], cosmetic: [] }),
|
|
120
|
+
).resolves.toStrictEqual({ functional: ['owner/a'], cosmetic: [] });
|
|
107
121
|
});
|
|
108
122
|
|
|
109
|
-
it('
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
123
|
+
it('leaves out Actors that only the branch changed before --since or only --base changed', async () => {
|
|
124
|
+
await expect(
|
|
125
|
+
getNarrowed({ functional: [actorA], cosmetic: [] }, { functional: [actorB], cosmetic: [] }),
|
|
126
|
+
).resolves.toStrictEqual({ functional: [], cosmetic: [] });
|
|
113
127
|
});
|
|
114
128
|
|
|
115
|
-
it('
|
|
116
|
-
|
|
117
|
-
expect(
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
129
|
+
it('takes the less impactful change when the two disagree', async () => {
|
|
130
|
+
// A validated functional change, then only cosmetic changes (e.g. a README merged in from base)
|
|
131
|
+
await expect(
|
|
132
|
+
getNarrowed({ functional: [actorA], cosmetic: [] }, { functional: [], cosmetic: [actorA] }),
|
|
133
|
+
).resolves.toStrictEqual({ functional: [], cosmetic: ['owner/a'] });
|
|
134
|
+
// A functional change merged in from base, while the branch only changes the README
|
|
135
|
+
await expect(
|
|
136
|
+
getNarrowed({ functional: [], cosmetic: [actorA] }, { functional: [actorA], cosmetic: [] }),
|
|
137
|
+
).resolves.toStrictEqual({ functional: [], cosmetic: ['owner/a'] });
|
|
138
|
+
});
|
|
139
|
+
|
|
140
|
+
it.each([
|
|
141
|
+
['is HEAD (a rerun)', headSha],
|
|
142
|
+
['is not in the local history', undefined],
|
|
143
|
+
])('checks the whole branch when --since %s', async (_, found) => {
|
|
144
|
+
vi.spyOn(Git, 'findCommitSha').mockResolvedValue(found);
|
|
145
|
+
const result = await getAffectedActors({ base: 'origin/master', since: sinceSha, ...selection });
|
|
146
|
+
expect(result.functionallyChangedActors).toStrictEqual([{ actorFullName: 'owner/a' }]);
|
|
147
|
+
// With no usable validated commit, the "since" diff falls back to the same range as the
|
|
148
|
+
// base diff, so getChangedActors runs twice for identical ranges instead of once.
|
|
149
|
+
expect(changedActorsSpy).toHaveBeenCalledTimes(2);
|
|
121
150
|
});
|
|
122
151
|
});
|
|
123
152
|
});
|
|
@@ -131,54 +160,23 @@ describe('getAffectedActors', () => {
|
|
|
131
160
|
commitsBetweenSpy = vi.spyOn(Git, 'getCommitsBetween').mockResolvedValue(commits);
|
|
132
161
|
});
|
|
133
162
|
|
|
134
|
-
it('inspects everything after --since up to
|
|
163
|
+
it('inspects everything after --since up to HEAD', async () => {
|
|
135
164
|
const result = await getAffectedActors({ since: 'HEAD~2', ...selection });
|
|
136
165
|
|
|
137
166
|
expect(result).toStrictEqual({
|
|
138
|
-
|
|
167
|
+
version: 1,
|
|
168
|
+
head: headSha,
|
|
139
169
|
commits,
|
|
140
170
|
changedFiles,
|
|
141
171
|
changelog: '- Added foo',
|
|
142
|
-
|
|
143
|
-
|
|
172
|
+
// Only the names, the config file stays the source of truth for the rest
|
|
173
|
+
functionallyChangedActors: [{ actorFullName: 'owner/a' }],
|
|
174
|
+
cosmeticallyChangedActors: [{ actorFullName: 'owner/b' }],
|
|
144
175
|
});
|
|
145
176
|
expect(resolveBaseSpy).toHaveBeenCalledWith('HEAD~2');
|
|
146
177
|
expect(commitsBetweenSpy).toHaveBeenCalledWith(sinceSha, headSha);
|
|
147
178
|
expect(Git.getChangedFilesBetween).toHaveBeenCalledWith(sinceSha, headSha);
|
|
148
179
|
expect(Git.getChangelogAdditions).toHaveBeenCalledWith(sinceSha, headSha, changedFiles);
|
|
149
180
|
});
|
|
150
|
-
|
|
151
|
-
it('has no commits when head is the --since commit', async () => {
|
|
152
|
-
resolveBaseSpy.mockResolvedValue(headSha);
|
|
153
|
-
|
|
154
|
-
const result = await getAffectedActors({ since: headSha, ...selection });
|
|
155
|
-
|
|
156
|
-
expect(result.commits).toStrictEqual([]);
|
|
157
|
-
// Empty `git log x..x` output doesn't parse as a commit, so it's never run
|
|
158
|
-
expect(commitsBetweenSpy).not.toHaveBeenCalled();
|
|
159
|
-
});
|
|
160
|
-
});
|
|
161
|
-
});
|
|
162
|
-
|
|
163
|
-
describe('toAffectedActorsDocument', () => {
|
|
164
|
-
it('keeps only the Actor names, the config file stays the source of truth for the rest', () => {
|
|
165
|
-
expect(
|
|
166
|
-
toAffectedActorsDocument({
|
|
167
|
-
headSha,
|
|
168
|
-
commits,
|
|
169
|
-
changedFiles: ['src/main.ts'],
|
|
170
|
-
changelog: null,
|
|
171
|
-
functionallyChangedActors: [actorA],
|
|
172
|
-
cosmeticallyChangedActors: [actorB],
|
|
173
|
-
}),
|
|
174
|
-
).toStrictEqual({
|
|
175
|
-
version: 1,
|
|
176
|
-
head: headSha,
|
|
177
|
-
commits,
|
|
178
|
-
changedFiles: ['src/main.ts'],
|
|
179
|
-
changelog: null,
|
|
180
|
-
functionallyChangedActors: [{ actorFullName: 'owner/a' }],
|
|
181
|
-
cosmeticallyChangedActors: [{ actorFullName: 'owner/b' }],
|
|
182
|
-
});
|
|
183
181
|
});
|
|
184
182
|
});
|
|
@@ -1,15 +1,12 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { chmod, mkdtemp, rm } from 'node:fs/promises';
|
|
3
|
-
import path from 'node:path';
|
|
1
|
+
import { spawnSync } from 'node:child_process';
|
|
4
2
|
import process from 'node:process';
|
|
5
|
-
import { fileURLToPath } from 'node:url';
|
|
6
3
|
|
|
7
4
|
import { afterAll, beforeAll, describe, expect, it } from 'vitest';
|
|
8
5
|
|
|
9
|
-
|
|
10
|
-
|
|
6
|
+
import { compileCli } from './compiled-cli.js';
|
|
7
|
+
|
|
11
8
|
let cliPath: string;
|
|
12
|
-
let
|
|
9
|
+
let cleanup: (() => Promise<void>) | undefined;
|
|
13
10
|
|
|
14
11
|
const run = (command: string[], input: string, env: NodeJS.ProcessEnv = process.env) =>
|
|
15
12
|
spawnSync(cliPath, command, { encoding: 'utf8', input, stdio: ['pipe', 'pipe', 'pipe'], env });
|
|
@@ -17,14 +14,11 @@ const runBuild = (input: string, args: string[] = ['--version-number', '0.99'])
|
|
|
17
14
|
|
|
18
15
|
describe('build and notify-release CLI', () => {
|
|
19
16
|
beforeAll(async () => {
|
|
20
|
-
|
|
21
|
-
execFileSync(process.execPath, [compilerPath, '--outDir', buildDir], { cwd: projectRoot });
|
|
22
|
-
cliPath = path.join(buildDir, 'bin/main.js');
|
|
23
|
-
await chmod(cliPath, 0o755);
|
|
17
|
+
({ cliPath, cleanup } = await compileCli());
|
|
24
18
|
});
|
|
25
19
|
|
|
26
20
|
afterAll(async () => {
|
|
27
|
-
|
|
21
|
+
await cleanup?.();
|
|
28
22
|
});
|
|
29
23
|
|
|
30
24
|
it('builds nothing for an empty list and prints an empty build list', () => {
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { execFileSync } from 'node:child_process';
|
|
2
|
+
import { chmod, mkdtemp, rm } from 'node:fs/promises';
|
|
3
|
+
import path from 'node:path';
|
|
4
|
+
import process from 'node:process';
|
|
5
|
+
import { fileURLToPath } from 'node:url';
|
|
6
|
+
|
|
7
|
+
const projectRoot = fileURLToPath(new URL('../../../', import.meta.url));
|
|
8
|
+
const compilerPath = fileURLToPath(new URL('../../../node_modules/typescript/bin/tsc', import.meta.url));
|
|
9
|
+
|
|
10
|
+
/** Compiles the CLI from the sources into a temporary directory, so tests run it the way users do. */
|
|
11
|
+
export const compileCli = async () => {
|
|
12
|
+
const buildDir = await mkdtemp(path.join(projectRoot, '.cli-test-'));
|
|
13
|
+
execFileSync(process.execPath, [compilerPath, '--outDir', buildDir], { cwd: projectRoot });
|
|
14
|
+
const cliPath = path.join(buildDir, 'bin/main.js');
|
|
15
|
+
await chmod(cliPath, 0o755);
|
|
16
|
+
return { cliPath, cleanup: async () => rm(buildDir, { recursive: true, force: true }) };
|
|
17
|
+
};
|