Skip to content

์‘๋‹ต ๋ชจ๋ธ

์–ด๋–ค ๊ฒฝ๋กœ ๋™์ž‘์ด๋“  ๋งค๊ฐœ๋ณ€์ˆ˜ response_model๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์‘๋‹ต์„ ์œ„ํ•œ ๋ชจ๋ธ์„ ์„ ์–ธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค:

  • @app.get()
  • @app.post()
  • @app.put()
  • @app.delete()
  • ๊ธฐํƒ€.
from typing import List, Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = None
    price: float
    tax: Union[float, None] = None
    tags: List[str] = []


@app.post("/items/", response_model=Item)
async def create_item(item: Item):
    return item

์ฐธ๊ณ 

response_model์€ "๋ฐ์ฝ”๋ ˆ์ดํ„ฐ" ๋ฉ”์†Œ๋“œ(get, post, ๋“ฑ)์˜ ๋งค๊ฐœ๋ณ€์ˆ˜์ž…๋‹ˆ๋‹ค. ๋ชจ๋“  ๋งค๊ฐœ๋ณ€์ˆ˜๋“ค๊ณผ ๋ณธ๋ฌธ(body)์ฒ˜๋Ÿผ ๊ฒฝ๋กœ ๋™์ž‘ ํ•จ์ˆ˜๊ฐ€ ์•„๋‹™๋‹ˆ๋‹ค.

Pydantic ๋ชจ๋ธ ์–ดํŠธ๋ฆฌ๋ทฐํŠธ๋ฅผ ์„ ์–ธํ•œ ๊ฒƒ๊ณผ ๋™์ผํ•œ ํƒ€์ž…์„ ์ˆ˜์‹ ํ•˜๋ฏ€๋กœ Pydantic ๋ชจ๋ธ์ด ๋  ์ˆ˜ ์žˆ์ง€๋งŒ, List[Item]๊ณผ ๊ฐ™์ด Pydantic ๋ชจ๋ธ๋“ค์˜ list์ผ ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค.

FastAPI๋Š” ์ด response_model๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ:

  • ์ถœ๋ ฅ ๋ฐ์ดํ„ฐ๋ฅผ ํƒ€์ž… ์„ ์–ธ์œผ๋กœ ๋ณ€ํ™˜.
  • ๋ฐ์ดํ„ฐ ๊ฒ€์ฆ.
  • OpenAPI ๊ฒฝ๋กœ ๋™์ž‘์˜ ์‘๋‹ต์— JSON ์Šคํ‚ค๋งˆ ์ถ”๊ฐ€.
  • ์ž๋™ ์ƒ์„ฑ ๋ฌธ์„œ ์‹œ์Šคํ…œ์— ์‚ฌ์šฉ.

ํ•˜์ง€๋งŒ ๊ฐ€์žฅ ์ค‘์š”ํ•œ ๊ฒƒ์€:

  • ํ•ด๋‹น ๋ชจ๋ธ์˜ ์ถœ๋ ฅ ๋ฐ์ดํ„ฐ ์ œํ•œ. ์ด๊ฒƒ์ด ์–ผ๋งˆ๋‚˜ ์ค‘์š”ํ•œ์ง€ ์•„๋ž˜์—์„œ ๋ณผ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๊ธฐ์ˆ  ์„ธ๋ถ€์‚ฌํ•ญ

์‘๋‹ต ๋ชจ๋ธ์€ ํ•จ์ˆ˜์˜ ํƒ€์ž… ์–ด๋…ธํ…Œ์ด์…˜ ๋Œ€์‹  ์ด ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ์„ ์–ธํ•˜๋Š”๋ฐ, ๊ฒฝ๋กœ ํ•จ์ˆ˜๊ฐ€ ์‹ค์ œ ์‘๋‹ต ๋ชจ๋ธ์„ ๋ฐ˜ํ™˜ํ•˜์ง€ ์•Š๊ณ  dict, ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ๊ฐ์ฒด๋‚˜ ๊ธฐํƒ€ ๋‹ค๋ฅธ ๋ชจ๋ธ์„ response_model์„ ์‚ฌ์šฉํ•˜์—ฌ ํ•„๋“œ ์ œํ•œ๊ณผ ์ง๋ ฌํ™”๋ฅผ ์ˆ˜ํ–‰ํ•˜๊ณ  ๋ฐ˜ํ™˜ํ•  ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์ž…๋‹ˆ๋‹ค

