CATEGORY

Backend

요청과 데이터가 서버에서 어떻게 처리되는지 — 백엔드 기본기.

19 Posts

Backend

Redis LRU는 진짜 LRU가 아니다 — 근사 퇴거 알고리즘 실전 이해

2026년 9월 5일

안녕하세요. 자바파커입니다. LRU(Least Recently Used)는 캐시가 가득 찼을 때 가장 오래 사용하지 않은 항목을 버리는 정책입니다. 교과서 구현은 모든 키의 사용 순서를 정확히 유지합니다. 그런데 Redis의 는 정확한 LRU가 아닙니다. Redis는 전체 키를 정렬하지 않고 일부 후보를 샘플링해 가장 오래 사용하지 않은 키를 제거합니다.…


Backend

일관된 해싱이란? 서버 추가 시 캐시 키 이동을 최소화하는 방법

2026년 9월 4일

안녕하세요. 자바파커입니다. 분산 캐시에 서버가 세 대 있다고 가정해 보겠습니다. 가장 단순한 배치식은 다음과 같습니다. 이 방식은 빠르고 이해하기 쉽습니다. 하지만 네 번째 서버를 추가하는 순간 식이 로 바뀝니다. 같은 키의 해시값은 그대로인데 나누는 수가 달라져 기존 키 대부분의 목적지가 달라질 수 있습니다. 일관된 해싱의 목적은 데이터를 완벽히 균등…


Backend

블룸 필터란? 확실한 NO와 틀릴 수 있는 YES

2026년 9월 3일

안녕하세요. 자바파커입니다. 데이터가 수억 건 있는 저장소에 어떤 키가 존재하는지 확인해야 한다고 생각해 보겠습니다. 매 요청마다 DB나 디스크를 읽으면 정확하지만 비쌉니다. 그렇다고 모든 키를 메모리에 보관하면 메모리가 커집니다. 블룸 필터(Bloom Filter)는 이 문제에 독특한 답을 냅니다. 없다고 판정하면 확실히 없습니다. 있다고 판정하면 실제…



Backend

서킷 브레이커란? 재시도가 전체 장애를 만드는 순간

2026년 8월 28일

안녕하세요. 자바파커입니다. 결제 서버 하나가 느려졌습니다. 주문 서버는 친절하게 세 번 재시도했습니다. 잠시 뒤 주문·재고·알림 서버까지 모두 느려졌습니다. 실패를 줄이려던 재시도가 왜 전체 장애를 만들었을까요? 서킷 브레이커는 실패를 없애는 장치가 아닙니다. 실패가 다른 서비스로 번지는 것을 막는 장치입니다. 요청이 쌓이다 차단기가 열리고, 시험 요청…


Backend

캐시 스탬피드란? 적중률 99%인데 DB가 터지는 1초

2026년 8월 27일

안녕하세요. 자바파커입니다. 캐시 적중률이 99%인데 DB가 갑자기 멈췄습니다. 캐시를 더 많이 쓰고 있었는데 왜 장애가 났을까요? 원인은 인기 키 하나의 만료 시각이었습니다. 캐시가 없어서가 아니라, 모두가 같은 순간 캐시가 없다는 사실을 발견해서 터집니다. TTL이 이 되는 순간 요청이 DB로 폭발하고, 락 하나로 다시 한 줄이 되는 과정은 52초 영…


Backend

로드 밸런싱이란? 요청 수를 똑같이 나눠도 한 서버가 터지는 이유

2026년 8월 26일

안녕하세요. 자바파커입니다. 서버가 세 대라서 요청도 세 대에 똑같이 나눴습니다. 그런데 잠시 뒤 1번 서버의 연결은 8개, 2번과 3번 서버는 각각 1개가 됐습니다. 요청 개수는 공평했는데 왜 부하는 공평하지 않을까요? 로드 밸런싱의 목표는 요청 개수를 똑같이 만드는 것이 아니라, 사용 가능한 서버가 감당할 수 있도록 트래픽을 분배하는 것입니다. 요청이…


Backend

메시지 큐란? 일을 빨리 하는 게 아니라 안전하게 기다리게 한다

2026년 8월 25일

