HTTP Digest Authentication

33 views
Skip to first unread message

Tim Perrett

unread,
Nov 9, 2008, 8:45:59 AM11/9/08
to Lift
Hey guys,

How would I go about implementing digest authentication within lift? I
don't really want to implement this at pure web-server level (e.g.
jetty or tomcat) as I need it to interact with my application.

I've done some reading, and whilst there seem to be a few browser
compatibility issues with various different client implementations
(with IE for instance), it seems to just be a case of presenting the
right HTTP headers. My use case is for this is for REST type services,
so the browser issues shouldn't be an issue at all as we'll document
the implementation used in lift for anyone who wants to implement it.

So then, my question is, where can I implement this functionality?
Ideally, what Id like is to build some kind of hook system so that
people can wire up there own functions upon the authentication request
(e.g. to query a database etc)

Thoughts?

Cheers

Tim

David Pollak

unread,
Nov 9, 2008, 8:49:55 AM11/9/08
to lif...@googlegroups.com
On Sun, Nov 9, 2008 at 5:45 AM, Tim Perrett <he...@timperrett.com> wrote:

Hey guys,

How would I go about implementing digest authentication within lift? I
don't really want to implement this at pure web-server level (e.g.
jetty or tomcat) as I need it to interact with my application.

For standard HTML pages or for for REST (Dispatch) or for both?
 


I've done some reading, and whilst there seem to be a few browser
compatibility issues with various different client implementations
(with IE for instance), it seems to just be a case of presenting the
right HTTP headers. My use case is for this is for REST type services,
so the browser issues shouldn't be an issue at all as we'll document
the implementation used in lift for anyone who wants to implement it.

So then, my question is, where can I implement this functionality?
Ideally, what Id like is to build some kind of hook system so that
people can wire up there own functions upon the authentication request
(e.g. to query a database etc)

Thoughts?

Cheers

Tim




--
Lift, the simply functional web framework http://liftweb.net
Collaborative Task Management http://much4.us
Follow me: http://twitter.com/dpp
Git some: http://github.com/dpp

Tim Perrett

unread,
Nov 9, 2008, 8:52:25 AM11/9/08
to Lift

> For standard HTML pages or for for REST (Dispatch) or for both?

Sure, for REST dispatch. For instance, listing users and there details
would be restricted functionality which requires authentication.

David Pollak

unread,
Nov 9, 2008, 9:00:34 AM11/9/08
to lif...@googlegroups.com
I would do something like this in my DispatchPf:

{
  case RequestState("api" :: _, _, ) if !goodAuthHeader => return 401
  case RequestSate(....) ....
}

So, the first pattern matches any API request (anything to "/api/....").  It tests for a good auth header (this is where your code pulls the auth header, inspects it against the RDBMS).  If the auth fails, you return a 401 and none of the other cases are tested.

Thanks,

David

Tim Perrett

unread,
Nov 9, 2008, 9:19:15 AM11/9/08
to Lift
Sure, I've done this type of request matching before so im familiar
with that.

In terms of implementing the digest auth on the server-side, We'll
need some stuff in lift to process the authorization and the headers.
Im guessing i'll need to modify some of the HTTP stuff to do this...
have you any suggestions for where this would fit best?

The request / response cycle as I understand it should be:

request -> challenge response -> request with credentials ->
authorization -> authorized or unauthorized response

OR

request with credentials -> authorization -> authorized or
unauthorized response

Cheers

Tim

On Nov 9, 2:00 pm, "David Pollak" <feeder.of.the.be...@gmail.com>
wrote:
> Collaborative Task Managementhttp://much4.us

David Pollak

unread,
Nov 9, 2008, 9:27:14 AM11/9/08
to lif...@googlegroups.com
On Sun, Nov 9, 2008 at 6:19 AM, Tim Perrett <he...@timperrett.com> wrote:

Sure, I've done this type of request matching before so im familiar
with that.

In terms of implementing the digest auth on the server-side, We'll
need some stuff in lift to process the authorization and the headers.
The headers are not processed in Lift, but in your application as per my example.

Im guessing i'll need to modify some of the HTTP stuff to do this...

No, you won't.
 

have you any suggestions for where this would fit best?

You have to implement a single method.  The method gets the current request from S, finds the Auth header and parses it.  The only thing that's not built into Lift is the facility for parsing the value of the Auth header.  If I remember correctly, you have to split the header value at ";"  Then you have to make sure the digest is correct.  This is going to be your program logic anyway because it's going to put the record from the database.
 


The request / response cycle as I understand it should be:

request -> challenge response -> request with credentials ->
authorization -> authorized or unauthorized response

OR

request with credentials -> authorization -> authorized or
unauthorized response

And that's exactly what you'll get if you follow the code I've already posted.  In the case that the auth header doesn't exist or is wrong, then a 401 will be returned.  In the case that the auth header is properly presented, then the appropriate response will be presented.

Thanks,

David
 


Cheers

Tim