๋™์ผํ•œ ์ž…๋ ฅ ๋ฐ์ดํ„ฐ ๋ฐ˜ํ™˜

์—ฌ๊ธฐ์„œ ์šฐ๋ฆฌ๋Š” ํ‰๋ฌธ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ํฌํ•จํ•˜๋Š” UserIn ๋ชจ๋ธ์„ ์„ ์–ธํ•ฉ๋‹ˆ๋‹ค:

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel, EmailStr

app = FastAPI()


class UserIn(BaseModel):
    username: str
    password: str
    email: EmailStr
    full_name: Union[str, None] = None


# Don't do this in production!
@app.post("/user/", response_model=UserIn)
async def create_user(user: UserIn):
    return user

๊ทธ๋ฆฌ๊ณ  ์ด ๋ชจ๋ธ์„ ์‚ฌ์šฉํ•˜์—ฌ ์ž…๋ ฅ์„ ์„ ์–ธํ•˜๊ณ  ๊ฐ™์€ ๋ชจ๋ธ๋กœ ์ถœ๋ ฅ์„ ์„ ์–ธํ•ฉ๋‹ˆ๋‹ค:

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel, EmailStr

app = FastAPI()


class UserIn(BaseModel):
    username: str
    password: str
    email: EmailStr
    full_name: Union[str, None] = None


# Don't do this in production!
@app.post("/user/", response_model=UserIn)
async def create_user(user: UserIn):
    return user

์ด์ œ ๋ธŒ๋ผ์šฐ์ €๊ฐ€ ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ์‚ฌ์šฉ์ž๋ฅผ ๋งŒ๋“ค ๋•Œ๋งˆ๋‹ค API๋Š” ์‘๋‹ต์œผ๋กœ ๋™์ผํ•œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋ฐ˜ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

์ด ๊ฒฝ์šฐ, ์‚ฌ์šฉ์ž๊ฐ€ ์Šค์Šค๋กœ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋ฐœ์‹ ํ–ˆ๊ธฐ ๋•Œ๋ฌธ์— ๋ฌธ์ œ๊ฐ€ ๋˜์ง€ ์•Š์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ทธ๋Ÿฌ๋‚˜ ๋™์ผํ•œ ๋ชจ๋ธ์„ ๋‹ค๋ฅธ ๊ฒฝ๋กœ ๋™์ž‘์—์„œ ์‚ฌ์šฉํ•  ๊ฒฝ์šฐ, ๋ชจ๋“  ํด๋ผ์ด์–ธํŠธ์—๊ฒŒ ์‚ฌ์šฉ์ž์˜ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋ฐœ์‹ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์œ„ํ—˜

์ ˆ๋Œ€๋กœ ์‚ฌ์šฉ์ž์˜ ํ‰๋ฌธ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ €์žฅํ•˜๊ฑฐ๋‚˜ ์‘๋‹ต์œผ๋กœ ๋ฐœ์‹ ํ•˜์ง€ ๋งˆ์‹ญ์‹œ์˜ค.

์ถœ๋ ฅ ๋ชจ๋ธ ์ถ”๊ฐ€

๋Œ€์‹  ํ‰๋ฌธ ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ์ž…๋ ฅ ๋ชจ๋ธ์„ ๋งŒ๋“ค๊ณ  ํ•ด๋‹น ๋น„๋ฐ€๋ฒˆํ˜ธ ์—†์ด ์ถœ๋ ฅ ๋ชจ๋ธ์„ ๋งŒ๋“ค ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค:

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel, EmailStr

app = FastAPI()


class UserIn(BaseModel):
    username: str
    password: str
    email: EmailStr
    full_name: Union[str, None] = None


class UserOut(BaseModel):
    username: str
    email: EmailStr
    full_name: Union[str, None] = None


@app.post("/user/", response_model=UserOut)
async def create_user(user: UserIn):
    return user