안녕하세요. 자바파커입니다. 초당 요청이 100건 들어오는데 서버는 20건밖에 처리하지 못한다고 해보겠습니다. 직접 호출이라면 20건은 처리되고 나머지는 타임아웃이나 오류가 됩니다. 그 사이에 메시지 큐를 넣으면 어떻게 될까요? 서버가 빨라지는 것은 아닙니다. 처리하지 못한 80건이 실패 대신 대기가 됩니다. 이것이 메시지 큐의 핵심입니다. 메시지 큐는 …



Backend

데드락(교착 상태) — 락을 거는 순서만 통일하면 사라집니다

2026년 8월 23일

안녕하세요, 자바파커입니다. 요청이 멈췄습니다. CPU도 한가하고 DB 부하도 평소와 같습니다. 그리고 로그에 이게 찍힙니다. 멈춘 게 아닙니다. 서로를 기다리고 있는 겁니다. 결론부터 말씀드리면 — 데드락은 고리입니다. T1이 T2를 기다리고, T2가 다시 T1을 기다리면 둘 다 영원히 못 갑니다. 그리고 이 고리는 락을 거는 순서만 통일하면 만들어지…


Backend

N+1 쿼리 — 목록 하나 불렀는데 쿼리가 101번 나가는 이유

2026년 8월 22일

안녕하세요, 자바파커입니다. 게시글 100개를 불렀습니다. 쿼리는 101번 나갔습니다. 로컬에서는 아무 문제가 없습니다. 데이터가 열 건뿐이니까요. 그런데 운영에 올라가고 목록에 천 건이 쌓이는 순간, 응답이 갑자기 느려집니다. 로그를 켜 보면 똑같은 모양의 SQL이 화면을 가득 채우고 있습니다. N+1 문제입니다. 그리고 솔직히 말씀드리면, 지금 여러분…


Backend

비밀번호는 어떻게 저장되나 — 암호화가 아니라 해시입니다

2026년 8월 22일

비밀번호를 잊어버렸을 때, 어떤 서비스도 원래 비밀번호를 알려주지 않습니다. 항상 재설정 링크만 보냅니다. 불친절해서가 아닙니다. 서비스도 모르기 때문입니다. 이 글은 그 이유 하나에서 출발합니다. 왜 모르는지, 모르는데 어떻게 로그인을 통과시키는지, 그리고 그것만으로는 왜 부족한지 순서대로 따라갑니다. 되돌아오지 못하는 과정을 눈으로 보고 싶으시면 53…


Backend

JWT vs 세션 — 서버가 기억하느냐, 토큰이 들고 다니느냐

2026년 8월 21일

안녕하세요, 자바파커입니다. 로그아웃 버튼을 눌렀습니다. 그런데 아까 그 토큰으로 API를 호출하니 아직 됩니다. 로그아웃이 안 된 건가요? 로그아웃은 됐습니다. 토큰이 안 죽었을 뿐입니다. 결론부터 말씀드리면 — 세션과 JWT의 차이는 딱 하나입니다. 로그인 상태를 서버가 기억하느냐, 토큰이 들고 다니느냐. 나머지 차이는 전부 여기서 파생됩니다. 위 현…


Backend

트랜잭션 격리 수준 — 같은 쿼리를 두 번 했는데 값이 다른 이유

2026년 8월 20일

안녕하세요, 자바파커입니다. 트랜잭션 안에서 같은 를 두 번 했습니다. 첫 번째는 , 두 번째는 . 저는 아무것도 안 바꿨습니다. 버그인가요? 버그가 아닙니다. 설정한 대로 동작한 겁니다. 결론부터 말씀드리면 — 격리 수준은 "내 트랜잭션이 도는 동안 남이 한 일을 얼마나 보게 할 것인가"를 정하는 다이얼입니다. 남을 덜 볼수록 결과가 안정적이고, 대신 …


Backend

CDN 동작 원리 — 거리가 곧 지연이고, 캐시가 그 거리를 줄인다

2026년 8월 19일

안녕하세요, 자바파커입니다. 서버는 서울에 있습니다. 국내 사용자는 빠릿합니다. 그런데 브라질 사용자가 "느리다"고 합니다. 서버 사양을 올렸습니다. 그대로입니다. 당연합니다. 서버가 느린 게 아니라 멀어서 느린 거니까요. 결론부터 말씀드리면 — 네트워크 지연의 바닥은 거리가 정합니다. CPU를 아무리 올려도 이 바닥은 안 내려갑니다. CDN은 서버를 빠…


