Copy & Paste, Struggling
This commit is contained in:
42
src/main/java/demo/api/jwt/JwtTokenFilter.java
Normal file
42
src/main/java/demo/api/jwt/JwtTokenFilter.java
Normal file
@@ -0,0 +1,42 @@
|
||||
package demo.api.jwt;
|
||||
|
||||
import demo.api.jwt.exception.CustomException;
|
||||
import java.io.IOException;
|
||||
import javax.servlet.FilterChain;
|
||||
import javax.servlet.ServletException;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import org.springframework.security.core.Authentication;
|
||||
import org.springframework.security.core.context.SecurityContextHolder;
|
||||
import org.springframework.web.filter.OncePerRequestFilter;
|
||||
|
||||
// Request 이전에 1회 작동할 필터
|
||||
public class JwtTokenFilter extends OncePerRequestFilter {
|
||||
private JwtTokenProvider jwtTokenProvider;
|
||||
|
||||
public JwtTokenFilter(JwtTokenProvider jwtTokenProvider) {
|
||||
this.jwtTokenProvider = jwtTokenProvider;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doFilterInternal(
|
||||
HttpServletRequest request,
|
||||
HttpServletResponse response,
|
||||
FilterChain filterChain
|
||||
) throws ServletException, IOException {
|
||||
String token = jwtTokenProvider.resolveToken(request);
|
||||
try {
|
||||
if (token != null && jwtTokenProvider.validateToken(token)) {
|
||||
Authentication auth = jwtTokenProvider.getAuthentication(token);
|
||||
SecurityContextHolder.getContext().setAuthentication(auth);
|
||||
}
|
||||
} catch (CustomException ex) {
|
||||
//this is very important, since it guarantees the user is not authenticated at all
|
||||
SecurityContextHolder.clearContext();
|
||||
response.sendError(ex.getHttpStatus().value(), ex.getMessage());
|
||||
return;
|
||||
}
|
||||
|
||||
filterChain.doFilter(request, response);
|
||||
}
|
||||
}
|
||||
84
src/main/java/demo/api/jwt/JwtTokenProvider.java
Normal file
84
src/main/java/demo/api/jwt/JwtTokenProvider.java
Normal file
@@ -0,0 +1,84 @@
|
||||
package demo.api.jwt;
|
||||
|
||||
import demo.api.jwt.exception.CustomException;
|
||||
import io.jsonwebtoken.Claims;
|
||||
import io.jsonwebtoken.ExpiredJwtException;
|
||||
import io.jsonwebtoken.JwtException;
|
||||
import io.jsonwebtoken.Jwts;
|
||||
import io.jsonwebtoken.MalformedJwtException;
|
||||
import java.util.Base64;
|
||||
import java.util.Date;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.security.core.Authentication;
|
||||
import org.springframework.security.core.userdetails.UserDetails;
|
||||
import org.springframework.security.core.userdetails.UserDetailsService;
|
||||
import org.springframework.stereotype.Component;
|
||||
import javax.annotation.PostConstruct;
|
||||
|
||||
// 유저 정보로 JWT 토큰을 만들거나 토큰을 바탕으로 유저 정보를 가져옴
|
||||
@Component
|
||||
public class JwtTokenProvider {
|
||||
/**
|
||||
* THIS IS NOT A SECURE PRACTICE! For simplicity, we are storing a static key here. Ideally, in a
|
||||
* microservices environment, this key would be kept on a config-server.
|
||||
*/
|
||||
@Value("${jwt.token.open-secret-key}")
|
||||
private String secret_key;
|
||||
|
||||
@Value("${jwt.token.expire-length}")
|
||||
private long expire_time;
|
||||
|
||||
@Autowired
|
||||
private UserDetailsService userDetailsService;
|
||||
|
||||
@PostConstruct // 의존성 주입이 이루어진 후 초기화를 수행
|
||||
protected void init() {
|
||||
secret_key = Base64.getEncoder().encodeToString(secret_key.getBytes());
|
||||
}
|
||||
|
||||
public String createToken(String username, List<AppUserRole> appUserRoles) {
|
||||
|
||||
Claims claims = Jwts.claims().setSubject(username);
|
||||
claims.put("auth", appUserRoles.stream().map(s -> new SimpleGrantedAuthority(s.getAuthority())).filter(Objects::nonNull).collect(Collectors.toList()));
|
||||
|
||||
Date now = new Date();
|
||||
Date validity = new Date(now.getTime() + expire_time);
|
||||
|
||||
return Jwts.builder()
|
||||
.setClaims(claims)
|
||||
.setIssuedAt(now)
|
||||
.setExpiration(validity)
|
||||
.signWith(SignatureAlgorithm.HS256, secret_key)
|
||||
.compact();
|
||||
}
|
||||
|
||||
public Authentication getAuthentication(String token) {
|
||||
UserDetails userDetails = userDetailsService.loadUserByUsername(getUsername(token));
|
||||
return new UsernamePasswordAuthenticationToken(userDetails, "", userDetails.getAuthorities());
|
||||
}
|
||||
|
||||
public String getUsername(String token) {
|
||||
return Jwts.parser().setSigningKey(secret_key).parseClaimsJws(token).getBody().getSubject();
|
||||
}
|
||||
|
||||
public String resolveToken(HttpServletRequest req) {
|
||||
String bearerToken = req.getHeader("Authorization");
|
||||
if (bearerToken != null && bearerToken.startsWith("Bearer ")) {
|
||||
return bearerToken.substring(7);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public boolean validateToken(String token) {
|
||||
try {
|
||||
Jwts.parser().setSigningKey(secret_key).parseClaimsJws(token);
|
||||
return true;
|
||||
} catch (JwtException e) {
|
||||
// MalformedJwtException | ExpiredJwtException | IllegalArgumentException
|
||||
throw new CustomException("Error on Token", HttpStatus.INTERNAL_SERVER_ERROR);
|
||||
}
|
||||
}
|
||||
}
|
||||
26
src/main/java/demo/api/jwt/exception/CustomException.java
Normal file
26
src/main/java/demo/api/jwt/exception/CustomException.java
Normal file
@@ -0,0 +1,26 @@
|
||||
package demo.api.jwt.exception;
|
||||
|
||||
import org.springframework.http.HttpStatus;
|
||||
|
||||
public class CustomException extends RuntimeException {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private final String message;
|
||||
private final HttpStatus httpStatus;
|
||||
|
||||
public CustomException(String message, HttpStatus httpStatus) {
|
||||
this.message = message;
|
||||
this.httpStatus = httpStatus;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMessage() {
|
||||
return message;
|
||||
}
|
||||
|
||||
public HttpStatus getHttpStatus() {
|
||||
return httpStatus;
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user