Python/파이썬 오픈소스 배포

Context Manager (2)

monstro 2025. 6. 24. 17:38
728x90
반응형

- 개요

Context Manager원하는 타이밍에 정확하게 리소스를 할당제공, 반환하는 역할을 담당한다

그러나 위의 역할 말고도 Context Manager는 작업을 확장하여 수행하는 것도 가능하다

 

이번에 알아볼 Context Manager를 통한 작업의 확장은 이전과 마찬가지로 with 메서드를 통해 이뤄지며

Context Manager 클래스 내부에서 정의한 매직 메서드를 통해 동작한다

 

- 작업의 확장 : 작업 시간을 출력하는 타이머 Context Manager

import time

class ExecutionWithTimer(object):
    def __init__(self, msg):
        self.msg = msg

    # 작업을 시작하는 시점의 시간 저장
    def __enter__(self):
        # time.monotonic : 시간을 숫자형으로 반환
        self._start = time.monotonic()
        return self._start


    # __exit__ 매직 메서드가 호출되는 시점은 작업을 종료하는 시점
    # (작업을 종료하는 시점의 시간 - 작업을 시작하는 시점의 시간)의 값을 반환하여 순수하게 작업한 시간을 반환
    def __exit__(self, errorType, errorValue, errorPoint):
        if(errorType):
            print(f"Execption occurred : {errorType} {errorValue} {errorPoint}")
            return False
        else:
            print(f"{self.msg} : {time.monotonic() - self._start}")
        return True

 

ExecutionWithTimer 클래스는 Context Manager 클래스로서, 

이전의 파일과 관련한 동작이 아닌 작업과 연관되어 있으므로 최상위 객체인 object를 인자로 받아 동작한다 

 

생성자에서는 msg를 인자로 받아 클래스의 msg 프로퍼티를 설정한다

 

작업이 시작되는 시점에서 호출하는 __enter__ 메서드에서는

time 모듈monotonic 함수를 사용하여 __enter__ 메서드를 호출하는 시점을 기록한다

기록한 값을 _start 프로퍼티에 저장하고 반환한다

 

작업이 완료되는 시점에서 호출하는 __exit__ 메서드에서는

에러가 발생하면 에러의 타입 / 에러의 값 / 에러가 발생한 위치출력하고 False를 리턴한다

에러가 발생하지 않았다msg 프로퍼티순수하게 작업한 시간을 출력하고 True를 리턴한다

 

 - 실제 사용 (1)

with ExecutionWithTimer("Total time for execution") as ce:
    print(f'Received Start at {ce}')
    for i in range(30000000):
        pass

 

Context Manager 클래스를 통해 작업하기 위해서는 with 메서드에서 사용해야 한다

생성자에 Total time for execution 문자열을 넘겨주어 msg 프로퍼티를 설정한다

이후 __enter__ 메서드가 호출되는 시점의 시간을 출력하고

30000000의 루프를 돈 후 __exit__ 메서드가 호출되므로 최종 작업시간이 출력된다

 

 

최종 실행 결과는 위와 같다

작업이 시작된 시점과 순수하게 작업한 시간이 출력되었다

 

- 실제 사용 (2)

with ExecutionWithTimer("Total time for execution") as ce:
    print(f'Received Start at {ce}')
    for i in range(30000000):
        pass
    raise Exception("Forced Error")

 

이번에는 고의적인 예외를 발생시켜 결과를 확인한다

예외의 타입은 Exception으로, 예외의 값은 Forced Error로 설정하였다

 

 

실행 결과는 위와 같다

__enter__ 메서드는 문제없이 동작하였지만,

__exit__ 메서드에서 예외로 인해 로그가 출력되고 있는 것을 확인할 수 있다

728x90
반응형

'Python > 파이썬 오픈소스 배포' 카테고리의 다른 글

언더스코어(_)의 사용  (0) 2025.06.30
Context Manager Annotation  (0) 2025.06.27
Context Manager (1)  (0) 2025.06.24
객체의 복사  (0) 2025.06.23
람다 함수의 활용  (0) 2025.06.23