问题描述
各位开发者好,
我正在尝试在 repl.it 上编写一个概念验证程序,该程序使用 BCrypt 安全地存储凭据。为了避免与 sql 打交道,我正在使用内置的 repl.it 数据库进行原型设计来存储凭据。
有问题的方法如下:
def SignUp(self):
'''Takes the username and password used to initialise the object,and stores them securely'''
username = self.__username_input
# Convert password input into bytes object
password_bytes = bytes(self.__password_input,"UTF-8")
# Hash password using the BCrypt algorithm
hashed_password = bcrypt.hashpw(password_bytes,bcrypt.gensalt(rounds=14))
username_available = True # True for testing - change to False for production
# Checks if the username is available
try:
db[username]
except KeyError:
username_available = True
if username_available:
# Store password in database
db[username] = hashed_password
self.Username = username
self.IsAuthenticated = True
print(db[username])
return True
else:
return False
目前,当我运行此程序时,出现以下错误:
TypeError: Object of type bytes is not JSON serializable
现在我已经尝试将 db[username] = hashed_password
更改为 db[username] = str(hashed_password)
,效果很好,但是当我像这样从数据库中取出散列密码时 bcrypt.checkpw(password_bytes,bytes(db[username],"UTF-8"))
,BCrypt 抛出了这个错误:
ValueError: Invalid salt
任何建议都会很棒。
谢谢!
解决方法
问题似乎是 db
只支持可序列化的对象。
由于我不知道 db
是什么,在我过时的答案中,我假设您使用的是字典,但事实并非如此。
# Store the password by encoding the bytes
db[username] = hashed_password.decode()
# Check it decoding the string
bcrypt.checkpw(password_bytes,db[username].encode())
使用 str()
和 bytes()
与使用 .encode()
和 .decode()
的区别
password = '123123'
password_bytes = bytes(password,"UTF-8")
str_convert = str(password_bytes)
bytes_convert = bytes(str_convert,"UTF-8")
# str_convert = "b'123123'"
# bytes_convert = b"b'123123'"
decode = password_bytes.decode()
encode = decode.encode()
# decode = '123123'
# encode = b'123123'
即使您第一次使用 password_bytes = bytes(password,"UTF-8")
并且它有效,我也不建议以这种方式将字符串转换为字节。最好使用 .encode()