WAFFLE authentication with Multiple options

Jul 5, 2011 at 10:08 PM

Hi there,

We have spring app which serves our employees as well as some of our customers.  It can be accessed from intranet and internet (user logon).  With Waffle, our intranet employee users can do single sign on with no problem.  But for our internet customers, who don't have AD records, I would like to use AS400UserRegistry to do the auth.  So my question is that: if that possible to do auth with multiple options?  For example,  user (from intranet or internet) will be auth with AD first, if the AD auth fails, we will use as AS400UserRegistry to do auth.

Or anyone's got better ideas?

Jul 6, 2011 at 8:46 PM

Oh wow, AS400 :)

I think you have a few options, in order of what I think you should do.

  1. Look at the Mixed-mode authentication sample in Waffle. It lets you do NTLM vs. Basic Auth. Replace Basic Auth by your AS400UserRegistry implementation and you're done. It won't be completely seamless, but it's good enough.
  2. If AS400 authentication has an SSPI package on Windows it might just work. Ask IBM. The Java implementation is not useful here.
  3. I have a patent owned by Microsoft that's quite involved about repackaging security creds. It consists of logging in a Guest user whenever you see some other credentials and populating group SIDs to do proper server-side permissions. This is roughly how Passport authentication works across AD domains where you can assign permissions to a file before a user even logs into this domain. It's complicated, but if you're a big company with resources I could help someone get this done.
Jul 7, 2011 at 7:20 PM
Edited Jul 7, 2011 at 10:25 PM

Hi dblock,

I actually tried to use NTLM + Basic Auth with Spring/Filter. I added both NegotoateSecurityFilterProvider and BasicSecurityFilterProvider to SecurityFilterProviderCollection.  I managed to call doFilter() of NegotoateSecurityFilterProvider first and and if it fails, try Basic Auth. But the problem is that usernnamePasswordArray in doFilter() of BasicSecusityFilterProvider is invalid (it seems like that it is encoded?).   How can I get the user name and password that user typed in from web browser pop-up (baisc auth rather Form auth)?  Or do I have to change it to Form auth so that I can get them from request parameters just like what you did with the mixed-mode?

Thanks and I apprecite your help!

Jul 8, 2011 at 2:36 PM

You won't be able to make it work with "fallback". You have to let the user choose upfront.

A user makes an HTTP request to which the server tells it "please Negotiate or fallback to Basic auth". If the browser is capable of Negotiate, which any windows-based PC will be capable of, the browser chooses Negotiate and never prompts for a password. There're a few exchanges and if authentication fails you get a popup. The user enters a username and password and the browser attempts a local logon and restarts Negotiate. Nowhere in this exchange a username and password is sent to the server.

Because there's no way to know one HTTP request from another (your local one from users capable of Negotiate vs. a remote one from users not in the same AD), you have to force the browser to do Basic auth upfront. The only way I know of is to let the user choose, first. That's what's implemented in the mixed authenticators in Waffle - the user chooses whether to enter a username and password or asks to Negotiate by clicking on different buttons.

Jul 8, 2011 at 3:54 PM

Thanks a lot dblock!

So in login.jsp file of your mixed-mode sample,  the action queryString "j_security_check"/"j_negotiate_check" actually have meanings other than just IDs. With "j_security_check", the web browser will pass "j_username" and "j_password" to the server as parameters for Auth.  Otherwise, when "j_negotiate_check" is used, the web browser with negotiate with the server, in which case, user creditial will be passed to the server.  Did I get right? 

Jul 8, 2011 at 4:34 PM

Correct. I did write up some more details here.