본문 바로가기

TIL

fastapi에서 mongo db 사용할 때 _id 처리하기

반응형

fastapi는 pydantic을 사용하여 데이터 모델을 정의한다.

mongo db의 경우 object id가 _id로 정의된다. 그래서 정수 a, b, c를 가지는 mongo db의 모델을 pydantic으로 정의한뒤 fastapi에서 쓴다고 치면 아래와 같이 정의를 해볼 수 있을 것이다. 

from pydantic import BaseModel

class DataModel(BaseModel):
  _id: str
  a: int
  b: int
  c: int

아마 _id를 str이 아닌 objectID 같은 타입으로 선언할 거 같긴 한데 일단 str이라고 하자.

여기서 문제가 발생하는데 pydantic의 데이터 모델은 언더스코어(_)로 시작하는 변수를 private으로 간주하고 접근할 수 없게 해놓는다. 그래서 데이터를 주고 받을 때 id에 접근을 할 수가 없다. 이에 대한 해결 법은 여러개가 있지만 내가 본 것 중에 가장 간단한 것은 alias를 사용하는 것이다.

from pydantic import BaseModel, BaseConfig, Field

class DataModel(BaseModel):
  id: str = Field(alias="_id")
  a: int
  b: int
  c: int
  class Config(BaseConfig):
  	allow_population_by_field_name=True

위와 같이 id라고 정의하고 alias="_id"를 추가하고 allow_population_by_field_name=True를 Config로 사용해주면 리퀘스트로 넘어올 때 id를 잘 받을 수 있다.

리스폰스에 데이터를 실어서 넘겨줄 때는 DataModel.json(by_alias=True), DataModel.dict(by_alias=True) 처럼 alias를 사용하게 하면 _id로 잘 바뀌어서 넘어간다.

 

fastapi랑 mongoDB를 같이 쓸 때 _id에 관련된 문제는 이미 많이 알려져 있다. 그래서 fastapi 레포에 대응법을 정리해둔 글 또한 존재한다. 링크

 

[QUESTION] FastApi & MongoDB - the full guide · Issue #1515 · tiangolo/fastapi

Description In this issue i'd like to gather all the information about the use of MongoDB, FastApi and Pydantic. At this point this is a "rather complete" solution, but i'd like t...

github.com

 

반응형