그림 그리는 개발자
  • javascript 에서 aes256 암호화, 복호화 하기
    2023년 07월 26일 22시 07분 42초에 업로드 된 글입니다.
    작성자: 루루개발자

    안녕하세요. 루루개발자 입니다.

    이번 글에서는 javascript 에서 aes256 암호화, 복호화 하는 방법에 대해 공유드리고자 합니다.

     

    먼저 이 글을 보시는 분들께서는 가까운 시일 내에 또는 지금 당장 javascript 에서 aes256 암호화, 복호화를 적용해야 하는 상황이실 거라 생각됩니다. 그래서 먼저 제가 만들어 둔 코드를 공유 드리겠습니다.

    import { AES, enc } from 'crypto-js';
    
    export function encrypt(data: string, key: string): string {
      const dataWA = enc.Utf8.parse(data);
      const keyWA = enc.Utf8.parse(key);
      const ivWA = enc.Utf8.parse(key.substring(0, 16));
    
      const cipher = AES.encrypt(dataWA, keyWA, { iv: ivWA });
      return cipher.ciphertext.toString(enc.Base64url); // url query 파라미터 대응하기 위해 일반 base64 가 아닌 base64url 로 변환
    }
    
    export function decrypt(encData: string, key: string): string {
      const keyWA = enc.Utf8.parse(key);
      const ivWA = enc.Utf8.parse(key.substring(0, 16));
    
      const cipher = AES.decrypt(enc.Base64url.parse(encData.replace(/=/gi, '')).toString(enc.Base64), keyWA, { iv: ivWA }); // 해쉬된 값이 url encode 일 수도 있으므로 base64url 로 파싱하고 다시 base64 로 인코딩
      return cipher.toString(enc.Utf8);
    }

    typescript 기반으로 작성하였으며, crypto-js 라는 npm 패키지를 사용하여 만든 aes256 기반의 encrpyt 함수와 decrypt 함수입니다. 위 코드는 브라우저(클라이언트)에서도 사용 가능하며, 백엔드(node.js 등) 에서도 사용 가능합니다. 기능 구현이 급하신 분들께서는 crypto-js 라는 npm 패키지를 설치하신 후, 먼저 위 코드를 사용하시면 되겠습니다.

     

    위 코드를 구현하기 까지 여러가지 난관(?)이 있었습니다. 분명 규격에 맞춰 encrypt 를 했는데 decrypt 가 되지 않거나, 동일한 key 를 기준으로 했을 때 클라이언트에서 encrypt 된 데이터가 서버에서 decrypt 가 되지 않는 등의 이슈가 발생하였습니다.

     

    이러한 이슈들을 해결하다보니 위와 같은 코드를 작성하게 되었습니다. https://www.npmjs.com/package/crypto-js 에 나와있는 예시에는 key 나 data 를 별도의 인코딩 과정 없이 바로 encrypt, decrypt 하도록 나와 있는데 이렇게 하니 제 환경에서는 정상적으로 작동하지 않았습니다. 그렇게 구글링을 하면서 코드를 수정해나가다 보니 key 나 data 를 utf8 로 인코딩 해주어야 정상적으로 작동함을 확인하였습니다. 그렇지 않은 경우에는 저처럼 일부 환경에서는 정상적으로 작동하지 않을 수 있습니다. 

     

    위 이슈를 해결하고 나니 이제 다른 이슈가 저를 맞이하고 있었습니다. 클라이언트에서 암호화 한 데이터를 서버에 전달 하고 서버는 그 데이터를 복호화를 해야 했는데, 서버에서 복호화가 되지 않았습니다. 이 역시 구글링 하며 원인을 찾아보니 클라이언트에서 암호화된 데이터를 서버에 전달 할 때 url query string 으로 전달을 하였는데 암호화 할 때 url query string 관련 대응을 하지 않으면 url encoding 현상 때문에 해시 값이 다르게 서버에 전달되어 복호화가 되지 않는 거였습니다. 그래서 이 부분도 encrypt 를 할 때 base64 가 아닌 base64url 로 옵션을 수정하여 해결 할 수 있었습니다.

     

    생각했던 것보다 금방 끝날 것 같았던 aes256 암호화, 복호화 작업이 이 두가지 이슈로 인해 길어졌습니다. 이 글을 보시는 여러분들께서는 짧은 시간 안에 암호화, 복호화를 구현하시고 나머지 작업에 집중하실 수 있으시길 바라는 마음에 이 글을 작성해보았습니다.

     

    그럼 오늘도 즐거운 코딩하세요~

     

     

     

     

     

     

    댓글