Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -76,25 +76,25 @@ public void withdraw(String token) {
tokenBlacklist.add(token);
}

// 인증을 처리하는 함수, 카카오 로그인일 경우 그 외 분기하여 처리
public Member getCurrentMember(Authentication authentication) {
Object principal = authentication.getPrincipal();

// ✅ JWT 필터나 세션이 바로 Member를 넣어준 경우
if (principal instanceof Member member) {
return member;
}


// OAuth2 (카카오) 로그인인 경우
// ✅ OAuth2 (카카오) 로그인인 경우
if (principal instanceof OAuth2User oAuth2User) {
String kakaoId = oAuth2User.getAttribute("id").toString();
return memberRepository.findByKakaoId(kakaoId)
.orElseThrow(() -> new GeneralException(MemberErrorCode.MEMBER_NOT_FOUND));
}

// 그 밖의 경우 (기본적으로 username = email로 보는 경우) ex.jwt_token
// 그 밖의 경우 (기본적으로 username = email로 보는 경우)
String email = authentication.getName();
return memberRepository.findByEmailAndDeletedAtIsNull(email)
.orElseThrow(() -> new GeneralException(MemberErrorCode.MEMBER_NOT_FOUND));


}

// 카카오 로그인 시 유저 정보가 존재하지 않을 때, 카카오 데이터 기반으로 DB에 회원 정보 저장 (비밀번호의 경우 사용자의 kakaoId를 암호화해서 저장)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,4 @@ public interface CategoryRepository extends JpaRepository<Category, Long> {

}


Original file line number Diff line number Diff line change
Expand Up @@ -83,10 +83,12 @@ public SecurityFilterChain securityFilterChain(HttpSecurity http,
)

.addFilterBefore(
new JwtAuthenticationFilter(jwtTokenProvider, tokenBlacklist),
new JwtAuthenticationFilter(jwtTokenProvider, tokenBlacklist,
memberRepository, passwordEncoder()),
UsernamePasswordAuthenticationFilter.class
);


return http.build();
}

Expand All @@ -107,4 +109,4 @@ public CorsConfigurationSource corsConfigurationSource() {
source.registerCorsConfiguration("/**", configuration);
return source;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,18 +5,36 @@
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.RequiredArgsConstructor;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.oauth2.core.user.OAuth2User;
import org.springframework.util.StringUtils;
import org.springframework.web.filter.OncePerRequestFilter;
import umc9th_hackathon.daybreak.domain.member.entity.Member;
import umc9th_hackathon.daybreak.domain.member.repository.MemberRepository;
import umc9th_hackathon.daybreak.global.enums.Role;

import java.io.IOException;
import java.util.List;

@RequiredArgsConstructor
public class JwtAuthenticationFilter extends OncePerRequestFilter {

private final JwtTokenProvider jwtTokenProvider;
private final TokenBlacklist tokenBlacklist;
private final MemberRepository memberRepository;
private final PasswordEncoder passwordEncoder;

public JwtAuthenticationFilter(JwtTokenProvider jwtTokenProvider, TokenBlacklist tokenBlacklist, MemberRepository memberRepository, PasswordEncoder passwordEncoder) {
this.jwtTokenProvider = jwtTokenProvider;
this.tokenBlacklist = tokenBlacklist;
this.memberRepository = memberRepository;
this.passwordEncoder = passwordEncoder;
}


// 클래스 내부에 resolveToken 메서드 넣기!
Expand All @@ -37,14 +55,41 @@ protected void doFilterInternal(HttpServletRequest request, HttpServletResponse
// 1. JWT 먼저 확인
String jwt = resolveToken(request);
if (jwt != null && jwtTokenProvider.validateToken(jwt)) {
if (tokenBlacklist.isBlacklisted(jwt)) {
filterChain.doFilter(request, response);
return;
}
Authentication auth = jwtTokenProvider.getAuthentication(jwt);
SecurityContextHolder.getContext().setAuthentication(auth);
// JWT 처리...
filterChain.doFilter(request, response);
return;
}
// 2. OAuth2 세션 확인 (가장 중요!)
Authentication auth = SecurityContextHolder.getContext().getAuthentication();
if (auth != null && auth.getPrincipal() instanceof OAuth2User oAuth2User) {
String kakaoId = ((OAuth2User) auth.getPrincipal()).getAttribute("id").toString();

// kakaoId로 DB 사용자 조회/생성
Member member = memberRepository.findByKakaoId(kakaoId)
.orElseGet(() -> {

Member newMember = Member.builder()
.kakaoId(kakaoId)
.name(oAuth2User.getAttribute("nickname") != null ?
oAuth2User.getAttribute("nickname").toString() : "KakaoUser")
.email("kakao_" + kakaoId.substring(0, 8) + "@example.com")
.password(passwordEncoder.encode("OAUTH2_USER"))
.role(Role.ROLE_USER)
.build();
return memberRepository.save(newMember);
});

List<GrantedAuthority> authorities = List.of(
new SimpleGrantedAuthority("ROLE_" + member.getRole().name()) // "ROLE_USER"
);

// SecurityContext에 Member 정보 설정
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(
member, null,
authorities
);
SecurityContextHolder.getContext().setAuthentication(token);
}
filterChain.doFilter(request, response);
}
}