NestJS Tutorial (8) - TypeORM

Hoony·2023년 6월 27일
0

NestJS

목록 보기
8/8


TypeORM 설치

# Nest.js에서 TypeORM을 연동시켜주기 위해 사용하는 모듈
$ npm install --save @nestjs/typeorm

# typeorm module
$ npm install --save typeorm

# install mysql
$ npm install --save mysql2


Typeorm Config 설정하기

typeorm.config.ts

import { TypeOrmModuleOptions } from '@nestjs/typeorm/dist/interfaces/typeorm-options.interface';
import { Member } from './member/entities/member.entity';

export const typeORMConfig: TypeOrmModuleOptions = {
  type: 'mysql',
  host: '127.0.0.1',
  port: 3306,
  username: 'root',
  password: '1234',
  database: 'nestjs_tutorial',
  entities: [Member],
  synchronize: true,
};

synchronize 는 엔티티와 데이터베이스 테이블을 자동으로 동기화할지 여부를 지정합니다.

만약 현재 엔티티와 데이터베이스 간의 불일치가 존재하면 해당 테이블을 DROP 한 뒤 다시 생성합니다.

  • 반드시 개발 단계에서만 사용해야 합니다. 배포 단계에서는 false로 설정해야 데이터 손실이 없습니다.

app.module.ts

