Skip to content

Commit 90e3d40

Browse files
authored
feat(runtime): add test context hooks (#125)
## Summary - add a minimal runtime test context with `task` metadata for tests and per-test hooks - support Vitest-style `ctx.skip()`, `ctx.onTestFinished()`, and `ctx.onTestFailed()` with behavior covered by runner tests - stabilize the runtime test environment by removing a redundant URL polyfill import in `getWSServer` and simplifying the symbolicate mock used by runner-context tests ## Testing - pnpm nx lint runtime - pnpm nx typecheck runtime - pnpm nx test runtime
1 parent caab9c3 commit 90e3d40

20 files changed

Lines changed: 846 additions & 42 deletions

File tree

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
__default__: patch
3+
---
4+
5+
Harness test callbacks now consistently receive a `HarnessTestContext` in `test`, `it`, `beforeEach`, and `afterEach`, exposing task metadata, dynamic skipping with `context.skip(...)`, and per-test `onTestFinished` / `onTestFailed` lifecycle hooks.

apps/playground/rn-harness.config.mjs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ export default {
7979
}),
8080
applePlatform({
8181
name: 'ios',
82-
device: appleSimulator('iPhone 17 Pro', '26.2'),
82+
device: appleSimulator('iPhone 17 Pro', '26.4'),
8383
bundleId: 'com.harnessplayground',
8484
}),
8585
applePlatform({

apps/playground/src/__tests__/smoke.harness.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,4 +4,17 @@ describe('Smoke test', () => {
44
test('should run a simple test', () => {
55
expect(1 + 1).toBe(2);
66
});
7+
8+
test('should expose task context to tests', (context) => {
9+
expect(context).toBeDefined();
10+
expect(context.task.type).toBe('test');
11+
expect(context.task.mode).toBe('run');
12+
expect(context.task.file.name).toBe('src/__tests__/smoke.harness.ts');
13+
expect(context.task.suite.name).toBe('Smoke test');
14+
expect(context.task.name).toBe('should expose task context to tests');
15+
});
16+
17+
test('should report dynamic skips as skipped', (context) => {
18+
context.skip('skip from test context');
19+
});
720
});

packages/bridge/src/shared.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,13 @@ export type {
8181
TestSuite,
8282
TestCase,
8383
CollectionResult,
84+
TestFn,
85+
SuiteHookFn,
8486
} from './shared/test-collector.js';
87+
export type {
88+
HarnessTaskContext,
89+
HarnessTestContext,
90+
} from './shared/test-context.js';
8591
export type {
8692
TestRunnerEvents,
8793
TestRunnerFileStartedEvent,

packages/bridge/src/shared/test-collector.ts

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,10 @@
1+
import type { HarnessTestContext } from './test-context.js';
2+
13
export type TestStatus = 'active' | 'skipped' | 'todo';
24

3-
export type TestFn = () => void | Promise<void>;
5+
export type TestFn = (context: HarnessTestContext) => void | Promise<void>;
6+
7+
export type SuiteHookFn = () => void | Promise<void>;
48

59
export type TestCase = {
610
name: string;
@@ -13,8 +17,8 @@ export type TestSuite = {
1317
tests: TestCase[];
1418
suites: TestSuite[];
1519
parent?: TestSuite;
16-
beforeAll: TestFn[];
17-
afterAll: TestFn[];
20+
beforeAll: SuiteHookFn[];
21+
afterAll: SuiteHookFn[];
1822
beforeEach: TestFn[];
1923
afterEach: TestFn[];
2024
status?: TestStatus;
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
export type HarnessTaskContext = {
2+
name: string;
3+
type: 'test';
4+
mode: 'run' | 'skip' | 'todo';
5+
file: {
6+
name: string;
7+
};
8+
suite: {
9+
name: string;
10+
};
11+
};
12+
13+
export type HarnessTestContext = {
14+
task: HarnessTaskContext;
15+
onTestFailed: (fn: () => void | Promise<void>) => void;
16+
onTestFinished: (fn: () => void | Promise<void>) => void;
17+
skip: {
18+
(note?: string): never;
19+
(condition: boolean, note?: string): void;
20+
};
21+
};

packages/coverage-ios/tsconfig.json

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33
"files": [],
44
"include": [],
55
"references": [
6+
{
7+
"path": "../config"
8+
},
69
{
710
"path": "./tsconfig.lib.json"
811
}

packages/coverage-ios/tsconfig.lib.json

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,5 +10,10 @@
1010
"types": ["node"],
1111
"lib": ["DOM", "ES2022"]
1212
},
13-
"include": ["src/**/*.ts"]
13+
"include": ["src/**/*.ts"],
14+
"references": [
15+
{
16+
"path": "../config/tsconfig.lib.json"
17+
}
18+
]
1419
}

0 commit comments

Comments
 (0)