웹에서 저장한 고전 학습자료가 MHTML 파일로 흩어져 있었다. MHTML은 웹페이지와 관련 자원을 한 파일에 담는 보관 형식인데, 여러 파일을 책처럼 넘겨 읽기에는 불편했다. 이어 읽을 수 있도록 화면 비율을 유지한 PDF로 바꾸고, 폴더별로 합쳐 북마크를 붙이는 작업을 했다.
요구한 기준은 파일 하나를 PDF 한 쪽으로 옮기는 것이었다. 내용을 다시 편집해 A4에 맞추기보다 화면에서 읽던 배치를 유지하고 싶었다. 없앨 메뉴와 머리말도 정했으며, 변환 스크립트 작성과 렌더링 오류를 좁히는 과정에는 AI의 코드 지원을 받았다.
같은 좌표 대신 페이지 안의 요소를 찾기
정리할 메뉴의 위치가 모든 파일에서 같지는 않았다. 코드에서는 머리말이나 학습도구를 페이지 요소의 식별자로 찾고, 꼬리말은 특정 문구로 시작하는 블록을 찾아 제거했다. 화면 위에서 몇 픽셀을 잘라낸다는 규칙에만 맡기지 않은 것이다. 이 정리는 렌더링하는 페이지 안에서 이루어지고 원래 MHTML 파일을 다시 저장하지는 않는다.
파일 순서는 이름 속 숫자를 숫자로 읽어 정렬했다. 단순한 문자열 정렬에서는 10이 2보다 먼저 올 수 있기 때문이다. 자연 정렬로 읽을 순서를 정한 뒤, 합칠 때 각 파일의 첫 페이지에 북마크를 붙였다.
내용 높이와 인쇄 높이를 따로 확인하기
브라우저는 메뉴를 지운 뒤에도 빈 컨테이너의 높이를 남길 수 있었다. 그래서 실제 글자나 이미지가 있는 말단 요소의 끝을 측정하는 쪽으로 바꿨다. 보이는 내용의 아래에 24픽셀 여백을 두고, 일반적인 높이 범위에서는 인쇄 오차를 위한 8픽셀을 더해 페이지 높이를 정했다. 렌더링 배율은 1로 유지했다.
MHTML에 스타일을 추가하는 호출이 끝나지 않는 문제는 별도로 다뤘다. 최종 코드에서는 스타일 요소를 직접 만들어 넣고, 측정한 높이를 문서 높이로 고정했다. 기다림이 끝나지 않는 문제와 몇 픽셀 때문에 빈 둘째 쪽이 생기는 문제를 같은 실패로 뭉뚱그리지 않으려 했다. 아주 긴 입력은 한 쪽 기준의 예외가 되므로, 한 파일·한 쪽은 모든 문서에 대한 보장이 아니라 이 자료 묶음에서 확인할 목표였다.
중간 결과를 남기고 다시 이어 가기
낱장 PDF가 만들어지면 별도 폴더에 두고, 합본은 그 파일들을 읽어 생성했다. 재실행할 때는 일정 크기 이상인 기존 PDF를 건너뛰도록 했다. 늦게 멈춘 작업을 처음부터 다시 렌더링하지 않아도 되지만, 이 크기 검사가 PDF 내용의 정상 여부까지 검증하는 것은 아니다.
8월 15일 실행 기록에는 네 합본이 각각 82쪽, 149쪽, 884쪽, 1,019쪽으로 남아 있다. 합계는 2,134쪽이다. 9월 7일 보존된 입력 파일과 PDF 구조를 다시 확인했을 때도 MHTML 2,134개와 PDF 총 2,134쪽, 같은 수의 북마크 항목이 있었다.
당시 로그의 ‘실패 0건’은 변환 과정에서 기록한 오류 수다. 원문 누락이나 글자 잘림을 전수 대조해 오류가 없다고 판정한 수치는 아니다. 이번 확인도 파일 수와 PDF 페이지·북마크 구조를 읽은 것이며, 새로 전체 화면 품질을 검수하지 않았다.
이렇게 개인 열람용 합본 네 개를 만들었다. 외부 이용 규모는 측정하지 않았고, 원자료와 변환물을 재배포할 권리도 확인하지 않았다. 따라서 여기에는 원문이나 화면, 합본 다운로드를 싣지 않는다. 내가 정리한 것은 읽을 순서와 파일 형식이며, 원자료를 새로 창작하거나 공개한 작업은 아니다.
