@react-native-harness/jest 1.4.0 → 1.5.0

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.
Files changed (133) hide show
  1. package/dist/execute-run.d.ts.map +1 -1
  2. package/dist/execute-run.js +2 -1
  3. package/dist/harness-session.d.ts.map +1 -1
  4. package/dist/harness-session.js +74 -30
  5. package/dist/resource-lock.d.ts.map +1 -1
  6. package/dist/resource-lock.js +12 -2
  7. package/dist/toJestStatus.d.ts +4 -0
  8. package/dist/toJestStatus.d.ts.map +1 -0
  9. package/dist/toJestStatus.js +2 -0
  10. package/dist/toTestResult.d.ts +3 -2
  11. package/dist/toTestResult.d.ts.map +1 -1
  12. package/dist/toTestResult.js +2 -1
  13. package/package.json +8 -8
  14. package/src/execute-run.ts +2 -1
  15. package/src/harness-session.ts +86 -27
  16. package/src/resource-lock.ts +15 -2
  17. package/src/toJestStatus.ts +6 -0
  18. package/src/toTestResult.ts +5 -3
  19. package/dist/__tests__/bridge.test.d.ts +0 -2
  20. package/dist/__tests__/bridge.test.d.ts.map +0 -1
  21. package/dist/__tests__/bridge.test.js +0 -167
  22. package/dist/__tests__/client-log-handler.test.d.ts +0 -2
  23. package/dist/__tests__/client-log-handler.test.d.ts.map +0 -1
  24. package/dist/__tests__/client-log-handler.test.js +0 -306
  25. package/dist/__tests__/crash-monitor.test.d.ts +0 -2
  26. package/dist/__tests__/crash-monitor.test.d.ts.map +0 -1
  27. package/dist/__tests__/crash-monitor.test.js +0 -230
  28. package/dist/__tests__/crash-supervisor.test.d.ts +0 -2
  29. package/dist/__tests__/crash-supervisor.test.d.ts.map +0 -1
  30. package/dist/__tests__/crash-supervisor.test.js +0 -151
  31. package/dist/__tests__/environment-reset.test.d.ts +0 -2
  32. package/dist/__tests__/environment-reset.test.d.ts.map +0 -1
  33. package/dist/__tests__/environment-reset.test.js +0 -238
  34. package/dist/__tests__/errors.test.d.ts +0 -2
  35. package/dist/__tests__/errors.test.d.ts.map +0 -1
  36. package/dist/__tests__/errors.test.js +0 -98
  37. package/dist/__tests__/execute-run.test.d.ts +0 -2
  38. package/dist/__tests__/execute-run.test.d.ts.map +0 -1
  39. package/dist/__tests__/execute-run.test.js +0 -639
  40. package/dist/__tests__/fixtures/mock-platform-runner.d.ts +0 -7
  41. package/dist/__tests__/fixtures/mock-platform-runner.d.ts.map +0 -1
  42. package/dist/__tests__/fixtures/mock-platform-runner.js +0 -6
  43. package/dist/__tests__/format-harness-error.test.d.ts +0 -2
  44. package/dist/__tests__/format-harness-error.test.d.ts.map +0 -1
  45. package/dist/__tests__/format-harness-error.test.js +0 -27
  46. package/dist/__tests__/harness-cache.test.d.ts +0 -2
  47. package/dist/__tests__/harness-cache.test.d.ts.map +0 -1
  48. package/dist/__tests__/harness-cache.test.js +0 -72
  49. package/dist/__tests__/harness-session-signal.test.d.ts +0 -2
  50. package/dist/__tests__/harness-session-signal.test.d.ts.map +0 -1
  51. package/dist/__tests__/harness-session-signal.test.js +0 -298
  52. package/dist/__tests__/harness-session.test.d.ts +0 -2
  53. package/dist/__tests__/harness-session.test.d.ts.map +0 -1
  54. package/dist/__tests__/harness-session.test.js +0 -233
  55. package/dist/__tests__/harness.test.d.ts +0 -2
  56. package/dist/__tests__/harness.test.d.ts.map +0 -1
  57. package/dist/__tests__/harness.test.js +0 -636
  58. package/dist/__tests__/hook-queue.test.d.ts +0 -2
  59. package/dist/__tests__/hook-queue.test.d.ts.map +0 -1
  60. package/dist/__tests__/hook-queue.test.js +0 -56
  61. package/dist/__tests__/index.test.d.ts +0 -2
  62. package/dist/__tests__/index.test.d.ts.map +0 -1
  63. package/dist/__tests__/index.test.js +0 -150
  64. package/dist/__tests__/metro-port.test.d.ts +0 -2
  65. package/dist/__tests__/metro-port.test.d.ts.map +0 -1
  66. package/dist/__tests__/metro-port.test.js +0 -54
  67. package/dist/__tests__/resource-lock.test.d.ts +0 -2
  68. package/dist/__tests__/resource-lock.test.d.ts.map +0 -1
  69. package/dist/__tests__/resource-lock.test.js +0 -138
  70. package/dist/__tests__/run.test.d.ts +0 -2
  71. package/dist/__tests__/run.test.d.ts.map +0 -1
  72. package/dist/__tests__/run.test.js +0 -48
  73. package/dist/__tests__/test-file-platform-filter.test.d.ts +0 -2
  74. package/dist/__tests__/test-file-platform-filter.test.d.ts.map +0 -1
  75. package/dist/__tests__/test-file-platform-filter.test.js +0 -47
  76. package/dist/cli-args.test.d.ts +0 -2
  77. package/dist/cli-args.test.d.ts.map +0 -1
  78. package/dist/cli-args.test.js +0 -1
  79. package/dist/crash-supervisor.d.ts +0 -21
  80. package/dist/crash-supervisor.d.ts.map +0 -1
  81. package/dist/crash-supervisor.js +0 -210
  82. package/dist/diagnostics/__tests__/derivers.test.d.ts +0 -2
  83. package/dist/diagnostics/__tests__/derivers.test.d.ts.map +0 -1
  84. package/dist/diagnostics/__tests__/derivers.test.js +0 -248
  85. package/dist/diagnostics/__tests__/report.test.d.ts +0 -2
  86. package/dist/diagnostics/__tests__/report.test.d.ts.map +0 -1
  87. package/dist/diagnostics/__tests__/report.test.js +0 -97
  88. package/dist/event-mapper.d.ts +0 -16
  89. package/dist/event-mapper.d.ts.map +0 -1
  90. package/dist/event-mapper.js +0 -120
  91. package/dist/global-setup.d.ts +0 -3
  92. package/dist/global-setup.d.ts.map +0 -1
  93. package/dist/global-setup.js +0 -60
  94. package/dist/global-teardown.d.ts +0 -3
  95. package/dist/global-teardown.d.ts.map +0 -1
  96. package/dist/global-teardown.js +0 -11
  97. package/dist/harness-reporter.d.ts +0 -8
  98. package/dist/harness-reporter.d.ts.map +0 -1
  99. package/dist/harness-reporter.js +0 -12
  100. package/dist/harness.d.ts +0 -47
  101. package/dist/harness.d.ts.map +0 -1
  102. package/dist/harness.js +0 -619
  103. package/dist/jest-options.d.ts +0 -2
  104. package/dist/jest-options.d.ts.map +0 -1
  105. package/dist/jest-options.js +0 -1
  106. package/dist/setup.d.ts +0 -3
  107. package/dist/setup.d.ts.map +0 -1
  108. package/dist/setup.js +0 -80
  109. package/dist/teardown.d.ts +0 -3
  110. package/dist/teardown.d.ts.map +0 -1
  111. package/dist/teardown.js +0 -10
  112. package/dist/tsconfig.lib.tsbuildinfo +0 -1
  113. package/dist/types.d.ts +0 -17
  114. package/dist/types.d.ts.map +0 -1
  115. package/dist/types.js +0 -1
  116. package/src/__tests__/bridge.test.ts +0 -224
  117. package/src/__tests__/client-log-handler.test.ts +0 -364
  118. package/src/__tests__/crash-monitor.test.ts +0 -323
  119. package/src/__tests__/environment-reset.test.ts +0 -308
  120. package/src/__tests__/errors.test.ts +0 -157
  121. package/src/__tests__/execute-run.test.ts +0 -849
  122. package/src/__tests__/format-harness-error.test.ts +0 -32
  123. package/src/__tests__/harness-cache.test.ts +0 -91
  124. package/src/__tests__/harness-session.test.ts +0 -303
  125. package/src/__tests__/hook-queue.test.ts +0 -77
  126. package/src/__tests__/index.test.ts +0 -221
  127. package/src/__tests__/metro-port.test.ts +0 -63
  128. package/src/__tests__/resource-lock.test.ts +0 -179
  129. package/src/__tests__/run.test.ts +0 -74
  130. package/src/__tests__/test-file-platform-filter.test.ts +0 -83
  131. package/src/diagnostics/__tests__/derivers.test.ts +0 -300
  132. package/src/diagnostics/__tests__/report.test.ts +0 -128
  133. package/tsconfig.tsbuildinfo +0 -1
