如何使用子进程加密文件,因此输出将为字符串。
password = '%030x' % random.randrange(16**30)
encrypted_file = subprocess.geststatusoutput("echo "+password+
"|gpg --password-fd 0 < "+ name_of_selected_file)
我想将_file加密为字符串,以便将其作为加密文件用于上传请求 使用gnupg库的最佳方法是什么?
答案 0 :(得分:2)
您可以使用subprocess.Popen()
执行这样的gpg命令:
import shlex
import random
from subprocess import Popen, PIPE
passphrase = '%030x' % random.randrange(16**30)
source_filename = '/tmp/somefile'
cmd = 'gpg --batch --symmetric --cipher-algo AES256 --passphrase-fd 0 --output - {}'.format(source_filename)
# error handling omitted
p = Popen(shlex.split(cmd), stdout=PIPE, stdin=PIPE, stderr=PIPE)
encrypted_data = p.communicate(passphrase.encode())[0]
# Decryption - should work for Python 2 & 3
import os
r, w = os.pipe() # pipe for sending passphrase from parent to child
try:
os.set_inheritable(r, True)
except AttributeError: # new in version 3.4
pass
cmd = 'gpg --batch --decrypt --passphrase-fd {}'.format(r)
p = Popen(shlex.split(cmd), stdout=PIPE, stdin=PIPE, stderr=PIPE, close_fds=False)
os.close(r) # closes fd in parent, child needs it
f = os.fdopen(w, 'w')
f.write(passphrase + '\n') # '\n' seems required for Python 2 ???
f.close()
decrypted_data, stderr = p.communicate(encrypted_data)
# check that data was successfully roundtripped
assert open(source_filename).read() == decrypted_data.decode()
或者,仅针对Python 3进行解密:
import os
r, w = os.pipe()
cmd = 'gpg --batch --decrypt --passphrase-fd {}'.format(r)
p = Popen(shlex.split(cmd), stdout=PIPE, stdin=PIPE, stderr=PIPE, pass_fds=(r,))
os.close(r) # closes fd in parent, child needs it
open(w, 'w').write(passphrase)
decrypted_data, stderr = p.communicate(encrypted_data)
# check that data was successfully roundtripped
assert open(source_filename).read() == decrypted_data.decode()
现在我不是这种方法安全性的专家,但是,将密码直接写入子进程&#39;使用communicate()
的stdin比在命令行上回显密码更好 - 任何可以运行ps
或等效的人都可以看到。
此外,依赖命令的shell级别IO重定向将需要Popen的shell=True
参数,这可能具有其他安全隐患(请参阅Popen()
文档中的警告)。
我在gpg
命令中假设您打算使用对称加密(您的示例不另行建议)。如果远程服务器需要能够解密加密的文件内容,您将如何共享生成的密码?
您可能最好不要使用公钥加密。