์—ฌ๊ธฐ์„œ ๊ฒฝ๋กœ ๋™์ž‘ ํ•จ์ˆ˜๊ฐ€ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ํฌํ•จํ•˜๋Š” ๋™์ผํ•œ ์ž…๋ ฅ ์‚ฌ์šฉ์ž๋ฅผ ๋ฐ˜ํ™˜ํ• ์ง€๋ผ๋„:

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel, EmailStr

app = FastAPI()


class UserIn(BaseModel):
    username: str
    password: str
    email: EmailStr
    full_name: Union[str, None] = None


class UserOut(BaseModel):
    username: str
    email: EmailStr
    full_name: Union[str, None] = None


@app.post("/user/", response_model=UserOut)
async def create_user(user: UserIn):
    return user

...response_model์„ UserOut ๋ชจ๋ธ๋กœ ์„ ์–ธํ–ˆ๊ธฐ ๋•Œ๋ฌธ์— ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ํฌํ•จํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค:

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel, EmailStr

app = FastAPI()


class UserIn(BaseModel):
    username: str
    password: str
    email: EmailStr
    full_name: Union[str, None] = None


class UserOut(BaseModel):
    username: str
    email: EmailStr
    full_name: Union[str, None] = None


@app.post("/user/", response_model=UserOut)
async def create_user(user: UserIn):
    return user

๋”ฐ๋ผ์„œ FastAPI๋Š” ์ถœ๋ ฅ ๋ชจ๋ธ์—์„œ ์„ ์–ธํ•˜์ง€ ์•Š์€ ๋ชจ๋“  ๋ฐ์ดํ„ฐ๋ฅผ (Pydantic์„ ์‚ฌ์šฉํ•˜์—ฌ) ํ•„ํ„ฐ๋งํ•ฉ๋‹ˆ๋‹ค.

๋ฌธ์„œ์—์„œ ๋ณด๊ธฐ

์ž๋™ ์ƒ์„ฑ ๋ฌธ์„œ๋ฅผ ๋ณด๋ฉด ์ž…๋ ฅ ๋ชจ๋ธ๊ณผ ์ถœ๋ ฅ ๋ชจ๋ธ์ด ๊ฐ์ž์˜ JSON ์Šคํ‚ค๋งˆ๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ์Œ์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค:

๊ทธ๋ฆฌ๊ณ  ๋‘ ๋ชจ๋ธ ๋ชจ๋‘ ๋Œ€ํ™”ํ˜• API ๋ฌธ์„œ์— ์‚ฌ์šฉ๋ฉ๋‹ˆ๋‹ค:

์‘๋‹ต ๋ชจ๋ธ ์ธ์ฝ”๋”ฉ ๋งค๊ฐœ๋ณ€์ˆ˜

์‘๋‹ต ๋ชจ๋ธ์€ ์•„๋ž˜์™€ ๊ฐ™์ด ๊ธฐ๋ณธ๊ฐ’์„ ๊ฐ€์งˆ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค:

from typing import List, Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = None
    price: float
    tax: float = 10.5
    tags: List[str] = []


items = {
    "foo": {"name": "Foo", "price": 50.2},
    "bar": {"name": "Bar", "description": "The bartenders", "price": 62, "tax": 20.2},
    "baz": {"name": "Baz", "description": None, "price": 50.2, "tax": 10.5, "tags": []},
}


@app.get("/items/{item_id}", response_model=Item, response_model_exclude_unset=True)
async def read_item(item_id: str):
    return items[item_id]
  • description: Optional[str] = None์€ ๊ธฐ๋ณธ๊ฐ’์œผ๋กœ None์„ ๊ฐ–์Šต๋‹ˆ๋‹ค.
  • tax: float = 10.5๋Š” ๊ธฐ๋ณธ๊ฐ’์œผ๋กœ 10.5๋ฅผ ๊ฐ–์Šต๋‹ˆ๋‹ค.
  • tags: List[str] = [] ๋นˆ ๋ฆฌ์ŠคํŠธ์˜ ๊ธฐ๋ณธ๊ฐ’์œผ๋กœ: [].

