로그에 커스텀값을 출력할 때,
보통 loggerAdapter를 사용한다.
근데 이 방법을 사용하면, 예약된 이름에 원하는 변수를 출력할 수 없다.
'myfavoritemovie' = 'realsteel' 과 같은 출력은 가능하지만,
'ip' = '123.123.123.123' 과 같은 코드는 "trying to overwrite exist name" 뭐시기 같은 오류가 난다.
여기서 문제 :
원래 ip를 출력하면 서버의 ip가 나오는데, 그때 그때 클라이언트의 ip를 출력하고 싶다면?
계속 고민하다가
신입개발자의 짧은 생각으로 편법을 만들어냈으니...
#logSetter.py
import logging
import logging.handlers
client_ip = ''
class ContextFilter(logging.Filter):
def filter(self, record):
record.ip = getIP()
def getIP():
global client_ip
output = client_ip
client_ip = ''
return output
def setIP(request):
global client_ip
client_ip = request.environ.get('HTTP_X_REAL_IP', request.remote_addr)
mylogger = logging.getLogger('my')
contextFilter = ContextFilter()
mylogger.addFilter(contextFilter)
formatter = logging.Formatter(' [%(asctime)s - %(ip)s] [%(message)s] ')
streamHandler = logging.StreamHandler()
streamHandler.setFormatter(formatter)
mylogger.addHandler(streamHandler)
ContextFilter와 그 밑에 filter는 아무리해도 parameter가 들어가지 않는다.
client_ip 를 전역변수로 두고 ip값을 담아 옮기는 것이 핵심이다.
사용법:
이 파일의 이름을 logSetter.py 라고 했을 때,
외부 py파일에서 사용하는 방법은 아래와 같다.
import logSetter
from logSetter import mylogger
from flask import request
@app.route('/')
def index():
logSetter.setIP(request)
mylogger.info('whats up!!')
return "hello world"
저렇게 request 들어온 것을 넘기면,
request 속에서 ip 를 뽑아서 전역변수에 넣어주고,
로그 속 contextFilter에서 전역변수 ip를 뽑아서 출력하고,
초기화 시켜놓는다.
사실 getIP 함수는 없어도 된다. 그냥 초기화용.
나 스스로도 편법이라고 생각되어서 그리 추천하고 싶진 않지만..
이런 방법도 할 수 있구나 라고 참고만 하시길
반응형
'개발 > Python & Flask' 카테고리의 다른 글
[Python] URI쿼리 인코딩여부 판별 프로그램 (0) | 2021.01.12 |
---|---|
[Python] Outlook 메일 자동 읽어오기 (0) | 2021.01.11 |
pymysql 사용법, 간편한 축약 코드 예시! (0) | 2020.11.13 |
Python 전역변수 다루기 (0) | 2020.11.13 |
pymysql exception error (예외 처리 정리 및 해석!) (0) | 2020.11.10 |