본문 바로가기

직접 만든 소프트웨어, 두 가지 개발 기록

구현 구조와 적용 범위, 확인한 기능과 남은 한계를 함께 기록합니다.

전체 글158

Nginx 499 Client Closed Request 해결: 요청 취소·시간 제한·백엔드 지연 점검 Nginx access log에 499 Client Closed Request가 늘었다면 클라이언트 쪽 연결이 응답 완료 전에 닫혔다는 의미부터 확인해야 합니다. 사용자가 화면을 나갔을 수도 있고, 앱·앞단 프록시의 시간 제한보다 백엔드가 오래 걸렸을 수도 있습니다. Nginx의 시간 제한을 무조건 늘리는 것보다 누가 먼저 연결을 닫았고 어느 구간에서 기다렸는지를 같은 요청의 기록으로 비교해야 원인을 줄일 수 있습니다.1. 499와 504는 관찰한 위치가 다릅니다Cloudflare의 499 공식 설명은 Nginx가 요청을 처리하는 중 클라이언트가 연결을 닫은 상황을 설명합니다. 499는 Nginx에서 쓰는 비표준 값이며, 이미 연결을 끊은 이용자에게 정상적인 HTTP 499 응답이 전달됐다고 가정하면 안.. 2026. 10. 1.
Docker exec format error 해결: amd64·arm64·멀티플랫폼 이미지 점검 Mac에서 만든 Docker 이미지를 Linux 서버에 올렸더니 exec format error로 시작하지 않는다면 실행 파일의 CPU 아키텍처부터 확인하세요. Apple Silicon의 arm64와 일반적인 x86 서버의 amd64가 다를 수 있습니다. 다만 같은 오류가 시작 스크립트의 실행 형식에서도 생길 수 있으므로 “무조건 amd64로 설정”하는 해결법으로 끝내면 재발합니다. 이미지 플랫폼 → 실제 실행 파일 → ENTRYPOINT 순서로 점검하는 방법을 정리합니다.1. 오류가 난 실행 파일과 Docker 서버 위치를 확인하기먼저 오류에 나온 경로가 /bin/sh인지, 애플리케이션 바이너리인지, entrypoint.sh인지 기록합니다. Docker 명령을 실행하는 노트북과 실제 Docker 데몬의.. 2026. 10. 1.
Amazon MQ와 자체 RabbitMQ 비교: 메시지 브로커 비용·가용성·운영 책임 작업 큐나 서비스 간 메시지 전달에 RabbitMQ를 쓰려 할 때 Amazon MQ for RabbitMQ로 관리 부담을 줄일지, 직접 운영할지 고민하게 됩니다. 브로커를 관리할 인력이 부족하고 AWS 안의 애플리케이션과 연결하려면 관리형 구성을 먼저 검증할 수 있습니다. 반대로 필요한 버전·플러그인·세부 설정을 직접 통제해야 한다면 자체 운영도 후보입니다. 선택의 핵심은 서버 요금보다 장애 시 누가 무엇을 복구하며 메시지 재처리를 어떻게 다루는지입니다.1. 비교 대상은 RabbitMQ 기반의 같은 작업 흐름입니다이 글은 RabbitMQ 애플리케이션을 Amazon MQ for RabbitMQ와 자체 RabbitMQ에서 운영하는 상황을 비교합니다. Amazon MQ에는 다른 엔진도 있으므로 견적과 문서에서.. 2026. 10. 1.
S3와 Cloudflare R2 비교: 파일 다운로드 비용·S3 호환성·이전 체크리스트 Amazon S3와 Cloudflare R2 중 파일 저장소를 고를 때 저장 용량 단가만 비교하면 결론이 달라질 수 있습니다. 고객이 파일을 얼마나 자주 내려받는지, CDN을 거치는지, AWS 권한·암호화 기능에 얼마나 의존하는지를 함께 봐야 합니다. 외부 다운로드가 많은 서비스라면 R2의 전송료 구조를 검토할 가치가 있고, AWS 안에서 이미 운영 중인 파일 처리 체계가 있다면 S3를 유지하는 비용과 이전 비용을 먼저 비교하는 편이 합리적입니다. 이 글은 일반적인 첨부 파일·이미지·다운로드 서비스의 선택 기준을 정리합니다.1. 저장량과 다운로드량을 먼저 분리하세요저장량은 보관하고 있는 객체의 크기이고, 다운로드량은 이용자에게 전달한 데이터의 합계입니다. 100GB를 저장해도 같은 파일을 여러 번 내려받.. 2026. 10. 1.
PostgreSQL deadlock detected 해결: 40P01·잠금 순서·트랜잭션 재시도 PostgreSQL 로그에 deadlock detected가 나타나면 데이터베이스가 멈춘 것이 아니라 서로의 잠금을 기다리는 트랜잭션 중 하나를 중단해 순환을 끊은 상황입니다. 애플리케이션에는 보통 SQLSTATE 40P01로 전달됩니다. 무작정 max_connections를 올리거나 모든 세션을 종료하기 전에, 어떤 순서로 잠금을 잡았는지와 재시도 범위를 확인하세요. 이 글은 두 세션의 간단한 예와 운영 환경에서 증거를 모으는 방법을 설명합니다.1. 두 트랜잭션이 서로 기다리는 구조테스트 데이터베이스에 accounts(id, balance)라는 테이블과 id 1, 2가 있다고 가정합니다. 세션 A가 1번 행을 수정하고 세션 B가 2번 행을 수정한 뒤, 서로 상대가 잡은 행을 수정하려고 하면 대기 순환이.. 2026. 9. 30.
Kubernetes OOMKilled 해결: 메모리 limit·request·노드 압박 점검 순서 Kubernetes Pod가 반복 재시작되고 상태에 OOMKilled가 보인다면 먼저 '어느 컨테이너가 언제 왜 종료됐는지'를 확인하세요. 메모리 한도를 바로 올리면 잠시 안정될 수 있지만 누수, 동시 요청 증가, 메모리 기반 임시 볼륨 사용 같은 원인을 놓칠 수 있습니다. 이 글은 읽기 전용 명령으로 증거를 모으고, 애플리케이션 사용량과 클러스터 용량을 함께 고려해 수정하는 순서를 설명합니다.1. 종료 원인을 먼저 확정하세요Pod 이름·네임스페이스·컨테이너 이름을 실제 값으로 바꿔 다음 명령을 실행합니다. describe의 Last State, Reason, Exit Code, Events를 읽고 이전 컨테이너 로그를 보관하세요. 여러 컨테이너가 있는 Pod라면 문제가 난 컨테이너를 정확히 지정해야 합.. 2026. 9. 30.