[jcifs] Alternating Users

Tapperson Kevin Kevin.Tapperson at hcahealthcare.com
Wed Apr 13 13:24:00 GMT 2005


We have a setup like this working.  It took some customization of the
NtlmHttpFilter to accomplish, but it is rather simple.  Here is some pseudo
code to get started.  This will only invoke the NTLM process once for the
life of the HTTP session.  Once the NTLM process has established the
authenticity of the user it will save the application specific user object
in the session.  After that, the NTLM process will only be re-invoked if 1)
the user issues a POST request or 2) if the application's user object is
removed from session.  This enables you to logout an automatically
authenticated user and login another user by implementing application logic
to switch the user object that is stored in the session; just use
session.setAttribute() to replace the user object.  We support both NTLM
authentication and LDAP authentication to our application in this manner.

	public void doFilter(ServletRequest req, ServletResponse resp,
FilterChain chain) throws IOException, ServletException
	{
		HttpServletRequest request = (HttpServletRequest)req;
		HttpServletResponse response = (HttpServletResponse)resp;
		HttpSession session = request.getSession();		

		//only attempt anything with NTLM if there is no user in
session yet or if the HTTP request is a POST
		if ((session.getAttribute(USER_OBJECT) == null) ||
		    ("POST".equals(request.getMethod())))
		{
			//see if NTLM has been initiated yet
			String msg = request.getHeader("Authorization");
			if ((msg != null) && (msg.startsWith("NTLM ")))
			{
				if (type1 NTLM message)
				{
					//generate challenge
					//send type2 NTLM message
					//do not chain to the next filter
					return;
				}
				else if (type3 NTLM message)
				{
					try
					{
						String domain =
type3.getDomain();
						String username =
type3.getUser();
						NtlmPasswordAuthentication
ntlm = new NtlmPasswordAuthentication(domain, username, challenge,
lmResponse, ntResponse);
						SmbSession.logon(dc, ntlm);

						//SmbSession.logon
succeeded; user is authenticated
						//retrieve the application
specific authorization user object
						User user =
getApplicationAuthorizationUser(domain, username);
	
session.setAttribute(USER_OBJECT, user);
						chain.doFilter();
					}
					catch (Exception)
					{
						//SmbSession.logon failed;
user cannot be authenticated
						//display an error page
						return;
					}
				}
			}
			else
			{
				//either NTLM hasn't been initiated yet or
this is a simple POST request from a user that didn't use NTLM to login
				if (session.getAttribute(USER_OBJECT) ==
null)
				{
					//initiate the NTLM process now
					//do not chain to the next filter
					return;
				}
				else
				{
					//simple POST request from a user
that didn't use NTLM to login
					chain.doFilter();
				}
			}
		}
		else
		{
			chain.doFilter();
		}
	}


>On 4/12/05, Michael B Allen <mba2000 at ioplex.com> wrote:
>> We get this type of question occasionally and I believe the prevailing
>> answer is to use 'Basic' authentication w/ SSL. Of course that is not
>> transparent to the user though. With a good understanding of the NTLM
>> HTTP Authentication protocol [1] you might figure out a way to use a
>> combination of NTLM and Basic authentication and customize the filter
>> to trick IE into renegotiating credentials on demand.
>
>Well you could just use jcifs to get the current user's credentials
>and use that to automatically log them into your application level
>security and allow them to logoff the application so someone else can
>logon with their application credentials (not their Windows logon).
>However all they would need to do is close the browser and reopen to
>get logged on as the logged in Windows user.



More information about the jcifs mailing list