Skip to content

Commit

Permalink
Register Client Use Case Unit Test
Browse files Browse the repository at this point in the history
  • Loading branch information
AnderGI committed Feb 15, 2025
1 parent 8404e10 commit 940eb3a
Show file tree
Hide file tree
Showing 17 changed files with 212 additions and 1 deletion.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@
"rabbitmq:configure": "npx ts-node ./src/scripts/configure-rabbitmq/configure-rabbitmq.ts",
"rabbitmq:consume": "npx ts-node ./src/scripts/configure-rabbitmq/consume-rabbitmq.ts",
"test:backoffice:backend:spotify-user":"npm run test:backoffice:backend:spotify-user:unit && npm run test:backoffice:backend:spotify-user:integration",
"test:backoffice:backend:spotify-user:unit":"cross-env NODE_ENV=test jest --passWithNoTests --testPathPattern './tests/contexts/backoffice/spotify-user/application/.*\\.test\\.ts'",
"test:backoffice:backend:clients:unit":"cross-env NODE_ENV=test jest --passWithNoTests --testPathPattern './tests/contexts/backoffice/clients/application/.*\\.test\\.ts'",
"test:backoffice:backend:spotify-user:integration":"cross-env NODE_ENV=test NODE_OPTIONS=\"--experimental-vm-modules\" jest --passWithNoTests --testPathPattern './tests/contexts/backoffice/spotify-user/infrastructure/.*/.*\\.test\\.ts'"
},
"dependencies": {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import Client from '../../domain/Client';
import ClientRepository from '../../domain/ClientRepository';
import RegisterClientCommand from './RegisterClientCommand';

export default class ClientRegistrar {
constructor(private readonly repository: ClientRepository) {}
async registar(command: RegisterClientCommand): Promise<void> {
await Client.save(command)(this.repository);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import Command from '../../../../../shared/domain/command/Command';

type CreateClientPrimitives = {
id: string;
name: string;
email: string;
phone: string;
company: string;
position: string;
};
export default class RegisterClientCommand implements Command {
constructor(readonly data: CreateClientPrimitives) {}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import Command from '../../../../../shared/domain/command/Command';
import CommandHandler from '../../../../../shared/domain/command/CommandHandler';
import ClientRegistrar from './ClientRegistrar';
import RegisterClientCommand from './RegisterClientCommand';

export default class RegisterClientCommandHandler implements CommandHandler<RegisterClientCommand> {
constructor(private readonly registrar: ClientRegistrar) {}

subscribedTo(): Command {
return RegisterClientCommand;
}

async handle(command: RegisterClientCommand): Promise<void> {
await this.registrar.registar(command);
}
}
56 changes: 56 additions & 0 deletions src/contexts/backoffice/clients/domain/Client.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
import RegisterClientCommand from '../application/register/RegisterClientCommand';
import ClientCompany from './ClientCompany';
import ClientEmail from './ClientEmail';
import ClientId from './ClientId';
import ClientName from './ClientName';
import ClientPhone from './ClientPhone';
import ClientPosition from './ClientPosition';
import ClientRepository from './ClientRepository';
import ClientSaver from './save/ClientSaver';

type CreateClientPrimitives = {
id: string;
name: string;
email: string;
phone: string;
company: string;
position: string;
};
export default class Client {
constructor(
readonly id: ClientId,
readonly name: ClientName,
readonly email: ClientEmail,
readonly phone: ClientPhone,
readonly company: ClientCompany,
readonly position: ClientPosition
) {}

public static create(_: CreateClientPrimitives): Client {
return new Client(
new ClientId(_.id),
new ClientName(_.name),
new ClientEmail(_.email),
new ClientPhone(_.phone),
new ClientCompany(_.company),
new ClientPosition(_.position)
);
}

public static fromPrimitives(_: CreateClientPrimitives): Client {
return new Client(
new ClientId(_.id),
new ClientName(_.name),
new ClientEmail(_.email),
new ClientPhone(_.phone),
new ClientCompany(_.company),
new ClientPosition(_.position)
);
}

static save(command: RegisterClientCommand) {
return async (repository: ClientRepository): Promise<void> => {
await ClientSaver.save(command, repository);
};
}
}
3 changes: 3 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientCompany.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import { StringValueObject } from '../../../shared/domain/value-object/StringValueObject';

export default class ClientCompany extends StringValueObject {}
3 changes: 3 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientEmail.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import { StringValueObject } from '../../../shared/domain/value-object/StringValueObject';

export default class ClientEmail extends StringValueObject {}
3 changes: 3 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientId.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import { UuidValueObject } from '../../../shared/domain/value-object/UuidValueObject';

export default class ClientId extends UuidValueObject {}
3 changes: 3 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientName.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import { StringValueObject } from '../../../shared/domain/value-object/StringValueObject';

export default class ClientName extends StringValueObject {}
3 changes: 3 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientPhone.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import { StringValueObject } from '../../../shared/domain/value-object/StringValueObject';

export default class ClientPhone extends StringValueObject {}
3 changes: 3 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientPosition.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import { StringValueObject } from '../../../shared/domain/value-object/StringValueObject';

export default class ClientPosition extends StringValueObject {}
5 changes: 5 additions & 0 deletions src/contexts/backoffice/clients/domain/ClientRepository.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import Client from './Client';

export default interface ClientRepository {
save(_: Client): Promise<void>;
}
18 changes: 18 additions & 0 deletions src/contexts/backoffice/clients/domain/save/ClientSaver.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import RegisterClientCommand from '../../application/register/RegisterClientCommand';
import Client from '../Client';
import ClientRepository from '../ClientRepository';

export default class ClientSaver {
static async save(command: RegisterClientCommand, repository: ClientRepository): Promise<void> {
const { data } = command;
const client = Client.create({
id: data.id,
name: data.name,
email: data.email,
phone: data.phone,
company: data.company,
position: data.position
});
await repository.save(client);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import ClientRegistrar from '../../../../../../src/contexts/backoffice/clients/application/register/ClientRegistrar';
import RegisterClientCommandHandler from '../../../../../../src/contexts/backoffice/clients/application/register/RegisterClientCommandHandler';
import { ClientMother } from '../../domain/ClientMother';
import MockClientRepository from '../../domain/MockClientRepository';
import { RegisterClientCommandMother } from './RegisterClientCommandMother';

describe('ClientRegistrar', () => {
describe('#register', () => {
it('Should register a non existing client', () => {
const command = RegisterClientCommandMother.random();
const repository = new MockClientRepository();
const client = ClientMother.fromCommand(command);
const registar = new ClientRegistrar(repository);
const handler = new RegisterClientCommandHandler(registar);

handler.handle(command);

repository.ensureSaveHasBeenCalledWith(client);
});
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import * as fs from 'faker';

import RegisterClientCommand from '../../../../../../src/contexts/backoffice/clients/application/register/RegisterClientCommand';

export class RegisterClientCommandMother {
static random(): RegisterClientCommand {
const primitives = {
id: fs.datatype.uuid(),
name: fs.name.firstName(),
email: fs.internet.email(),
phone: fs.phone.phoneNumber(),
company: fs.company.companyName(),
position: fs.name.jobType()
};

return new RegisterClientCommand(primitives);
}
}
17 changes: 17 additions & 0 deletions tests/contexts/backoffice/clients/domain/ClientMother.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import RegisterClientCommand from '../../../../../src/contexts/backoffice/clients/application/register/RegisterClientCommand';
import Client from '../../../../../src/contexts/backoffice/clients/domain/Client';

export class ClientMother {
static fromCommand(_: RegisterClientCommand): Client {
const { data } = _;

return Client.fromPrimitives({
id: data.id,
name: data.name,
email: data.email,
phone: data.phone,
company: data.company,
position: data.position
});
}
}
19 changes: 19 additions & 0 deletions tests/contexts/backoffice/clients/domain/MockClientRepository.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import Client from '../../../../../src/contexts/backoffice/clients/domain/Client';
import ClientRepository from '../../../../../src/contexts/backoffice/clients/domain/ClientRepository';

export default class MockClientRepository implements ClientRepository {
private readonly mockSave: jest.Mock;
constructor() {
this.mockSave = jest.fn();
}

async save(_: Client): Promise<void> {
this.mockSave(_);

return Promise.resolve();
}

ensureSaveHasBeenCalledWith(client: Client): void {
expect(this.mockSave).toHaveBeenCalledWith(client);
}
}

0 comments on commit 940eb3a

Please sign in to comment.