OSSCA(오픈소스 컨트리뷰션 아카데미) 경험한 내용 중 ‘python-mysql-replication 라이브러리의 기능을 개발하면서 기여한 내용을 정리해서 적어보려고합니다
개발했던 기능에 대해 설명하기 전 저희 프로젝트에 대한 이해가 필요로 합니다. 다른 게시글에 작성된 내용을 참고하시면 개발했던 기능에 대해서 좀 더 상세하게 이해하실 수 있을 거예요!
시간이 부족하신 분들을 위해 참여했던 프로젝트를 간단하게 설명을 하면 mysql masater 서버에서 SQL이 발생할 때 생성되는 Binary Log를 전달받아 python 객체로 변환해 주는 프로젝트입니다.
이를 통해 master에서 어떠한 SQL이 발생했고 이를 통해 어떠한 이벤트 등이 발생했는 지를 추적하는 라이브러리입니다!
상세하게 이해하고 싶으신 분들은 아래 링크를 참조해주세요
총 개발한 기능은 이벤트 개발(3건)과 logging 기능 입니다.
이벤트란?
master에서 SQL이 발생했을 시 작성되는 binlog를 의미합니다 binary 형태로 되어있는 데이터라고 보시면 됩니다!
제가 참여한 이벤트 개발은 모두 mariadb에서 발생되는 이벤트들인데요. 아래와 같은 이벤트들을 파싱 하는 클래스를 개발하였습니다.
해당 이벤트는 rows event와 연관성이 깊은 이벤트입니다.
rows event는 insert 되거나 update,delete 된 rows에 대해 설명해주는 이벤트 입니다. 하지만 이벤트 내에서 SQL query를 담고있지는 않습니다.
해당 부족한 부분을 annotate_rows_event를 통해 보충할 수 있습니다. 해당 이벤트를 통해 rows_event를 발생시키는 SQL 쿼리문 자체를 확인할 수 있습니다.
=== MariadbAnnotateRowsEvent ===
Date: 2023-10-11T16:06:03
Log position: 1558
Event size: 75
Read bytes: 75
SQL statement : b"insert into r1 (c1) values ('#1'),('#2'),('#3'),('#4'),('#5'),('#6'),('#7')"
하지만 rows_event가 발생할 때마다 추가적으로 event가 생성됨으로 불필요한 이벤트 처리를 해야 하는 상황이 발생합니다 이에 따라 binlog를 읽기 위한 객체 생성 때 파라미터를 통해 annotate_rows_event 처리 여부를 확인하여 반영하도록 합니다.
def main():
...
...
...
stream = BinLogStreamReader(
connection_settings=MYSQL_SETTINGS, server_id=3, blocking=True, annotate_rows_event=True, is_mariadb=True
)
mariaDB에서 보안을 위해 암호키를 사용해 binlog 파일을 암호화하는 과정이 발생했을 때 사용할 수 있는 이벤트입니다.
이벤트를 발생시키기 위해서는 file_key_management
플러그인 추가와 암호화 키로 사용할 key파일이 필요로 하게 됩니다. encrypt_binlog
값을 ‘ON’으로 입력시켜줌으로 써 활성화시킬 수 있습니다
# MariaDB conf file
[mariadb]
plugin_load_add = file_key_management
# Key files that are not encrypted
loose_file_key_management_filename = /opt/key_file/no_encryption_key.key
# Set encrypt_binlog
encrypt_binlog=ON
#encrypt key file
1;dda0ccb18a28b0b4c2448b5f0217a134
해당 이벤트는 binlogfile 작성되어질 때 최초에 한번 발생하며 어떠한 key 값이 사용되었는지 확인할 수 있습니다.
=== MariadbStartEncryptionEvent ===
Date: 2023-10-11T16:09:22
Log position: 296
Event size: 17
Read bytes: 17
Schema: 1
Key version: 1
Nonce: b'\xbbx\x05\xc6\x93\xc4(\xd6Pc\xb8\x14'
해당 이벤트는 binlog 파일이 새롭게 작성될 때 발생하는 이벤트입니다.
새롭게 작성되는 binlog 파일의 시작 GTID를 담고 있으며 이 정보를 통해 사용자가 원하는 binlog 파일부터 읽을 수 있습니다.
=== MariadbGtidListEvent ===
Date: 2023-10-11T13:19:27
Log position: 285
Event size: 6
Read bytes: 4
GTID LIST: ['0-1-15']
auto_position
파라미터에 gtid 값을 넣어 줌으로 써 해당 gtid를 가진 log 파일부터 데이터를 읽어올 수 있습니다
stream = BinLogStreamReader(
connection_settings=MARIADB_SETTINGS,
...
...
...
auto_position='0-1-15',
is_mariadb=True,
annotate_rows_event=True,
)
3개의 기능(이벤트)을 구현하면서 어려웠던 점은 구현보다도 테스트 코드 작성이었습니다. 이전 직장 생활을 할 때도 테스트 코드를 작성하지 않았었는데요.
테스트 코드를 처음 작성해볼 뿐더러 해당 이벤트를 만들어 내기위한 여러가지 설정들이 많은 기능들이었어요. (암호화 설정이라던지…binlog파일 크기를 조절해서 새로운 파일을 만들어내게끔 한다던지…)
테스트 코드 작성은 이번 프로젝트에서 가장 큰 도전이었던 것 같아요. 많이 놓쳤던 부분이지만 이번에 그 중요성을 깊이 느꼈습니다.(사실 메인테이너가 PR마다 요청해서 진행을 했지만….) 테스트 코드는 코드의 안정성을 확보하며, 예상치 못한 오류를 빠르게 파악하게 해주는 핵심 도구입니다. 앞으로의 작업에서도 이를 꾸준히 포함시키며, 코드의 품질을 지속적으로 향상시키기위해 테스트코드 작성을 부지런히 해야겠습니다!
또 의도한 건 아니였는데 메인테이너 분께서 'mariaDB 지원이 이루어지면서 'python-mysql-replication'이 변화를 따라잡을 수 있었다라고 말씀도해주셔서 정말 뿌듯했습니다!'