[Python] Nested Exception 에서 모든 예외 로깅하기 Develop Tip

파이썬의 예외처리는 다른 일반적인 (객체지향)언어에서의 예외처리와 겅의 동일합니다.

일반적인 예외가 발생할 때 각각의 예외처리 구문은 Nest 될 수 있습니다.
이 의미는 다음과 같습니다.

def mA():
  try:
    ...
  except Exception as e:
    print e

def mB():
  try:
    mA()
  except Exception as e:
    print e

def mC():
  try:
    mB()
  except Exception as e:
    print e

위와 같이 프로그램이 되어 있다면 
mA, mB 혹은 mC 어디에서 예외가 발생하건 간에
그 스택을 모두 가지지 못하고 예외에서 그냥 마지막 상황만 출력하고
예외 스택을 잃어버리게 됩니다.

한가지 다른 방법으로는

def mA():
  try:
    ...
  except Exception as e:
    print e
    raise

def mB():
  try:
    mA()
  except Exception as e:
    print e
    raise

def mC():
  try:
    mB()
  except Exception as e:
    print e
    raise

위와 같이 모든 except 블럭에서 현재 예외를 다시 상위로 그대로 toss (빈 raise 구문)
함으로써 그 스택을 그대로 가지고 있습니다.

그런데 이것이 많은 사람들, 많은 함수들, 많은 클래스가 서로 뒤 얽히다 보면
그 예외 발생한 부분을 trace 하는데 어려움이 있을 수 있습니다.

그런 경우 아래와 같이

def log_exception():
exc_info = sys.exc_info()
out = traceback.format_exception(*exc_info)
del exc_info
logger = get_exception_logger()
logger.info("[%s]%s\n%s" % (datetime.now(), '='*50, ''.join(out)))

와 같이 현재 오류 발생 오류를 얻어 (sys.exc_info())
해당 스택의 정보를 구하고  traceback.format_exception(*exc_info)
이를 출력하는 것입니다.

logger를 준 이유는 혹시라도 커질 수 있는 예외 로그를 log rotate 시키기 위함입니다.

위의 full code를 다음과 같이 except_log.py 에 저장되어 있다고 치면

상단 샘플코드는 

def mA():
  try:
    ...
  except Exception as e:
    print e
    log_exception()

def mB():
  try:
    mA()
  except Exception as e:
    print e
    log_exception()

def mC():
  try:
    mB()
  except Exception as e:
    print e
    log_exception()


와 같이 줌으로써

log_exception.log 파일에 예외 스택이 저장되는데,
1024가 넘으면 log_exception.log.1 이 되며, 이것이 .4 까지만 5개가 생깁니다.


어느분께는 도움이 되셨기를...

덧글

댓글 입력 영역

구글애드텍스트