package/dist/harness.js DELETED
@@ -1,619 +0,0 @@
1
- import { getBridgeServer, } from '@react-native-harness/bridge/server';
2
- import { HARNESS_BRIDGE_PATH, } from '@react-native-harness/bridge';
3
- import { getMetroInstance, isMetroCacheReusable, waitForMetroBackedAppReady, } from '@react-native-harness/bundler-metro';
4
- import { createHarnessPluginManager, } from '@react-native-harness/plugins';
5
- import { logger, createCrashArtifactWriter, getTimeoutSignal, raceAbortSignals, } from '@react-native-harness/tools';
6
- import { PlatformReadyTimeoutError } from './errors.js';
7
- import { createCrashSupervisor, } from './crash-supervisor.js';
8
- import { createClientLogListener } from './client-log-handler.js';
9
- import path from 'node:path';
10
- import { logMetroCacheReused, logMetroPortFallback, logRunnerStarting, logRunnerStillWaitingInQueue, logRunnerWaitingInQueue, } from './logs.js';
11
- import { createResourceLockManager } from './resource-lock.js';
12
- import { resolveHarnessMetroPort } from './metro-port.js';
13
- const harnessLogger = logger.child('runtime');
14
- const resourceLockManager = createResourceLockManager();
15
- export const maybeLogMetroCacheReuse = (config, platform, projectRoot) => {
16
- if (config.unstable__enableMetroCache && isMetroCacheReusable(projectRoot)) {
17
- logMetroCacheReused(platform);
18
- }
19
- };
20
- const createAbortError = () => new DOMException('The operation was aborted', 'AbortError');
21
- const getDefaultResourceLockKey = (platform) => `${platform.platformId}:${platform.name}`;
22
- const waitForAbort = (signal) => {
23
- if (signal.aborted) {
24
- return Promise.reject(signal.reason ?? createAbortError());
25
- }
26
- return new Promise((_, reject) => {
27
- signal.addEventListener('abort', () => {
28
- reject(signal.reason ?? createAbortError());
29
- }, { once: true });
30
- });
31
- };
32
- const withPlatformReadyTimeout = async (options) => {
33
- const timeoutSignal = getTimeoutSignal(options.timeout);
34
- const combinedSignal = raceAbortSignals([options.signal, timeoutSignal]);
35
- try {
36
- return await options.work(combinedSignal);
37
- }
38
- catch (error) {
39
- if (error instanceof DOMException &&
40
- error.name === 'AbortError' &&
41
- timeoutSignal.aborted &&
42
- !options.signal.aborted) {
43
- throw new PlatformReadyTimeoutError(options.timeout);
44
- }
45
- throw error;
46
- }
47
- };
48
- export const waitForAppReady = async (options) => {
49
- const { metroInstance, serverBridge, platformInstance, platformId, bundleStartTimeout, readyTimeout, maxAppRestarts, testFilePath, crashSupervisor, appLaunchOptions, launchApp = () => platformInstance.restartApp(appLaunchOptions), } = options;
50
- const signal = options.signal ?? new AbortController().signal;
51
- const logWait = (message, ...args) => {
52
- harnessLogger.debug(`waitForAppReady: ${message}`, ...args);
53
- };
54
- return await waitForMetroBackedAppReady({
55
- metro: metroInstance,
56
- platformId,
57
- bundleStartTimeout,
58
- readyTimeout,
59
- maxAppRestarts,
60
- signal,
61
- startAttempt: async () => {
62
- logWait('launching app for %s', testFilePath);
63
- await launchApp();
64
- logWait('launch request completed, waiting for bridge ready');
65
- },
66
- waitForReady: async (signal) => {
67
- logWait('waiting for runtime ready');
68
- return await Promise.race([
69
- new Promise((resolve) => {
70
- const onReady = () => {
71
- cleanup();
72
- crashSupervisor.markReady();
73
- logWait('runtime ready received');
74
- resolve();
75
- };
76
- const onAbort = () => {
77
- cleanup();
78
- };
79
- const cleanup = () => {
80
- serverBridge.off('ready', onReady);
81
- signal.removeEventListener('abort', onAbort);
82
- };
83
- serverBridge.on('ready', onReady);
84
- signal.addEventListener('abort', onAbort, { once: true });
85
- }),
86
- waitForAbort(signal),
87
- ]);
88
- },
89
- waitForCrash: async (signal) => {
90
- try {
91
- logWait('waiting for crash or runtime ready');
92
- return await Promise.race([
93
- crashSupervisor.waitForCrash(testFilePath),
94
- waitForAbort(signal),
95
- ]);
96
- }
97
- finally {
98
- crashSupervisor.cancelCrashWaiters();
99
- }
100
- },
101
- onAttemptStart: () => {
102
- logWait('beginning launch attempt for %s', testFilePath);
103
- crashSupervisor.beginLaunch(testFilePath);
104
- },
105
- onAttemptReset: () => {
106
- logWait('resetting launch attempt state');
107
- crashSupervisor.cancelCrashWaiters();
108
- },
109
- });
110
- };
111
- const getHarnessInternal = async (config, platform, projectRoot, signal) => {
112
- const context = {
113
- platform,
114
- };
115
- harnessLogger.debug('creating Harness internals for runner=%s platform=%s', platform.name, platform.platformId);
116
- const resourceLockKey = await (platform.getResourceLockKey?.() ??
117
- getDefaultResourceLockKey(platform));
118
- let didWaitForResourceLock = false;
119
- let lastStillWaitingLogAt = 0;
120
- const resourceLease = await resourceLockManager.acquire(resourceLockKey, {
121
- signal,
122
- onWait: () => {
123
- didWaitForResourceLock = true;
124
- logRunnerWaitingInQueue(platform);
125
- harnessLogger.debug('waiting in queue for runner=%s key=%s', platform.name, resourceLockKey);
126
- },
127
- onStillWaiting: (elapsedMs) => {
128
- if (elapsedMs - lastStillWaitingLogAt < 5000) {
129
- return;
130
- }
131
- lastStillWaitingLogAt = elapsedMs;
132
- logRunnerStillWaitingInQueue(platform);
133
- harnessLogger.debug('still waiting in queue for runner=%s key=%s elapsedMs=%d', platform.name, resourceLockKey, elapsedMs);
134
- },
135
- });
136
- if (didWaitForResourceLock) {
137
- logRunnerStarting(platform);
138
- }
139
- harnessLogger.debug('resource lock acquired for runner=%s key=%s', platform.name, resourceLockKey);
140
- try {
141
- const { config: runtimeConfig, metroPortLease, initialMetroPort, didFallback, } = await resolveHarnessMetroPort({
142
- config,
143
- platform,
144
- resourceLockManager,
145
- signal,
146
- });
147
- if (didFallback) {
148
- logMetroPortFallback(initialMetroPort, runtimeConfig.metroPort);
149
- }
150
- maybeLogMetroCacheReuse(runtimeConfig, platform, projectRoot);
151
- const pluginAbortController = new AbortController();
152
- const pluginManager = createHarnessPluginManager({
153
- plugins: (runtimeConfig.plugins ?? []),
154
- projectRoot,
155
- config: runtimeConfig,
156
- runner: platform,
157
- abortSignal: pluginAbortController.signal,
158
- });
159
- let currentRun = null;
160
- let activeTestFilePath;
161
- const pendingHookPromises = new Set();
162
- let pendingHookError;
163
- const getCurrentRunId = () => currentRun?.runId;
164
- const toRelativeTestFilePath = (testFilePath) => testFilePath == null
165
- ? undefined
166
- : path.relative(projectRoot, testFilePath);
167
- const setActiveTestFilePath = (testFilePath) => {
168
- activeTestFilePath = toRelativeTestFilePath(testFilePath);
169
- };
170
- const flushPendingHooks = async () => {
171
- if (pendingHookPromises.size > 0) {
172
- await Promise.allSettled([...pendingHookPromises]);
173
- }
174
- if (pendingHookError !== undefined) {
175
- const error = pendingHookError;
176
- pendingHookError = undefined;
177
- throw error;
178
- }
179
- };
180
- const trackHook = (promise) => {
181
- const trackedPromise = promise
182
- .catch((error) => {
183
- pendingHookError ??= error;
184
- })
185
- .finally(() => {
186
- pendingHookPromises.delete(trackedPromise);
187
- });
188
- pendingHookPromises.add(trackedPromise);
189
- };
190
- const scheduleHook = (name, payload) => {
191
- trackHook(pluginManager.callHook(name, payload));
192
- };
193
- const serverBridge = await getBridgeServer({
194
- noServer: true,
195
- timeout: runtimeConfig.bridgeTimeout,
196
- context,
197
- });
198
- harnessLogger.debug('starting Metro, platform runner, and bridge initialization');
199
- harnessLogger.debug('bridge server initialized on Metro websocket path %s', HARNESS_BRIDGE_PATH);
200
- const [metroInstance, platformInstance] = await (async () => {
201
- try {
202
- return await Promise.all([
203
- getMetroInstance({
204
- projectRoot,
205
- harnessConfig: runtimeConfig,
206
- websocketEndpoints: {
207
- [HARNESS_BRIDGE_PATH]: serverBridge.ws,
208
- },
209
- }, signal).then((instance) => {
210
- harnessLogger.debug('Metro initialized');
211
- return instance;
212
- }),
213
- withPlatformReadyTimeout({
214
- timeout: runtimeConfig.platformReadyTimeout,
215
- signal,
216
- work: async () => {
217
- return await import(platform.runner)
218
- .then((module) => module.default(platform.config, runtimeConfig, {
219
- signal,
220
- }))
221
- .then((instance) => {
222
- harnessLogger.debug('platform runner initialized');
223
- return instance;
224
- });
225
- },
226
- }),
227
- ]);
228
- }
229
- catch (error) {
230
- await Promise.allSettled([
231
- resourceLease.release(),
232
- metroPortLease?.release(),
233
- serverBridge.dispose(),
234
- ]);
235
- throw error;
236
- }
237
- })();
238
- const crashArtifactWriter = createCrashArtifactWriter({
239
- runnerName: platform.name,
240
- platformId: platform.platformId,
241
- });
242
- const appMonitor = platformInstance.createAppMonitor({
243
- crashArtifactWriter,
244
- });
245
- const appLaunchOptions = platform.config.appLaunchOptions;
246
- const clientLogListener = createClientLogListener();
247
- const bridgeEventListener = (event) => {
248
- const runId = getCurrentRunId();
249
- if (!runId) {
250
- return;
251
- }
252
- switch (event.type) {
253
- case 'collection-started':
254
- scheduleHook('collection:started', {
255
- runId,
256
- file: event.file,
257
- });
258
- break;
259
- case 'collection-finished':
260
- scheduleHook('collection:finished', {
261
- runId,
262
- file: event.file,
263
- duration: event.duration,
264
- totalTests: event.totalTests,
265
- });
266
- break;
267
- case 'suite-started':
268
- scheduleHook('suite:started', {
269
- runId,
270
- file: event.file,
271
- name: event.name,
272
- });
273
- break;
274
- case 'suite-finished':
275
- scheduleHook('suite:finished', {
276
- runId,
277
- file: event.file,
278
- name: event.name,
279
- duration: event.duration,
280
- status: event.status,
281
- error: event.error,
282
- });
283
- break;
284
- case 'test-started':
285
- scheduleHook('test:started', {
286
- runId,
287
- file: event.file,
288
- suite: event.suite,
289
- name: event.name,
290
- });
291
- break;
292
- case 'test-finished':
293
- scheduleHook('test:finished', {
294
- runId,
295
- file: event.file,
296
- suite: event.suite,
297
- name: event.name,
298
- duration: event.duration,
299
- status: event.status,
300
- error: event.error,
301
- });
302
- break;
303
- case 'module-bundling-started':
304
- scheduleHook('metro:bundle-started', {
305
- runId,
306
- target: 'module',
307
- file: event.file,
308
- });
309
- break;
310
- case 'module-bundling-finished':
311
- scheduleHook('metro:bundle-finished', {
312
- runId,
313
- target: 'module',
314
- file: event.file,
315
- duration: event.duration,
316
- });
317
- break;
318
- case 'module-bundling-failed':
319
- scheduleHook('metro:bundle-failed', {
320
- runId,
321
- target: 'module',
322
- file: event.file,
323
- duration: event.duration,
324
- error: event.error,
325
- });
326
- break;
327
- case 'setup-file-bundling-started':
328
- scheduleHook('metro:bundle-started', {
329
- runId,
330
- target: 'setupFile',
331
- file: event.file,
332
- setupType: event.setupType,
333
- });
334
- break;
335
- case 'setup-file-bundling-finished':
336
- scheduleHook('metro:bundle-finished', {
337
- runId,
338
- target: 'setupFile',
339
- file: event.file,
340
- setupType: event.setupType,
341
- duration: event.duration,
342
- });
343
- break;
344
- case 'setup-file-bundling-failed':
345
- scheduleHook('metro:bundle-failed', {
346
- runId,
347
- target: 'setupFile',
348
- file: event.file,
349
- setupType: event.setupType,
350
- duration: event.duration,
351
- error: event.error,
352
- });
353
- break;
354
- }
355
- };
356
- const onMetroEvent = (event) => {
357
- const runId = getCurrentRunId();
358
- if (runId && event.type === 'client_log') {
359
- scheduleHook('metro:client-log', {
360
- runId,
361
- level: event.level,
362
- data: event.data,
363
- });
364
- }
365
- };
366
- const crashSupervisor = createCrashSupervisor({
367
- appMonitor,
368
- platformRunner: platformInstance,
369
- });
370
- const onReady = (device) => {
371
- crashSupervisor.markReady();
372
- const runId = getCurrentRunId();
373
- if (!runId) {
374
- return;
375
- }
376
- scheduleHook('runtime:ready', {
377
- runId,
378
- device,
379
- });
380
- };
381
- const onDisconnect = () => {
382
- const runId = getCurrentRunId();
383
- if (!runId) {
384
- return;
385
- }
386
- scheduleHook('runtime:disconnected', {
387
- runId,
388
- reason: 'bridge-disconnected',
389
- });
390
- };
391
- const onAppMonitorEvent = (event) => {
392
- const runId = getCurrentRunId();
393
- if (!runId) {
394
- return;
395
- }
396
- if (event.type === 'app_started') {
397
- scheduleHook('app:started', {
398
- runId,
399
- testFile: activeTestFilePath,
400
- pid: event.pid,
401
- source: event.source,
402
- line: event.line,
403
- });
404
- return;
405
- }
406
- if (event.type === 'app_exited') {
407
- scheduleHook('app:exited', {
408
- runId,
409
- testFile: activeTestFilePath,
410
- pid: event.pid,
411
- source: event.source,
412
- line: event.line,
413
- isConfirmed: event.isConfirmed,
414
- crashDetails: event.crashDetails,
415
- });
416
- return;
417
- }
418
- if (event.type === 'possible_crash') {
419
- scheduleHook('app:possible-crash', {
420
- runId,
421
- testFile: activeTestFilePath,
422
- pid: event.pid,
423
- source: event.source,
424
- line: event.line,
425
- isConfirmed: event.isConfirmed,
426
- crashDetails: event.crashDetails,
427
- });
428
- }
429
- };
430
- serverBridge.on('ready', onReady);
431
- serverBridge.on('disconnect', onDisconnect);
432
- serverBridge.on('event', bridgeEventListener);
433
- metroInstance.events.addListener(onMetroEvent);
434
- appMonitor.addListener(onAppMonitorEvent);
435
- harnessLogger.debug('registered runtime, bridge, and Metro listeners');
436
- if (runtimeConfig.forwardClientLogs) {
437
- metroInstance.events.addListener(clientLogListener);
438
- harnessLogger.debug('client log forwarding enabled');
439
- }
440
- let disposePromise = null;
441
- const disposeOnce = async (reason = 'normal') => {
442
- harnessLogger.debug('disposing Harness (reason=%s)', reason);
443
- let hookError;
444
- try {
445
- await flushPendingHooks();
446
- await pluginManager.callHook('harness:after-run', {
447
- runId: currentRun?.runId,
448
- reason,
449
- summary: currentRun?.summary,
450
- status: currentRun?.status,
451
- error: currentRun?.error,
452
- });
453
- await flushPendingHooks();
454
- await pluginManager.callHook('harness:before-dispose', {
455
- runId: currentRun?.runId,
456
- reason,
457
- summary: currentRun?.summary,
458
- status: currentRun?.status,
459
- error: currentRun?.error,
460
- });
461
- await flushPendingHooks();
462
- }
463
- catch (error) {
464
- hookError = error;
465
- }
466
- if (runtimeConfig.forwardClientLogs) {
467
- metroInstance.events.removeListener(clientLogListener);
468
- }
469
- metroInstance.events.removeListener(onMetroEvent);
470
- appMonitor.removeListener(onAppMonitorEvent);
471
- serverBridge.off('ready', onReady);
472
- serverBridge.off('disconnect', onDisconnect);
473
- serverBridge.off('event', bridgeEventListener);
474
- let cleanupError;
475
- try {
476
- await Promise.all([
477
- crashSupervisor.dispose(),
478
- serverBridge.dispose(),
479
- platformInstance.dispose(),
480
- metroInstance.dispose(),
481
- metroPortLease?.release(),
482
- ]);
483
- }
484
- catch (error) {
485
- cleanupError = error;
486
- }
487
- finally {
488
- await resourceLease.release();
489
- pluginAbortController.abort();
490
- }
491
- harnessLogger.debug('Harness resources disposed');
492
- if (hookError) {
493
- throw hookError;
494
- }
495
- if (cleanupError) {
496
- throw cleanupError;
497
- }
498
- };
499
- const dispose = (reason = 'normal') => {
500
- disposePromise ??= disposeOnce(reason);
501
- return disposePromise;
502
- };
503
- if (signal.aborted) {
504
- await dispose('abort');
505
- throw new DOMException('The operation was aborted', 'AbortError');
506
- }
507
- try {
508
- await pluginManager.callHook('harness:before-creation', {
509
- appLaunchOptions,
510
- });
511
- await flushPendingHooks();
512
- await appMonitor.start();
513
- harnessLogger.debug('app monitor started');
514
- await pluginManager.callHook('harness:before-run', {
515
- appLaunchOptions,
516
- });
517
- await flushPendingHooks();
518
- }
519
- catch (error) {
520
- const runState = currentRun;
521
- if (runState) {
522
- runState.error = error;
523
- currentRun = runState;
524
- }
525
- await dispose(error instanceof DOMException && error.name === 'AbortError'
526
- ? 'abort'
527
- : 'error');
528
- throw error;
529
- }
530
- const ensureAppReady = async (testFilePath) => {
531
- await flushPendingHooks();
532
- setActiveTestFilePath(testFilePath);
533
- crashSupervisor.setActiveTestFile(testFilePath);
534
- harnessLogger.debug('ensuring app is ready for %s', testFilePath);
535
- if (crashSupervisor.isReady() &&
536
- (await platformInstance.isAppRunning())) {
537
- harnessLogger.debug('reusing existing ready app for %s', testFilePath);
538
- return;
539
- }
540
- crashSupervisor.reset();
541
- harnessLogger.debug('app not ready, waiting for launch and runtime readiness');
542
- await waitForAppReady({
543
- metroInstance,
544
- serverBridge,
545
- platformInstance: platformInstance,
546
- platformId: platform.platformId,
547
- bundleStartTimeout: runtimeConfig.bundleStartTimeout ?? 60000,
548
- readyTimeout: runtimeConfig.bridgeTimeout,
549
- maxAppRestarts: runtimeConfig.maxAppRestarts ?? 2,
550
- testFilePath,
551
- crashSupervisor,
552
- appLaunchOptions,
553
- });
554
- await flushPendingHooks();
555
- harnessLogger.debug('app is ready for %s', testFilePath);
556
- };
557
- const restart = async (testFilePath) => {
558
- await flushPendingHooks();
559
- await crashSupervisor.stop();
560
- setActiveTestFilePath(testFilePath);
561
- harnessLogger.debug('restarting app (testFile=%s mode=%s)', testFilePath ?? 'n/a', testFilePath ? 'stop-and-ensure-ready' : 'direct-restart');
562
- if (testFilePath) {
563
- harnessLogger.debug('stopping app before restart');
564
- await platformInstance.stopApp();
565
- }
566
- else {
567
- harnessLogger.debug('requesting direct app restart');
568
- await platformInstance.restartApp(appLaunchOptions);
569
- }
570
- crashSupervisor.reset();
571
- await crashSupervisor.start();
572
- if (testFilePath) {
573
- await ensureAppReady(testFilePath);
574
- }
575
- await flushPendingHooks();
576
- harnessLogger.debug('restart completed');
577
- };
578
- return {
579
- context,
580
- config: runtimeConfig,
581
- runTests: async (path, options) => {
582
- await flushPendingHooks();
583
- activeTestFilePath = path;
584
- const client = serverBridge.rpc.clients.at(-1);
585
- if (!client) {
586
- throw new Error('No client found');
587
- }
588
- harnessLogger.debug('running test file on client: %s', path);
589
- const result = await client.runTests(path, {
590
- ...options,
591
- runner: platform.runner,
592
- });
593
- await flushPendingHooks();
594
- return result;
595
- },
596
- ensureAppReady,
597
- restart,
598
- dispose: () => dispose('normal'),
599
- crashSupervisor,
600
- callHook: async (name, payload) => {
601
- await flushPendingHooks();
602
- await pluginManager.callHook(name, payload);
603
- await flushPendingHooks();
604
- },
605
- setRunState: (runState) => {
606
- currentRun = runState;
607
- },
608
- getRunState: () => currentRun,
609
- };
610
- }
611
- catch (error) {
612
- await resourceLease.release();
613
- throw error;
614
- }
615
- };
616
- export const getHarness = async (config, platform, projectRoot) => {
617
- harnessLogger.debug('creating Harness with platform ready timeout %dms', config.platformReadyTimeout);
618
- return await getHarnessInternal(config, platform, projectRoot, new AbortController().signal);
619
- };
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=jest-options.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"jest-options.d.ts","sourceRoot":"","sources":["../src/jest-options.ts"],"names":[],"mappings":""}
@@ -1 +0,0 @@
1
- export {};
package/dist/setup.d.ts DELETED
@@ -1,3 +0,0 @@
1
- import type { Config as JestConfig } from 'jest-runner';
2
- export declare const setup: (globalConfig: JestConfig.GlobalConfig) => Promise<void>;
3
- //# sourceMappingURL=setup.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"setup.d.ts","sourceRoot":"","sources":["../src/setup.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,MAAM,IAAI,UAAU,EAAE,MAAM,aAAa,CAAC;AA4CxD,eAAO,MAAM,KAAK,GAAU,cAAc,UAAU,CAAC,YAAY,kBA6EhE,CAAC"}