728x90
1. 에러 로그 및 문제점
org.springframework.beans.factory.UnsatisfiedDependencyException
: Error creating bean with name 'customSecurityConfig' defined in file
[C:\SEO\BE\build\classes\java\main\com\omd\dashboard\common\config\CustomSecurityConfig.class]
: Unsatisfied dependency expressed through constructor parameter 1
: Error creating bean with name 'JWTTokenProvider' defined in file
[C:\SEO\BE\build\classes\java\main\com\omd\dashboard\common\util\JWTTokenProvider.class]
: Failed to instantiate [com.omd.dashboard.common.util.JWTTokenProvider]
: Constructor threw exception
JWTTokenProvider 클래스의 생성자에서 예외가 발생하여 Bean 생성에 실패했다는 로그가 떴다.
2. 원인 분석 및 해결방법
JWTTokenProvider 클래스에서 application.properties에 있는 값을 가져와
사용하고 있기 때문에 application.properties에서 잘못됐을 가능성이 커보였다.
하지만, jasypt를 이용하여 값을 잘 넣어두었고,
오타도 딱히 발견하지 못하였다.
// application.properties
spring.jwt.secret=ENC(jwt secret 값)
spring.jwt.access.expirationTime=ENC(accessToken 만료 시간)
spring.jwt.refresh.expirationTime=ENC(refreshToken 만료 시간)
따라서 아래처럼 JWTTokenProvider 생성자에 try-catch문과 에러 로그를 설정하였다.
@Log4j2
@Component
public class JWTTokenProvider {
private final Key key;
private final long accessTokenExpTime;
private final long refreshTokenExpTime;
public JWTTokenProvider(
@Value("${spring.jwt.secret}") String secretKey,
@Value("${spring.jwt.access.expirationTime}") long accessTokenExpTime,
@Value("${spring.jwt.refresh.expirationTime}") long refreshTokenExpTime
) {
try {
byte[] keyBytes = Decoders.BASE64.decode(secretKey);
this.key = Keys.hmacShaKeyFor(keyBytes);
this.accessTokenExpTime = accessTokenExpTime;
this.refreshTokenExpTime = refreshTokenExpTime;
} catch (Exception e) {
log.error("JWTTokenProvider 생성자 error", e);
throw e;
}
}
}
다시 실행 후 콘솔에 찍힌 에러 로그는 아래와 같았다.
io.jsonwebtoken.io.DecodingException
: Illegal base64 character: '('
spring.jwt.secret 값에 (를 사용해 발생하는 에러인 것 같았다.
찾아보니 Base64에서 사용하는 특수문자는 +와 -뿐이라고 한다.
따라서 secret 값을 특수문자가 없이 수정했고, 위 문제는 해결이 되었다.
그런데 다른 에러가 떴다.
io.jsonwebtoken.security.WeakKeyException
: The specified key byte array is 88 bits
which is not secure enough for any JWT HMAC-SHA algorithm.
The JWT JWA Specification (RFC 7518, Section 3.2) states
that keys used with HMAC-SHA algorithms MUST have a size >= 256 bits
(the key size must be greater than or equal to the hash output size).
Consider using the io.jsonwebtoken.security.Keys#secretKeyFor(SignatureAlgorithm) method
to create a key guaranteed to be secure enough for your preferred HMAC-SHA algorithm.
See https://tools.ietf.org/html/rfc7518#section-3.2 for more information.
key 길이가 충분하지 않아 발생하는 에러였다.
따라서 secret 값 길이를 256바이트 이상으로 설정해 해결했다.
3. 정리
- Base64 인코딩을 이용할 때는 특수문자 없이. 특수문자를 사용하더라도 +나 -만 사용하기
- key를 생성할 때는 256비트 이상으로 설정
참고
Base64 인코딩이란?
Base64 인코딩을 알아보기 전, 인코딩에 대해서 먼저 알아봐야한다. 인코딩(encoding)이란? 인코딩(encoding)은 컴퓨터를 이용해 영상 · 이미지 · 소리 데이터를 생성할 때 데이터의 양을 줄이기 위해
suzzeong.tistory.com
728x90