Skip to content

Commit

Permalink
fix: 쿼리 인터페이스 대신 레포지토리를 사용하도록 수정 (#72)
Browse files Browse the repository at this point in the history
  • Loading branch information
Coalery authored Oct 15, 2024
2 parents c9e5289 + 6884aee commit 21f00f8
Show file tree
Hide file tree
Showing 8 changed files with 108 additions and 61 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,9 @@ import { Test } from '@nestjs/testing';
import { advanceTo, clear } from 'jest-date-mock';

import { UpdateDoorLockPasswordCommand } from '@khlug/app/application/infraBlue/command/updateDoorLockPassword/UpdateDoorLockPasswordCommand';
import {
FACILITY_TEAM_PASSWORD_CACHE_ID,
JAJUDY_PASSWORD_CACHE_ID,
MASTER_PASSWORD_CACHE_ID,
UpdateDoorLockPasswordCommandHandler,
} from '@khlug/app/application/infraBlue/command/updateDoorLockPassword/UpdateDoorLockPasswordCommandHandler';
import { UpdateDoorLockPasswordCommandHandler } from '@khlug/app/application/infraBlue/command/updateDoorLockPassword/UpdateDoorLockPasswordCommandHandler';

import { Cache } from '@khlug/app/domain/cache/model/Cache';
import { Cache, CacheId } from '@khlug/app/domain/cache/model/Cache';

import { CacheFixture } from '@khlug/__test__/fixtures/CacheFixture';
import { Message } from '@khlug/constant/message';
Expand Down Expand Up @@ -58,15 +53,15 @@ describe('UpdateDoorLockPasswordCommandHandler', () => {

test('비밀번호를 변경해야 한다', async () => {
const masterPassword = CacheFixture.raw({
id: MASTER_PASSWORD_CACHE_ID,
id: CacheId.masterPassword,
content: 'oldMaster',
});
const jajudyPassword = CacheFixture.raw({
id: JAJUDY_PASSWORD_CACHE_ID,
id: CacheId.jajudyPassword,
content: 'oldJajudy',
});
const facilityTeamPassword = CacheFixture.raw({
id: FACILITY_TEAM_PASSWORD_CACHE_ID,
id: CacheId.facilityTeamPassword,
content: 'oldFacilityTeam',
});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,10 @@ import { CommandHandler, ICommandHandler } from '@nestjs/cqrs';

import { UpdateDoorLockPasswordCommand } from '@khlug/app/application/infraBlue/command/updateDoorLockPassword/UpdateDoorLockPasswordCommand';

import { Cache } from '@khlug/app/domain/cache/model/Cache';
import { Cache, CacheId } from '@khlug/app/domain/cache/model/Cache';

import { Message } from '@khlug/constant/message';

export const MASTER_PASSWORD_CACHE_ID = '100';
export const JAJUDY_PASSWORD_CACHE_ID = '101';
export const FACILITY_TEAM_PASSWORD_CACHE_ID = '102';

@CommandHandler(UpdateDoorLockPasswordCommand)
export class UpdateDoorLockPasswordCommandHandler
implements ICommandHandler<UpdateDoorLockPasswordCommand, void>
Expand All @@ -28,21 +24,21 @@ export class UpdateDoorLockPasswordCommandHandler
const passwords = await this.cacheRepository.find({
id: {
$in: [
MASTER_PASSWORD_CACHE_ID,
JAJUDY_PASSWORD_CACHE_ID,
FACILITY_TEAM_PASSWORD_CACHE_ID,
CacheId.masterPassword,
CacheId.jajudyPassword,
CacheId.facilityTeamPassword,
],
},
});

const masterPassword = passwords.find(
(password) => password.id === MASTER_PASSWORD_CACHE_ID,
(password) => password.id === CacheId.masterPassword,
);
const jajudyPassword = passwords.find(
(password) => password.id === JAJUDY_PASSWORD_CACHE_ID,
(password) => password.id === CacheId.jajudyPassword,
);
const facilityTeamPassword = passwords.find(
(password) => password.id === FACILITY_TEAM_PASSWORD_CACHE_ID,
(password) => password.id === CacheId.facilityTeamPassword,
);

if (!masterPassword || !jajudyPassword || !facilityTeamPassword) {
Expand Down
7 changes: 0 additions & 7 deletions src/app/application/infraBlue/query/ICacheQuery.ts

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,17 +1,19 @@
import { EntityRepository } from '@mikro-orm/mysql';
import { getRepositoryToken } from '@mikro-orm/nestjs';
import { Test } from '@nestjs/testing';
import { advanceTo, clear } from 'jest-date-mock';

import { GetDoorLockPasswordQueryHandler } from '@khlug/app/application/infraBlue/query/getDoorLockPassword/GetDoorLockPasswordQueryHandler';
import { GetDoorLockPasswordQueryResult } from '@khlug/app/application/infraBlue/query/getDoorLockPassword/GetDoorLockPasswordQueryResult';
import {
CacheQueryToken,
ICacheQuery,
} from '@khlug/app/application/infraBlue/query/ICacheQuery';
import { DoorLockPasswordView } from '@khlug/app/application/infraBlue/query/view/DoorLockPasswordView';

import { Cache, CacheId } from '@khlug/app/domain/cache/model/Cache';

import { CacheFixture } from '@khlug/__test__/fixtures/CacheFixture';
import { Message } from '@khlug/constant/message';

describe('GetDoorLockPasswordQueryHandler', () => {
let handler: GetDoorLockPasswordQueryHandler;
let cacheQuery: jest.Mocked<ICacheQuery>;
let cacheRepository: jest.Mocked<EntityRepository<Cache>>;

beforeAll(() => advanceTo(new Date()));

Expand All @@ -22,30 +24,53 @@ describe('GetDoorLockPasswordQueryHandler', () => {
providers: [
GetDoorLockPasswordQueryHandler,
{
provide: CacheQueryToken,
useValue: { getDoorLockPassword: jest.fn() },
provide: getRepositoryToken(Cache),
useValue: { find: jest.fn() },
},
],
}).compile();

handler = testModule.get(GetDoorLockPasswordQueryHandler);
cacheQuery = testModule.get(CacheQueryToken);
cacheRepository = testModule.get(getRepositoryToken(Cache));
});

afterEach(() => clear());

describe('execute', () => {
test('도어락 비밀번호 뷰를 반환해야 한다', async () => {
const view: DoorLockPasswordView = {
master: '1234',
forJajudy: '2345',
forFacilityTeam: '3456',
};
test('도어락 비밀번호가 존재하지 않으면 예외를 발생시켜야 한다', async () => {
cacheRepository.find.mockResolvedValue([]);

await expect(handler.execute()).rejects.toThrow(
Message.SOME_DOOR_LOCK_PASSWORD_NOT_FOUND,
);
});

test('도어락 비밀번호를 반환해야 한다', async () => {
const masterPassword = CacheFixture.raw({
id: CacheId.masterPassword,
content: 'master',
});
const jajudyPassword = CacheFixture.raw({
id: CacheId.jajudyPassword,
content: 'jajudy',
});
const facilityTeamPassword = CacheFixture.raw({
id: CacheId.facilityTeamPassword,
content: 'facilityTeam',
});

cacheQuery.getDoorLockPassword.mockResolvedValue(view);
cacheRepository.find.mockResolvedValue([
masterPassword,
jajudyPassword,
facilityTeamPassword,
]);

const result = await handler.execute();
const expected = new GetDoorLockPasswordQueryResult(view);
const expected = new GetDoorLockPasswordQueryResult({
master: 'master',
forJajudy: 'jajudy',
forFacilityTeam: 'facilityTeam',
});

expect(result).toEqual(expected);
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,25 +1,54 @@
import { Inject } from '@nestjs/common';
import { EntityRepository } from '@mikro-orm/mysql';
import { InjectRepository } from '@mikro-orm/nestjs';
import { NotFoundException } from '@nestjs/common';
import { IQueryHandler, QueryHandler } from '@nestjs/cqrs';

import { GetDoorLockPasswordQuery } from '@khlug/app/application/infraBlue/query/getDoorLockPassword/GetDoorLockPasswordQuery';
import { GetDoorLockPasswordQueryResult } from '@khlug/app/application/infraBlue/query/getDoorLockPassword/GetDoorLockPasswordQueryResult';
import {
CacheQueryToken,
ICacheQuery,
} from '@khlug/app/application/infraBlue/query/ICacheQuery';

import { Cache, CacheId } from '@khlug/app/domain/cache/model/Cache';

import { Message } from '@khlug/constant/message';

@QueryHandler(GetDoorLockPasswordQuery)
export class GetDoorLockPasswordQueryHandler
implements
IQueryHandler<GetDoorLockPasswordQuery, GetDoorLockPasswordQueryResult>
{
constructor(
@Inject(CacheQueryToken)
private readonly cacheQuery: ICacheQuery,
@InjectRepository(Cache)
private readonly cacheRepository: EntityRepository<Cache>,
) {}

async execute(): Promise<GetDoorLockPasswordQueryResult> {
const doorLockPasswordView = await this.cacheQuery.getDoorLockPassword();
return new GetDoorLockPasswordQueryResult(doorLockPasswordView);
const passwords = await this.cacheRepository.find({
id: {
$in: [
CacheId.masterPassword,
CacheId.jajudyPassword,
CacheId.facilityTeamPassword,
],
},
});

const masterPassword = passwords.find(
(password) => password.id === CacheId.masterPassword,
);
const jajudyPassword = passwords.find(
(password) => password.id === CacheId.jajudyPassword,
);
const facilityTeamPassword = passwords.find(
(password) => password.id === CacheId.facilityTeamPassword,
);

if (!masterPassword || !jajudyPassword || !facilityTeamPassword) {
throw new NotFoundException(Message.SOME_DOOR_LOCK_PASSWORD_NOT_FOUND);
}

return new GetDoorLockPasswordQueryResult({
master: masterPassword.content,
forJajudy: jajudyPassword.content,
forFacilityTeam: facilityTeamPassword.content,
});
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,15 @@
import { IQueryResult } from '@nestjs/cqrs';

import { DoorLockPasswordView } from '@khlug/app/application/infraBlue/query/view/DoorLockPasswordView';
import { Typeof } from '@khlug/util/types';

export class GetDoorLockPasswordQueryResult implements IQueryResult {
constructor(readonly view: DoorLockPasswordView) {}
master: string;
forJajudy: string;
forFacilityTeam: string;

constructor(params: Typeof<GetDoorLockPasswordQueryResult>) {
this.master = params.master;
this.forJajudy = params.forJajudy;
this.forFacilityTeam = params.forFacilityTeam;
}
}

This file was deleted.

6 changes: 6 additions & 0 deletions src/app/domain/cache/model/Cache.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,12 @@ export type CacheConstructorParams = {
updatedAt: Date;
};

export const CacheId = {
masterPassword: '100',
jajudyPassword: '101',
facilityTeamPassword: '102',
};

// 흔히 사용되는 용어 "캐시"를 가리키는 것이 아님.
// 레거시 모델로써, 테이블로 만들기에는 데이터의 수가 상당히 적으나,
// 동적으로 변경되어야 하는 데이터들이 모여있는 테이블.
Expand Down

0 comments on commit 21f00f8

Please sign in to comment.