반응형

 

-------------------------------------------------------------

FastAPI 세 가지 에러 핸들링 방법

-------------------------------------------------------------

[출처] https://python.plainenglish.io/3-ways-to-handle-errors-in-fastapi-that-you-need-to-know-e1199e833039

 

1. 기본 HTTPException 이용하기

----------------------------------

fastapi 모듈에 기본으로 사용할 수 있으며, import 한 후에 raise를 이용하여 호출한다.

 

1) from fastapi import FastAPI, HTTPException

2) raise HTTPException(status_code = 204, detail = "")

 

기본적으로 “status_code”와 “detail” 항목이 있다.

“status_code”에는 HTTP status를 넣는대 200, 204, 404, 500 등이 이용된다.

“detail”에는 관련된 응답 메시지를 넣는다.

 

test_database = {

  "12345": "User1",

  "23456": "User2",

  "34567": "User3",

  "45678": "User4"

}

 

if id in test_database: 

  print("Found it!!")

  return id

else:

  raise HTTPException(status_code = 404, detail= "Id not found")

 

[결과 메시지]

{

  "detail": "Id not found"

}

 

 

2. 사용자 Exception 만들어 이용하기

---------------------------------------

HTTPException 처리 기능이 부족하면 직접 사용자 에러를 만들어 사용한다.

먼저 아래처럼 두 모듈을 import해야 한다.

 

from fastapi import FastAPI, Request

from fastapi.responses import JSONResponse

 

그후에 사용자 예외 클래스 객체를 만든다.

 

class MyCustomException(Exception):

def __init__(self, name: str):

  self.name = name

 

이제 예외 핸들러를 만들고 우리 클래스 객체에 전달한다.

 

@app.exception_handler(MyCustomException)

async def MyCustomExceptionHandler(request: Request, exception: MyCustomException):

  return JSONResponse (status_code = 500,

                               content = {"message": "Something critical happened"})

 

에러가 발생하고 예외가 발생하면 상태 코드는 500이 되고 메시지를 출력하게 된다.

 

@app.get("/testapi/v1/{triggererror}")

async def GetTestException(triggererror: str):

  if triggererror == "yes":

    raise MyCustomException(name = triggererror)

  return results

 

[결과 메시지]

{

  "message": "Something critical happened"

}

 

 

3. HTTPException 오버라이드

 

HttpException 예외를 오버라이드하는 방법도 가능하다.

일단 아래 두줄처럼 import 한다.

 

from fastapi.responses import PlainTextResponse

from starlette.exceptions import HTTPException as StarletteHTTPException

 

그 후에 예외를 오버라이드하는 예외 핸들러를 만든다.

 

@app.exception_handler(StarletteHTTPException)

async def my_exception_handler(request, exception):

  return PlainTextResponse(str(exception.detail),

                                   status_code = exception.status_code)

 

이 핸들러는 예외를 오버라이드하고 JSON 대신에 평문을 돌려준다.

 

[결과 화면]

Critical error occurred.

 

================== ===================================

 

[참고] If you provide a custom model, the OpenAPI specs will pick them up.

---------------------------------------------------------------------------------

@app.post( "/cookies", status_code=201,

responses={ 201: {"model": MyCustomOutputModel},

422: {"model": MyValidationModel},

500: {"model": UnexpectedServerError}, }, include_in_schema=True, )

 

 

=======================================================

 

Fast API Handling Errors

[출처] https://lucky516.tistory.com/101

 

HTTP Exception

------------------

HTTPException 클래스를 이용하면 에러를 일으킬 수 있다.

예제는 접근하려는 아이템이 없을 경우 404 에러를 일이키는 코드이다.

 

from fastapi import FastAPI, HTTPException

 

app = FastAPI()

 

items = {"foo": "The Foo Wrestlers"}

 

@app.get("/items/{item_id}")

async def read_item(item_id: str):

  if item_id not in items:

    raise HTTPException(status_code=404, detail="Item not found")

  return {"item": items[item_id]}

 

HTTPException은 파이썬 exception에 api 관련 정보를 추가한 exception이라 raise 이용한다.

예외 발생 시 리퀘스트는 종료되며(이후 코드 무시) 클라이언트에 HTTP error를 전달한다.

 

(예) foo 존재하여 성공한 경우(http://example.com/items/foo), 결과 메시지

{

  "item": "The Foo Wrestlers"

}

 

(예) bar가 없어서 실패한 경우(http://example.com/items/bar), 결과 메시지

{

  "detail": "Item not found"

}

 

 

커스텀 헤더 추가하기

------------------------

HTTP error에 커스텀 헤더를 추가할 수 있다. 보안 문제로 이것을 이용하면 유용하다.

 

from fastapi import FastAPI, HTTPException

 

app = FastAPI()

 

items = {"foo": "The Foo Wrestlers"}

 

@app.get("/items-header/{item_id}")

async def read_item_header(item_id: str):

  if item_id not in items:

    raise HTTPException( status_code=404, detail="Item not found",

                                headers={"X-Error": "There goes my error"}, )

  return {"item": items[item_id]}

 

 

커스텀 예외 만들기

---------------------

커스텀 예외를 만드는 방법은 아래와 같다

 

1) Exception을 상속하는 클래스를 만든다.

2) @app.exception_handler() 데코레이션을 사용하여 handler를 등록한다.

 

from fastapi import FastAPI, Request

from fastapi.responses import JSONResponse

 

class UnicornException(Exception):

def __init__(self, name: str):

  self.name = name

 

app = FastAPI()

 

@app.exception_handler(UnicornException)

async def unicorn_exception_handler(request: Request, exc: UnicornException):

  return JSONResponse( status_code=418,

                              content={"message": f"Oops! {exc.name} did something."}, )

 

@app.get("/unicorns/{name}")

async def read_unicorn(name: str):

  if name == "yolo":

    raise UnicornException(name=name)

  return {"unicorn_name": name}

 

 

반응형

'FastAPI' 카테고리의 다른 글

Nginx로 FastAPI 배포하기  (0) 2022.01.25
FastAPI 시작, 중지, 재시작  (2) 2022.01.25
gunicorn 설정  (0) 2022.01.12
FastAPI 서버 API 버전 관리  (0) 2022.01.10
FastAPI + HTTPS (Windows)  (0) 2021.12.30

+ Recent posts