시그널
플라스크는 시그널(signal) 라이브러리인 Blinker 를 통합한다.
이 라이브러리는 특정 이벤트를 '구독' 했다가 이벤트가 발생했을 때 필요한 함수를 실행한다.
여기서 말하는 이벤트는 고유한 이름표를 갖고 blinker.signal 클래스를 통해 생성된 인스턴스이다.
플라스크 0.12는 요청을 처리하는 과정 중 중요한 순간마다 총 10개의 시그널을 발생시킨다. (시그널은 다음 사이트 참고)
- 시그널은 connect 함수를 사용해서 특정 이벤트를 등록할 수 있다.
- 시그널은 코드가 시그널의 send 함수를 호출하면 트리거된다.
- send 함수는 추가적인 인수를 받아서 모든 등록된 함수에 데이터를 전달한다.
다음 예제에서는 request_finished 시그널에 finished 함수를 등록한다.
우선 blinker를 설치하자
pip3 install blinker
예제 코드
# flask_blinker.py
from flask import Flask, jsonify, g, request_finished
from flask.signals import signals_available
if not signals_available:
# blinker가 없는 경우
raise RuntimeError("install blinker > pip install blinker")
app = Flask(__name__)
def finished(sender, response, **extra):
print('about to send a Response')
print(response)
request_finished.connect(finished) # request_finished 시그널에 finished 함수 등록
@app.route('/api')
def my_microservice():
return jsonify({"Hello": "World"})
if __name__ == "__main__":
app.run()
- 요청이 끝난 경우 finished() ** 함수가 호출되어 서버에 **response 가 출력된다.
- 위의 예제 처럼 request 객체가 만들어지고 처리되고 소멸되는 과정에서 발생하는 시그널들은 특히 로그를 남길 때 유용하다.
실행 결과
about to send a Response
<Response 18 bytes [200 OK]>
- 서버에 요청이 오고 사라지는 경우 다음과 같이 출력된다.
- 블링커 사용 시 한가지 유의해야할 점이 있는데 모든 등록된 함수들은 signal.send 호출 시 특별한 순서 없이 동기적으로 호출된다는 점이다. 따라서 너무 많은 시그널을 사용하면 요청 처리 시간도 그만큼 늘어나므로 병목현상 을 유발할 수 있다.
- 응답에 영향을 미치지 않는 작업이 필요하다면 RabbitMQ 와 같은 비동기 큐를 사용해 작업을 큐에 넣고 다른 분리된 서비스에서 이 작업을 처리하는 방식을 고려할 수 있다.
다음 도서를 참고하였습니다.
https://www.aladin.co.kr/shop/wproduct.aspx?ItemId=191830482
'About > Flask' 카테고리의 다른 글
[Flask] 에러 처리 (사용자 정의 에러 핸들러, JSON 에러 핸들러) (0) | 2021.12.13 |
---|---|
[Flask] Jinja2 템플릿을 이용한 이메일 생성 (0) | 2021.12.13 |
[Python] Flask 전역 공간 (Flask.g) (0) | 2021.09.25 |
[Python] Flask Session 저장, 불러오기, 삭제 (0) | 2021.09.05 |
[Python] Flask url_for 함수 (0) | 2021.09.05 |