๊ทธ๋Ÿฌ๋‚˜ ์‹ค์ œ๋กœ ์ €์žฅ๋˜์ง€ ์•Š์•˜์„ ๊ฒฝ์šฐ ๊ฒฐ๊ณผ์—์„œ ๊ฐ’์„ ์ƒ๋žตํ•˜๊ณ  ์‹ถ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์˜ˆ๋ฅผ ๋“ค์–ด, NoSQL ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค์— ๋งŽ์€ ์„ ํƒ์  ์†์„ฑ์ด ์žˆ๋Š” ๋ชจ๋ธ์ด ์žˆ์ง€๋งŒ, ๊ธฐ๋ณธ๊ฐ’์œผ๋กœ ๊ฐ€๋“ ์ฐฌ ๋งค์šฐ ๊ธด JSON ์‘๋‹ต์„ ๋ณด๋‚ด๊ณ  ์‹ถ์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

response_model_exclude_unset ๋งค๊ฐœ๋ณ€์ˆ˜ ์‚ฌ์šฉ

๊ฒฝ๋กœ ๋™์ž‘ ๋ฐ์ฝ”๋ ˆ์ดํ„ฐ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ response_model_exclude_unset=True๋กœ ์„ค์ • ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค:

from typing import List, Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = None
    price: float
    tax: float = 10.5
    tags: List[str] = []


items = {
    "foo": {"name": "Foo", "price": 50.2},
    "bar": {"name": "Bar", "description": "The bartenders", "price": 62, "tax": 20.2},
    "baz": {"name": "Baz", "description": None, "price": 50.2, "tax": 10.5, "tags": []},
}


@app.get("/items/{item_id}", response_model=Item, response_model_exclude_unset=True)
async def read_item(item_id: str):
    return items[item_id]

์ด๋Ÿฌํ•œ ๊ธฐ๋ณธ๊ฐ’์€ ์‘๋‹ต์— ํฌํ•จ๋˜์ง€ ์•Š๊ณ  ์‹ค์ œ๋กœ ์„ค์ •๋œ ๊ฐ’๋งŒ ํฌํ•จ๋ฉ๋‹ˆ๋‹ค.

๋”ฐ๋ผ์„œ ํ•ด๋‹น ๊ฒฝ๋กœ ๋™์ž‘์— ID๊ฐ€ foo์ธ ํ•ญ๋ชฉ(items)์„ ์š”์ฒญ์œผ๋กœ ๋ณด๋‚ด๋ฉด (๊ธฐ๋ณธ๊ฐ’์„ ์ œ์™ธํ•œ) ์‘๋‹ต์€ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค:

{
    "name": "Foo",
    "price": 50.2
}

์ •๋ณด

FastAPI๋Š” ์ด๋ฅผ ์œ„ํ•ด Pydantic ๋ชจ๋ธ์˜ .dict()์˜ exclude_unset ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.

์ •๋ณด

์•„๋ž˜ ๋˜ํ•œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค:

  • response_model_exclude_defaults=True
  • response_model_exclude_none=True

Pydantic ๋ฌธ์„œ์—์„œ exclude_defaults ๋ฐ exclude_none์— ๋Œ€ํ•ด ์„ค๋ช…ํ•œ ๋Œ€๋กœ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ธฐ๋ณธ๊ฐ’์ด ์žˆ๋Š” ํ•„๋“œ๋ฅผ ๊ฐ–๋Š” ๊ฐ’์˜ ๋ฐ์ดํ„ฐ

ํ•˜์ง€๋งŒ ๋ชจ๋ธ์˜ ํ•„๋“œ๊ฐ€ ๊ธฐ๋ณธ๊ฐ’์ด ์žˆ์–ด๋„ ID๊ฐ€ bar์ธ ํ•ญ๋ชฉ(items)์ฒ˜๋Ÿผ ๋ฐ์ดํ„ฐ๊ฐ€ ๊ฐ’์„ ๊ฐ–๋Š”๋‹ค๋ฉด:

{
    "name": "Bar",
    "description": "The bartenders",
    "price": 62,
    "tax": 20.2
}

์‘๋‹ต์— ํ•ด๋‹น ๊ฐ’๋“ค์ด ํฌํ•จ๋ฉ๋‹ˆ๋‹ค.

