2020/02/12 - [Back-end/Python] - [Pyftpdlib] FTP 서버 만들기 (1) - 설치 및 실행
2020/02/12 - [Back-end/Python] - [Pyftpdlib] FTP 서버 만들기 (2) - 사용자 인증 설정
0. 서론
지난 포스트에서 지정된 폴더와 권한을 가진 유저를 생성하여 FTP서버에 접속하는 방법에 대해서 알아보았다. 유저 인증 방식을 통해 FTP서버의 보안을 강화하는 효과를 얻을 수 있었다. 하지만, 사용자의 패스워드가 암호화 되지않은 일반 텍스트이기 때문에 해킹에 취약할 수 밖에 없다. 그래서, 이번 포스트에서는 사용자의 패스워드를 암호화하고 이를 이용하여 로그인하는 방법에 대해서 알아보도록 하겠다.
1. 패스워드 암호화
1-1. 스크립트 작성
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | #md5_hash.py import sys import argparse from hashlib import md5 parser = argparse.ArgumentParser(description='패스워드 암호화') parser.add_argument('--pwd', required=True, help="패스워드를 입력해주세요.") args = parser.parse_args() password = args.pwd if sys.version_info >= (3, 0):     password = password.encode('utf-8') md5_hash = md5(password).hexdigest() print( 'password: {}'.format( password ) ) print( 'hashed: {}'.format( md5_hash ) ) | cs | 
- 3 ln: arguments를 파싱해서 사용하기 좋게 만들어주는 모듈.
- 4 ln: 파이썬 기본 라이브리러인 hashlib에서 MD5 알고리즘 모듈만 사용.
  * MD5(Message-Digest algorithm 5): 128비트 길이의 암호화 해시 함수.
- 6~8 ln: 사용자의 패스워드를 입력받는 Arguments Parser 생성.
- 11~12 ln: 파이썬이 3버전 이상인 경우, 'utf-8'로 인코딩. (Bytes 타입으로 변경)
  * md5 모듈이 파이썬 2버전에서는 String을 사용하는데, 3버전부터 Bytes를 사용.
- 14 ln: 입력받은 패스워드를 128비트 길이의 암호화 해시로 변경.
1-2. 실행
$ python md5_hash.py --pwd admin1234
1-3. 실행 결과

- 'admin1234'는 MD5 암고리즘을 통해 'c93ccd78b2076528346216b3b2f701e6'으로 변경.
- 'user1234'는 MD5 암고리즘을 통해 'b5b73fae0d87d8b4e2573105f8fbe7bc'으로 변경.
- 이 패스워드를 FTP서버에 적용해보자.
2. FTP 서버 사용자 패스워드 검증
2-1. 스크립트 작성
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | #ftp_server_auth.py import os import sys from hashlib import md5 from pyftpdlib.authorizers import DummyAuthorizer, AuthenticationFailed from pyftpdlib.handlers import FTPHandler from pyftpdlib.servers import FTPServer FTP_HOST = '0.0.0.0' FTP_PORT = 9021 FTP_ADMIN_DIR = os.path.join(os.getcwd(), 'storage') FTP_USERS_DIR = os.path.join(os.getcwd(), 'storage/users') class DummyMD5Authorizer(DummyAuthorizer):     def validate_authentication(self, username, password, handler):         if sys.version_info >= (3, 0):             password = password.encode('utf-8')         hash = md5(password).hexdigest()         try:             if self.user_table[username]['pwd'] != hash:                 raise KeyError         except KeyError:             raise AuthenticationFailed def main():     authorizer = DummyMD5Authorizer()     authorizer.add_user('admin', 'c93ccd78b2076528346216b3b2f701e6', FTP_ADMIN_DIR, perm='elradfmwMT')     authorizer.add_user('user', 'b5b73fae0d87d8b4e2573105f8fbe7bc', FTP_USERS_DIR, perm='elr')     handler = FTPHandler     handler.banner = "Dochi's FTP Server."     handler.authorizer = authorizer     handler.passive_ports = range(60000, 65535)     address = (FTP_HOST, FTP_PORT)     server = FTPServer(address, handler)     server.max_cons = 256     server.max_cons_per_ip = 5     server.serve_forever() if __name__ == '__main__':     main() | cs | 
- 16 ln: DummyAuthorizer Class를 상속 받은 DummyMD5Authorizer Class 생성.
- 17 ln: validate_authentication 함수를 오버라이드(재정의).
  * 사용자가 로그인을 시도할 때, 입력한 패스워드와 사용자의 패스워드를 비교하는 함수.
- 18~25 ln: 사용자 패스워드를 검증하는 로직.
- 28 ln: DummyMD5Authorizer 객체 생성
- 30~31 ln: 암호화된 사용자 패스워드 입력.
2-2. FTP서버 실행
$ python ftp_server_auty.py
2-3. FTP서버 실행 결과

2-4. FTP서버 접속 결과

- 사용자명 'admin', 패스워드 'admin1234'를 입력하여 접속 성공.
마치며
- 사용자의 패스워드를 암호화함으로써 한층 더 보안이 강화된 느낌이다.
- 지금은 MD5 해싱 알고리즘을 사용했는데, base64나 대칭키 기반의 AES256을 적용해보는 것도 좋을것 같다.
'Back-end > Python' 카테고리의 다른 글
| [SMTP] Python으로 메일 발송 하기. (With. 첨부파일 ) (1) | 2020.02.22 | 
|---|---|
| [Pyftpdlib] FTP 서버 만들기 (4) - SSL/TLS FTP 서버 (0) | 2020.02.18 | 
| [Pyftpdlib] FTP 서버 만들기 (2) - 사용자 인증 설정 (0) | 2020.02.12 | 
| [Pyftpdlib] FTP 서버 만들기 (1) - 설치 및 실행 (0) | 2020.02.12 | 
| [크롤링] Selenium으로 특가 상품 수집 (5) - Telegram Bot (0) | 2020.02.03 | 
 
										
									 
										
									 
										
									 
										
									
댓글