@Module({
  imports: [TypeOrmModule.forRoot(typeORMConfig), MemberModule],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}

App Module 에 위에서 설정한 TypeORMConfig를 연결해줍니다.



Resoure 생성

직접 entity, repository, service, controller 등 생성하는 방법도 있지만, cli를 통해 한번에 생성할 수 있습니다.

$ nest g resource [entity-name]


TEAM Resource 생성

team.entity.ts

export class Team {}

team.service.ts

import { Injectable } from '@nestjs/common';
import { CreateTeamDto } from './dto/create-team.dto';
import { UpdateTeamDto } from './dto/update-team.dto';

@Injectable()
export class TeamService {
  create(createTeamDto: CreateTeamDto) {
    return 'This action adds a new team';
  }

  findAll() {
    return `This action returns all team`;
  }

  findOne(id: number) {
    return `This action returns a #${id} team`;
  }

  update(id: number, updateTeamDto: UpdateTeamDto) {
    return `This action updates a #${id} team`;
  }

  remove(id: number) {
    return `This action removes a #${id} team`;
  }
}

team.controller.ts

import { Controller, Get, Post, Body, Patch, Param, Delete } from '@nestjs/common';
import { TeamService } from './team.service';
import { CreateTeamDto } from './dto/create-team.dto';
import { UpdateTeamDto } from './dto/update-team.dto';

@Controller('team')
export class TeamController {
  constructor(private readonly teamService: TeamService) {}

  @Post()
  create(@Body() createTeamDto: CreateTeamDto) {
    return this.teamService.create(createTeamDto);
  }

  @Get()
  findAll() {
    return this.teamService.findAll();
  }

  @Get(':id')
  findOne(@Param('id') id: string) {
    return this.teamService.findOne(+id);
  }

  @Patch(':id')
  update(@Param('id') id: string, @Body() updateTeamDto: UpdateTeamDto) {
    return this.teamService.update(+id, updateTeamDto);
  }

  @Delete(':id')
  remove(@Param('id') id: string) {
    return this.teamService.remove(+id);
  }
}

team.module.ts

import { Module } from '@nestjs/common';
import { TeamService } from './team.service';
import { TeamController } from './team.controller';

@Module({
  controllers: [TeamController],
  providers: [TeamService],
})
export class TeamModule {}

이런 식으로 기본적인 형태를 지닌 entity, service, controller, module이 생성됩니다.

이후 함수 안에 세부적인 로직만 넣으면 간단한 CRUD는 금방 구현할 수 있습니다.



Entity 설정

@Entity 데코레이션을 통해 엔티티를 설정합니다.

이후 @Column 데코레이션들을 통해 Entity 칼럼들을 설정합니다.


@Entity({ name: 'member' })
export class Member {
  @PrimaryGeneratedColumn({ name: 'member_id' })
  id: number;

  @Column({ length: 50 })
  name: string;

  @Column()
  age: number;

  @Column()
  gender: boolean; //남자1, 여자0

  @CreateDateColumn({ name: 'created_at' })
  createdAt: Date;

  @UpdateDateColumn({ name: 'updated_at' })
  updatedAt: Date;

  @DeleteDateColumn({ name: 'deleted_at' })
  deletedAt?: Date;

}

이후 moduletyeporm.config.ts 에 해당 entity를 설정합니다.

app.module.ts

@Module({
  imports: [TypeOrmModule.forRoot(typeORMConfig), MemberModule],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}

typeorm.config.ts

import { TypeOrmModuleOptions } from '@nestjs/typeorm/dist/interfaces/typeorm-options.interface';
import { Member } from './member/entities/member.entity';
import { Team } from './team/entities/team.entity';

export const typeORMConfig: TypeOrmModuleOptions = {
  type: 'mysql',
  host: '127.0.0.1',
  port: 3306,
  username: 'root',
  password: '1234',
  database: 'nestjs_tutorial',
  entities: [Member],
  synchronize: true,
};


Service 설정 - 간단한 CRUD 구현

@InjectRepository 데코레이션을 통해 해당 엔티티의 Repository 의존성 주입합니다.

이후 Reposiotry 내부의 메서드를 이용하여 엔티티 CRUD 로직을 구현합니다.

@Injectable()
export class MemberService {
  constructor(
    @InjectRepository(Member) private memberRepository: Repository<Member>,
  ) {}

  async create(createMemberDto: CreateMemberDto): Promise<Member> {
    const newMember = this.memberRepository.create(createMemberDto);
    return this.memberRepository.save(newMember);
  }

  async findAll(): Promise<Member[]> {
    return await this.memberRepository.find();
  }

  async findOne(id: number): Promise<Member> {
    const member = await this.memberRepository.findOne({ where: { id: id } });

    if (!member) {
      throw new NotFoundException('Member not found');
    }

    return member;
  }

  async update(id: number, updateMemberDto: UpdateMemberDto): Promise<Member> {
    const updateResult = await this.memberRepository.update(
      id,
      updateMemberDto,
    );

    if (updateResult.affected === 0) {
      throw new NotFoundException('Member not found');
    }

    return this.memberRepository.findOne({ where: { id: id } });
  }

  async remove(id: number) {
    const deleteResult = await this.memberRepository.delete(id);

    if (deleteResult.affected === 0) {
      throw new NotFoundException('Member not found');
    }
  }
}

이때, 해당 service의 module 에 엔티티를 등록해야 Repository<Entity> 인식이 가능합니다.

member.module.ts

@Module({
  imports: [TypeOrmModule.forFeature([Member])],
  controllers: [MemberController],
  providers: [MemberService],
})
export class MemberModule {}


Controller 설정

다음과 같이 constructor에 위에서 만든 service 객체를 의존성 주입합니다.

@Controller('members')
export class MemberController {
  constructor(private readonly memberService: MemberService) {}

  @Post()
  create(@Body() createMemberDto: CreateMemberDto) {
    return this.memberService.create(createMemberDto);
  }

  @Get()
  findAll() {
    return this.memberService.findAll();
  }

  @Get(':id')
  findOne(@Param('id') id: string) {
    return this.memberService.findOne(+id);
  }

  @Patch(':id')
  update(@Param('id') id: string, @Body() updateMemberDto: UpdateMemberDto) {
    return this.memberService.update(+id, updateMemberDto);
  }

  @Delete(':id')
  remove(@Param('id') id: string) {
    return this.memberService.remove(+id);
  }
}
profile
Just Do it!

0개의 댓글

관련 채용 정보