관리 메뉴

솜씨좋은장씨

[Python] sourcedefender를 활용하여 코드를 암호화 하는 방법 본문

Programming/Python

[Python] sourcedefender를 활용하여 코드를 암호화 하는 방법

솜씨좋은장씨 2021. 7. 8. 21:38
728x90
반응형

최근 python 코드를 암호화해야할 일이 생겨 sourcedefender를 활용하여 진행해보았습니다.

 

다음은 sourcedefender를 활용하여 암호화를 진행하는 방법입니다.

 

상업적으로 사용할때에는 라이센스 문제가 있기 때문에 사용에 주의하시기 바랍니다@~@

1. sourcedefender 설치

먼저 pip를 활용하여 sourcedefender를 설치합니다.

$ pip install sourcedefender
$ pip install sourcedefender==6.0.21

설치는 위의 두 명령어 중 하나를 골라 설치하면 됩니다.

 

2. 실행할 코드 속 __name__ == "__main__" 지우기

그 다음 실행 할 코드 속 

if __name__ == "__main__"":

main 라인을 삭제합니다.

 

3. 코드 암호화 하기

$ sourcedefender encrypt --remove [file_path]

2번까지의 과정을 다 거쳤다면 위의 명령어를 통해서 암호화를 진행합니다.

 

여기서 --remove 옵션은 암호화가 끝나면 기존의 .py 파일은 삭제가 되는 옵션입니다.

자세한 내용은 아래의 링크를 참고 바랍니다.

 

sourcedefender

Advanced encryption protecting your python codebase.

pypi.org

 

3-1. python 코드를 활용하여 코드를 암호화하기

이 방법은 특정 directory에 있는 모든 Python 파일 ( .py ) 을 한번에 쉽게 암호화 하는 방법입니다.

encrypt.py

import os
import argparse

parser = argparse.ArgumentParser(formatter_class=argparse.RawTextHelpFormatter)


def get_arguments():
    parser.add_argument("-target", "--target",
                        help="input path of module\n",
                        type=str, required=True)
    parser.add_argument("-encrypt", "--encrypt", action="store_true",
                        help="encrypt .py files")
    parser.add_argument("-remove", "--remove", action="store_true",
                        help="remove .py files")
    _args = parser.parse_args()

    return _args


args = get_arguments()

if not args.encrypt and not args.remove:
    print("Please use '--encrypt, --remove' option!\n")
    exit(-1)


def search(dirname):
    try:
        filenames = os.listdir(dirname)
        for filename in filenames:
            full_filename = os.path.join(dirname, filename)
            if os.path.isdir(full_filename):
                search(full_filename)
            else:
                ext = os.path.splitext(full_filename)[-1]
                if ext == '.py':
                    if args.encrypt and args.remove:
                        os.system("sourcedefender --remove encrypt " + full_filename)
                    elif args.encrypt:
                        os.system("sourcedefender encrypt " + full_filename)
                    elif args.remove:
                        os.system("rm " + full_filename)
                        print("rm", full_filename)
    except PermissionError:
        pass


if __name__ == '__main__':
    search(args.target)

위와 같은 코드로 구성되어있는 Python 코드를 하나 작성해줍니다.

$ python encrypt.py --target [target_dir] --encrypt
$ python encrypt.py --target [target_dir] --encrypt --remove

그 다음 위의 명령어를 통해서 특정 디렉토리에 있는 모든 python 파일을 암호화 합니다. ( 둘 중에 하나 선택 )

 

여기서 --remove 가 붙는 명령어는 암호화 후에 기존 Python 코드를 삭제하고 암호화 파일만 남기는 방법입니다.

 

그럼 암호화가 완료됩니다.

 

4. 암호화한 파일을 command 창에서 명령어를 통하여 실행하는 방법

암호화가 진행되고 나면 .py 파일들이 .pye 로 변환되게 됩니다. 

$ python -m sourcedefender [ 암호화된 pye 파일 ]

이 변환된 파일을 바로 실행하는 방법은 위의 명령어를 활용하면 됩니다.

 

사용 시 참고해야할 사항

1. argparse 사용 불가

명령어를 사용할때 -- 뒤에 여러 옵션들의 파라미터를 설정해주는 argparse는 사용이 불가합니다.

 

이를 해결하기 위해서는 자주 변하는 변수에 대해서

- 별도의 config 파일을 생성하거나

- docker-compose 파일의 환경 변수로 설정

해주는 것을 추천합니다.

 

2. uwsgi 를 활용하여 배포하는 api의 경우

이 경우에는 모든 파일을 암호화 한 후에 uwsgi --ini 명령어를 통하여 실행하면

ModuleNotFoundError: No module named 'app'

오류를 만나게 됩니다.

 

이 경우는 uwsgi에서 참조하려는 파일이 pye로 암호화 되어있어

기존의 방식으로는 제대로 읽을 수 없어 발생하는 문제입니다.

 

해결방법은 다음과 같습니다.

 

먼저 모든 python 파일을 위의 암호화 방식 대로 암호화를 진행합니다.

암호화가 완료되면 wsgi.py 파일을 하나 만들어줍니다.

 

app.py ( 암호화 되기전의 app.py )

-- 생략 --

app = Flask(__name__)

-- 생략 --

 

wsgi.py

import sourcedefender
import app
from app import app

한 줄 씩 보면

sourcedefender를 import 하고

그 다음중레 app.pye를 import 합니다.

그리고 마지막으로 app.pye 안에 있는 app 을 import 해줍니다.

 

그 다음 uwsgi.ini 파일에서 wsgi-file  = wsgi.py , callable = app 을 설정해주면 됩니다.

 

uwsgi.ini

[uwsgi]

http = :4292
chdir = ./
wsgi-file = wsgi.py
callable = app
-- 생략 --

 

그럼 정상적으로 작동하는 것을 볼 수 있습니다.

 

읽어주셔서 감사합니다.

Comments