apify-test-tools 0.10.2-beta.2 → 0.10.2-beta.21
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/.gitattributes +1 -0
- package/.github/actionlint.yaml +11 -0
- package/.github/actions/checkout-restore-dependencies/action.yaml +58 -6
- package/.github/cli/apify-test-tools.mjs +135 -142
- package/.github/scripts/mask-config-secrets.sh +17 -0
- package/.github/scripts/run-with-apify-tokens.mjs +63 -103
- package/.github/workflows/_check_code.yaml +5 -21
- package/.github/workflows/_move_major_tag.yaml +2 -2
- package/.github/workflows/public_platform-tests-claude-investigate-and-fix.yaml +89 -8
- package/.github/workflows/public_platform-tests.yaml +68 -30
- package/.github/workflows/public_pr-build-test.yaml +77 -38
- package/.github/workflows/public_push-build-latest.yaml +49 -11
- package/.github/workflows/public_review.yaml +5 -4
- package/.github/workflows/public_stale-issues.yaml +51 -0
- package/.husky/pre-commit +4 -4
- package/.prettierignore +2 -1
- package/CHANGELOG.md +23 -0
- package/CONTRIBUTING.md +117 -17
- package/README.md +221 -595
- package/bin/actor-ids.ts +41 -0
- package/bin/affected-actors.ts +211 -0
- package/bin/build-from-local.ts +19 -1
- package/bin/build.ts +105 -39
- package/bin/diff-changes.ts +69 -36
- package/bin/diff-json-schema.ts +5 -6
- package/bin/git.ts +73 -175
- package/bin/main.ts +142 -189
- package/bin/notify.ts +198 -0
- package/bin/run-tests.ts +182 -0
- package/bin/slack.ts +16 -76
- package/bin/stdin-input.ts +156 -0
- package/bin/test-files-glob.ts +126 -0
- package/bin/test-report.ts +141 -140
- package/bin/types.ts +4 -7
- package/bin/utils/config/load-config.ts +20 -2
- package/bin/utils/config/parser.ts +40 -8
- package/bin/utils/config/structures/grouped.ts +2 -2
- package/bin/utils/config/structures/legacy.ts +1 -1
- package/dist/bin/actor-ids.d.ts +15 -0
- package/dist/bin/actor-ids.d.ts.map +1 -0
- package/dist/bin/actor-ids.js +30 -0
- package/dist/bin/actor-ids.js.map +1 -0
- package/dist/bin/affected-actors.d.ts +55 -0
- package/dist/bin/affected-actors.d.ts.map +1 -0
- package/dist/bin/affected-actors.js +142 -0
- package/dist/bin/affected-actors.js.map +1 -0
- package/dist/bin/build-from-local.d.ts +2 -1
- package/dist/bin/build-from-local.d.ts.map +1 -1
- package/dist/bin/build-from-local.js +6 -2
- package/dist/bin/build-from-local.js.map +1 -1
- package/dist/bin/build.d.ts +18 -5
- package/dist/bin/build.d.ts.map +1 -1
- package/dist/bin/build.js +74 -24
- package/dist/bin/build.js.map +1 -1
- package/dist/bin/diff-changes.d.ts +21 -5
- package/dist/bin/diff-changes.d.ts.map +1 -1
- package/dist/bin/diff-changes.js +41 -28
- 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 +26 -34
- package/dist/bin/git.d.ts.map +1 -1
- package/dist/bin/git.js +60 -143
- package/dist/bin/git.js.map +1 -1
- package/dist/bin/main.js +126 -140
- package/dist/bin/main.js.map +1 -1
- package/dist/bin/notify.d.ts +35 -0
- package/dist/bin/notify.d.ts.map +1 -0
- package/dist/bin/notify.js +131 -0
- package/dist/bin/notify.js.map +1 -0
- package/dist/bin/run-tests.d.ts +21 -0
- package/dist/bin/run-tests.d.ts.map +1 -0
- package/dist/bin/run-tests.js +149 -0
- package/dist/bin/run-tests.js.map +1 -0
- package/dist/bin/slack.d.ts +2 -14
- package/dist/bin/slack.d.ts.map +1 -1
- package/dist/bin/slack.js +17 -46
- package/dist/bin/slack.js.map +1 -1
- package/dist/bin/stdin-input.d.ts +79 -0
- package/dist/bin/stdin-input.d.ts.map +1 -0
- package/dist/bin/stdin-input.js +124 -0
- package/dist/bin/stdin-input.js.map +1 -0
- package/dist/bin/test-files-glob.d.ts +18 -0
- package/dist/bin/test-files-glob.d.ts.map +1 -0
- package/dist/bin/test-files-glob.js +108 -0
- package/dist/bin/test-files-glob.js.map +1 -0
- package/dist/bin/test-report.d.ts +69 -8
- package/dist/bin/test-report.d.ts.map +1 -1
- package/dist/bin/test-report.js +76 -67
- package/dist/bin/test-report.js.map +1 -1
- package/dist/bin/types.d.ts +4 -7
- package/dist/bin/types.d.ts.map +1 -1
- package/dist/bin/utils/config/load-config.d.ts +8 -0
- package/dist/bin/utils/config/load-config.d.ts.map +1 -1
- package/dist/bin/utils/config/load-config.js +14 -1
- package/dist/bin/utils/config/load-config.js.map +1 -1
- package/dist/bin/utils/config/parser.d.ts +15 -2
- package/dist/bin/utils/config/parser.d.ts.map +1 -1
- package/dist/bin/utils/config/parser.js +29 -8
- package/dist/bin/utils/config/parser.js.map +1 -1
- package/dist/bin/utils/config/structures/grouped.js +2 -2
- package/dist/bin/utils/config/structures/grouped.js.map +1 -1
- package/dist/bin/utils/config/structures/legacy.js +1 -1
- package/dist/bin/utils/config/structures/legacy.js.map +1 -1
- package/dist/lib/extend-expect.d.ts.map +1 -1
- package/dist/lib/extend-expect.js +37 -218
- package/dist/lib/extend-expect.js.map +1 -1
- package/dist/lib/lib.d.ts +1 -5
- package/dist/lib/lib.d.ts.map +1 -1
- package/dist/lib/lib.js +19 -31
- package/dist/lib/lib.js.map +1 -1
- package/dist/lib/run-checks.d.ts +14 -0
- package/dist/lib/run-checks.d.ts.map +1 -0
- package/dist/lib/run-checks.js +82 -0
- package/dist/lib/run-checks.js.map +1 -0
- package/dist/lib/run-test-result.d.ts +3 -6
- package/dist/lib/run-test-result.d.ts.map +1 -1
- package/dist/lib/run-test-result.js +41 -54
- package/dist/lib/run-test-result.js.map +1 -1
- package/dist/test/bundle/cli-bundle.test.js +76 -56
- package/dist/test/bundle/cli-bundle.test.js.map +1 -1
- package/dist/test/bundle/token-wrapper.test.d.ts +2 -0
- package/dist/test/bundle/token-wrapper.test.d.ts.map +1 -0
- package/dist/test/bundle/token-wrapper.test.js +80 -0
- package/dist/test/bundle/token-wrapper.test.js.map +1 -0
- package/dist/test/e2e/cli-bundle.e2e.test.js +33 -68
- 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/actor-filtering.test.js +7 -0
- package/dist/test/unit/bin/actor-filtering.test.js.map +1 -1
- package/dist/test/unit/bin/actor-ids.test.d.ts +2 -0
- package/dist/test/unit/bin/actor-ids.test.d.ts.map +1 -0
- package/dist/test/unit/bin/actor-ids.test.js +40 -0
- package/dist/test/unit/bin/actor-ids.test.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 +224 -0
- package/dist/test/unit/bin/affected-actors-cli.test.js.map +1 -0
- package/dist/test/unit/bin/affected-actors.test.d.ts +2 -0
- package/dist/test/unit/bin/affected-actors.test.d.ts.map +1 -0
- package/dist/test/unit/bin/affected-actors.test.js +153 -0
- package/dist/test/unit/bin/affected-actors.test.js.map +1 -0
- package/dist/test/unit/bin/build-cli.test.d.ts +2 -0
- package/dist/test/unit/bin/build-cli.test.d.ts.map +1 -0
- package/dist/test/unit/bin/build-cli.test.js +49 -0
- package/dist/test/unit/bin/build-cli.test.js.map +1 -0
- package/dist/test/unit/bin/build-from-local.test.js +12 -0
- package/dist/test/unit/bin/build-from-local.test.js.map +1 -1
- package/dist/test/unit/bin/build.test.js +116 -6
- package/dist/test/unit/bin/build.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 +23 -0
- package/dist/test/unit/bin/compiled-cli.js.map +1 -0
- package/dist/test/unit/bin/diff-changes.test.js +168 -114
- 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 +67 -288
- package/dist/test/unit/bin/git.test.js.map +1 -1
- package/dist/test/unit/bin/notify.test.d.ts +2 -0
- package/dist/test/unit/bin/notify.test.d.ts.map +1 -0
- package/dist/test/unit/bin/notify.test.js +222 -0
- package/dist/test/unit/bin/notify.test.js.map +1 -0
- package/dist/test/unit/bin/stdin-input.test.d.ts +2 -0
- package/dist/test/unit/bin/stdin-input.test.d.ts.map +1 -0
- package/dist/test/unit/bin/stdin-input.test.js +92 -0
- package/dist/test/unit/bin/stdin-input.test.js.map +1 -0
- package/dist/test/unit/bin/test-cli.test.d.ts +2 -0
- package/dist/test/unit/bin/test-cli.test.d.ts.map +1 -0
- package/dist/test/unit/bin/test-cli.test.js +165 -0
- package/dist/test/unit/bin/test-cli.test.js.map +1 -0
- package/dist/test/unit/bin/test-files-glob.test.d.ts +2 -0
- package/dist/test/unit/bin/test-files-glob.test.d.ts.map +1 -0
- package/dist/test/unit/bin/test-files-glob.test.js +102 -0
- package/dist/test/unit/bin/test-files-glob.test.js.map +1 -0
- package/dist/test/unit/bin/test-report.test.d.ts +2 -0
- package/dist/test/unit/bin/test-report.test.d.ts.map +1 -0
- package/dist/test/unit/bin/test-report.test.js +100 -0
- package/dist/test/unit/bin/test-report.test.js.map +1 -0
- package/dist/test/unit/bin/utils/config/load-config.test.js +19 -1
- package/dist/test/unit/bin/utils/config/load-config.test.js.map +1 -1
- package/dist/test/unit/bin/utils/config/parser.test.js +36 -4
- package/dist/test/unit/bin/utils/config/parser.test.js.map +1 -1
- package/dist/test/unit/bin/utils/config/structures/grouped.test.js +6 -0
- package/dist/test/unit/bin/utils/config/structures/grouped.test.js.map +1 -1
- package/dist/test/unit/bin/utils/config/structures/legacy.test.js +1 -0
- package/dist/test/unit/bin/utils/config/structures/legacy.test.js.map +1 -1
- package/dist/test/unit/github-scripts/mask-config-secrets.test.d.ts +2 -0
- package/dist/test/unit/github-scripts/mask-config-secrets.test.d.ts.map +1 -0
- package/dist/test/unit/github-scripts/mask-config-secrets.test.js +50 -0
- package/dist/test/unit/github-scripts/mask-config-secrets.test.js.map +1 -0
- package/dist/test/unit/github-scripts/run-with-apify-tokens.test.d.ts +2 -0
- package/dist/test/unit/github-scripts/run-with-apify-tokens.test.d.ts.map +1 -0
- package/dist/test/unit/github-scripts/run-with-apify-tokens.test.js +102 -0
- package/dist/test/unit/github-scripts/run-with-apify-tokens.test.js.map +1 -0
- package/dist/test/unit/run-checks.test.d.ts +2 -0
- package/dist/test/unit/run-checks.test.d.ts.map +1 -0
- package/dist/test/unit/run-checks.test.js +62 -0
- package/dist/test/unit/run-checks.test.js.map +1 -0
- package/dist/test/unit/run-test-result.test.d.ts +2 -0
- package/dist/test/unit/run-test-result.test.d.ts.map +1 -0
- package/dist/test/unit/run-test-result.test.js +34 -0
- package/dist/test/unit/run-test-result.test.js.map +1 -0
- package/dist/test/unit/should-built-and-test.test.js +41 -38
- package/dist/test/unit/should-built-and-test.test.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/workflow-scripts-src/run-with-apify-tokens.d.ts +3 -0
- package/dist/workflow-scripts-src/run-with-apify-tokens.d.ts.map +1 -0
- package/dist/workflow-scripts-src/run-with-apify-tokens.js +100 -0
- package/dist/workflow-scripts-src/run-with-apify-tokens.js.map +1 -0
- package/docs/cli.md +473 -0
- package/docs/lib.md +276 -0
- package/docs/workflows.md +455 -0
- package/eslint.config.mjs +10 -1
- package/lib/extend-expect.ts +48 -258
- package/lib/lib.ts +25 -34
- package/lib/run-checks.ts +101 -0
- package/lib/run-test-result.ts +45 -55
- package/package.json +4 -2
- package/platform-tests-investigate-and-fix/skills/assess-impact/SKILL.md +42 -0
- package/platform-tests-investigate-and-fix/skills/measure-flakiness/SKILL.md +4 -2
- package/test/bundle/cli-bundle.test.ts +97 -67
- package/test/bundle/token-wrapper.test.ts +110 -0
- package/test/e2e/cli-bundle.e2e.test.ts +60 -93
- package/test/e2e/git-build-release.e2e.test.ts +113 -0
- package/test/e2e/helpers.ts +82 -0
- package/test/unit/bin/actor-filtering.test.ts +8 -0
- package/test/unit/bin/actor-ids.test.ts +47 -0
- package/test/unit/bin/affected-actors-cli.test.ts +271 -0
- package/test/unit/bin/affected-actors.test.ts +221 -0
- package/test/unit/bin/build-cli.test.ts +61 -0
- package/test/unit/bin/build-from-local.test.ts +16 -0
- package/test/unit/bin/build.test.ts +149 -5
- package/test/unit/bin/compiled-cli.ts +23 -0
- package/test/unit/bin/diff-changes.test.ts +181 -114
- package/test/unit/bin/diff.test.ts +25 -28
- package/test/unit/bin/git.test.ts +76 -361
- package/test/unit/bin/notify.test.ts +299 -0
- package/test/unit/bin/stdin-input.test.ts +120 -0
- package/test/unit/bin/test-cli.test.ts +207 -0
- package/test/unit/bin/test-files-glob.test.ts +118 -0
- package/test/unit/bin/test-report.test.ts +118 -0
- package/test/unit/bin/utils/config/load-config.test.ts +26 -1
- package/test/unit/bin/utils/config/parser.test.ts +46 -5
- package/test/unit/bin/utils/config/structures/grouped.test.ts +12 -0
- package/test/unit/bin/utils/config/structures/legacy.test.ts +1 -0
- package/test/unit/github-scripts/mask-config-secrets.test.ts +61 -0
- package/test/unit/github-scripts/run-with-apify-tokens.test.ts +115 -0
- package/test/unit/run-checks.test.ts +76 -0
- package/test/unit/run-test-result.test.ts +44 -0
- package/test/unit/should-built-and-test.test.ts +46 -39
- package/tsconfig.json +1 -1
- package/vitest.config.ts +9 -0
- package/workflow-scripts-src/run-with-apify-tokens.ts +112 -0
- package/.github/scripts/check-major-tag-refs.mjs +0 -72
- package/dist/test/unit/bin/logging.test.d.ts +0 -2
- package/dist/test/unit/bin/logging.test.d.ts.map +0 -1
- package/dist/test/unit/bin/logging.test.js +0 -43
- package/dist/test/unit/bin/logging.test.js.map +0 -1
- package/dist/test/unit/bin/slack.test.d.ts +0 -2
- package/dist/test/unit/bin/slack.test.d.ts.map +0 -1
- package/dist/test/unit/bin/slack.test.js +0 -54
- package/dist/test/unit/bin/slack.test.js.map +0 -1
- package/test/unit/bin/logging.test.ts +0 -52
- package/test/unit/bin/slack.test.ts +0 -65
package/docs/lib.md
ADDED
|
@@ -0,0 +1,276 @@
|
|
|
1
|
+
# Vitest library API
|
|
2
|
+
|
|
3
|
+
```ts
|
|
4
|
+
import { describe, testActor, testStandbyActor, RunTestResult, ExpectStatic } from 'apify-test-tools';
|
|
5
|
+
```
|
|
6
|
+
|
|
7
|
+
Requires `vitest` `3.2.4` or later as a peer dependency.
|
|
8
|
+
|
|
9
|
+
## Environment variables
|
|
10
|
+
|
|
11
|
+
The library reads these when the test file is loaded:
|
|
12
|
+
|
|
13
|
+
| Variable | Description |
|
|
14
|
+
| -------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
|
|
15
|
+
| `TESTER_APIFY_TOKEN` | Token the tests start runs and read their data with. Without it, every `describe` block is skipped, so a plain `npm test` stays unaffected. |
|
|
16
|
+
| `ACTOR_BUILDS` | JSON array of Actors to test, e.g. the builds the CLI's [`build`](cli.md#building-actors-build) and [`build-from-local`](cli.md#build-from-local-source-build-from-local) print. Only tests of Actors listed here run, against the listed build, or the default build for an Actor listed without one. |
|
|
17
|
+
|
|
18
|
+
`ACTOR_BUILDS` entries look like this, and are matched to tests by `actorFullName` or `actorRawId`:
|
|
19
|
+
|
|
20
|
+
```json
|
|
21
|
+
[{ "buildId": "...", "actorRawId": "...", "buildNumber": "1.2.3", "actorFullName": "john.doe/my-actor" }]
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
## `describe(name, fn, options?)`
|
|
25
|
+
|
|
26
|
+
Same as vitest's `describe`, but skipped unless `TESTER_APIFY_TOKEN` is set. Its tests
|
|
27
|
+
run concurrently by default. Use it instead of vitest's `describe` for platform tests.
|
|
28
|
+
|
|
29
|
+
## `testActor(actorId, testName, fn, options?)`
|
|
30
|
+
|
|
31
|
+
Registers a test for an Actor. `actorId` is the Actor's full name (`owner/name`) or its raw platform ID. The test
|
|
32
|
+
only runs when the Actor is in `ACTOR_BUILDS`. Its name is
|
|
33
|
+
`<actorId>: <testName>`.
|
|
34
|
+
|
|
35
|
+
`fn` gets the vitest test context, with `expect` extended by the [custom matchers](#custom-matchers), and a `run`
|
|
36
|
+
function.
|
|
37
|
+
|
|
38
|
+
`expect` is soft: a failed assertion marks the test as failed but the test keeps going, so one run reports every
|
|
39
|
+
failed check at once. Use `expect.hard(...)` for an assertion that must stop the test, e.g. before indexing into a
|
|
40
|
+
list that may be empty.
|
|
41
|
+
|
|
42
|
+
```ts
|
|
43
|
+
import { describe, testActor } from 'apify-test-tools';
|
|
44
|
+
|
|
45
|
+
describe('test', () => {
|
|
46
|
+
testActor(actorId, 'actor test 1', async ({ expect, run }) => {
|
|
47
|
+
const runResult = await run({ input });
|
|
48
|
+
|
|
49
|
+
// your checks
|
|
50
|
+
});
|
|
51
|
+
|
|
52
|
+
testActor(actorId, 'actor test 2', async ({ expect, run }) => {
|
|
53
|
+
const runResult = await run({ input });
|
|
54
|
+
|
|
55
|
+
// your checks
|
|
56
|
+
});
|
|
57
|
+
});
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
### Test options
|
|
61
|
+
|
|
62
|
+
The fourth argument takes vitest's test options:
|
|
63
|
+
|
|
64
|
+
| Option | Default |
|
|
65
|
+
| ------------ | ------- |
|
|
66
|
+
| `timeout` | 1 hour |
|
|
67
|
+
| `retry` | `1` |
|
|
68
|
+
| `concurrent` | `true` |
|
|
69
|
+
|
|
70
|
+
```ts
|
|
71
|
+
testActor(
|
|
72
|
+
actorId,
|
|
73
|
+
'slow actor test',
|
|
74
|
+
async ({ expect, run }) => {
|
|
75
|
+
const runResult = await run({ input });
|
|
76
|
+
await expect(runResult).toFinishWith({ datasetItemCount: 100 });
|
|
77
|
+
},
|
|
78
|
+
{
|
|
79
|
+
timeout: 2 * 60 * 60 * 1000, // 2 hours
|
|
80
|
+
retry: 3,
|
|
81
|
+
},
|
|
82
|
+
);
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
### `run(options)`
|
|
86
|
+
|
|
87
|
+
Starts the Actor, waits for the run to finish, and returns a [`RunTestResult`](#runtestresult). It runs the build
|
|
88
|
+
from `ACTOR_BUILDS`, or the Actor's default build when it isn't listed there. Before returning, it waits 20 seconds
|
|
89
|
+
for the run's dataset and statistics to sync, since the platform is only eventually consistent. The run's Console
|
|
90
|
+
link is added to the test as a vitest annotation.
|
|
91
|
+
|
|
92
|
+
| Option | Description |
|
|
93
|
+
| ---------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
94
|
+
| `input` | Actor input |
|
|
95
|
+
| `prefilledInput` | When `true`, `input` is merged on top of the Actor's prefilled input |
|
|
96
|
+
| `options` | [Actor call options](https://docs.apify.com/api/client/js/reference/interface/ActorCallOptions) like `memory`. `timeout` is in seconds and defaults to the Actor's default run timeout, at most 59 minutes, so the run finishes before the test times out |
|
|
97
|
+
| `runId` | Don't start a run; return this existing run instead. Every other option is ignored |
|
|
98
|
+
|
|
99
|
+
#### Using prefilled input
|
|
100
|
+
|
|
101
|
+
```ts
|
|
102
|
+
testActor(actorId, 'with prefilled input', async ({ expect, run }) => {
|
|
103
|
+
const runResult = await run({
|
|
104
|
+
prefilledInput: true,
|
|
105
|
+
input: { maxItems: 10 }, // merged on top of the prefilled input
|
|
106
|
+
});
|
|
107
|
+
await expect(runResult).toFinishWith({ datasetItemCount: 10 });
|
|
108
|
+
});
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
#### Testing an existing run
|
|
112
|
+
|
|
113
|
+
Useful for iterating on the checks of a test without waiting for a new run:
|
|
114
|
+
|
|
115
|
+
```ts
|
|
116
|
+
testActor(actorId, 'validate existing run', async ({ expect, run }) => {
|
|
117
|
+
const runResult = await run({ runId: 'some-run-id' });
|
|
118
|
+
await expect(runResult).toFinishWith({ datasetItemCount: 100 });
|
|
119
|
+
});
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
## `testStandbyActor(actorId, testName, fn, options?)`
|
|
123
|
+
|
|
124
|
+
Same as `testActor`, for Actors in standby mode. It creates a temporary task with the build from `ACTOR_BUILDS` (or
|
|
125
|
+
the Actor's standby build) and deletes it after the test. Instead of `run`, `fn` gets `callStandby`, which sends a
|
|
126
|
+
`POST` request with `input` as the JSON body to the task's standby URL, plus `path`, and returns
|
|
127
|
+
`{ data, status, headers }`, where `data` is the parsed JSON response.
|
|
128
|
+
|
|
129
|
+
```ts
|
|
130
|
+
import { describe, testStandbyActor } from 'apify-test-tools';
|
|
131
|
+
|
|
132
|
+
describe('standby tests', () => {
|
|
133
|
+
testStandbyActor(actorId, 'standby request', async ({ expect, callStandby }) => {
|
|
134
|
+
const { data, status } = await callStandby({
|
|
135
|
+
input: { query: 'test' },
|
|
136
|
+
path: '/search',
|
|
137
|
+
headers: { 'Content-Type': 'application/json' },
|
|
138
|
+
});
|
|
139
|
+
|
|
140
|
+
expect(status).toBe(200);
|
|
141
|
+
expect(data.results).toBeNonEmptyArray();
|
|
142
|
+
});
|
|
143
|
+
});
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
It fails if the Actor doesn't support standby mode.
|
|
147
|
+
|
|
148
|
+
## `RunTestResult`
|
|
149
|
+
|
|
150
|
+
What `run` returns. Every getter fetches its data on the first call and returns the same result afterwards, so you
|
|
151
|
+
can call them freely.
|
|
152
|
+
|
|
153
|
+
| Member | Returns |
|
|
154
|
+
| -------------------------- | -------------------------------------------------------------------------------------------------------- |
|
|
155
|
+
| `id` | The run ID |
|
|
156
|
+
| `status` | The run status when it finished |
|
|
157
|
+
| `getDataset<T>()` | `{ items: T[] }`, every item of the default dataset |
|
|
158
|
+
| `getLog()` | The run log as a string |
|
|
159
|
+
| `getStatistics()` | The crawler statistics from the `SDK_CRAWLER_STATISTICS_0` record, or `undefined` for non-crawler Actors |
|
|
160
|
+
| `getInput<T>()` | The `INPUT` record of the default key-value store |
|
|
161
|
+
| `getKeyValueStoreClient()` | An `apify-client` client for the default key-value store |
|
|
162
|
+
| `getRunInfo()` | The run object, fetched again so it reflects changes after the run finished |
|
|
163
|
+
|
|
164
|
+
```ts
|
|
165
|
+
testActor(actorId, 'check dataset items', async ({ expect, run }) => {
|
|
166
|
+
const runResult = await run({ input });
|
|
167
|
+
|
|
168
|
+
const { items } = await runResult.getDataset();
|
|
169
|
+
expect(items[0].title).toBeNonEmptyString();
|
|
170
|
+
|
|
171
|
+
const log = await runResult.getLog();
|
|
172
|
+
expect(log).toContain('Crawl finished');
|
|
173
|
+
|
|
174
|
+
const stats = await runResult.getStatistics();
|
|
175
|
+
expect(stats?.requestsFinished).toBeGreaterThan(0);
|
|
176
|
+
|
|
177
|
+
const kvs = runResult.getKeyValueStoreClient();
|
|
178
|
+
const record = await kvs.getRecord('OUTPUT');
|
|
179
|
+
|
|
180
|
+
const runInfo = await runResult.getRunInfo();
|
|
181
|
+
});
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
## `toFinishWith(options)`
|
|
185
|
+
|
|
186
|
+
Validates the common run properties in a single call and reports every failed check at once. Only
|
|
187
|
+
`datasetItemCount` is required; the rest have defaults. Numeric checks take an exact number or a range: `{ min }`,
|
|
188
|
+
`{ max }` or `{ min, max }`. Set a check with a default to `null` to skip it.
|
|
189
|
+
|
|
190
|
+
| Option | Default | Checks |
|
|
191
|
+
| ---------------------- | --------------------------------- | ------------------------------------------------------------------------------------------------ |
|
|
192
|
+
| `datasetItemCount` | required | Number of items in the default dataset |
|
|
193
|
+
| `status` | `'SUCCEEDED'` | Run status |
|
|
194
|
+
| `duration` | `{ min: 600, max: 600_000 }` | Run duration in milliseconds (0.6 s to 10 min) |
|
|
195
|
+
| `failedRequests` | `0` | Failed requests in the crawler statistics |
|
|
196
|
+
| `requestsRetries` | `{ max: 3 }` | Request retries in the crawler statistics |
|
|
197
|
+
| `maxRetriesPerRequest` | `null` | The most retries any single request needed |
|
|
198
|
+
| `forbiddenLogs` | `['ReferenceError', 'TypeError']` | Strings that must not appear in the log |
|
|
199
|
+
| `chargedEventCounts` | not checked | Pay-per-event counts, per event name. An event you omit is expected to have been charged 0 times |
|
|
200
|
+
|
|
201
|
+
`failedRequests` and `requestsRetries` come from the crawler statistics, so they fail for an Actor that doesn't
|
|
202
|
+
write them. Set both to `null` for Actors that don't use a Crawlee crawler.
|
|
203
|
+
|
|
204
|
+
```ts
|
|
205
|
+
await expect(runResult).toFinishWith({
|
|
206
|
+
datasetItemCount: { min: 80, max: 120 },
|
|
207
|
+
duration: { max: 30 * 60 * 1000 },
|
|
208
|
+
chargedEventCounts: {
|
|
209
|
+
'actor-start': 1,
|
|
210
|
+
'place-scraped': { min: 80, max: 120 },
|
|
211
|
+
},
|
|
212
|
+
});
|
|
213
|
+
```
|
|
214
|
+
|
|
215
|
+
## Custom matchers
|
|
216
|
+
|
|
217
|
+
`expect` in `testActor` and `testStandbyActor` is extended with:
|
|
218
|
+
|
|
219
|
+
- `toBeArray()` / `toBeEmptyArray()` / `toBeNonEmptyArray()`
|
|
220
|
+
- `toBeString()` / `toBeNonEmptyString()` / `toStartWith(prefix)`
|
|
221
|
+
- `toBeNumber()` / `toBeWholeNumber()` / `toBeWithinRange(min, max)`
|
|
222
|
+
- `toBeBoolean()` / `toBeTrue()` / `toBeFalse()`
|
|
223
|
+
- `toBeObject()` / `toBeNonEmptyObject()`
|
|
224
|
+
- [`toFinishWith(options)`](#tofinishwithoptions)
|
|
225
|
+
|
|
226
|
+
Pass a message as the second argument of `expect` to say what failed:
|
|
227
|
+
|
|
228
|
+
```ts
|
|
229
|
+
expect(place.title, `London Eye's title`).toEqual('lastminute.com London Eye');
|
|
230
|
+
```
|
|
231
|
+
|
|
232
|
+
### Custom validation functions
|
|
233
|
+
|
|
234
|
+
Wrap shared checks in your own functions, e.g. in `test/platform/utils.ts`, and pass them `expect`. Use the
|
|
235
|
+
`ExpectStatic` type so the custom matchers type-check:
|
|
236
|
+
|
|
237
|
+
```ts
|
|
238
|
+
import { ExpectStatic } from 'apify-test-tools';
|
|
239
|
+
|
|
240
|
+
export const validateItem = (expect: ExpectStatic, item: any) => {
|
|
241
|
+
expect(item.title, 'Item title').toBeString();
|
|
242
|
+
};
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
## Running tests locally
|
|
246
|
+
|
|
247
|
+
Run every command from the root of the Actor repository.
|
|
248
|
+
|
|
249
|
+
**Against the current default builds.** Enough when you only change the tests. List the Actors with
|
|
250
|
+
[`get-actor-configs`](cli.md#listing-actors-get-actor-configs), all of them or a few with `--actors`, and pass them to
|
|
251
|
+
[`test`](cli.md#running-tests-test), which tests each on its default build:
|
|
252
|
+
|
|
253
|
+
```bash
|
|
254
|
+
npx apify-test-tools get-actor-configs --actors john.doe/my-actor | TESTER_APIFY_TOKEN=<token> npx apify-test-tools test
|
|
255
|
+
```
|
|
256
|
+
|
|
257
|
+
This also runs a test that reuses an existing run with [`runId`](#testing-an-existing-run), as long as its Actor is
|
|
258
|
+
listed.
|
|
259
|
+
|
|
260
|
+
**Against builds of your changes.** Build the Actors with the CLI, either from local files with
|
|
261
|
+
[`build-from-local`](cli.md#build-from-local-source-build-from-local) or from a pushed branch with
|
|
262
|
+
[`build`](cli.md#building-actors-build), and pass the output to [`test`](cli.md#running-tests-test):
|
|
263
|
+
|
|
264
|
+
```bash
|
|
265
|
+
APIFY_TOKEN_JOHN_DOE=<token> npx apify-test-tools build-from-local --actors john.doe/my-actor > builds.json
|
|
266
|
+
|
|
267
|
+
TESTER_APIFY_TOKEN=<token> npx apify-test-tools test < builds.json
|
|
268
|
+
```
|
|
269
|
+
|
|
270
|
+
`test` passes the builds to vitest as `ACTOR_BUILDS`, so plain vitest works too:
|
|
271
|
+
`ACTOR_BUILDS="$(cat builds.json)" TESTER_APIFY_TOKEN=<token> npx vitest run test/platform`.
|
|
272
|
+
|
|
273
|
+
You can change the tests and re-run them against the same builds.
|
|
274
|
+
|
|
275
|
+
`TESTER_APIFY_TOKEN` can be the token of any account with enough memory for the runs. To run only some tests, pass a specific file instead of `test/platform`, or filter by
|
|
276
|
+
name with vitest's `-t <name>` when running vitest directly. See [Running locally](cli.md#running-locally) for the full flow.
|