- 이번 프로그램은 이전글(2022.11.20 - [분류 전체보기] - 파이썬 GUI/윈도우 암호화 프로그램 만들기 - 2.패스워드 입력 및 해시 처리)에 이은 3번째 글로 암호화 하기 위해 입력받은 패스워드와 선택된 파일을 암호화 처리하는 방식에 대하여 설명합니다.
(본 블로그의 내용은 유튜브 동영상(파이썬 GUI/윈도우 암호화 프로그램 만들기-3.암호화 처리(making GUI/Windows Encryption program byPython 3.encryption))에서 더욱 자세히 보실 수 있습니다.)
1. 원본 파일(aa.txt)을 확인결과 파일내용이 'aa'로 확인 됩니다.(없는 경우 하나 만드시기 바랍니다.)
2. 아래와 같이 프로그램 실행 후 (1) 패스워드 입력, (2) 암호화할 파일 선택, (3) 암호화 버튼 클릭 하면 파일('aa.txt')이 정상적으로 암호화 됩니다.
3. 실제 폴더에 가서 파일 확인 결과 이전 파일 내용('aa')과는 다른 암호화된 내용으로 잘 변경되었음을 확인합니다.
O 시작전 준비 사항
- 프로그램을 실행하기 위해서는 아래 모듈들이 필요합니다. 아래와 같이 임포트 해줍니다.
import base64
import hashlib
from Crypto.Cipher import AES # 대칭키를 사용하기 위한 모듈 임포트
***에러 발생시 조치 사항(에러가 없는 경우 안보셔도 됩니다.)
--------------------------------------------------------------------------------------
만일 아래와 같이 에러 발생 시
ModuleNotFoundError: No module named 'Crypto'
pip install pycrypto <-- 현재 이 모듈은 더 이상 안전하지 않아 설치 되지 않음
pip install pycryptodome <-- 이 모듈을 설치
위의 모듈 설치 후에도 계속 동일한 에러 발생 시
ModuleNotFoundError: No module named 'Crypto'
아래 부분을 에서 와 같이 수정
from Crypto.cipher import PKCS1_OAEP # 소문자를
이렇게 수정
from Crypto.Cipher import PKCS1_OAEP # 대문자로 수정
--------------------------------------------------------------------------------------
여기까지 이상없이 되셨다면 이제 우리는 다음 단계로 넘어갈 준비가 되었습니다.
# -*- coding: utf-8 -*-
import sys
from PyQt5.QtWidgets import *
from PyQt5 import uic
from PyQt5.QtGui import *
import base64
import hashlib
from Crypto.Cipher import AES # 대칭키를 사용하기 위한 모듈 임포트
form_class = uic.loadUiType("gui_encryption_program4.ui")[0]
class MyWindow(QMainWindow, form_class):
def __init__(self):
global pad, unpad
super().__init__()
BS = 16 # blocksize를 16바이트로 고정시켜야 함(AES의 특징)
# AES에서는 블럭사이즈가 128bit 즉 16byte로 고정되어 있어야 하므로 문자열을 encrypt()함수 인자로 전달시
# 입력 받은 데이터의 길이가 블럭사이즈의 배수가 아닐때 아래와 같이 패딩을 해주어야 한다.
# 패딩: 데이터의 길이가 블럭사이즈의 배수가 아닐때 마지막 블록값을 추가해 블록사이즈의 배수로 맞추어 주는 행위
pad = (lambda s: s+ (BS - len(s) % BS) * chr(BS - len(s) % BS).encode())
unpad = (lambda s: s[:-ord(s[len(s)-1:])])
self.setFixedSize(700,700)
self.setWindowIcon(QIcon("pagichacha.png"))
self.setupUi(self)
self.toolButton_4.clicked.connect(self.select_toEncryptFile)
self.pushButton_3.clicked.connect(self.trigger_encrypt)
##################################################################################
# 1. 키(패스워드) 생성 + 해시 처리
##################################################################################
def make_key(self):
global key
self.textEdit.clear()
key_org = self.lineEdit_4.text()
self.textEdit.append("1. 원본 키(key) : "+key_org)
self.key = hashlib.sha256(key_org.encode()).digest()
print("AES Key(Key 문장 암호화) : ", self.key)
self.textEdit.append("2. Key에 해시 적용 후 결과 : "+str(self.key)+"\n")
return self.key
##################################################################################
# 2.암호화
##################################################################################
def select_toEncryptFile(self):
global toEncryptFile
toEncryptFile = QFileDialog.getOpenFileName(self, "Open file", './')
print(type(toEncryptFile))
self.textEdit.append('{}'.format(toEncryptFile[0]))
# return toEncryptFile
def encrypt(self, message):
message = message.encode()
raw = pad(message)
key = self.make_key()
cipher = AES.new(key, AES.MODE_CBC, self.__iv().encode('utf8'))
enc = cipher.encrypt(raw)
return base64.b64encode(enc).decode('utf-8')
def trigger_encrypt(self):
global encrypt_data
self.textEdit.clear()
# print(toEncryptFile[0])
f = open(toEncryptFile[0], "r", encoding="euckr")
data = f.read()
f.close()
print("원문 내용", data)
encrypt_data = self.encrypt(data)
# f = open("aa_enc.txt", "w")
f = open(toEncryptFile[0], "w")
f.write(str(encrypt_data))
f.close()
print("-"*100, "\n")
print("원문을 키로 암호화 결과: ", encrypt_data)
print("-"*100, "\n")
self.textEdit.append("-"*70)
self.textEdit.append("3. 원문 내용 : "+data)
self.textEdit.append("4. 원문을 키로 암호화 결과:"+ encrypt_data)
self.textEdit.append("-"*70)
QMessageBox.about(self, "암호화!!", "파일이 암호화 되었습니다.")
def __iv(self):
return chr(0) * 16
app=QApplication(sys.argv)
window = MyWindow()
window.show()
print("Before event loop")
app.exec_()
print("After event loop")
> python total2.py
아래 12번까지는 이전글(2022.11.20 - [분류 전체보기] - 파이썬 GUI/윈도우 암호화 프로그램 만들기 - 2.패스워드 입력 및 해시 처리)과 동일하며, 13번부터 새롭게 추가 되었습니다.
1.from Crypto.Cipher import AES <-- 대칭키를 사용하기 위한 모듈 임포트
2.BS = 16 <-- blocksize를 16바이트로 고정시켜야 함(AES의 특징)
3.pad = (lambda s: s+ (BS - len(s) % BS) * chr(BS - len(s) % BS).encode()) <-- 패딩 처리
# AES에서는 블럭사이즈가 128bit 즉 16byte로 고정되어 있어야 하므로 문자열을 encrypt()함수 인자로 전달시
# 입력 받은 데이터의 길이가 블럭사이즈의 배수가 아닐때 아래와 같이 패딩을 해주어야 한다.
# 패딩: 데이터의 길이가 블럭사이즈의 배수가 아닐때 마지막 블록값을 추가해 블록사이즈의 배수로 맞추어 주는 행위
4.unpad = (lambda s: s[:-ord(s[len(s)-1:])]) <-- 패딩처리된 부분은 원래대로 처리
5.self.setupUi(self) <-- 위에서 만든 UI를 클래스에 반영
6.self.pushButton_3.clicked.connect(self.test) <-- 'pushButton_3'(암호화) 버튼이 클릭되면 test함수 호출
7.key = self.make_key() <--make_key()함수의 리턴값을 key변수에 저장
8.self.textEdit.clear() <-- 텍스트에디트('실행결과' 화면)를 클리어(빈 화면으로)
9.key_org = self.lineEdit_4.text() <-- lineEdit_4의 입력값(패스워드(키)입력 값)을 key_org변수에 할당
10.self.textEdit.append("1. 원본 키(key) : "+key_org) <-- 텍스트에디트('실행결과' 화면)에 입력한 패스워드를 보여줌
11.self.key = hashlib.sha256(key_org.encode()).digest() <-- 키가 쉽게 노출되는 것을 막기 위해 키를 어렵게 처리하는 과정으로 보통 해시를 적용
12.self.textEdit.append("2. Key에 해시 적용 후 결과 : "+str(self.key)+"\n") <-- 텍스트에디트('실행결과' 화면)에 입력한 패스워드의 해시처리된 값을 보여줌
13.global toEncryptFile <-- toEncryptFile변수를 다른 함수에서 사용할 수 있도록 global 처리
14.toEncryptFile = QFileDialog.getOpenFileName(self, "Open file", './') <-- 파일선택
15.self.textEdit.append('{}'.format(toEncryptFile[0])) <-- 실행결과 화면에 선택된 파일의 전체 경로를 보여줌
16.key = self.make_key() <-- 입력한 패스워드를 해시처리한 값을 리턴
17.cipher = AES.new(key, AES.MODE_CBC, self.__iv().encode('utf8')) <-- AES 알고리즘 적용
18.enc = cipher.encrypt(raw) <-- AES알고리즘으로 암호화 처리
19.f = open(toEncryptFile[0], "r", encoding="euckr") <-- 파일을 읽기모드로 연다.
20.encrypt_data = self.encrypt(data) <-- data(원문)를 암호화 처리
21.
def __iv(self): <--패딩처리를 위한 함수
return chr(0) * 16
1.기본 소스에 대한 설명은 위에서 설명 드린 바와 같으며, 'total2.py' 소스 실행 후 암호화할 파일을 클릭(toolButton_4)하면암호화할 파일 선택할 수 있습니다. 그리고 나서 암호화 버튼(pushButton_3)을 클릭하면 trigger_encrypt() 함수가 실행되고,
2. trigger_encrypt() 함수는
-선택한 파일의 내용을 읽은 후 읽은 데이터('aa')를 encrypt(data) 함수에 넘겨 주고, 암호화된 값(encrypt_data)을 리턴 받습니다.
- 이후 동일한 파일명(toEncryptFile[0]) <-- 'aa.txt')으로 해당 파일에 리턴 받은 값(암호화된 값)을 쓰기 작업으로 파일을 만듭니다.
- 그리고 나서 '정상적으로 암호화가 되었다' 라고 메시지 박스를 띄웁니다.
3. 실제 암호화 처리 함수인 encrypt()함수는 전달받은 메시지('aa')를 AES 암호화 알고리즘으로 암호화 처리 후 그 결과를 리턴합니다.
오늘은 여기까지이며, 위의 내용이 유익하셨다면, 좋아요와 구독 부탁드립니다.
감사합니다.
'파이썬 실습 > GUI,윈도우 암호화 프로그램 만들기' 카테고리의 다른 글
파이썬 GUI/윈도우 암호화 프로그램 만들기 - 2.패스워드 입력 및 해시 처리 (0) | 2022.11.24 |
---|---|
파이썬 GUI/윈도우 암호화 프로그램 만들기 - 1.소개편 (0) | 2022.11.20 |