CS로 알아보는 프로젝트 - env와 API_KEY

 

안녕하세요.

 

혹시 여러분들은 env에 대해 자세히 알고 계신가요? 

 

웹 개발자 분들이라면 프런트엔드 프레임워크에서 보신 분들도 있을 것이고 서버를 개발해 보셨다면 Dockerfile을 작성하시거나 nginx에서 설정할 때 그리고 그 외 등등에서 보신 분들이 다수 존재하실 거라고 생각합니다.

 

웹 개발자 관점에서 다음과 같은 고민을 하시다가 해당 포스팅에 들어오셨으리라 생각합니다.

(다른 관점에서도 작성되었으니 끝가지 봐주시면 감사하겠습니다.)

 

과연, FE 프레임워크에서 작성하는 env에 API_KEY를 저장해도 되는 걸까요? 

 

정답부터 말씀드리면 "안된다" 입니다. 

 

해결 방안에 대해서는 아래에서 자세하게 다루어 보도록 하겠습니다.

 

 

 

그전에 env 파일이 무엇을 하는 파일인지 알아볼까요? 

 

env는 key-value 형태로 환경변수를 저장하기 위한 파일입니다.

 

애플리케이션의 설정이나 민감 정보를 안전하게 관리하는데 주로 사용되곤 합니다. 

 

아래 자료와 같이 Dockerfile에서 포트번호, key 등을 환경 변수로 빼는 등으로 사용할 수도 있으며 

FE에서 엔드포인트를 지정하거나 NGINX에서 API_KEY를 관리하는 등에 사용할 수 있습니다.

 

아래에서 더욱 자세하게 알아보도록 하겠습니다. 

 

 

env 사용에 있어 어떤 부분을 주의해야할까요?

 

유저에게 제공되는 env의 경우 민간정보를 포함하면 안 되며 git에 해당 파일을 올리는 것도 조심해야 합니다. 

 

유저에게 제공되는 env에 api키가 들어가 있다면 유저가 해당 API를 탈취하여 악용할 수 있습니다. 

 

그렇기 때문에 FE에서 유저에게 env를 제공한다면 엔드포인트 및 민감정보가 없는 환경 변수 파일만을 제공해야 합니다.

 

env 파일의 활용을 더 자세하게 알아볼까요? 

 

 

 

FE 관점에서는 end-point를 전달하는 용도로 사용할 수 있습니다.

FE에서 바라보는 엔드포인트를 전부 환경변수 처리해 뒀다면 바라보는 서버가 변경되더라도 해당 파일만 수정하면 모든 엔드 포인트가 변경되기 때문에 보다 유지보수하기 편리하게 설계할 수 있습니다.

 

Dockerfile 관점에서의 env도 확인해 볼까요?

 

다른 개발자에게 Dockerfile을 공유하거나 Git에 올릴 때 서버 내의 정보를 감추는 데 사용할 수도 있습니다.

 

아래 예제와 같이 Port 번호, user정보 등을 가릴 수 있게 되는 것이죠. 

 

 

그럼 FE에서 API_KEY를 env를 에 넣지 않는다면 어떤 식으로 관리할 수 있을까요? 

 

먼저 지속적으로 말씀드렸던 잘 못 된 사용 예시를 보도록 하겠습니다.

 

FE에서 env에 End_point 및 API_KEY를 넘겨주었다면 유저는 직접 헤더에 API_KEY를 넣어 요청을 보내게 될 것입니다.

 

그럼 유저는 API를 직접 가지고 있게 되는 것이고 이를 탈취하여 악용할 가능성이 매우 전무하여 보안적으로 굉장히 취약한 상황이 발생하게 됩니다.

 

이를 해결하기 위해서는 어떤 형태로 API_KEY를 관리해야 할까요? 

 

 

 

가장 권장되는 방법은 BE가 API_KEY를 가지고 외부  API Server에 요청을 보내는 방식입니다. 

 

BE Server가 API_KEY를 관리하고 있고 외부 API Server로 요청을 보냄으로써 FE는 API_KEY를 모르더라도 해당 서버에 요청이 가능하게 됩니다.

 

 

 

효과적인 방법은 아니지만 BE Server에서 API_KEY를 관리하고 싶지 않다면 NGINX를 활용하는 방법도 있습니다.

 

FE에서는 엔드 포인트만 관리하고 NGINX에 환경 변수를 세팅하여 API 서버에 요청을 보내는 것입니다.

 

이로 인해 API_KEY 노출로부터 안전한 관리가 가능해집니다. 

 

이때 NGINX는 유저의 요청에 API_KEY를 Header에 추가하여 보내게 됩니다. 

 

다음과 같이 nginx에 env 파일을 등록하고 해당 요청에 header 값을 삽입하여 전송이 가능합니다. 

 

해당 코드는 이미지 아래 작성해 두겠습니다. 

http {
    ...

    # 환경 변수 파일 지정
    env_file /path/to/api_keys.env;

    server {
        listen 80;
        server_name yourdomain.com;

        location /api/ {
            proxy_pass http://api.example.com;  # 백엔드 API 서버 주소

            # API 키를 헤더에 추가
            proxy_set_header Authorization "Bearer $API_KEY_1";  # 환경 변수 사용

            # 필요한 경우 다른 헤더도 추가할 수 있습니다.
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        }

        ...
    }

    ...
}

 

 

오늘은 env의 활용에 대해 알아보았습니다.

 

FE가 내려주는 env에는 절대 API_KEY를 삽입하면 안 되겠죠?? 

 

추가적으로 궁금한 부분 있다면 댓글 남겨주시면 답변드리도록 하겠습니다. 감사합니다.