영호

[TypeORM] Active-record 패턴 본문

TypeORM

[TypeORM] Active-record 패턴

0h0 2022. 5. 19. 12:55
반응형

들어가며

이번 글에서는 공식문서에서 소개하는 TypeORM의 2가지 패턴 중 Active-record패턴에 대해 코드로 알아보겠습니다.

 

Active-recode패턴 이란?

  • 각 entity파일에서 정의한 쿼리 메소드들을 이용해 데이터베이스에 접근하는 패턴입니다. 그리고 entity파일들은 find, save등의 기본 기능을 제공해주는 BaseEntity를 상속받아야 합니다.
  • 크기가 크지 않고, 복잡하지 않은 프로젝트에 적용하기 좋은 패턴으로, 추후 프로젝트의 규모가 커지고, 복잡해질 경우 data-mapper패턴으로의 리팩토링을 고려해야 합니다.
BaseEntity는 repository의 표준 기능들을 다 가지고 있기 때문에 repository, EntityManager를 사용하지 않아도 됩니다.
repository는 data-mapper패턴에서 사용됩니다.
TypeORM 공식문서에 나와있는 내용을 번역 한겁니다.

 

Code

  • 아래 코드는 제가 진행하는 프로젝트 코드로 공식문서의 코드를 보고 싶으시면 링크를 참고해주세요.

entity/Mapping.ts

import {Entity, PrimaryGeneratedColumn, Column, CreateDateColumn, Timestamp, ManyToOne, JoinColumn, OneToMany, BaseEntity} from "typeorm";
import { Alarm } from './Alarm';
import {BabySitter} from './BabySitter'
import {Parent} from './Parent'
import { WorkDiary } from './WorkDiary';

@Entity()
export class Mapping extends BaseEntity {

    @PrimaryGeneratedColumn()
    mappingId: number;

    @CreateDateColumn({})
    createdAt: Timestamp

    // 1: 매핑된거 2: 대기 3: 거절
    @Column({default : 2})
    status : number

    // mapping(N) <->  baby sitter(1)
    @ManyToOne(
        () => BabySitter, 
        babySitter => babySitter.mapping, { nullable: false, onDelete: 'CASCADE' })
    @JoinColumn({name: "bsId"})
    babySitter : BabySitter

    
    // mapping(N) <->  baby parent(1)
    @ManyToOne(
        () => Parent, 
        parent => parent.mapping, { nullable: false, onDelete: 'CASCADE' }
        )
    @JoinColumn({name: "parentId"})
    parent : Parent


    // Mapping(1) <-> Alarm(N)
    @OneToMany(
        () => Alarm,
        alarm => alarm.mapping,{ nullable: false, onDelete: 'CASCADE' }
    )
    alarm: Alarm[];


    // Mapping(1) <-> WorkDiary(N)
    @OneToMany(
        () => WorkDiary,
        workDiary => workDiary.mapping,{ nullable: false, onDelete: 'CASCADE' }
    )
    diary: WorkDiary[];

    // 부모 ID를 기준으로 매핑되어 있는 보모 정보를 반환
    static async findMappingList(parentId: number) {
        return await this.createQueryBuilder("mapping")
            .leftJoinAndSelect("mapping.babySitter", "babySitter")
            .where("mapping.parentId = :parentId", { parentId: parentId })
            .getMany();
    }


    // 이미 동일한 요청이 있는 경우 체크하기 위한 함수
    static async checkDuplicate(parentId: number, bsId: number){

        return await this.createQueryBuilder("mapping")
            .where("mapping.parentId = :parentId", {parentId:parentId})
            .andWhere("mapping.bsId = :bsId", {bsId:bsId})
            .getMany();
    }
}
  • static을 이용해 외부에서 Mapping.ts의 객체를 만들지 않고 .ts파일로 메소드를 사용할 수 있게 해줬습니다.

 

controllers/mapping.ts

import { NextFunction, Request, Response } from 'express';
import { BabySitter } from '../entity/BabySitter';
import { Mapping } from '../entity/Mapping';

const findParentList = async (req:Request, res: Response, next: NextFunction) => {
    try{
        const bsId : number = +req.params.bsId; 
    
    await BabySitter.findById(bsId)
    const result = await Mapping.findMappingParentList(bsId);

    
}

export default{
    findParentList
}
  • entity/Mapping.ts에서 정의한 쿼리 메소드들을 이용해 DB를 다루는 코드입니다.

 

마무리

  • 지금까지 Active-record패턴에 대해 알아봤습니다. 단순하게 entity파일에 필요한 메소드들을 정의하고 외부에서 해당 메소드를 이용하면 되기 때문에 사용방법은 매우 쉽다는 느낌을 받았습니다.
  •  추후 data-mapper패턴에 대해서도 알아보겠습니다.
반응형

'TypeORM' 카테고리의 다른 글

[TypeORM] @Transaction 적용  (0) 2022.05.20
[TypeORM] TypeORM entity 작성  (0) 2022.05.14
[TypeORM] 공식문서로 TypeORM + MySQL설정하기  (0) 2022.05.09
Comments