在 Cherrypy 中启用摘要身份验证 server.conf
Enabling digest authentication in Cherrypy server.conf
要在 Cherrypy 中启用摘要验证,他们说使用这样的代码:
from cherrypy.lib import auth_digest
USERS = {'jon': 'secret'}
conf = {
'/protected/area': {
'tools.auth_digest.on': True,
'tools.auth_digest.realm': 'localhost',
'tools.auth_digest.get_ha1': auth_digest.get_ha1_dict_plain(USERS),
'tools.auth_digest.key': 'a565c27146791cfb'
}
}
cherrypy.quickstart(myapp, '/', conf)
而且效果很好。但是我使用 server.conf 文件来存储我的应用程序的所有配置,我想继续使用这个文件。所以我在那里写了新的部分:
[/protected/area]
tools.auth_digest.on = True
tools.auth_digest.realm = 'localhost',
tools.auth_digest.get_ha1 = auth_digest.get_ha1_dict_plain({'jon': 'secret'}),
tools.auth_digest.key = 'a565c27146791cfb'
之后我遇到了错误:
ValueError: ('Config error in section: \'/protected/area\', option: \'tools.auth_digest.get_ha1\', value: "auth_digest.get_ha1_dict_plain({\'jon\': \'secret\'}),". Config values must be valid Python.', 'TypeError', ("unrepr could not resolve the name 'auth_digest'",))
我明白原因,但我不知道如何为 "valid Python" 提供 server.conf。请帮助我。
您可以在您的应用程序中调用该函数并在配置中使用生成的函数,例如:
myapp/__init__.py
:
get_ha1 = auth_digest.get_ha1_dict_plain({'jon': 'secret'})
server.conf
:
[/protected/area]
tools.auth_digest.on = True
tools.auth_digest.realm = 'localhost'
tools.auth_digest.get_ha1 = myapp.get_ha1
tools.auth_digest.key = 'a565c27146791cfb'
问题是您在代码中定义凭据。
可能值得一提的是,您可以使用其他功能,而不仅仅是您在字典中使用纯文本密码定义用户的功能,您可以使用来自 cherrypy.lib.auth_digest.get_ha1_file_htdigest
的 htdigest 文件或实现您的自己的 ha1 函数就像 get_ha1_dict_plain
returns:
def get_ha1_dict_plain(user_password_dict):
"""Returns a get_ha1 function which obtains a plaintext password from a
dictionary of the form: {username : password}.
If you want a simple dictionary-based authentication scheme, with plaintext
passwords, use get_ha1_dict_plain(my_userpass_dict) as the value for the
get_ha1 argument to digest_auth().
"""
def get_ha1(realm, username):
password = user_password_dict.get(username)
if password:
return md5_hex('%s:%s:%s' % (username, realm, password))
return None
return get_ha1
我实现了一个从数据库中获取 ha1 的方法,例如使用这个 sqlalchemy 模型 (https://github.com/cyraxjoe/maki/blob/master/maki/db/models.py#L174-L189):
class User(Base):
__tablename__ = 'users'
name = Column(String(32), unique=True, nullable=False)
vname = Column(String(64))
email = Column(String(64), nullable=False)
ha1 = Column(String(32), nullable=False)
active = Column(Boolean, server_default='True')
@validates('ha1')
def validates_ha1(self, key, passwd):
if self.name is None:
raise Exception('Set the name first')
pack = ':'.join([self.name, maki.constants.REALM, passwd])
return hashlib.md5(pack.encode()).hexdigest()
还有一个get_ha1函数(https://github.com/cyraxjoe/maki/blob/master/maki/db/utils.py#L63):
def get_user_ha1(realm, username):
# realm is not used the stored hash already used it.
user = db.ses.query(db.models.User).filter_by(name=username).scalar()
if user is not None:
return user.ha1
重要的是 ha1 只是 "user:real:password" 的 md5 散列,您可以在很多不同的地方实现它。
要在 Cherrypy 中启用摘要验证,他们说使用这样的代码:
from cherrypy.lib import auth_digest
USERS = {'jon': 'secret'}
conf = {
'/protected/area': {
'tools.auth_digest.on': True,
'tools.auth_digest.realm': 'localhost',
'tools.auth_digest.get_ha1': auth_digest.get_ha1_dict_plain(USERS),
'tools.auth_digest.key': 'a565c27146791cfb'
}
}
cherrypy.quickstart(myapp, '/', conf)
而且效果很好。但是我使用 server.conf 文件来存储我的应用程序的所有配置,我想继续使用这个文件。所以我在那里写了新的部分:
[/protected/area]
tools.auth_digest.on = True
tools.auth_digest.realm = 'localhost',
tools.auth_digest.get_ha1 = auth_digest.get_ha1_dict_plain({'jon': 'secret'}),
tools.auth_digest.key = 'a565c27146791cfb'
之后我遇到了错误:
ValueError: ('Config error in section: \'/protected/area\', option: \'tools.auth_digest.get_ha1\', value: "auth_digest.get_ha1_dict_plain({\'jon\': \'secret\'}),". Config values must be valid Python.', 'TypeError', ("unrepr could not resolve the name 'auth_digest'",))
我明白原因,但我不知道如何为 "valid Python" 提供 server.conf。请帮助我。
您可以在您的应用程序中调用该函数并在配置中使用生成的函数,例如:
myapp/__init__.py
:
get_ha1 = auth_digest.get_ha1_dict_plain({'jon': 'secret'})
server.conf
:
[/protected/area]
tools.auth_digest.on = True
tools.auth_digest.realm = 'localhost'
tools.auth_digest.get_ha1 = myapp.get_ha1
tools.auth_digest.key = 'a565c27146791cfb'
问题是您在代码中定义凭据。
可能值得一提的是,您可以使用其他功能,而不仅仅是您在字典中使用纯文本密码定义用户的功能,您可以使用来自 cherrypy.lib.auth_digest.get_ha1_file_htdigest
的 htdigest 文件或实现您的自己的 ha1 函数就像 get_ha1_dict_plain
returns:
def get_ha1_dict_plain(user_password_dict):
"""Returns a get_ha1 function which obtains a plaintext password from a
dictionary of the form: {username : password}.
If you want a simple dictionary-based authentication scheme, with plaintext
passwords, use get_ha1_dict_plain(my_userpass_dict) as the value for the
get_ha1 argument to digest_auth().
"""
def get_ha1(realm, username):
password = user_password_dict.get(username)
if password:
return md5_hex('%s:%s:%s' % (username, realm, password))
return None
return get_ha1
我实现了一个从数据库中获取 ha1 的方法,例如使用这个 sqlalchemy 模型 (https://github.com/cyraxjoe/maki/blob/master/maki/db/models.py#L174-L189):
class User(Base):
__tablename__ = 'users'
name = Column(String(32), unique=True, nullable=False)
vname = Column(String(64))
email = Column(String(64), nullable=False)
ha1 = Column(String(32), nullable=False)
active = Column(Boolean, server_default='True')
@validates('ha1')
def validates_ha1(self, key, passwd):
if self.name is None:
raise Exception('Set the name first')
pack = ':'.join([self.name, maki.constants.REALM, passwd])
return hashlib.md5(pack.encode()).hexdigest()
还有一个get_ha1函数(https://github.com/cyraxjoe/maki/blob/master/maki/db/utils.py#L63):
def get_user_ha1(realm, username):
# realm is not used the stored hash already used it.
user = db.ses.query(db.models.User).filter_by(name=username).scalar()
if user is not None:
return user.ha1
重要的是 ha1 只是 "user:real:password" 的 md5 散列,您可以在很多不同的地方实现它。