admin/front 분리
This commit is contained in:
@@ -1,39 +1,46 @@
|
||||
# 보안 및 응답 규칙
|
||||
|
||||
## 예외/응답 규칙
|
||||
- 공통 예외 응답은 `GlobalExceptionHandler` 에서 처리하므로 Controller 별 개별 예외 처리를 중복해서 늘리지 않는다.
|
||||
- `@Valid`, 바인딩 실패, JSON 파싱 실패, 타입 오류는 `CODE_4001` 로 통일하고 필드 오류가 있으면 `Map<String, String>` 형태로 반환한다.
|
||||
- 단순 성공/실패 문자열을 직접 내려주기보다 `ApiResponse.entity(...)` 와 `ApiResponseCode` 조합을 우선 사용한다.
|
||||
- 404/405/500 같은 공통 HTTP 오류도 가능하면 `ApiResponseCode` enum 으로 맞춘다.
|
||||
## 예외와 응답
|
||||
|
||||
- 공통 예외 응답은 `GlobalExceptionHandler`에서 처리합니다.
|
||||
- Controller는 `ApiResponse.entity(...)`와 `ApiResponseCode` 조합을 우선 사용합니다.
|
||||
- 바이너리 파일 view/download처럼 필요한 경우만 `ResponseEntity<Resource>`를 직접 반환합니다.
|
||||
- `@Valid`, 바인딩 실패, JSON 파싱 실패, 타입 오류는 `CODE_4001`로 통일합니다.
|
||||
|
||||
## 보안 구조
|
||||
- Swagger: `/v3/api-docs/**`, `/swagger-ui/**` → HTTP Basic 인증 (InMemory)
|
||||
- API: JWT Bearer 토큰 인증 (Stateless)
|
||||
- 세션/쿠키: Redis Session 저장소 사용, 쿠키 속성은 프로파일별 `cookie.*` 설정으로 제어
|
||||
- Admin API: `/admin/**` 는 별도 `SecurityFilterChain` 으로 분리하며 `/admin/auth/**`, `/admin/user/add` 만 공개하고 나머지는 `ADMIN` 권한을 요구한다.
|
||||
- 공개 경로: `/`, `/actuator/health`, `/sso/**`, `/auth/**`, `/user/add`, `/user/migration/list`, `/tus/file/hook`, `/tus/file/upload/auth`, `/file/**`
|
||||
- TUS 업로드 토큰은 일반 access token 이 아니므로 `/tus/file/upload/auth`, `/tus/file/hook` 은 공개 경로와 file-domain nginx `auth_request` 설정을 함께 맞춘다.
|
||||
- `JwtAuthenticationFilter` 는 shared API(`/tus/file/**`, `/file/**`, `/cors/**`)에서 user access token 또는 admin access token 모두 인증 주체로 받을 수 있다.
|
||||
- `/admin/auth/loginChecked` 는 admin access token 쿠키의 현재 로그인 상태 확인용이다. 토큰을 재발급하지 않으며 `isAdminAccessToken`, `isAdminRefreshToken`, `loggedIn`, `userId`, `userIdx`, `userTokenIdx`, `userRole` 형태의 값을 반환한다.
|
||||
- Swagger 인증과 API 인증은 `SecurityFilterChain` 을 분리해서 관리한다.
|
||||
|
||||
## 응답 코드 규칙
|
||||
- 응답 코드는 `ApiResponseCode` enum 으로 관리한다.
|
||||
- admin과 front는 각각 독립된 `SecurityConfig`와 `SecurityFilterChain`을 가집니다.
|
||||
- Swagger 경로는 HTTP Basic으로 별도 보호합니다.
|
||||
- API는 JWT Bearer 토큰 또는 서버별 HttpOnly 쿠키를 사용합니다.
|
||||
- admin JWT 필터는 `ADMIN` scope와 `adminAccessToken`만 인증합니다.
|
||||
- front JWT 필터는 `USER` scope와 `accessToken`만 인증합니다.
|
||||
- JWT 필터는 URL(`/admin/**` 등)로 서버 종류를 판단하지 않습니다.
|
||||
- 각 서버의 공개 경로와 역할 정책은 해당 서버 `SecurityConfig`에서 관리합니다.
|
||||
- admin/front는 물리적으로 분리되어 있으므로 API path에 `/admin` 또는 `/front` 접두어를 두지 않습니다. 서버 역할은 배포 대상과 `SecurityConfig`가 구분합니다.
|
||||
|
||||
| 코드 | 메시지 | HTTP Status | 용도 |
|
||||
|------|--------|-------------|------|
|
||||
| `CODE_200` | 성공 | 200 OK | 일반 성공 |
|
||||
| `CODE_400` | 잘못된 요청 | 400 Bad Request | 일반 클라이언트 오류 |
|
||||
| `CODE_401` | 인증 필요 합니다. | 401 Unauthorized | 인증 없음 |
|
||||
| `CODE_403` | 접근 권한 필요 합니다. | 403 Forbidden | 권한 없음 |
|
||||
| `CODE_404` | 페이지를 찾을 수 없습니다. | 404 Not Found | 리소스 없음 |
|
||||
| `CODE_405` | 잘못된 요청입니다. 요청 방식을 확인해 주세요. | 405 Method Not Allowed | 메서드 불일치 |
|
||||
| `CODE_500` | 요청을 처리하는 중 오류가 발생했습니다. | 500 Internal Server Error | 서버 오류 |
|
||||
| `CODE_2001` | {0} 정보 조회에 성공하였습니다. | 200 OK | 단건 조회 성공 |
|
||||
| `CODE_2002` | {0} 등록 되었습니다. | 201 Created | 등록 성공 |
|
||||
| `CODE_2003` | 조회된 정보가 없습니다. | 200 OK | 조회 결과 없음 |
|
||||
| `CODE_2004` | 중복된 {0} 정보 입니다. | 409 Conflict | 중복 데이터 |
|
||||
| `CODE_4001` | 입력값을 확인해주세요. | 400 Bad Request | `@Valid` / 바인딩 / 타입오류 / JSON 파싱 실패 |
|
||||
| `CODE_4003` | 필수 요청 파라미터가 누락되었습니다. | 400 Bad Request | 필수 파라미터 누락 |
|
||||
## 서버별 정책
|
||||
|
||||
- `{0}` 자리에 대상명 삽입 (예: `CODE_2001` → "회원 정보 조회에 성공하였습니다.")
|
||||
- admin API는 기본적으로 `ADMIN` 역할을 요구합니다.
|
||||
- front API는 사용자 토큰을 인증 주체로 사용합니다.
|
||||
- `/actuator/health`는 각 서버의 헬스체크 경로입니다.
|
||||
- TUS는 admin 서버 이관 대상이며, front에는 TUS 공개 경로를 두지 않습니다.
|
||||
|
||||
## 응답 코드
|
||||
|
||||
응답 코드는 `ApiResponseCode` enum으로 관리합니다.
|
||||
|
||||
| 코드 | HTTP Status | 용도 |
|
||||
|---|---|---|
|
||||
| `CODE_200` | 200 OK | 일반 성공 |
|
||||
| `CODE_400` | 400 Bad Request | 일반 클라이언트 오류 |
|
||||
| `CODE_401` | 401 Unauthorized | 인증 없음 |
|
||||
| `CODE_403` | 403 Forbidden | 권한 없음 |
|
||||
| `CODE_404` | 404 Not Found | 리소스 없음 |
|
||||
| `CODE_405` | 405 Method Not Allowed | 메서드 불일치 |
|
||||
| `CODE_500` | 500 Internal Server Error | 서버 오류 |
|
||||
| `CODE_2001` | 200 OK | 단건 조회 성공 |
|
||||
| `CODE_2002` | 201 Created | 등록 성공 |
|
||||
| `CODE_2003` | 200 OK | 조회 결과 없음 |
|
||||
| `CODE_2004` | 409 Conflict | 중복 데이터 |
|
||||
| `CODE_4001` | 400 Bad Request | 입력값, 바인딩, 타입 오류 |
|
||||
| `CODE_4003` | 400 Bad Request | 필수 요청 파라미터 누락 |
|
||||
|
||||
Reference in New Issue
Block a user