운영 Nginx 설정에 압축 옵션을 반영할 때, 설정 파일을 읽는 쪽이 어디인지부터 확인했습니다. Nginx 컨테이너는 호스트의 설정 디렉터리 전체 대신 설정 파일 하나를 읽기 전용으로 연결하고 있었습니다. 호스트에서 경로가 같은 파일을 새로 만들어 넣어도, 실행 중인 컨테이너는 이전 파일을 계속 볼 수 있는 구성입니다.
같은 이름과 같은 파일의 차이
Linux에서 경로는 파일을 찾는 이름입니다. 파일 하나를 bind mount하면 마운트는 그때 찾은 파일의 실체에 연결됩니다. 임시 파일을 만든 뒤 rename으로 기존 이름을 교체하면 호스트에서 같은 경로를 열 때 새 파일을 읽습니다. 컨테이너가 이미 연결한 파일은 그대로 남습니다. 반대로 기존 파일을 열어 내용을 덮어쓰면 inode를 유지하므로 컨테이너에서도 같은 파일의 바뀐 내용을 읽습니다.
디렉터리 전체를 마운트하고 그 아래 파일을 교체하는 경우에는, 연결한 디렉터리 안에서 새 파일 이름을 다시 찾습니다. 저희 구성에서 구별할 점은 마운트의 대상이 개별 파일이라는 사실이었습니다.
컨테이너에서 바뀐 내용 확인
먼저 컨테이너의 마운트 목록에서 실제 운영 파일을 찾았습니다. HTTP 설정은 저장소 버전과 비교했을 때 gzip 설정 7줄만 달랐습니다. HTTPS 설정에는 운영에서만 쓰는 iOS 테스트 설치 경로도 있어, 그 경로를 보존하며 압축 설정만 추가했습니다.
같은 Nginx 이미지와 파일 배치로 후보 설정을 먼저 검사했습니다. 적용할 때는 배포 도구와 같은 잠금을 잡고, 검토 후 원본이 바뀌지 않았는지 해시로 비교했습니다. 기존 파일은 접근을 제한한 별도 사본으로 남겼습니다. 그 뒤 원래 파일에 후보 내용을 덮어쓰고, 전후의 inode가 같은지와 컨테이너 안에서 새 설정 줄이 보이는지를 확인했습니다. 덮어쓰는 중에는 파일 내용이 일부만 보일 수 있으므로 쓰기가 끝난 뒤 운영 컨테이너에서 nginx -t를 실행하고 reload했습니다.
설정 검사가 성공한 뒤에는 실제 API 응답에서 Content-Encoding: gzip을 확인했습니다. 검사나 reload가 실패할 경우에는 같은 파일에 백업 내용을 되써서 설정도 되돌리는 절차를 마련했습니다. 이 작업에서 확인한 것은 inode를 유지한 적용과 실제 응답입니다. 운영 파일을 일부러 rename해서 오래된 내용이 남는 상황은 따로 재현하지 않았습니다. 압축을 요청했을 때 실제로 전송한 바이트 수는 곡 목록 글에 남겼습니다. 1.76MB 곡 목록에서 악보 덜어내기

댓글
댓글과 반응은 GitHub 계정으로 로그인해 남길 수 있어요.