On Nov 9, 2:00 pm, "David Pollak" <feeder.of.the.be...@gmail.com>
wrote:
> I would do something like this in my DispatchPf:
>
> {
>   case RequestState("api" :: _, _, ) if !goodAuthHeader => return 401
>   case RequestSate(....) ....
>
> }
>
> So, the first pattern matches any API request (anything to "/api/....").  It
> tests for a good auth header (this is where your code pulls the auth header,
> inspects it against the RDBMS).  If the auth fails, you return a 401 and
> none of the other cases are tested.
>
> Thanks,
>
> David
>
> On Sun, Nov 9, 2008 at 5:52 AM, Tim Perrett <he...@timperrett.com> wrote:
>
> > > For standard HTML pages or for for REST (Dispatch) or for both?
>
> > Sure, for REST dispatch. For instance, listing users and there details
> > would be restricted functionality which requires authentication.
>
> --
> Lift, the simply functional web frameworkhttp://liftweb.net
> Collaborative Task Managementhttp://much4.us




--
Lift, the simply functional web framework http://liftweb.net
Collaborative Task Management http://much4.us

Tim Perrett

unread,
Nov 9, 2008, 10:07:01 AM11/9/08
to Lift

> You have to implement a single method.  The method gets the current request
> from S, finds the Auth header and parses it.  The only thing that's not
> built into Lift is the facility for parsing the value of the Auth header.
> If I remember correctly, you have to split the header value at ";"  Then you
> have to make sure the digest is correct.  This is going to be your program
> logic anyway because it's going to put the record from the database.

Ok sweet - when I was asking about modifying the lift http package, it
was the addition of manipulating these authorization headers I was
suggesting adding as this appears to me to be generic, reusable
functionality. Thoughts?

> And that's exactly what you'll get if you follow the code I've already
> posted.  In the case that the auth header doesn't exist or is wrong, then a
> 401 will be returned.  In the case that the auth header is properly
> presented, then the appropriate response will be presented.

Ok cool, I'll take a look at this and give it a whirl.

Cheers, Tim

Tim Perrett

unread,
Nov 9, 2008, 11:08:46 AM11/9/08
to Lift
One other thought on this, if no credentials are found, wouldn't it be
best to challenge the requester with a 401, but with the www-
authenticate header or something? Rather than just providing a plain
401?

Perhaps this could be wrapped up in
DigestAuthenticationChallengeResponse or something?

Cheers, Tim

David Pollak

unread,
Nov 9, 2008, 2:45:03 PM11/9/08
to lif...@googlegroups.com

Steps:
  1. Get something running in a stand-alone app
  2. Roll the example into sites/example
  3. Refactor the example code into core Lift stuff
Thanks,

David
 


Cheers, Tim

Tim Perrett

unread,
Nov 9, 2008, 5:19:00 PM11/9/08
to Lift
Hey David,

I've been doing some noodling and think I have a good scheme to
implement this. I'll make a branch on github and then post to the list
when my alterations are ready.

Cheers

Tim

PS: sorry for my high-volume posting in a stream-of-consciousness
style! Its part of my process ;-)

On Nov 9, 7:45 pm, "David Pollak" <feeder.of.the.be...@gmail.com>
wrote:
> On Sun, Nov 9, 2008 at 8:08 AM, Tim Perrett <he...@timperrett.com> wrote:
>
> > One other thought on this, if no credentials are found, wouldn't it be
> > best to challenge the requester with a 401, but with the www-
> > authenticate header or something? Rather than just providing a plain
> > 401?
>
> > Perhaps this could be wrapped up in
> > DigestAuthenticationChallengeResponse or something?
>
> Steps:
>
>    1. Get something running in a stand-alone app
>    2. Roll the example into sites/example
>    3. Refactor the example code into core Lift stuff
>
> Thanks,
>
> David
>
>
>
> > Cheers, Tim
>
> --
> Lift, the simply functional web frameworkhttp://liftweb.net
> Collaborative Task Managementhttp://much4.us

David Pollak

unread,
Nov 9, 2008, 10:48:21 PM11/9/08
to lif...@googlegroups.com


Tim Perrett wrote:
Hey David,

I've been doing some noodling and think I have a good scheme to
implement this. I'll make a branch on github and then post to the list
when my alterations are ready.
  
Please do not do this.

Please write a stand-alone app before committing anything into Lift, example or otherwise.

Tim Perrett

unread,
Nov 15, 2008, 12:54:35 PM11/15/08
to Lift
Hi David,

Im working on a standalone app as requested - I keep changing my my
mind about the design however.

Creating the challenges is no problem, as they are just subclasses of
LiftResponse, however, I cant settle on how best to handle the
authorization. If I want to create a challenge, then that obviously
needs to be in a addDispatchBefore block as its a subclass of
LiftResponse. However, as I got thinking about this, and what would
happen if the client preempted the challenge and passed the
Authorization header we want to check the contents of that header
using the code im writing, and then continue with servicing that
request (or create a challenge if the auth failed)

So then - it strikes me that the security concepts of this belong with
SiteMap, but actually serving the challenges etc belong with
dispatching...

Can someone lend me some guidence on the most lift appropriate design?
Im all ears :-)

Cheers

Tim
Reply all
Reply to author
Forward
0 new messages