paste.auth.digest – HTTP Digest login

Digest HTTP/1.1 Authentication

This module implements Digest authentication as described by RFC 2617 1 .

Basically, you just put this module before your application, and it takes care of requesting and handling authentication requests. This module has been tested with several common browsers “out-in-the-wild”.

>>> from paste.wsgilib import dump_environ
>>> from paste.httpserver import serve
>>> # from paste.auth.digest import digest_password, AuthDigestHandler
>>> realm = 'Test Realm'
>>> def authfunc(environ, realm, username):
...     return digest_password(realm, username, username)
>>> serve(AuthDigestHandler(dump_environ, realm, authfunc))
serving on...

This code has not been audited by a security expert, please use with caution (or better yet, report security holes). At this time, this implementation does not provide for further challenges, nor does it support Authentication-Info header. It also uses md5, and an option to use sha would be a good thing.

1

http://www.faqs.org/rfcs/rfc2617.html

Module Contents

class paste.auth.digest.AuthDigestAuthenticator(realm, authfunc)

implementation of RFC 2617 - HTTP Digest Authentication

class paste.auth.digest.AuthDigestHandler(application, realm, authfunc)

middleware for HTTP Digest authentication (RFC 2617)

This component follows the procedure below:

  1. If the REMOTE_USER environment variable is already populated; then this middleware is a no-op, and the request is passed along to the application.

  2. If the HTTP_AUTHORIZATION header was not provided or specifies an algorithem other than digest, then a HTTPUnauthorized response is generated with the challenge.

  3. If the response is malformed or or if the user’s credientials do not pass muster, another HTTPUnauthorized is raised.

  4. If all goes well, and the user’s credintials pass; then REMOTE_USER environment variable is filled in and the AUTH_TYPE is listed as ‘digest’.

Parameters:

application

The application object is called only upon successful authentication, and can assume environ['REMOTE_USER'] is set. If the REMOTE_USER is already set, this middleware is simply pass-through.

realm

This is a identifier for the authority that is requesting authorization. It is shown to the user and should be unique within the domain it is being used.

authfunc

This is a callback function which performs the actual authentication; the signature of this callback is:

authfunc(environ, realm, username) -> hashcode

This module provides a ‘digest_password’ helper function which can help construct the hashcode; it is recommended that the hashcode is stored in a database, not the user’s actual password (since you only need the hashcode).

paste.auth.digest.digest_password(realm, username, password)

construct the appropriate hashcode needed for HTTP digest

paste.auth.digest.make_digest(app, global_conf, realm, authfunc, **kw)

Grant access via digest authentication

Config looks like this:

[filter:grant]
use = egg:Paste#auth_digest
realm=myrealm
authfunc=somepackage.somemodule:somefunction