개발 학습 실습실

이 사이트의 실습은 자바스크립트를 켜야 움직입니다. 아래는 같은 내용을 글로 적은 것입니다.

공부 › 보안 › 웹 공격과 방어

요청 수 제한

초당 5건까지만 받는다는 것의 세 가지 의미

요청이 한꺼번에 몰리면 서버를 지키기 위해 일부를 거절합니다(429 Too Many Requests). "초당 5건"이라는 같은 제한도 세는 방법에 따라 통과하는 요청이 달라집니다.

개념 모형 · 널리 쓰이는 알고리즘 정의대로 만든 모형

이 실습에 나오는 개념

Rate Limiting
일정 시간 동안 허용하는 요청의 수를 제한하는 것이다. 특정 사용자나 클라이언트가 과도한 요청을 보내 시스템 전체에 영향을 주는 것을 막고, 시스템이 감당할 수 있는 범위에서만 요청을 받도록 한다. 제한을 넘은 요청에는 보통 429 상태 코드로 응답한다.
HTTP 상태 코드
서버가 요청을 처리한 결과를 나타내는 세 자리 숫자다. 2xx는 성공, 3xx는 다른 위치로의 이동(리다이렉션), 4xx는 클라이언트의 요청에 문제가 있음, 5xx는 서버 쪽 오류를 뜻한다. 200(성공), 201(생성됨), 400(잘못된 요청), 401(인증 필요), 403(권한 없음), 404(없음), 500(서버 오류)이 자주 쓰인다.
API 게이트웨이
클라이언트의 모든 요청을 가장 먼저 받아 알맞은 내부 서비스로 전달하는 단일 진입점이다. 인증, 요청 수 제한, 로깅 같은 공통 기능을 한곳에서 처리한다. 클라이언트는 내부 서비스의 구성과 주소를 알 필요가 없다.

이렇게 바꿔 보세요

처음 설정으로 실행하면

  1. 0.80초에 요청 1: 0초대 카운터가 1입니다. 5 이하이므로 통과.
  2. 0.84초에 요청 2: 0초대 카운터가 2입니다. 5 이하이므로 통과.
  3. 0.88초에 요청 3: 0초대 카운터가 3입니다. 5 이하이므로 통과.
  4. 0.92초에 요청 4: 0초대 카운터가 4입니다. 5 이하이므로 통과.
  5. 0.96초에 요청 5: 0초대 카운터가 5입니다. 5 이하이므로 통과.
  6. 1.02초에 요청 6: 1초대 카운터가 1입니다. 5 이하이므로 통과.
  7. 1.06초에 요청 7: 1초대 카운터가 2입니다. 5 이하이므로 통과.
  8. 1.10초에 요청 8: 1초대 카운터가 3입니다. 5 이하이므로 통과.
  9. 1.14초에 요청 9: 1초대 카운터가 4입니다. 5 이하이므로 통과.
  10. 1.18초에 요청 10: 1초대 카운터가 5입니다. 5 이하이므로 통과.
  11. 2.20초에 요청 11: 2초대 카운터가 1입니다. 5 이하이므로 통과.
  12. 2.40초에 요청 12: 2초대 카운터가 2입니다. 5 이하이므로 통과.
  13. 2.60초에 요청 13: 2초대 카운터가 3입니다. 5 이하이므로 통과.
  14. 2.80초에 요청 14: 2초대 카운터가 4입니다. 5 이하이므로 통과.

실행 결과

코드

// 고정 윈도: 키 = 사용자 + 현재 초
String key = "rate:" + userId + ":" + (now / 1000);
long count = redis.incr(key);            // 이번 초의 요청 수 +1
if (count == 1) redis.expire(key, 1);    // 1초 뒤 사라짐
if (count > 5) return tooManyRequests(); // 429

이 모형의 전제

제한은 초당 5건으로 고정했습니다. 세 알고리즘의 동작은 널리 쓰이는 정의를 따랐습니다. 슬라이딩 윈도는 요청 시각을 모두 기록하는 방식(슬라이딩 윈도 로그)으로 구현했고, 토큰 버킷은 시간이 흐른 만큼 연속적으로 토큰이 채워진다고 보았습니다. 실제 서비스에서는 사용자나 IP, API 키 단위로 따로 셉니다.

앞 실습: 정보 누출 · 다음 실습: 의존성과 공급망

이 실습에 나오는 개념

이 실습에서 보는 것

설정

코드


      
    

그림

실행 비교

이렇게 바꿔 보세요