๊ธฐ๋ณธ๊ฐ’๊ณผ ๋™์ผํ•œ ๊ฐ’์„ ๊ฐ–๋Š” ๋ฐ์ดํ„ฐ

If the data has the same values as the default ones, like the item with ID baz: ID๊ฐ€ baz์ธ ํ•ญ๋ชฉ(items)์ฒ˜๋Ÿผ ๊ธฐ๋ณธ๊ฐ’๊ณผ ๋™์ผํ•œ ๊ฐ’์„ ๊ฐ–๋Š”๋‹ค๋ฉด:

{
    "name": "Baz",
    "description": None,
    "price": 50.2,
    "tax": 10.5,
    "tags": []
}

description, tax ๊ทธ๋ฆฌ๊ณ  tags๊ฐ€ ๊ธฐ๋ณธ๊ฐ’๊ณผ ๊ฐ™๋”๋ผ๋„ (๊ธฐ๋ณธ๊ฐ’์—์„œ ๊ฐ€์ ธ์˜ค๋Š” ๋Œ€์‹ ) ๊ฐ’๋“ค์ด ๋ช…์‹œ์ ์œผ๋กœ ์„ค์ •๋˜์—ˆ๋‹ค๋Š” ๊ฒƒ์„ ์ธ์ง€ํ•  ์ •๋„๋กœ FastAPI๋Š” ์ถฉ๋ถ„ํžˆ ๋˜‘๋˜‘ํ•ฉ๋‹ˆ๋‹ค(์‚ฌ์‹ค, Pydantic์ด ์ถฉ๋ถ„ํžˆ ๋˜‘๋˜‘ํ•ฉ๋‹ˆ๋‹ค).

๋”ฐ๋ผ์„œ JSON ์Šคํ‚ค๋งˆ์— ํฌํ•จ๋ฉ๋‹ˆ๋‹ค.

ํŒ

None ๋ฟ๋งŒ ์•„๋‹ˆ๋ผ ๋‹ค๋ฅธ ์–ด๋–ค ๊ฒƒ๋„ ๊ธฐ๋ณธ๊ฐ’์ด ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๋ฆฌ์ŠคํŠธ([]), float์ธ 10.5 ๋“ฑ์ด ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

response_model_include ๋ฐ response_model_exclude

๊ฒฝ๋กœ ๋™์ž‘ ๋ฐ์ฝ”๋ ˆ์ดํ„ฐ ๋งค๊ฐœ๋ณ€์ˆ˜ response_model_include ๋ฐ response_model_exclude๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด๋“ค์€ ํฌํ•จ(๋‚˜๋จธ์ง€ ์ƒ๋žต)ํ•˜๊ฑฐ๋‚˜ ์ œ์™ธ(๋‚˜๋จธ์ง€ ํฌํ•จ) ํ•  ์–ดํŠธ๋ฆฌ๋ทฐํŠธ์˜ ์ด๋ฆ„๊ณผ str์˜ set์„ ๋ฐ›์Šต๋‹ˆ๋‹ค.

Pydantic ๋ชจ๋ธ์ด ํ•˜๋‚˜๋งŒ ์žˆ๊ณ  ์ถœ๋ ฅ์—์„œ โ€‹โ€‹์ผ๋ถ€ ๋ฐ์ดํ„ฐ๋ฅผ ์ œ๊ฑฐํ•˜๋ ค๋Š” ๊ฒฝ์šฐ ๋น ๋ฅธ ์ง€๋ฆ„๊ธธ๋กœ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

ํŒ

ํ•˜์ง€๋งŒ ์ด๋Ÿฌํ•œ ๋งค๊ฐœ๋ณ€์ˆ˜ ๋Œ€์‹  ์—ฌ๋Ÿฌ ํด๋ž˜์Šค๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์œ„ ์•„์ด๋””์–ด๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์„ ์ถ”์ฒœํ•ฉ๋‹ˆ๋‹ค.

