티스토리 뷰
1. HTTP 상태코드 소개
인프런 김영한 님의 모든 개발자를 위한 HTTP 웹 기본 지식 강의를 듣고 내용을 정리한 글입니다.
상태코드
클라이언트가 보낸 요청의 처리 상태를 응답에서 알려주는 기능
1xx(informational)
: 요청이 수신되어 처리중2xx(Successful)
: 요청 정상 처리3xx(Redirection)
: 요청을 완료하려면 추가 행동 필요4xx(Client Error)
: 클라이언트 오류. 잘못된 문법 등으로 서버가 요청을 수행할 수 없음5xx(Server Error)
: 서버 오류. 서버가 정상 요청을 처리하지 못함
만약 모르는 상태 코드가 나타난다면? 클라이언트가 인식할 수 없는 상태를 서버가 반환하면?
클라이언트는 상위 상태코드로 해석해서 처리한다.
미래에 상태코드가 추가되어도 클라이언트를 변경하지 않아도 된다.
예를 들어,
코드 299는 2xx으로 해석하고
451은 4xx, 588은 5xx으로 해석한다.
1xx
요청이 수신되어 서버가 처리중이라는 뜻이다.
거의 사용하지 않으므로 생략한다.
2. 2xx - 성공
클라이언트의 요청을 성공적으로 처리했다는 의미.
200 OK
- 201 Created: 서버에서 리소스를 뭔가 생성함(주로 post)
- 202 Accepted
- 204 No Content
- 2xx .. 기타 등등
200 OK
요청
GET /members/100 -> 응답
HTTP/1.1 200 OK
201 Created
요청
POST /members -> 응답
HTTP/1.1 201 Created
응답
Location: /members/101(생성된 리소스는 응답의 Location 헤더 필드로 식별한다.)
202 Accepted
요청이 접수되었으나 처리가 완료되지 않았음
배치 처리 같은 곳에서 사용
- 예) 요청 접수 후 1시간 뒤에 배치 프로세스가 요청을 처리
204 No Content
서버가 요청을 성공적으로 수행했지만 응답 페이로드 본문에 보낼 데이터가 없음
예) 웹 문서 편집기 save 버튼
save 버튼의 결과로 아무 내용이 없어도 된다.
save 버튼을 눌러도 같은 화면을 유지해야 한다.
결과 내용이 없어도 204 메세지(2xx)만으로 성공을 인식할 수 있다.
3. 3xx - 리다이렉션1
3xx 리다이렉션 Redirection
요청을 완료하기 위해 유저 에이전트(클라이언트 프로그램, 주로 브라우저)의 추가 조치 필요
- 300 Multiple Choices
- 301 Moved Permanently
- 302 Found
- 303 See Other
- 304 Not Modified
- 307 Temporary Redirct
- 308 Permanent Redirect
301~308이 중요하다.
리다이렉션 이해
웹 브라우저는 3xx 응답 결과에 Location 헤더가 있으면 Location 위치로 자동 이동(리다이렉션, 리다이렉트)한다.
자동 리다이렉트 흐름을 살펴보면,
어떤 이벤트 페이지의 URI를 /event -> /new-event로 변경했을 때, 누군가 /event로 접근하면 서버가
HTTP/1.1 301 Moved Permanently
Location: /new-event
라는 응답을 준다.
그러면 브라우저는 자동으로 /new-event로 이동함(리다이렉트)
리다이렉션에는 영구 리다이렉션, 일시 리다이렉션이 있다.
1. 영구 리다이렉션
특정 리소스의 URI가 영구적으로 이동된 것.
예를 들면,
- /members -> /users
- /event -> /new-event
2. 일시 리다이렉션
일시적인 변경
- 주문완료 후 주문 내역 화면으로 이동
- PRG: Post/Redirect/Get
특수 리다이렉션
- 결과 대신 캐시 사용
영구 리다이렉션
- 301, 308이 대표적
- 리소스의 URI가 영구적으로 이동
- 원래의 URL을 사용 하지 않고 검색엔진 등에서도 변경 인지
301 Moved Permanently
- 리다이렉트 시 요청 메서드가 GET으로 변하고 본문이 제거될 수 있음(MAY) (근데 거의 제거됨)
308 Permanent Redirect
- 301과 기능은 같음
- 리다이렉트 시 요청 메서드와 본문 유지(처음 POST를 보내면 리다이렉트도 POST)
실무에서는 웬만하면 301을 씀(필요한 데이터 자체가 달라질 수 있음)
4. 3xx - 리다이렉션2
일시적 리다이렉션
302, 307, 303가 대표적
리소스의 uri가 일시적으로 변경, 따라서 검색 엔진 등에서 url을 변경하면 안된다.
302 found
- 리다이렉트 시 요청 메서드가 GET으로 변하고 본문이 제거될 수 있음(may)
307 temporary redirect
- 302와 기능은 같음
- 리다이렉트 시 요청 메서드와 본문 유지(요청 메서드를 변경하면 안된다. must not)
303 see other
- 302와 기능은 같음
- 리다이렉트 시 요청 메서드가 GET으로 변경(must)
뭔가 분명한 상황을 원하면 303과 307을 쓴다. 근데 대부분 302 씀
PRG
일시적인 리다이렉션이 필요한 상황을 예를 들면,
POST /orders -> 200 OK
이 해당 uri에서 새로고침 한 번 더하면
POST 요청을 한 번 더 해서 주문이 한 번 더 된다.
이걸 막는 방법은
POST로 주문 후에 주문 결과 화면을 GET 메서드로 리다이렉트시켜 새로 고침으로 인한 클라 중복을 방지하는 것이다.
새로고침을 해도 결과 화면이 GET으로 조회되며
중복 주문 대신에 결과 화면만 GET으로 요청
정리하면
POST /orders
->
302 Found
Location: /order-result/19
->
자동 리다이렉트 GET /order-result/19
-> 200 OK. html 결과 화면만 줌
이 상태에서는 새로고침을 아무리 많이 해도 결과화면만 노출된다.
PRG 이후 리다이렉트
- URL이 이미 POST -> GET으로 리다이렉트됨
- 새로고침해도 GET으로 결과 화면만 조회
PRG의 이점
- UX상으로도 좋고(불필요한 알림 안 써도 됨) 서버 에러도 줄어듦
정리
- 302 -> GET으로 변할 수 있음
- 307 -> 메서드로 변하면 안돼
- 303 -> 메서드가 GET으로 변해야 해
역사
처음 302 스펙의 의도는 HTTP 메소드를 유지하는 것이었다.
근데 웹 브라우저들이 대부분 GET으로 바꾸어 버렸고,
그래서 모호한 302를 대신하는 명화한 307, 303, 308 등 등장하게 되었다.
따라서 303, 307을 권장하지만 현실적으로 이미 많은 애플리케이션 라이브러리들이 302를 기본값으로 사용중이다.
자동 리다이렉션 시 GET으로 변해도 되면 그냥 302만 써도 큰 문제 없다.
기타 리다이렉션
300, 304
300 Multiple Choices
안 씀
304 Not Modified
많이 씀
- 캐시를 목적으로 사용
- 클라이언트에게 리소스가 수정되지 않았음을 알려줌 따라서 클라이언트는 로컬 pc에 저장된 캐시를 재사용한다. (캐시로 리다이렉트한다)
- 클라: 나 캐시 있긴 한데 변경된 거 같으니까 서버야 다시 줘 -> 서버: 리소스 안 변경되었으니까 그냥 너 있는 거 써라
- 304 응답은 응답에 메세지 바디를 포함하면 안 된다. (로컬 캐시를 사용해야 하므로)
- 조건부 GET, HEAD 요청 시 사용
5. 4xx - 클라이언트 오류, 5xx - 서버 오류
4xx client Error
클라이언트의 요청에 잘못된 문법 등 문제가 있어 서버가 요청을 수행할 수 없음
즉, 오류의 원인이 클라이언트에 있음
중요! 클라이언트가 이미 잘못된 요청, 데이터를 보내고 있기 때문에 똑같은 재시도가 실패한다. 즉 요청을 수정해야 함.
근데 5xx에러는 만약에 디비가 장애가 났다가 고쳐지면, 요청을 고치지 않아도 재시도가 성공할 수 있음
400 Bad Request
클라가 잘못된 요청을 해서 서버가 요청을 처리할 수 없음.
요청 구문, 메세지 등 오류
클라는 요청 내용을 다시 검토
요청 파라미터가 잘못되거나 API스펙에 맞지 않을 때 발생
서버 개발자가 밸리데이션을 제대로 해놓지 않으면 500 에러로 발생할 수 있음. 이러면 안 됨.
서버 개발자는 최대한 정확하게 오류 메세지를 클라에게 보내줘야 한다.
401 Unauthorized
클라이언트가 해당 리소스에 대한 인증이 필요함
인증 Authentication 되지 않음
401 발생 시 응답에 WWW-Authenticate 헤더와 함께 인증 방법을 설명
참고
인증(Authentication): 본인이 누구인지 확인. 예) 로그인
인가(Authorization): 권한부여. admin 권한처럼 특정 리소스에 접근할 수 있는 권한.
인증이 있어야 인가가 있음.
오류 메세지가 Unauthorized 이지만 인증되지않음
. 이름이 아쉽다.
403 Forbidden
서버가 요청을 이해했지만 승인 거부
인증 자격 증명은 있지만 접근 권환이 불충분
- 예) 어드민 등급이 아닌 사용자가 로그인은 했지만 어드민 등급의 리소스에 접근하는 경우
404 Not Found
요청 리소스를 찾을 수 없음
요청 리소스가 서버에 없음. 주로 url 오타
또는 클라가 권한이 부족한 리소스에 접근할 때, 해당 리소스를 숨기고 싶을 때 사용한다. (403으로 하면 아 리소스가 있긴 하구나? 하는 정보를 줄 수 있음)
5xx server error
서버 오류
서버 문제로 오류 발생
서버에 문제가 있기 때문에 재시도하면 성공할 수도 잇음(db 복구 등등)
500 Internal Server Error
서버 문제로 오류 발생, 애매하면 500 오류
서버 내부 문제로 오류 발생
503 service unavailable
서비스 이용 불가
서버가 일시적인 과부하 또는 예정된 작업으로 잠시 요청을 처리할 수 없음
Retry-After 헤더 필드로 얼마뒤에 복구되는지 보낼 수 있음
근데 대부분 언제 복구될지 알기 어렵기 때문에 503은 거의 안쓰고 500 씀
정리
4xx은 클라오류. 인증이나 API 스펙을 못 맞췄거나, 오타냈거나
5xx은 서버오류. 웬만하면 5xx 에러는 발생하면 안 된다. 진짜 물리적으로 서버가 터졌을 때만 내야한다.
예를 들면
고객이 주문하는데 잔고가 부족하다.
그렇다고 500 에러를 내면 안된다.
이건 그냥 비즈니스 로직은 문제가 없는데 어떤 일시적인 처리니까 200이나 400으로 처리해야한다.
모니터링 툴 같은 걸 썼을 때 진짜 서버가 문제 있을 때만 골라내야 하는데 여기저기 500 에러 쓰면 진짜 문제를 찾아내기 어렵다.
'Programming > Computer Science' 카테고리의 다른 글
[HTTP] HTTP 캐시와 조건부 요청, 검증 헤더, 프록시 캐시, 캐시 무효화 (0) | 2022.04.17 |
---|---|
[HTTP] HTTP 일반 헤더, 표현, 콘텐츠 협상, 인증, 쿠키 (0) | 2022.04.17 |
[HTTP] HTTP 메소드 활용, collection, store, POST 기반 설계, PUT 기반 설계 (0) | 2022.04.01 |
[HTTP] HTTP 메소드, GET, POST, PATCH, PUT, DELETE, 안전, 멱등 (0) | 2022.03.29 |
[HTTP] HTTP 메세지, stateless, 비연결성 (0) | 2022.02.04 |