blog.stackframe.dev

블로그 개발 삽질기 5 - 파서 리팩토링

  1. 블로그 개발 삽질기 0 - 발단
  2. 블로그 개발 삽질기 1 - 설계
  3. 블로그 개발 삽질기 2 - reStructuredText 파서 구현
  4. 블로그 개발 삽질기 3 - 템플릿 구현
  5. 블로그 개발 삽질기 4 - Service Worker
  6. 블로그 개발 삽질기 5 - 파서 리팩토링

PHP 8.1부터 Enum이 지원되어 내가 만든 reStructuredText 파서에 적용할 생각이었다. 그러던 중 아치리눅스 staging 레포지토리에 PHP 8.1이 올라온 걸 보았고, 적절한 시기라 판단되어 작업을 시작하였다.

문제는 내가 이전에 만든 파서 코드가 너무 난잡하여 가독성이 심각하게 떨어진다는 점이다. 파싱 데이터는 모두 배열과 문자열로 처리하여 다음 단계로 넘겼기 때문에 일관성이 떨어지고 처리 작업을 기준으로 코드가 묶여 있었기 때문에 새로운 기능을 추가하기 어려웠다. 거기다 PHP에 추가된 Enum은 C와는 다르게 일종의 객체로 취급되어 해당 부분만 수정하기는 곤란했다. 그래서 아예 처음부터 완전히 객체지향으로 리팩토링하게 되었다.

다행히도 문자열 파싱 부분은 거의 수정없이 사용할 수 있었다. 혹시나 버그가 있을까봐 모두 다시 타이핑하면서 검토하기까지 했는데 그 양이 많아서 내가 진짜 이걸 다 만들었는지 신기할 따름이었다. 아무튼 각 요소 별로 클래스를 만들고 Const로 Enum을 흉내낸 부분은 모두 Enum으로 수정했다.

모두 클래스로 만들었더니 파일은 많아졌지만 파서와 문서 요소를 분리할 수 있었고, 요소별 출력 형태를 각 클래스에 포함시킬 수 있었기 때문에 디버깅이 매우 편리해졌다. 무엇보다 상속을 통해 파싱과 HTML로 출력을 정해진 메소드로 구현하도록 하여 가독성과 확장성이 매우 높아졌다.

이 모든 작업을 완료하는데 약 9일 정도 걸렸다. 대부분의 시간을 예전 코드에서 파서 부분을 재검증하고 타이핑하는데 사용하였다. 처리 속도를 최대한으로 높이려고 정규표현식은 전혀 사용하지 않고 라인이나 한 글자씩 읽어서 처리하는 고전적인 완전 상태 머신으로 구현하였기 때문에 코드가 길어질 수 밖에 없었긴하다. 그래도 웹에서 실시간으로 처리하여 출력할 수 있을 정도로 성능이 괜찮아 매우 만족하고 있다. 이번 리팩토링을 진행한 후 이전 코드와 성능 비교를 해 본 결과도 큰 차이가 나지 않았기 때문에 리팩토링은 성공적이었다.

댓글