From e56b6aa228676ae05a10fb444d0faaabc75bf4b8 Mon Sep 17 00:00:00 2001 From: Ariba Siddiqui Date: Sat, 29 Oct 2022 09:49:17 +0200 Subject: [PATCH 1/6] initial changes --- .../checker/checker-child-process-proxy.ts | 7 ++++-- packages/core/src/checker/checker-factory.ts | 7 ++++-- .../src/child-proxy/child-process-proxy.ts | 25 +++++++++++++++---- packages/core/src/child-proxy/id-generator.ts | 9 +++++++ .../core/src/process/3-dry-run-executor.ts | 3 +++ .../child-process-test-runner-proxy.ts | 8 ++++-- packages/core/src/test-runner/index.ts | 11 +++++--- 7 files changed, 56 insertions(+), 14 deletions(-) create mode 100644 packages/core/src/child-proxy/id-generator.ts diff --git a/packages/core/src/checker/checker-child-process-proxy.ts b/packages/core/src/checker/checker-child-process-proxy.ts index d2c66e06d7..b5b324b2ba 100644 --- a/packages/core/src/checker/checker-child-process-proxy.ts +++ b/packages/core/src/checker/checker-child-process-proxy.ts @@ -6,6 +6,7 @@ import { Disposable } from 'typed-inject'; import { ChildProcessProxy } from '../child-proxy/child-process-proxy.js'; import { LoggingClientContext } from '../logging/index.js'; import { Resource } from '../concurrent/pool.js'; +import { IdGenerator } from '../child-proxy/id-generator'; import { CheckerWorker } from './checker-worker.js'; import { CheckerResource } from './checker-resource.js'; @@ -17,7 +18,8 @@ export class CheckerChildProcessProxy implements CheckerResource, Disposable, Re options: StrykerOptions, fileDescriptions: FileDescriptions, pluginModulePaths: readonly string[], - loggingContext: LoggingClientContext + loggingContext: LoggingClientContext, + idGenerator: IdGenerator ) { this.childProcess = ChildProcessProxy.create( new URL('./checker-worker.js', import.meta.url).toString(), @@ -27,7 +29,8 @@ export class CheckerChildProcessProxy implements CheckerResource, Disposable, Re pluginModulePaths, process.cwd(), CheckerWorker, - options.checkerNodeArgs + options.checkerNodeArgs, + idGenerator ); } diff --git a/packages/core/src/checker/checker-factory.ts b/packages/core/src/checker/checker-factory.ts index 44336c43ad..7cb7c6693a 100644 --- a/packages/core/src/checker/checker-factory.ts +++ b/packages/core/src/checker/checker-factory.ts @@ -2,6 +2,8 @@ import { FileDescriptions, StrykerOptions } from '@stryker-mutator/api/core'; import { LoggerFactoryMethod } from '@stryker-mutator/api/logging'; import { commonTokens, tokens } from '@stryker-mutator/api/plugin'; +import { IdGenerator } from '../child-proxy/id-generator'; + import { coreTokens } from '../di/index.js'; import { LoggingClientContext } from '../logging/logging-client-context.js'; @@ -21,13 +23,14 @@ export function createCheckerFactory( fileDescriptions: FileDescriptions, loggingContext: LoggingClientContext, pluginModulePaths: readonly string[], - getLogger: LoggerFactoryMethod + getLogger: LoggerFactoryMethod, + idGenerator: IdGenerator ): () => CheckerFacade { return () => new CheckerFacade( () => new CheckerRetryDecorator( - () => new CheckerChildProcessProxy(options, fileDescriptions, pluginModulePaths, loggingContext), + () => new CheckerChildProcessProxy(options, fileDescriptions, pluginModulePaths, loggingContext, idGenerator), getLogger(CheckerRetryDecorator.name) ) ); diff --git a/packages/core/src/child-proxy/child-process-proxy.ts b/packages/core/src/child-proxy/child-process-proxy.ts index c8afdef13e..afe849a5ad 100644 --- a/packages/core/src/child-proxy/child-process-proxy.ts +++ b/packages/core/src/child-proxy/child-process-proxy.ts @@ -16,6 +16,7 @@ import { ChildProcessCrashedError } from './child-process-crashed-error.js'; import { InitMessage, ParentMessage, ParentMessageKind, WorkerMessage, WorkerMessageKind } from './message-protocol.js'; import { OutOfMemoryError } from './out-of-memory-error.js'; import { ChildProcessContext } from './child-process-proxy-worker.js'; +import { IdGenerator } from './id-generator'; type Func = (...args: TS) => R; @@ -51,11 +52,23 @@ export class ChildProcessProxy implements Disposable { fileDescriptions: FileDescriptions, pluginModulePaths: readonly string[], workingDirectory: string, - execArgv: string[] + execArgv: string[], + idGenerator: IdGenerator ) { - this.worker = childProcess.fork(fileURLToPath(new URL('./child-process-proxy-worker.js', import.meta.url)), { silent: true, execArgv }); + const workerId = idGenerator.next().toString(); + this.worker = childProcess.fork(fileURLToPath(new URL('./child-process-proxy-worker.js', import.meta.url)), { + silent: true, + execArgv, + env: { STRYKER_MUTATOR_WORKER: workerId }, + }); this.initTask = new Task(); - this.log.debug('Started %s in child process %s%s', namedExport, this.worker.pid, execArgv.length ? ` (using args ${execArgv.join(' ')})` : ''); + this.log.debug( + 'Started %s in child process %s%s and env STRYKER_MUTATOR_WORKER as %s', + namedExport, + this.worker.pid, + workerId, + execArgv.length ? ` (using args ${execArgv.join(' ')})` : '' + ); // Listen to `close`, not `exit`, see https://github.com/stryker-mutator/stryker-js/issues/1634 this.worker.on('close', this.handleUnexpectedExit); this.worker.on('error', this.handleError); @@ -87,7 +100,8 @@ export class ChildProcessProxy implements Disposable { pluginModulePaths: readonly string[], workingDirectory: string, injectableClass: InjectableClass, - execArgv: string[] + execArgv: string[], + idGenerator: IdGenerator ): ChildProcessProxy { return new ChildProcessProxy( modulePath, @@ -97,7 +111,8 @@ export class ChildProcessProxy implements Disposable { fileDescriptions, pluginModulePaths, workingDirectory, - execArgv + execArgv, + idGenerator ); } diff --git a/packages/core/src/child-proxy/id-generator.ts b/packages/core/src/child-proxy/id-generator.ts new file mode 100644 index 0000000000..67ef623c57 --- /dev/null +++ b/packages/core/src/child-proxy/id-generator.ts @@ -0,0 +1,9 @@ +export class IdGenerator { + private childId; + constructor() { + this.childId = 0; + } + public next(): number { + return this.childId++; + } +} diff --git a/packages/core/src/process/3-dry-run-executor.ts b/packages/core/src/process/3-dry-run-executor.ts index ca551be4c7..7f5df883a9 100644 --- a/packages/core/src/process/3-dry-run-executor.ts +++ b/packages/core/src/process/3-dry-run-executor.ts @@ -30,6 +30,8 @@ import { CheckerFacade } from '../checker/index.js'; import { StrictReporter } from '../reporters/index.js'; import { objectUtils } from '../utils/object-utils.js'; +import { IdGenerator } from '../child-proxy/id-generator'; + import { MutationTestContext } from './4-mutation-test-executor.js'; import { MutantInstrumenterContext } from './2-mutant-instrumenter-executor.js'; @@ -69,6 +71,7 @@ export class DryRunExecutor { public async execute(): Promise> { const testRunnerInjector = this.injector + .provideClass('worker-id-generator', IdGenerator) .provideFactory(coreTokens.testRunnerFactory, createTestRunnerFactory) .provideValue(coreTokens.testRunnerConcurrencyTokens, this.concurrencyTokenProvider.testRunnerToken$) .provideFactory(coreTokens.testRunnerPool, createTestRunnerPool); diff --git a/packages/core/src/test-runner/child-process-test-runner-proxy.ts b/packages/core/src/test-runner/child-process-test-runner-proxy.ts index 0e636520cf..06221372c2 100644 --- a/packages/core/src/test-runner/child-process-test-runner-proxy.ts +++ b/packages/core/src/test-runner/child-process-test-runner-proxy.ts @@ -9,6 +9,8 @@ import { ChildProcessCrashedError } from '../child-proxy/child-process-crashed-e import { ChildProcessProxy } from '../child-proxy/child-process-proxy.js'; import { LoggingClientContext } from '../logging/index.js'; +import { IdGenerator } from '../child-proxy/id-generator'; + import { ChildProcessTestRunnerWorker } from './child-process-test-runner-worker.js'; const MAX_WAIT_FOR_DISPOSE = 2000; @@ -25,7 +27,8 @@ export class ChildProcessTestRunnerProxy implements TestRunner { sandboxWorkingDirectory: string, loggingContext: LoggingClientContext, pluginModulePaths: readonly string[], - private readonly log: Logger + private readonly log: Logger, + idGenerator: IdGenerator ) { this.worker = ChildProcessProxy.create( new URL('./child-process-test-runner-worker.js', import.meta.url).toString(), @@ -35,7 +38,8 @@ export class ChildProcessTestRunnerProxy implements TestRunner { pluginModulePaths, sandboxWorkingDirectory, ChildProcessTestRunnerWorker, - options.testRunnerNodeArgs + options.testRunnerNodeArgs, + idGenerator ); } diff --git a/packages/core/src/test-runner/index.ts b/packages/core/src/test-runner/index.ts index 6793a904cf..53269b0c70 100644 --- a/packages/core/src/test-runner/index.ts +++ b/packages/core/src/test-runner/index.ts @@ -7,6 +7,8 @@ import { LoggingClientContext } from '../logging/index.js'; import { coreTokens } from '../di/index.js'; import { Sandbox } from '../sandbox/sandbox.js'; +import { IdGenerator } from '../child-proxy/id-generator'; + import { RetryRejectedDecorator } from './retry-rejected-decorator.js'; import { TimeoutDecorator } from './timeout-decorator.js'; import { ChildProcessTestRunnerProxy } from './child-process-test-runner-proxy.js'; @@ -20,7 +22,8 @@ createTestRunnerFactory.inject = tokens( coreTokens.sandbox, coreTokens.loggingContext, commonTokens.getLogger, - coreTokens.pluginModulePaths + coreTokens.pluginModulePaths, + 'worker-id-generator' ); export function createTestRunnerFactory( options: StrykerOptions, @@ -28,7 +31,8 @@ export function createTestRunnerFactory( sandbox: Pick, loggingContext: LoggingClientContext, getLogger: LoggerFactoryMethod, - pluginModulePaths: readonly string[] + pluginModulePaths: readonly string[], + idGenerator: IdGenerator ): () => TestRunner { if (CommandTestRunner.is(options.testRunner)) { return () => new RetryRejectedDecorator(() => new TimeoutDecorator(() => new CommandTestRunner(sandbox.workingDirectory, options))); @@ -48,7 +52,8 @@ export function createTestRunnerFactory( sandbox.workingDirectory, loggingContext, pluginModulePaths, - getLogger(ChildProcessTestRunnerProxy.name) + getLogger(ChildProcessTestRunnerProxy.name), + idGenerator ) ), options From a30b41f5e3c905f2634b46c0f408513049ad9b1d Mon Sep 17 00:00:00 2001 From: Ariba Siddiqui Date: Sat, 29 Oct 2022 14:36:42 +0200 Subject: [PATCH 2/6] errors resolved --- .../checker/checker-child-process-proxy.ts | 2 +- packages/core/src/checker/checker-factory.ts | 5 +++-- .../src/child-proxy/child-process-proxy.ts | 8 +++---- packages/core/src/child-proxy/id-generator.ts | 2 +- .../process/2-mutant-instrumenter-executor.ts | 3 +++ .../core/src/process/3-dry-run-executor.ts | 2 +- .../child-process-test-runner-proxy.ts | 2 +- packages/core/src/test-runner/index.ts | 2 +- .../checker/create-checker-factory.it.spec.ts | 3 +++ .../child-process-proxy.it.spec.ts | 7 ++++++- .../create-test-runner-factory.it.spec.ts | 3 +++ .../checker-child-process-proxy.spec.ts | 11 +++++++--- .../child-proxy/child-process-proxy.spec.ts | 21 +++++++++++++++++-- .../unit/child-proxy/id-generator.spec.ts | 0 .../child-process-test-runner-proxy.spec.ts | 9 ++++++-- 15 files changed, 61 insertions(+), 19 deletions(-) create mode 100644 packages/core/test/unit/child-proxy/id-generator.spec.ts diff --git a/packages/core/src/checker/checker-child-process-proxy.ts b/packages/core/src/checker/checker-child-process-proxy.ts index b5b324b2ba..4ebcec9bd4 100644 --- a/packages/core/src/checker/checker-child-process-proxy.ts +++ b/packages/core/src/checker/checker-child-process-proxy.ts @@ -6,7 +6,7 @@ import { Disposable } from 'typed-inject'; import { ChildProcessProxy } from '../child-proxy/child-process-proxy.js'; import { LoggingClientContext } from '../logging/index.js'; import { Resource } from '../concurrent/pool.js'; -import { IdGenerator } from '../child-proxy/id-generator'; +import { IdGenerator } from '../child-proxy/id-generator.js'; import { CheckerWorker } from './checker-worker.js'; import { CheckerResource } from './checker-resource.js'; diff --git a/packages/core/src/checker/checker-factory.ts b/packages/core/src/checker/checker-factory.ts index 7cb7c6693a..165bfca375 100644 --- a/packages/core/src/checker/checker-factory.ts +++ b/packages/core/src/checker/checker-factory.ts @@ -2,7 +2,7 @@ import { FileDescriptions, StrykerOptions } from '@stryker-mutator/api/core'; import { LoggerFactoryMethod } from '@stryker-mutator/api/logging'; import { commonTokens, tokens } from '@stryker-mutator/api/plugin'; -import { IdGenerator } from '../child-proxy/id-generator'; +import { IdGenerator } from '../child-proxy/id-generator.js'; import { coreTokens } from '../di/index.js'; import { LoggingClientContext } from '../logging/logging-client-context.js'; @@ -16,7 +16,8 @@ createCheckerFactory.inject = tokens( commonTokens.fileDescriptions, coreTokens.loggingContext, coreTokens.pluginModulePaths, - commonTokens.getLogger + commonTokens.getLogger, + 'worker-id-generator' ); export function createCheckerFactory( options: StrykerOptions, diff --git a/packages/core/src/child-proxy/child-process-proxy.ts b/packages/core/src/child-proxy/child-process-proxy.ts index afe849a5ad..0247b56531 100644 --- a/packages/core/src/child-proxy/child-process-proxy.ts +++ b/packages/core/src/child-proxy/child-process-proxy.ts @@ -16,7 +16,7 @@ import { ChildProcessCrashedError } from './child-process-crashed-error.js'; import { InitMessage, ParentMessage, ParentMessageKind, WorkerMessage, WorkerMessageKind } from './message-protocol.js'; import { OutOfMemoryError } from './out-of-memory-error.js'; import { ChildProcessContext } from './child-process-proxy-worker.js'; -import { IdGenerator } from './id-generator'; +import { IdGenerator } from './id-generator.js'; type Func = (...args: TS) => R; @@ -63,11 +63,11 @@ export class ChildProcessProxy implements Disposable { }); this.initTask = new Task(); this.log.debug( - 'Started %s in child process %s%s and env STRYKER_MUTATOR_WORKER as %s', + 'Started %s in child process %s%s & env var STRYKER_MUTATOR_WORKER as %s', namedExport, this.worker.pid, - workerId, - execArgv.length ? ` (using args ${execArgv.join(' ')})` : '' + execArgv.length ? ` (using args ${execArgv.join(' ')})` : '', + workerId ); // Listen to `close`, not `exit`, see https://github.com/stryker-mutator/stryker-js/issues/1634 this.worker.on('close', this.handleUnexpectedExit); diff --git a/packages/core/src/child-proxy/id-generator.ts b/packages/core/src/child-proxy/id-generator.ts index 67ef623c57..34b913f503 100644 --- a/packages/core/src/child-proxy/id-generator.ts +++ b/packages/core/src/child-proxy/id-generator.ts @@ -1,5 +1,5 @@ export class IdGenerator { - private childId; + private childId: number; constructor() { this.childId = 0; } diff --git a/packages/core/src/process/2-mutant-instrumenter-executor.ts b/packages/core/src/process/2-mutant-instrumenter-executor.ts index 2b6472cbf0..1eef250eb9 100644 --- a/packages/core/src/process/2-mutant-instrumenter-executor.ts +++ b/packages/core/src/process/2-mutant-instrumenter-executor.ts @@ -16,6 +16,8 @@ import { TemporaryDirectory } from '../utils/temporary-directory.js'; import { UnexpectedExitHandler } from '../unexpected-exit-handler.js'; import { FileSystem, Project } from '../fs/index.js'; +import { IdGenerator } from '../child-proxy/id-generator.js'; + import { DryRunContext } from './3-dry-run-executor.js'; export interface MutantInstrumenterContext extends PluginContext { @@ -58,6 +60,7 @@ export class MutantInstrumenterExecutor { const checkerPoolProvider = concurrencyTokenProviderProvider .provideValue(coreTokens.checkerConcurrencyTokens, concurrencyTokenProvider.checkerToken$) + .provideClass('worker-id-generator', IdGenerator) .provideFactory(coreTokens.checkerFactory, createCheckerFactory) .provideFactory(coreTokens.checkerPool, createCheckerPool); const checkerPool = checkerPoolProvider.resolve(coreTokens.checkerPool); diff --git a/packages/core/src/process/3-dry-run-executor.ts b/packages/core/src/process/3-dry-run-executor.ts index 6d688cd71b..aaef0136aa 100644 --- a/packages/core/src/process/3-dry-run-executor.ts +++ b/packages/core/src/process/3-dry-run-executor.ts @@ -30,7 +30,7 @@ import { CheckerFacade } from '../checker/index.js'; import { StrictReporter } from '../reporters/index.js'; import { objectUtils } from '../utils/object-utils.js'; -import { IdGenerator } from '../child-proxy/id-generator'; +import { IdGenerator } from '../child-proxy/id-generator.js'; import { MutationTestContext } from './4-mutation-test-executor.js'; import { MutantInstrumenterContext } from './2-mutant-instrumenter-executor.js'; diff --git a/packages/core/src/test-runner/child-process-test-runner-proxy.ts b/packages/core/src/test-runner/child-process-test-runner-proxy.ts index 06221372c2..60b2ca5d02 100644 --- a/packages/core/src/test-runner/child-process-test-runner-proxy.ts +++ b/packages/core/src/test-runner/child-process-test-runner-proxy.ts @@ -9,7 +9,7 @@ import { ChildProcessCrashedError } from '../child-proxy/child-process-crashed-e import { ChildProcessProxy } from '../child-proxy/child-process-proxy.js'; import { LoggingClientContext } from '../logging/index.js'; -import { IdGenerator } from '../child-proxy/id-generator'; +import { IdGenerator } from '../child-proxy/id-generator.js'; import { ChildProcessTestRunnerWorker } from './child-process-test-runner-worker.js'; diff --git a/packages/core/src/test-runner/index.ts b/packages/core/src/test-runner/index.ts index 53269b0c70..85bfc65ed8 100644 --- a/packages/core/src/test-runner/index.ts +++ b/packages/core/src/test-runner/index.ts @@ -7,7 +7,7 @@ import { LoggingClientContext } from '../logging/index.js'; import { coreTokens } from '../di/index.js'; import { Sandbox } from '../sandbox/sandbox.js'; -import { IdGenerator } from '../child-proxy/id-generator'; +import { IdGenerator } from '../child-proxy/id-generator.js'; import { RetryRejectedDecorator } from './retry-rejected-decorator.js'; import { TimeoutDecorator } from './timeout-decorator.js'; diff --git a/packages/core/test/integration/checker/create-checker-factory.it.spec.ts b/packages/core/test/integration/checker/create-checker-factory.it.spec.ts index 48f403b285..be99432d4f 100644 --- a/packages/core/test/integration/checker/create-checker-factory.it.spec.ts +++ b/packages/core/test/integration/checker/create-checker-factory.it.spec.ts @@ -10,6 +10,8 @@ import { CheckerFacade, createCheckerFactory } from '../../../src/checker/index. import { coreTokens } from '../../../src/di/index.js'; import { LoggingClientContext } from '../../../src/logging/index.js'; +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; + import { TwoTimesTheCharm } from './additional-checkers.js'; describe(`${createCheckerFactory.name} integration`, () => { @@ -34,6 +36,7 @@ describe(`${createCheckerFactory.name} integration`, () => { createSut = testInjector.injector .provideValue(coreTokens.loggingContext, loggingContext) .provideValue(coreTokens.pluginModulePaths, pluginModulePaths) + .provideClass('worker-id-generator', IdGenerator) .injectFunction(createCheckerFactory); }); diff --git a/packages/core/test/integration/child-proxy/child-process-proxy.it.spec.ts b/packages/core/test/integration/child-proxy/child-process-proxy.it.spec.ts index 5507d43b8f..752805d0cd 100644 --- a/packages/core/test/integration/child-proxy/child-process-proxy.it.spec.ts +++ b/packages/core/test/integration/child-proxy/child-process-proxy.it.spec.ts @@ -16,6 +16,8 @@ import { currentLogMock } from '../../helpers/log-mock.js'; import { Mock } from '../../helpers/producers.js'; import { sleep } from '../../helpers/test-utils.js'; +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; + import { Echo } from './echo.js'; describe(ChildProcessProxy.name, () => { @@ -25,6 +27,7 @@ describe(ChildProcessProxy.name, () => { let fileDescriptions: FileDescriptions; const testRunnerName = 'echoRunner'; const workingDir = '..'; + const idGenerator: IdGenerator = new IdGenerator(); beforeEach(async () => { fileDescriptions = { @@ -35,6 +38,7 @@ describe(ChildProcessProxy.name, () => { const port = await loggingServer.listen(); testInjector.options.testRunner = testRunnerName; log = currentLogMock(); + idGenerator.next(); sut = ChildProcessProxy.create( new URL('./echo.js', import.meta.url).toString(), { port, level: LogLevel.Debug }, @@ -46,7 +50,8 @@ describe(ChildProcessProxy.name, () => { [ '--no-warnings', // test if node args are forwarded with this setting, see https://nodejs.org/api/cli.html#cli_no_warnings '--max-old-space-size=32', // reduce the amount of time we have to wait on the OOM test - ] + ], + idGenerator ); }); diff --git a/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts b/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts index 8c7279ac58..19ebbdaf19 100644 --- a/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts +++ b/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts @@ -15,6 +15,8 @@ import { sleep } from '../../helpers/test-utils.js'; import { coreTokens } from '../../../src/di/index.js'; import { TestRunnerResource } from '../../../src/concurrent/index.js'; +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; + import { additionalTestRunnersFileUrl, CounterTestRunner } from './additional-test-runners.js'; describe(`${createTestRunnerFactory.name} integration`, () => { @@ -45,6 +47,7 @@ describe(`${createTestRunnerFactory.name} integration`, () => { .provideValue(coreTokens.sandbox, { workingDirectory: path.dirname(fileURLToPath(import.meta.url)) }) .provideValue(coreTokens.loggingContext, loggingContext) .provideValue(coreTokens.pluginModulePaths, pluginModulePaths) + .provideClass('worker-id-generator', IdGenerator) .injectFunction(createTestRunnerFactory); rmSync(CounterTestRunner.COUNTER_FILE); diff --git a/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts b/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts index a4c121bf76..2143d11f74 100644 --- a/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts +++ b/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts @@ -8,20 +8,23 @@ import { CheckerChildProcessProxy } from '../../../src/checker/checker-child-pro import { CheckerWorker } from '../../../src/checker/checker-worker.js'; import { ChildProcessProxy } from '../../../src/child-proxy/child-process-proxy.js'; import { LoggingClientContext } from '../../../src/logging/index.js'; +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; describe(CheckerChildProcessProxy.name, () => { let childProcessProxyCreateStub: sinon.SinonStubbedMember; let loggingContext: LoggingClientContext; let fileDescriptions: FileDescriptions; + let idGenerator: IdGenerator; beforeEach(() => { childProcessProxyCreateStub = sinon.stub(ChildProcessProxy, 'create'); loggingContext = { port: 4200, level: LogLevel.Fatal }; fileDescriptions = { 'foo.js': { mutate: true } }; + idGenerator = new IdGenerator(); }); function createSut(): CheckerChildProcessProxy { - return new CheckerChildProcessProxy(testInjector.options, fileDescriptions, ['plugin', 'paths'], loggingContext); + return new CheckerChildProcessProxy(testInjector.options, fileDescriptions, ['plugin', 'paths'], loggingContext, idGenerator); } describe('constructor', () => { @@ -36,7 +39,8 @@ describe(CheckerChildProcessProxy.name, () => { ['plugin', 'paths'], process.cwd(), CheckerWorker, - [] + [], + idGenerator ); }); it('should provide arguments', () => { @@ -51,7 +55,8 @@ describe(CheckerChildProcessProxy.name, () => { sinon.match.any, sinon.match.any, sinon.match.any, - ['foo', 'bar'] + ['foo', 'bar'], + idGenerator ); }); }); diff --git a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts index a790bb8ff8..3e2bc364d9 100644 --- a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts +++ b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts @@ -25,6 +25,8 @@ import { OutOfMemoryError } from '../../../src/child-proxy/out-of-memory-error.j import { currentLogMock } from '../../helpers/log-mock.js'; import { Mock } from '../../helpers/producers.js'; +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; + import { HelloClass } from './hello-class.js'; const LOGGING_CONTEXT: LoggingClientContext = Object.freeze({ @@ -46,6 +48,7 @@ describe(ChildProcessProxy.name, () => { let killStub: sinon.SinonStub; let logMock: Mock; let clock: sinon.SinonFakeTimers; + let idGenerator: IdGenerator; beforeEach(() => { clock = sinon.useFakeTimers(); @@ -54,6 +57,7 @@ describe(ChildProcessProxy.name, () => { killStub = sinon.stub(objectUtils, 'kill'); forkStub.returns(childProcessMock); logMock = currentLogMock(); + idGenerator = new IdGenerator(); }); afterEach(() => { @@ -65,9 +69,11 @@ describe(ChildProcessProxy.name, () => { describe('constructor', () => { it('should create child process', () => { sut = createSut(); + const workerId = idGenerator.next().toString(); expect(forkStub).calledWith(fileURLToPath(new URL('../../../src/child-proxy/child-process-proxy-worker.js', import.meta.url)), { silent: true, execArgv: [], + env: { STRYKER_MUTATOR_WORKER: workerId }, }); }); @@ -82,10 +88,18 @@ describe(ChildProcessProxy.name, () => { createSut({ loggingContext: LOGGING_CONTEXT, execArgv: ['--cpu-prof', '--inspect'], + idGenerator, }); + const nextWorkerId = (idGenerator.next() - 1).toString(); // Assert - expect(logMock.debug).calledWith('Started %s in child process %s%s', 'HelloClass', childProcessMock.pid, ' (using args --cpu-prof --inspect)'); + expect(logMock.debug).calledWith( + 'Started %s in child process %s%s & env var STRYKER_MUTATOR_WORKER as %s', + 'HelloClass', + childProcessMock.pid, + ' (using args --cpu-prof --inspect)', + nextWorkerId + ); }); it('should listen to worker process', () => { @@ -354,6 +368,7 @@ function createSut({ fileDescriptions = { 'foo.js': { mutate: true } }, pluginModulePaths = ['plugin', 'path'], execArgv = [], + idGenerator = new IdGenerator(), }: { requirePath?: string; loggingContext?: LoggingClientContext; @@ -362,6 +377,7 @@ function createSut({ fileDescriptions?: FileDescriptions; pluginModulePaths?: readonly string[]; execArgv?: string[]; + idGenerator?: IdGenerator; } = {}): ChildProcessProxy { return ChildProcessProxy.create( requirePath, @@ -371,6 +387,7 @@ function createSut({ pluginModulePaths, workingDir, HelloClass, - execArgv + execArgv, + idGenerator ); } diff --git a/packages/core/test/unit/child-proxy/id-generator.spec.ts b/packages/core/test/unit/child-proxy/id-generator.spec.ts new file mode 100644 index 0000000000..e69de29bb2 diff --git a/packages/core/test/unit/test-runner/child-process-test-runner-proxy.spec.ts b/packages/core/test/unit/test-runner/child-process-test-runner-proxy.spec.ts index a5d6eed1de..93d3fcdfa8 100644 --- a/packages/core/test/unit/test-runner/child-process-test-runner-proxy.spec.ts +++ b/packages/core/test/unit/test-runner/child-process-test-runner-proxy.spec.ts @@ -11,6 +11,7 @@ import { ChildProcessProxy, Promisified } from '../../../src/child-proxy/child-p import { LoggingClientContext } from '../../../src/logging/index.js'; import { ChildProcessTestRunnerProxy } from '../../../src/test-runner/child-process-test-runner-proxy.js'; import { ChildProcessTestRunnerWorker } from '../../../src/test-runner/child-process-test-runner-worker.js'; +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; describe(ChildProcessTestRunnerProxy.name, () => { let options: StrykerOptions; @@ -20,6 +21,7 @@ describe(ChildProcessTestRunnerProxy.name, () => { let loggingContext: LoggingClientContext; let clock: sinon.SinonFakeTimers; let fileDescriptions: FileDescriptions; + const idGenerator = new IdGenerator(); beforeEach(() => { clock = sinon.useFakeTimers(); @@ -34,6 +36,7 @@ describe(ChildProcessTestRunnerProxy.name, () => { plugins: ['foo-plugin', 'bar-plugin'], }); loggingContext = { port: 4200, level: LogLevel.Fatal }; + idGenerator.next(); }); function createSut(): ChildProcessTestRunnerProxy { @@ -43,7 +46,8 @@ describe(ChildProcessTestRunnerProxy.name, () => { 'a working directory', loggingContext, ['plugin', 'paths'], - testInjector.logger + testInjector.logger, + idGenerator ); } @@ -59,7 +63,8 @@ describe(ChildProcessTestRunnerProxy.name, () => { ['plugin', 'paths'], 'a working directory', ChildProcessTestRunnerWorker, - ['--inspect', '--no-warnings'] + ['--inspect', '--no-warnings'], + idGenerator ); }); From 056fec8f561851fa8cf0d423e509be22d22a1cbf Mon Sep 17 00:00:00 2001 From: Ariba Siddiqui Date: Sat, 29 Oct 2022 15:53:00 +0200 Subject: [PATCH 3/6] review comments addressed --- packages/core/src/checker/checker-factory.ts | 2 +- packages/core/src/child-proxy/child-process-proxy.ts | 6 +++--- packages/core/src/child-proxy/id-generator.ts | 7 ++----- packages/core/src/di/core-tokens.ts | 1 + .../core/src/process/2-mutant-instrumenter-executor.ts | 2 +- packages/core/src/process/3-dry-run-executor.ts | 5 +++-- .../checker/create-checker-factory.it.spec.ts | 2 +- .../test-runner/create-test-runner-factory.it.spec.ts | 2 +- .../unit/checker/checker-child-process-proxy.spec.ts | 10 +++++----- .../test/unit/child-proxy/child-process-proxy.spec.ts | 6 +++--- 10 files changed, 21 insertions(+), 22 deletions(-) diff --git a/packages/core/src/checker/checker-factory.ts b/packages/core/src/checker/checker-factory.ts index 165bfca375..9ecdb6a871 100644 --- a/packages/core/src/checker/checker-factory.ts +++ b/packages/core/src/checker/checker-factory.ts @@ -17,7 +17,7 @@ createCheckerFactory.inject = tokens( coreTokens.loggingContext, coreTokens.pluginModulePaths, commonTokens.getLogger, - 'worker-id-generator' + coreTokens.workerIdGenerator ); export function createCheckerFactory( options: StrykerOptions, diff --git a/packages/core/src/child-proxy/child-process-proxy.ts b/packages/core/src/child-proxy/child-process-proxy.ts index 0247b56531..a0ecf3c5b3 100644 --- a/packages/core/src/child-proxy/child-process-proxy.ts +++ b/packages/core/src/child-proxy/child-process-proxy.ts @@ -63,11 +63,11 @@ export class ChildProcessProxy implements Disposable { }); this.initTask = new Task(); this.log.debug( - 'Started %s in child process %s%s & env var STRYKER_MUTATOR_WORKER as %s', + 'Started %s in worker process %s with pid %s %s', namedExport, + workerId, this.worker.pid, - execArgv.length ? ` (using args ${execArgv.join(' ')})` : '', - workerId + execArgv.length ? ` (using args ${execArgv.join(' ')})` : '' ); // Listen to `close`, not `exit`, see https://github.com/stryker-mutator/stryker-js/issues/1634 this.worker.on('close', this.handleUnexpectedExit); diff --git a/packages/core/src/child-proxy/id-generator.ts b/packages/core/src/child-proxy/id-generator.ts index 34b913f503..fac591345a 100644 --- a/packages/core/src/child-proxy/id-generator.ts +++ b/packages/core/src/child-proxy/id-generator.ts @@ -1,9 +1,6 @@ export class IdGenerator { - private childId: number; - constructor() { - this.childId = 0; - } + private id = 0; public next(): number { - return this.childId++; + return this.id++; } } diff --git a/packages/core/src/di/core-tokens.ts b/packages/core/src/di/core-tokens.ts index 43fe1c3d1d..b38e170260 100644 --- a/packages/core/src/di/core-tokens.ts +++ b/packages/core/src/di/core-tokens.ts @@ -29,3 +29,4 @@ export const fs = 'fs'; export const testCoverage = 'testCoverage'; export const incrementalDiffer = 'incrementalDiffer'; export const project = 'project'; +export const workerIdGenerator = 'worker-id-generator'; diff --git a/packages/core/src/process/2-mutant-instrumenter-executor.ts b/packages/core/src/process/2-mutant-instrumenter-executor.ts index 1eef250eb9..d45a653404 100644 --- a/packages/core/src/process/2-mutant-instrumenter-executor.ts +++ b/packages/core/src/process/2-mutant-instrumenter-executor.ts @@ -60,7 +60,7 @@ export class MutantInstrumenterExecutor { const checkerPoolProvider = concurrencyTokenProviderProvider .provideValue(coreTokens.checkerConcurrencyTokens, concurrencyTokenProvider.checkerToken$) - .provideClass('worker-id-generator', IdGenerator) + .provideClass(coreTokens.workerIdGenerator, IdGenerator) .provideFactory(coreTokens.checkerFactory, createCheckerFactory) .provideFactory(coreTokens.checkerPool, createCheckerPool); const checkerPool = checkerPoolProvider.resolve(coreTokens.checkerPool); diff --git a/packages/core/src/process/3-dry-run-executor.ts b/packages/core/src/process/3-dry-run-executor.ts index aaef0136aa..0f6e04b64c 100644 --- a/packages/core/src/process/3-dry-run-executor.ts +++ b/packages/core/src/process/3-dry-run-executor.ts @@ -71,7 +71,7 @@ export class DryRunExecutor { public async execute(): Promise> { const testRunnerInjector = this.injector - .provideClass('worker-id-generator', IdGenerator) + .provideClass(coreTokens.workerIdGenerator, IdGenerator) .provideFactory(coreTokens.testRunnerFactory, createTestRunnerFactory) .provideValue(coreTokens.testRunnerConcurrencyTokens, this.concurrencyTokenProvider.testRunnerToken$) .provideFactory(coreTokens.testRunnerPool, createTestRunnerPool); @@ -90,7 +90,8 @@ export class DryRunExecutor { .provideFactory(coreTokens.testCoverage, TestCoverage.from) .provideClass(coreTokens.incrementalDiffer, IncrementalDiffer) .provideClass(coreTokens.mutantTestPlanner, MutantTestPlanner) - .provideClass(coreTokens.mutationTestReportHelper, MutationTestReportHelper); + .provideClass(coreTokens.mutationTestReportHelper, MutationTestReportHelper) + .provideClass(coreTokens.workerIdGenerator, IdGenerator); } private validateResultCompleted(runResult: DryRunResult): asserts runResult is CompleteDryRunResult { diff --git a/packages/core/test/integration/checker/create-checker-factory.it.spec.ts b/packages/core/test/integration/checker/create-checker-factory.it.spec.ts index be99432d4f..cf5ef79061 100644 --- a/packages/core/test/integration/checker/create-checker-factory.it.spec.ts +++ b/packages/core/test/integration/checker/create-checker-factory.it.spec.ts @@ -36,7 +36,7 @@ describe(`${createCheckerFactory.name} integration`, () => { createSut = testInjector.injector .provideValue(coreTokens.loggingContext, loggingContext) .provideValue(coreTokens.pluginModulePaths, pluginModulePaths) - .provideClass('worker-id-generator', IdGenerator) + .provideClass(coreTokens.workerIdGenerator, IdGenerator) .injectFunction(createCheckerFactory); }); diff --git a/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts b/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts index 19ebbdaf19..f1101a85c2 100644 --- a/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts +++ b/packages/core/test/integration/test-runner/create-test-runner-factory.it.spec.ts @@ -47,7 +47,7 @@ describe(`${createTestRunnerFactory.name} integration`, () => { .provideValue(coreTokens.sandbox, { workingDirectory: path.dirname(fileURLToPath(import.meta.url)) }) .provideValue(coreTokens.loggingContext, loggingContext) .provideValue(coreTokens.pluginModulePaths, pluginModulePaths) - .provideClass('worker-id-generator', IdGenerator) + .provideClass(coreTokens.workerIdGenerator, IdGenerator) .injectFunction(createTestRunnerFactory); rmSync(CounterTestRunner.COUNTER_FILE); diff --git a/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts b/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts index 2143d11f74..738469580e 100644 --- a/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts +++ b/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts @@ -14,17 +14,17 @@ describe(CheckerChildProcessProxy.name, () => { let childProcessProxyCreateStub: sinon.SinonStubbedMember; let loggingContext: LoggingClientContext; let fileDescriptions: FileDescriptions; - let idGenerator: IdGenerator; + let idGeneratorMock: sinon.SinonStubbedInstance; beforeEach(() => { childProcessProxyCreateStub = sinon.stub(ChildProcessProxy, 'create'); loggingContext = { port: 4200, level: LogLevel.Fatal }; fileDescriptions = { 'foo.js': { mutate: true } }; - idGenerator = new IdGenerator(); + idGeneratorMock = sinon.createStubInstance(IdGenerator); }); function createSut(): CheckerChildProcessProxy { - return new CheckerChildProcessProxy(testInjector.options, fileDescriptions, ['plugin', 'paths'], loggingContext, idGenerator); + return new CheckerChildProcessProxy(testInjector.options, fileDescriptions, ['plugin', 'paths'], loggingContext, idGeneratorMock); } describe('constructor', () => { @@ -40,7 +40,7 @@ describe(CheckerChildProcessProxy.name, () => { process.cwd(), CheckerWorker, [], - idGenerator + idGeneratorMock ); }); it('should provide arguments', () => { @@ -56,7 +56,7 @@ describe(CheckerChildProcessProxy.name, () => { sinon.match.any, sinon.match.any, ['foo', 'bar'], - idGenerator + idGeneratorMock ); }); }); diff --git a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts index 3e2bc364d9..fe21aca872 100644 --- a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts +++ b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts @@ -94,11 +94,11 @@ describe(ChildProcessProxy.name, () => { const nextWorkerId = (idGenerator.next() - 1).toString(); // Assert expect(logMock.debug).calledWith( - 'Started %s in child process %s%s & env var STRYKER_MUTATOR_WORKER as %s', + 'Started %s in worker process %s with pid %s %s', 'HelloClass', + nextWorkerId, childProcessMock.pid, - ' (using args --cpu-prof --inspect)', - nextWorkerId + ' (using args --cpu-prof --inspect)' ); }); From d85804a28eee65f6a7f4549bd3c8fa85b1ef771e Mon Sep 17 00:00:00 2001 From: Ariba Siddiqui Date: Sun, 30 Oct 2022 12:03:35 +0100 Subject: [PATCH 4/6] 1 unit test for id_gen & other review changes --- .../src/child-proxy/child-process-proxy.ts | 2 +- .../checker-child-process-proxy.spec.ts | 10 +++++----- .../child-proxy/child-process-proxy.spec.ts | 19 +++++++++---------- .../unit/child-proxy/id-generator.spec.ts | 15 +++++++++++++++ 4 files changed, 30 insertions(+), 16 deletions(-) diff --git a/packages/core/src/child-proxy/child-process-proxy.ts b/packages/core/src/child-proxy/child-process-proxy.ts index a0ecf3c5b3..b041126401 100644 --- a/packages/core/src/child-proxy/child-process-proxy.ts +++ b/packages/core/src/child-proxy/child-process-proxy.ts @@ -59,7 +59,7 @@ export class ChildProcessProxy implements Disposable { this.worker = childProcess.fork(fileURLToPath(new URL('./child-process-proxy-worker.js', import.meta.url)), { silent: true, execArgv, - env: { STRYKER_MUTATOR_WORKER: workerId }, + env: { STRYKER_MUTATOR_WORKER: workerId, ...process.env }, }); this.initTask = new Task(); this.log.debug( diff --git a/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts b/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts index 738469580e..bceac1ad5e 100644 --- a/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts +++ b/packages/core/test/unit/checker/checker-child-process-proxy.spec.ts @@ -14,17 +14,17 @@ describe(CheckerChildProcessProxy.name, () => { let childProcessProxyCreateStub: sinon.SinonStubbedMember; let loggingContext: LoggingClientContext; let fileDescriptions: FileDescriptions; - let idGeneratorMock: sinon.SinonStubbedInstance; + let idGeneratorStub: sinon.SinonStubbedInstance; beforeEach(() => { childProcessProxyCreateStub = sinon.stub(ChildProcessProxy, 'create'); loggingContext = { port: 4200, level: LogLevel.Fatal }; fileDescriptions = { 'foo.js': { mutate: true } }; - idGeneratorMock = sinon.createStubInstance(IdGenerator); + idGeneratorStub = sinon.createStubInstance(IdGenerator); }); function createSut(): CheckerChildProcessProxy { - return new CheckerChildProcessProxy(testInjector.options, fileDescriptions, ['plugin', 'paths'], loggingContext, idGeneratorMock); + return new CheckerChildProcessProxy(testInjector.options, fileDescriptions, ['plugin', 'paths'], loggingContext, idGeneratorStub); } describe('constructor', () => { @@ -40,7 +40,7 @@ describe(CheckerChildProcessProxy.name, () => { process.cwd(), CheckerWorker, [], - idGeneratorMock + idGeneratorStub ); }); it('should provide arguments', () => { @@ -56,7 +56,7 @@ describe(CheckerChildProcessProxy.name, () => { sinon.match.any, sinon.match.any, ['foo', 'bar'], - idGeneratorMock + idGeneratorStub ); }); }); diff --git a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts index fe21aca872..7218cc38cc 100644 --- a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts +++ b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts @@ -41,6 +41,8 @@ class ChildProcessMock extends EventEmitter { public pid = 4648; } +let idGeneratorStub: sinon.SinonStubbedInstance; + describe(ChildProcessProxy.name, () => { let sut: ChildProcessProxy; let forkStub: sinon.SinonStub; @@ -48,7 +50,6 @@ describe(ChildProcessProxy.name, () => { let killStub: sinon.SinonStub; let logMock: Mock; let clock: sinon.SinonFakeTimers; - let idGenerator: IdGenerator; beforeEach(() => { clock = sinon.useFakeTimers(); @@ -57,7 +58,8 @@ describe(ChildProcessProxy.name, () => { killStub = sinon.stub(objectUtils, 'kill'); forkStub.returns(childProcessMock); logMock = currentLogMock(); - idGenerator = new IdGenerator(); + idGeneratorStub = sinon.createStubInstance(IdGenerator); + idGeneratorStub.next.returns(5); }); afterEach(() => { @@ -69,11 +71,10 @@ describe(ChildProcessProxy.name, () => { describe('constructor', () => { it('should create child process', () => { sut = createSut(); - const workerId = idGenerator.next().toString(); expect(forkStub).calledWith(fileURLToPath(new URL('../../../src/child-proxy/child-process-proxy-worker.js', import.meta.url)), { silent: true, execArgv: [], - env: { STRYKER_MUTATOR_WORKER: workerId }, + env: { STRYKER_MUTATOR_WORKER: '5', ...process.env }, }); }); @@ -88,15 +89,13 @@ describe(ChildProcessProxy.name, () => { createSut({ loggingContext: LOGGING_CONTEXT, execArgv: ['--cpu-prof', '--inspect'], - idGenerator, + idGenerator: idGeneratorStub, }); - - const nextWorkerId = (idGenerator.next() - 1).toString(); // Assert expect(logMock.debug).calledWith( 'Started %s in worker process %s with pid %s %s', 'HelloClass', - nextWorkerId, + '5', childProcessMock.pid, ' (using args --cpu-prof --inspect)' ); @@ -368,7 +367,7 @@ function createSut({ fileDescriptions = { 'foo.js': { mutate: true } }, pluginModulePaths = ['plugin', 'path'], execArgv = [], - idGenerator = new IdGenerator(), + idGenerator = idGeneratorStub, }: { requirePath?: string; loggingContext?: LoggingClientContext; @@ -377,7 +376,7 @@ function createSut({ fileDescriptions?: FileDescriptions; pluginModulePaths?: readonly string[]; execArgv?: string[]; - idGenerator?: IdGenerator; + idGenerator?: sinon.SinonStubbedInstance; } = {}): ChildProcessProxy { return ChildProcessProxy.create( requirePath, diff --git a/packages/core/test/unit/child-proxy/id-generator.spec.ts b/packages/core/test/unit/child-proxy/id-generator.spec.ts index e69de29bb2..9f83bd5d04 100644 --- a/packages/core/test/unit/child-proxy/id-generator.spec.ts +++ b/packages/core/test/unit/child-proxy/id-generator.spec.ts @@ -0,0 +1,15 @@ +import { expect } from 'chai'; + +import { IdGenerator } from '../../../src/child-proxy/id-generator.js'; + +describe(IdGenerator.name, () => { + let idGenerator: IdGenerator; + beforeEach(() => { + idGenerator = new IdGenerator(); + }); + it('should increment workerId on calling `next`', async () => { + const workerId = idGenerator.next(); + const nextWorkerId = idGenerator.next(); + expect(nextWorkerId - workerId).eq(1); + }); +}); From 47525b948e8bd5d69b2e770895879a3543411423 Mon Sep 17 00:00:00 2001 From: Ariba Siddiqui Date: Sun, 30 Oct 2022 15:14:52 +0100 Subject: [PATCH 5/6] nit: improvement --- .../core/test/unit/child-proxy/child-process-proxy.spec.ts | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts index 7218cc38cc..484bea236a 100644 --- a/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts +++ b/packages/core/test/unit/child-proxy/child-process-proxy.spec.ts @@ -50,6 +50,7 @@ describe(ChildProcessProxy.name, () => { let killStub: sinon.SinonStub; let logMock: Mock; let clock: sinon.SinonFakeTimers; + const workerId = 5; beforeEach(() => { clock = sinon.useFakeTimers(); @@ -59,7 +60,7 @@ describe(ChildProcessProxy.name, () => { forkStub.returns(childProcessMock); logMock = currentLogMock(); idGeneratorStub = sinon.createStubInstance(IdGenerator); - idGeneratorStub.next.returns(5); + idGeneratorStub.next.returns(workerId); }); afterEach(() => { @@ -74,7 +75,7 @@ describe(ChildProcessProxy.name, () => { expect(forkStub).calledWith(fileURLToPath(new URL('../../../src/child-proxy/child-process-proxy-worker.js', import.meta.url)), { silent: true, execArgv: [], - env: { STRYKER_MUTATOR_WORKER: '5', ...process.env }, + env: { STRYKER_MUTATOR_WORKER: workerId.toString(), ...process.env }, }); }); @@ -95,7 +96,7 @@ describe(ChildProcessProxy.name, () => { expect(logMock.debug).calledWith( 'Started %s in worker process %s with pid %s %s', 'HelloClass', - '5', + workerId.toString(), childProcessMock.pid, ' (using args --cpu-prof --inspect)' ); From 9d90ae089f36491dc98ff176bec3ed9f3a4e3185 Mon Sep 17 00:00:00 2001 From: Ariba Siddiqui Date: Sun, 30 Oct 2022 17:35:13 +0100 Subject: [PATCH 6/6] added missed coreToken and added one unit test --- packages/core/src/test-runner/index.ts | 2 +- packages/core/test/unit/child-proxy/id-generator.spec.ts | 6 +++++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/packages/core/src/test-runner/index.ts b/packages/core/src/test-runner/index.ts index 85bfc65ed8..1e838dc20d 100644 --- a/packages/core/src/test-runner/index.ts +++ b/packages/core/src/test-runner/index.ts @@ -23,7 +23,7 @@ createTestRunnerFactory.inject = tokens( coreTokens.loggingContext, commonTokens.getLogger, coreTokens.pluginModulePaths, - 'worker-id-generator' + coreTokens.workerIdGenerator ); export function createTestRunnerFactory( options: StrykerOptions, diff --git a/packages/core/test/unit/child-proxy/id-generator.spec.ts b/packages/core/test/unit/child-proxy/id-generator.spec.ts index 9f83bd5d04..99667741a5 100644 --- a/packages/core/test/unit/child-proxy/id-generator.spec.ts +++ b/packages/core/test/unit/child-proxy/id-generator.spec.ts @@ -7,7 +7,11 @@ describe(IdGenerator.name, () => { beforeEach(() => { idGenerator = new IdGenerator(); }); - it('should increment workerId on calling `next`', async () => { + it('should return 0 on first call to `next`', async () => { + const workerId = idGenerator.next(); + expect(workerId).eq(0); + }); + it('should increment `workerId` on calling `next`', async () => { const workerId = idGenerator.next(); const nextWorkerId = idGenerator.next(); expect(nextWorkerId - workerId).eq(1);