Backend

GC는 무엇을 지우나 — 안 쓰는 객체가 아니라 닿지 않는 객체

2026년 8월 18일

안녕하세요, 자바파커입니다. "메모리는 GC가 알아서 정리해 주는 거 아닌가요? 그런데 왜 가 나죠?" 정리해 줍니다. 다만 여러분이 생각하는 기준으로 정리하지 않습니다. 결론부터 말씀드리면 — GC는 "안 쓰는 객체"를 지우는 게 아니라 "닿을 수 없는 객체"를 지웁니다. 이 둘은 다릅니다. 그리고 그 차이가 메모리 누수의 정체입니다. 참조 하나가 끊기…


Backend

CORS 에러는 왜 나나 — 서버는 200인데 브라우저가 막는 이유

2026년 8월 17일

안녕하세요, 자바파커입니다. 콘솔에 이게 뜹니다. 그런데 네트워크 탭을 보면 응답은 200입니다. Postman으로 쏴 보면 잘 됩니다. 결론부터 말씀드리면 — CORS 에러는 서버가 요청을 거부한 게 아닙니다. 서버는 정상적으로 응답했고, 브라우저가 그 응답을 자바스크립트에 넘겨주지 않은 것입니다. 이 한 줄을 이해하면 나머지가 전부 따라옵니다. 응답…


Backend

경쟁 상태와 락 — 2000이 나와야 하는데 1847이 나오는 이유

2026년 8월 16일

안녕하세요, 자바파커입니다. 스레드 둘이 각각 1000번씩 했습니다. 결과는? 1847입니다. 다시 돌리면 1923이고, 또 돌리면 1786입니다. 코드는 그대로인데 매번 다릅니다. 결론부터 말씀드리면 — 는 한 동작이 아닙니다. 읽고, 더하고, 쓰는 세 동작입니다. 그 사이에 다른 스레드가 끼어들면 증가 하나가 통째로 사라집니다. 증가가 사라지는 순간…


Backend

HTTPS 핸드셰이크 완전 정리 — 자물쇠가 붙기까지 오가는 것들

2026년 8월 16일

안녕하세요, 자바파커입니다. "HTTPS는 암호화되는 거잖아요. 그런데 왜 첫 연결만 유독 느리죠?" 주소창의 자물쇠는 그냥 붙지 않습니다. 브라우저와 서버가 여러 번 오간 뒤에야 붙습니다. 그리고 그 왕복 횟수가 그대로 첫 응답 지연이 됩니다. 결론부터 말씀드리면 — HTTPS는 HTTP를 대체한 프로토콜이 아니라, HTTP 밑에 TLS 한 층을 끼운 …


Backend

커넥션 풀 고갈 — 멀쩡한 서버가 멈추는 진짜 이유

2026년 8월 16일

안녕하세요, 자바파커입니다. 서버 CPU는 20%, 메모리도 여유롭고, DB 부하도 평소와 같습니다. 그런데 응답이 안 옵니다. 그리고 잠시 뒤 로그에 이게 찍힙니다. 결론부터 말씀드리면 — 커넥션 풀 고갈은 DB가 느려서 생기는 문제가 아닙니다. 대부분은 애플리케이션이 커넥션을 필요 이상으로 오래 붙잡고 있어서 생깁니다. 그래서 DB 지표를 아무리 봐…


Backend

DB 인덱스는 왜 빨라지나 — 풀 스캔부터 인덱스가 안 먹는 경우까지

2026년 8월 16일

안녕하세요, 자바파커입니다. "인덱스 걸었는데 왜 여전히 느리죠?" 인덱스는 "걸면 빨라지는 것"으로 배웁니다. 그런데 실무에서는 걸었는데 안 빨라지는 경우가 꽤 자주 나옵니다. 원리를 모르면 왜 안 먹는지도 알 수 없습니다. 결론부터 말씀드리면 — 인덱스는 "정렬된 사본"입니다. 정렬돼 있으니 이분 탐색처럼 몇 번 만에 도달할 수 있고, 정렬을 활용할 …