diff --git a/packages/ddd-toolkit/.changeset/slimy-queens-sniff.md b/packages/ddd-toolkit/.changeset/slimy-queens-sniff.md new file mode 100644 index 0000000..31fc184 --- /dev/null +++ b/packages/ddd-toolkit/.changeset/slimy-queens-sniff.md @@ -0,0 +1,5 @@ +--- +'@fizzbuds/ddd-toolkit': minor +--- + +throw on send with unregistered command handler diff --git a/packages/ddd-toolkit/src/command-bus/local-command-bus.spec.ts b/packages/ddd-toolkit/src/command-bus/local-command-bus.spec.ts index 46d0b45..6d40ed1 100644 --- a/packages/ddd-toolkit/src/command-bus/local-command-bus.spec.ts +++ b/packages/ddd-toolkit/src/command-bus/local-command-bus.spec.ts @@ -39,9 +39,9 @@ describe('LocalCommandBus', () => { describe('When send a foo command', () => { it('Should log warning message', async () => { const command = new FooCommand({ foo: 'bar' }); - await commandBus.send(command); - - expect(loggerMock.warn).toBeCalledWith(`No handler found for ${FooCommand.name}`); + await expect(async () => await commandBus.send(command)).rejects.toThrow( + `No handler found for ${FooCommand.name}`, + ); }); }); }); @@ -64,7 +64,7 @@ describe('LocalCommandBus', () => { const command = new FooCommand({ foo: 'bar' }); await commandBus.send(command); - await waitFor(() => expect(FooHandlerMock).toBeCalledWith(command)); + await waitFor(() => expect(FooHandlerMock).toHaveBeenCalledWith(command)); }); }); @@ -97,8 +97,8 @@ describe('LocalCommandBus', () => { const command = new FooCommand({ foo: 'bar' }); await commandBus.send(command); - await waitFor(() => expect(FooHandlerMock).toBeCalledWith(command)); - expect(BarHandlerMock).not.toBeCalled(); + await waitFor(() => expect(FooHandlerMock).toHaveBeenCalledWith(command)); + expect(BarHandlerMock).not.toHaveBeenCalled(); }); }); @@ -107,8 +107,8 @@ describe('LocalCommandBus', () => { const command = new BarCommand({ foo: 'bar' }); await commandBus.send(command); - expect(FooHandlerMock).not.toBeCalled(); - expect(BarHandlerMock).toBeCalledWith(command); + expect(FooHandlerMock).not.toHaveBeenCalled(); + expect(BarHandlerMock).toHaveBeenCalledWith(command); }); }); }); @@ -135,21 +135,21 @@ describe('LocalCommandBus', () => { it('handler should be called two times', async () => { await waitFor(() => { - expect(handlerMock).toBeCalledTimes(2); + expect(handlerMock).toHaveBeenCalledTimes(2); }); }); it('should not log error for failing handler', async () => { await waitFor(() => { - expect(handlerMock).toBeCalledTimes(2); - expect(loggerMock.error).not.toBeCalled(); + expect(handlerMock).toHaveBeenCalledTimes(2); + expect(loggerMock.error).not.toHaveBeenCalled(); }); }); it('should log one retry for failing handler', async () => { await waitFor(() => { - expect(loggerMock.warn).toBeCalledTimes(1); - expect(loggerMock.warn).toBeCalledWith( + expect(loggerMock.warn).toHaveBeenCalledTimes(1); + expect(loggerMock.warn).toHaveBeenCalledWith( expect.stringContaining( 'FooCommandHandlerOk failed to handle FooCommand command. Attempt 1/3', ), diff --git a/packages/ddd-toolkit/src/command-bus/local-command-bus.ts b/packages/ddd-toolkit/src/command-bus/local-command-bus.ts index c270bc8..c722d3c 100644 --- a/packages/ddd-toolkit/src/command-bus/local-command-bus.ts +++ b/packages/ddd-toolkit/src/command-bus/local-command-bus.ts @@ -26,10 +26,7 @@ export class LocalCommandBus implements ICommandBus { public async send>(command: C): Promise { const handler = this.handlers[command.name] as ICommandHandler; - if (!handler) { - this.logger.warn(`No handler found for ${command.name}`); - return; - } + if (!handler) throw new Error(`No handler found for ${command.name}`); void this.handleCommand(command, handler); } @@ -37,6 +34,7 @@ export class LocalCommandBus implements ICommandBus { public async sendSync>(command: C): Promise { const handler = this.handlers[command.name] as ICommandHandler; if (!handler) throw new Error(`No handler found for ${command.name}`); + return await handler.handle(command); }