실제로 활용한다면 위 코드처럼 하나의 파일에 저장하지 않고 user.py, order.py 두 개 파일에 각각 저장한다.
예제 프로젝트 구조
Error Handling
- 서버에서 Error가 발생한 경우, 어떤 Error가 발생했는지 알아야 하고 요청한 클라이언트에 해당 정보를 전달해 대응할 수 있어야 함 - 서버 개발자는 모니터링 도구를 사용해 Error Log를 수집해야 함 - 발생하고 있는 오류를 빠르게 수정할 수 있도록 예외 처리를 잘 만들 필요가 있음
- FastAPI의 HTTPException은 Error Response를 더 쉽게 보낼 수 있도록 하는 Class - HTTPException을 이용해서 클라이언트에게 더 자세한 에러 메시지를 보내는 코드 작성
''' #https://github.com/jjeongah/Boostcamp-AI-Tech-Product-Serving/blob/main/part3/01-fastapi/examples/13_exception_handling.py
- item_id가 1~3까진 정상
- 4 이상의 숫자가 들어올 경우 Key Error가 발생
- 5인 경우 Internal Server Error
'''
from fastapi import FastAPI, HTTPException
import uvicorn
app = FastAPI()
items = {
1: "Boostcamp",
2: "AI",
3: "Tech"
}
@app.get("/v1/{item_id}")
async def find_by_id(item_id: int):
return items[item_id]
@app.get("/v2/{item_id}")
async def find_by_id(item_id: int):
try:
item = items[item_id]
except KeyError:
raise HTTPException(status_code=404, detail=f"아이템을 찾을 수 없습니다 [id: {item_id}]")
return item
if __name__ == '__main__':
uvicorn.run(app, host="0.0.0.0", port=8000)
Background Task
- FastAPI는 Starlett이라는 비동기 프레임워크를 래핑해서 사용 - FastAPI의 기능 중 Background Tasks 기능은 오래 걸리는 작업들을 background에서 실행함 - Online Serving에서 CPU 사용이 많은 작업들을 Background Task로 사용하면, 클라이언트는 작업 완료를 기다리지 않고 즉시 Response를 받아볼 수 있음
- Background Tasks를 사용하지 않은 작업들은 작업 시간 만큼 응답을 기다림
app_1 = FastAPI()
def cpu_bound_task(wait_time: int):
sleep(wait_time)
return f"task done after {wait_time}"
class TaskInput(BaseModel):
wait_time: int = Field(default=1, le=10, ge=1)
@app_1.post("/task")
def create_task(task_input: TaskInput):
return cpu_bound_task(task_input.wait_time)
tasks = [{"wait_time": i} for i in range(1, 10)]
start_time = datetime.now()
run_tasks_in_fastapi(app_1, tasks)
end_time = datetime.now()
print(f"Simple Tasks: Took {(end_time - start_time).seconds}")
- Background Tasks를 사용한 작업들은 기다리지 않고 바로 응답을 주기 때문에 0초 소요 - 실제 작업은 Background에서 실행됨