2019.05.21 - 클래스 데코레이터를 이용한 데이터 직렬화 (Clean) 코드
def hide_field(field) -> str: return "**민감한 정보 삭제" def show_original(event_field): return event_field class EventSerializer: def __init__(self, serialization_fields: dict) -> None: self.serialization_fields = serialization_fields def serialize(self, event) -> dict: return { field: transformation(getattr(event, field)) for field, transformation in self.serialization_fields.items() } class Serialization: def __init__(self, **transformations): self.serializer = EventSerializer(transformations) def __call__(self, event_class): def serialize_method(event_instance): return self.serializer.serialize(event_instance) event_class.serialize = serialize_method return event_class @Serialization( name=show_original, password=hide_field ) @dataclassclass LoginEvent: name: str password: str
일단 EventSerializer는 읽어보면 이해가 되는 코드이므로 pass
Serialization이 데코레이팅 하는 클래스라서 이 친구를 먼저 좀 알아야한다.
일단 초기화 함수에서 가변 키워드 인자를 받는다.
만약 @Serialization이었다면 LoginEvent 클래스를 인자로 받아서 Argument Error가 났을 것이다.
일단은 초기화함수에 대응하는 인자들은 (name=show_original, password=hide_field)가 되겠다.
Serialization 클래스는 초기화가 된 후 LoginEvent 클래스를 데코레이팅한다.
원래 Serialization의 __call__이 호출 되려면 Serialization()()이 되어야 하는데
LoginEvent의 인스턴스를 생성할 때도 저 __call__이 호출된다.
inst = LoginEvent() 는 일반적인 LoginEvent의 인스턴스를 생성하는 것처럼 보이지만
LoginEvent는 데코레이팅 되기 때문에
사실상 Serialization(LoginEvent)()와 같다.
그렇기 때문에 LoginEvent는 serialize라는 메소드를 가진 클래스가 될 수 있고
serialize 메소드를 사용할 수 있다.
댓글
댓글 쓰기