์ด๋Š” ์ผ๋ถ€ ์–ดํŠธ๋ฆฌ๋ทฐํŠธ๋ฅผ ์ƒ๋žตํ•˜๊ธฐ ์œ„ํ•ด response_model_include ๋˜๋Š” response_model_exclude๋ฅผ ์‚ฌ์šฉํ•˜๋”๋ผ๋„ ์•ฑ์˜ OpenAPI(๋ฐ ๋ฌธ์„œ)๊ฐ€ ์ƒ์„ฑํ•œ JSON ์Šคํ‚ค๋งˆ๊ฐ€ ์—ฌ์ „ํžˆ ์ „์ฒด ๋ชจ๋ธ์— ๋Œ€ํ•œ ์Šคํ‚ค๋งˆ์ด๊ธฐ ๋•Œ๋ฌธ์ž…๋‹ˆ๋‹ค.

๋น„์Šทํ•˜๊ฒŒ ์ž‘๋™ํ•˜๋Š” response_model_by_alias ์—ญ์‹œ ๋งˆ์ฐฌ๊ฐ€์ง€๋กœ ์ ์šฉ๋ฉ๋‹ˆ๋‹ค.

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = None
    price: float
    tax: float = 10.5


items = {
    "foo": {"name": "Foo", "price": 50.2},
    "bar": {"name": "Bar", "description": "The Bar fighters", "price": 62, "tax": 20.2},
    "baz": {
        "name": "Baz",
        "description": "There goes my baz",
        "price": 50.2,
        "tax": 10.5,
    },
}


@app.get(
    "/items/{item_id}/name",
    response_model=Item,
    response_model_include={"name", "description"},
)
async def read_item_name(item_id: str):
    return items[item_id]


@app.get("/items/{item_id}/public", response_model=Item, response_model_exclude={"tax"})
async def read_item_public_data(item_id: str):
    return items[item_id]

ํŒ

๋ฌธ๋ฒ• {"name", "description"}์€ ๋‘ ๊ฐ’์„ ๊ฐ–๋Š” set์„ ๋งŒ๋“ญ๋‹ˆ๋‹ค.

์ด๋Š” set(["name", "description"])๊ณผ ๋™์ผํ•ฉ๋‹ˆ๋‹ค.

set ๋Œ€์‹  list ์‚ฌ์šฉํ•˜๊ธฐ

list ๋˜๋Š” tuple ๋Œ€์‹  set์„ ์‚ฌ์šฉํ•˜๋Š” ๋ฒ•์„ ์žŠ์—ˆ๋”๋ผ๋„, FastAPI๋Š” set์œผ๋กœ ๋ณ€ํ™˜ํ•˜๊ณ  ์ •์ƒ์ ์œผ๋กœ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค:

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = None
    price: float
    tax: float = 10.5


items = {
    "foo": {"name": "Foo", "price": 50.2},
    "bar": {"name": "Bar", "description": "The Bar fighters", "price": 62, "tax": 20.2},
    "baz": {
        "name": "Baz",
        "description": "There goes my baz",
        "price": 50.2,
        "tax": 10.5,
    },
}


@app.get(
    "/items/{item_id}/name",
    response_model=Item,
    response_model_include=["name", "description"],
)
async def read_item_name(item_id: str):
    return items[item_id]


@app.get("/items/{item_id}/public", response_model=Item, response_model_exclude=["tax"])
async def read_item_public_data(item_id: str):
    return items[item_id]

์š”์•ฝ

์‘๋‹ต ๋ชจ๋ธ์„ ์ •์˜ํ•˜๊ณ  ๊ฐœ์ธ์ •๋ณด๊ฐ€ ํ•„ํ„ฐ๋˜๋Š” ๊ฒƒ์„ ๋ณด์žฅํ•˜๊ธฐ ์œ„ํ•ด ๊ฒฝ๋กœ ๋™์ž‘ ๋ฐ์ฝ”๋ ˆ์ดํ„ฐ์˜ ๋งค๊ฐœ๋ณ€์ˆ˜ response_model์„ ์‚ฌ์šฉํ•˜์„ธ์š”.

๋ช…์‹œ์ ์œผ๋กœ ์„ค์ •๋œ ๊ฐ’๋งŒ ๋ฐ˜ํ™˜ํ•˜๋ ค๋ฉด response_model_exclude_unset์„ ์‚ฌ์šฉํ•˜์„ธ์š”.