Skip to content

MoggoseJS 에서 TypeSript 사용하기

Kimakjun edited this page Nov 22, 2020 · 1 revision

MongooseJS Typescript



Mongoose 에서 Typescript 적용하기 🦖


  • 스키마 & 모델 생성 방법
import monggoes, { Model } from 'mongoose';

interface IUser extends monggoes.Document{
    nick: string;
    email: string;
    password: string;
}

const userSchema: Schema  = new monggoes.Schema({
    nick: {
        type: String,
        required: true
    },
    email: {
        type: String,
        required: true
    },
    password: {
        type: String,
        required: true
    },
})



export const UserModel = monggoes.model<IUser>("User", userSchema);
  • UserShema를 생성하기위해 IUser 라는 인터페이스를 정의했다. 이때 monggoes.Document 를 상속 받아서 interface 를 정의해줘야한다. monggoes.Document 를 상속받아야 기본적으로 몽고디비 다큐먼트 내장되어있는 document.save() 같은 함수를 사용 하기 위함이다.

ex)

   const user = new UserModel({nick, email, password});
   user.save()


몽고디비 사용자 정의 함수 🐎

몽구스는 스키마나 다큐먼트에 사용자 정의함수를 구현 할 수 있는 편의 기능을 제공한다. 다큐먼트 같은 경우는 userSchema.methods.함수 로 생성하고 스키마 같은 경우는 userSchema.statics.함수로 생성이 가능하다.

  1. 다큐먼트 사용자 정의함수는 스키마로 생성된 다큐먼트로 실행할 수 있는 함수이다. 이때 getEmail 이메일 안에서 this 는 이함수를 실행시키는 다큐먼트 객체를 가르키게 된다. Arrow function 을 쓰게 되면 this 를 찾을 수 없기때문에 function(){} 형태로 함수를 구현했다.다큐먼트 사용자 정의함수 같은 경우는 스키마 인터페이스에 해당 함수를 추가해주면된다.

ex)

선언)

interface IUser extends monggoes.Document{
    nick: string;
    email: string;
    password: string;
    getEmail(): string;
}

userSchema.methods.getEmail = function(){
    return this.email;
} 
// 사용
import {UserModel} from '@models/user';

const newUser = await UserModel.create({
                    nick,
                    email,
                    password, 
                })
console.log(newUser.getEmail());




  1. 스키마 사용자 정의함수는 스키마 모델로 생성된 다큐먼트에서 사용하는 함수가 아닌 모델 자체에서 사용할 수 있는 함수이다.

ex)

선언)
   userSchema.statics.findByEmail = async function(email: string): Promise<IUser[]>{
    const exUser = await this.find({email}); 
    return exUser;
}

사용)
import {UserModel} from '@models/user';

const exUser = await UserModel.findByEmail(email);



스키마 정의함수를 다큐먼트 정의함수와 같이 선언해주면 findByEmail 함수를 찾지 못하고 다음과 같은 오류가 뜨게 된다.

선언)
interface IUser extends monggoes.Document{
    nick: string;
    email: string;
    password: string;
    getEmail(): string;
    findByEmail(email: string): Promise<IUser[]>
}

사용)
import {UserModel} from '@models/user';

const exUser = await UserModel.findByEmail(email);
**Property 'findByEmail' does not exist on type 'Model<IUser, {}>'.ts(2339)**

스키마 사용자 정의함수를 사용하기 위해서는 Model 를 상속 받는 인터페이스를 선언해주고 모델 생성시에 제네릭 두번째 인자에 이를 추가해주면된다. 그러면 typescript 가 위에 예시에서는 찾지 못했던 findByEmail 잘 찾는 것을 확인할 수 있다.

ex)

import monggoes, { Model, Schema } from 'mongoose';

interface IUser extends monggoes.Document{
    nick: string;
    email: string;
    password: string;
    getEmail(): string;
    findByEmail(email: string): Promise<IUser[]>
}

선언)
interface IUserModel extends Model<IUser> {
    findByEmail(email: string): Promise<IUser[]>
}

const userSchema: Schema = new monggoes.Schema({
    nick: {
        type: String,
        required: true
    },
    email: {
        type: String,
        required: true
    },
    password: {
        type: String,
        required: true
    },
})

// eslint-disable-next-line func-names
userSchema.methods.getEmail = function(){
    return this.email;
}

// eslint-disable-next-line func-names
userSchema.statics.findByEmail = async function(email: string): Promise<IUser[]>{
    const exUser = await this.find({email}); 
    return exUser;
}


생성)
export const UserModel = monggoes.model<IUser, IUserModel>("User", userSchema);


참고 https://www.zerocho.com/category/MongoDB/post/59a1870210b942001853e250

https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/mongoose#static-methods

Clone this wiki locally