서버 프로젝트를 진행하다보면 숨겨야 할 키들이 다양하게 생기게 된다.
DB URL, username, password
외부 API 키
jwt 키
oAuth 클라이언트 시크릿
등등..
그리고 이런 요소들은 보통 다음과 같이 application.yml
파일에 작성된다.
datasource:
url: {url}
username: {username}
password: {password}
driver-class-name: {driver}
프로젝트의 코드에 이런 비밀번호가 적혀있다면 타인에게 소스코드를 공개할 수 없을 뿐 아니라, 보안 상 문제가 생길 수도 있다.
물론 어플리케이션에서 환경변수로 입력받을 수도 있다. 하지만 이런 키들이 많아질 수록 설정해야하는 환경 변수의 양도 너무 많아지고 번잡해지게 된다.
Jasypt로 프로퍼티 암호화하기
Jasypt는 개발자가 암호화 작동 방식에 대한 깊은 지식이 없어도 최소한의 노력으로 프로젝트에 기본적인 암호화 기능을 추가할 수 있는 자바 라이브러리다.
홈페이지에서 직접 스프링, 스프링 시큐리티와 통합하기 편리하다고 적혀있는데, 스프링 부트가 아니라 스프링에 대해 설명이 적혀있는 관계로 조금 설정이 복잡하다.
http://www.jasypt.org/spring31.html
따라서 스프링 부트 버전으로 확인해보려고 한다.
Spring Boot와 통합하기
다음의 멋진 깃허브 레포지토리를 참고한 내용이다.
라이브러리 추가하기
implementation 'com.github.ulisesbocchio:jasypt-spring-boot-starter:3.0.5'
먼저 이 플러그인을 build.gradle
에 추가해준다.
Jasypt 설정 추가하기
@Configuration
@EnableEncryptableProperties
public class JasyptConfig {
@Value("${jasypt.encryptor.password}")
private String password;
@Bean("jasyptStringEncryptor")
public StringEncryptor stringEncryptor() {
PooledPBEStringEncryptor encryptor = new PooledPBEStringEncryptor();
SimpleStringPBEConfig config = new SimpleStringPBEConfig();
config.setPassword("password");
config.setAlgorithm("PBEWITHHMACSHA512ANDAES_256");
config.setKeyObtentionIterations("1000");
config.setPoolSize("1");
config.setProviderName("SunJCE");
config.setSaltGenerator(new RandomSaltGenerator());
config.setIvGenerator(new RandomIvGenerator());
encryptor.setConfig(config);
return encryptor;
}
}
다음과 같이 Config 파일을 추가해준다.
(깃허브 레포지토리의 공식 설명에 적혀있는 코드에서, 몇 중복 설정이나 불필요한 리플렉션을 대체했다)
프로퍼티 암호화하기
이제 프로퍼티를 암호화할 시간이다. 암호화는 다음 주소에서 사용할 수 있다.
cloud:
aws:
region: ap-northeast-2
credentials:
access-key: ABCDEFGHIJKLMNOP
다음과 같은 설정이 있었다고 가정해보자.
다음과 같이 Enter Plain Text To Encrypt
부분에 암호화 하고 싶은 텍스트를 넣는다. 그 후 Type은 Two Way Encryption
을 지정해주고 (스프링에서 다시 복호화해서 쓸 수 있어야 하니..) Enter Secret Key
에 내가 원하는 암호화 키를 적어주자.
마무리로 암호화 버튼을 눌러주면 내가 지정해준 암호화 키로 풀 수 있는 암호화된 문자열이 생성된다.
cloud:
aws:
region: ap-northeast-2
credentials:
access-key: ENC(Q8X55qnH5/9b1H+9yWOdFXqqkbFvgsjjn8FVrv9xazg=)
이 문자열을 다음과 같이 대체해주자. ENC(암호화 결과)
와 같이 ENC()로 감싸서 넣어주면 된다.
환경변수로 암호화 키 지정하기
마지막으로, 암호화에 사용했던 시크릿 키를 환경변수로 넣어주자.
앞에서 @Value("${jasypt.encryptor.password}")
라고 코드를 작성했는데, 이와 같이 jasypt.encryptor.password
를 환경변수로 지정해주면 자동으로 해당 값이 @Value에 들어가게 된다.
인텔리제이 기준으로 다음과 같이 구성 편집에 들어가자.
그 다음 이렇게 자기가 사용했던 시크릿 키를 환경변수로 지정해주면 된다.
그러면 끝!
마무리
설정들을 전부 암호화 완료했다면, 서버를 구동해서 제대로 동작하는지 확인하여 마무리해보자