Skip to content

[한성지] sprint9 #454

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Conversation

hyanyul
Copy link
Collaborator

@hyanyul hyanyul commented May 26, 2025

요구사항

기본

Spring Security 환경 설정

  • 프로젝트에 Spring Security 의존성을 추가하세요.
  • Security 설정 클래스를 생성하세요.
    • 패키지명: com.sprint.mission.discodeit.config
    • 클래스명: SecurityConfig
  • SecurityFilterChain Bean을 선언하세요.
    • 가장 기본적인 SecurityFilterChain을 등록하고, 이때 등록되는 필터 목록을 디버깅해보세요. 필터 목록은 PR에 첨부하세요.

      • 필터 목록
        • 아래 코드를 SecurityConfig/filterChain에 작성하여 필터 확인

          SecurityFilterChain chain = http.build();
            if (chain instanceof DefaultSecurityFilterChain securityFilterChain) {
              System.out.println("========= 필터 목록 =========");
            for (Filter filter : securityFilterChain.getFilters()) {
              System.out.println(filter.getClass().getSimpleName());
            }
          }
          
        • 결과

          ========= 필터 목록 =========
          DisableEncodeUrlFilter
          WebAsyncManagerIntegrationFilter
          SecurityContextHolderFilter
          HeaderWriterFilter
          CsrfFilter
          LogoutFilter
          RequestCacheAwareFilter
          SecurityContextHolderAwareRequestFilter
          AnonymousAuthenticationFilter
          ExceptionTranslationFilter
          
    • 모든 요청에 대해 인증이 수행되도록 하세요.

    • /api/를 포함하지 않는 모든 url에 대한 요청(정적 리소스, swagger, actuator 등)은 인증을 수행하지 않도록 하세요.

  • LogoutFilter를 제외하세요.
    • 디스코드잇은 로그아웃 페이지를 CSR로 처리하기 때문에 LogoutFilter는 사용하지 않습니다.
  • 개발 환경에서 Spring Security 모듈의 로깅 레벨을 trace로 설정하세요.
    • 각 요청마다 통과하는 필터 목록을 확인할 수 있습니다.

CSRF 보호 설정하기

디스코드잇은 CSR 방식이기 때문에 CSRF 토큰을 프론트엔드에서 명시적으로 관리합니다.

  1. 페이지가 로드될 때 서버로부터 CSRF 토큰 발급
  2. CSRF 토큰을 쿠키(CSRF-TOKEN)에 저장
  3. 매 요청마다 쿠키에 저장된 CSRF 토큰을 헤더(X-CSRF-TOKEN)에 포함
  • CSRF 토큰을 발급하는 API를 구현하세요.

    엔드포인트 요청 응답
    GET /api/auth/csrf-token 없음 200 CsrfToken
    • 다이어그램

  • 권한이 수정된 사용자가 로그인 상태라면, 강제 로그아웃 되도록 합니다.

    디스코드잇 프론트엔드에서는 401 응답인 경우에 강제 로그아웃 되도록 구현되었습니다.

인가 처리

  • 회원가입, 로그인, csrf 토큰 발급 등을 제외한 모든 API는 최소 ROLE_USER 권한을 가져야합니다.
  • 퍼블릭 채널 생성, 수정, 삭제는 최소 ROLE_CHANNEL_MANAGER 권한을 가져야합니다.
  • 사용자 권한 수정은 ROLE_ADMIN 권한을 가져야합니다.

심화

프론트엔드 버전업

심화 요구 사항을 위해 프론트엔드 코드를 버전업하세요. v2.1.0

Remember-Me

  • 다음의 조건을 만족하도록 로그인 유지 기능을 구현하세요.
  • 토큰은 데이터베이스에 저장하세요.
  • 쿠키에 저장되는 토큰의 유효기간은 3주로 지정하세요.
  • 로그아웃 시 데이터베이스에 저장된 토큰을 삭제하고, 클라이언트 쿠키도 삭제하세요.

동시 로그인 제한

  • 하나의 사용자 ID로 동시 로그인을 제한하세요. 새로운 로그인 발생 시 기존 세션을 무효화하세요.

세션 고정 보호

  • 세션 고정 보호를 위해 필요한 설정을 구현하세요.

사용자 로그인 상태 고도화

  • Session 정보를 활용해 사용자의 로그인 상태를 판단하도록 리팩토링하세요.
  • UserStatus 엔티티와 관련된 모든 코드는 삭제하세요.

인가 고도화

  • 사용자 정보 수정, 삭제는 본인 또는 ROLE_ADMIN 권한을 가진 사용자만 호출할 수 있습니다.
  • 메시지 수정은 메시지를 작성한 사람만 호출할 수 있습니다.
  • 메시지 삭제는 메시지를 작성한 사람 또는 ROLE_ADMIN 권한을 가진 사용자만 호출할 수 있습니다.
  • 읽음 상태 생성, 수정은 본인만 호출할 수 있습니다.

주요 변경사항

스크린샷

image

멘토에게

  • 계속 403 에러가 나는데 어디가 문제인지 모르겠습니다.

@hyanyul hyanyul changed the title Part4 한성지 sprint9 [한성지] sprint9 May 26, 2025
@hyanyul hyanyul force-pushed the part4-한성지-sprint9 branch from f7e0ac2 to ba20927 Compare May 26, 2025 05:01
@hyanyul hyanyul requested a review from youngxpepp May 26, 2025 05:02
Copy link
Collaborator

@youngxpepp youngxpepp left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

성지님 고생하셨습니다!
403 에러는 제가 채점 다 끝낸 후에 디버깅 해볼게요~~

Comment on lines +54 to +63
// 세션 무효화
HttpSession session = request.getSession(false);
if (session != null) {
session.invalidate();
}

// securityContext 초기화
SecurityContextHolder.clearContext();

return ResponseEntity.ok().build();
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

https://limvik.github.io/posts/spring-security-logout-operation/

위 글 읽어보시면 좋아요. 로그아웃시 정리되어야 하는게 session, context 외에도 있더라구요~

Comment on lines +144 to +153
@Override
public UserDto updateRole(RoleUpdateRequest request) {

User user = userRepository.findById(request.userId())
.orElseThrow(() -> UserNotFoundException.withId(request.userId()));

user.updateRole(request.newRole());

return userMapper.toDto(user);
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

권한 변경 후 로그아웃이 되면 좋을텐데! 아쉽습니당!

@youngxpepp youngxpepp merged commit 783d065 into codeit-bootcamp-spring:part3-한성지 Jun 1, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants