users@javaee-spec.java.net

[javaee-spec users] JASPIC doesn't support HttpServletRequest#login?

From: arjan tijms <arjan.tijms_at_gmail.com>
Date: Tue, 29 Jan 2013 00:57:25 +0100

Hi,

I'm playing around with JASPIC in various containers, and from experiments
it looks like JASPIC doesn't support the HttpServletRequest#login method. I
tried GlassFish 3.1.2.2, JBoss AS 7.1.3 (EAP 6.0.1) and WebLogic 12.1.1.

For GlassFish I tried both declarative configuration (as e.g. described
here
http://www-02.imixs.com/roller/ralphsjavablog/entry/openid_serverauthmodule_jsr_196_with)
and programmatic configuration (as I described on my own blog here
http://arjan-tijms.blogspot.com/2012/11/implementing-container-authentication.html).
For JBoss AS and WebLogic I only tried the programmatic option.

In all cases, the SAM is correctly called when a resource is accessed, but
it's NOT called whenever I call HttpServletRequest#login (e.g. from within
the doGet method of a simple Servlet). Instead, a default login module
(default realm) is called. This doesn't seem quite right. When a SAM is
configured and indeed called in some situations, but then a completely
different login module is called in another situation.

Upon inspection of the source code of both GlassFish and JBoss AS, it
doesn't seem there's any code present that even could delegate this call to
a JASPIC SAM.

For instance, in GlassFish the HttpServletRequest#login call is to
org.apache.catalina.connector.RequestFacade#login, which directly calls
org.apache.catalina.connector.Request#login (see
http://grepcode.com/file/repo1.maven.org/maven2/org.glassfish.web/web-core/3.1.1/org/apache/catalina/connector/Request.java#Request.login%28java.lang.String%2Cchar%5B%5D%29),
this will call through to com.sun.web.security.RealmAdapter#authenticate
where "realm_name" will be the empty string.

From there a
call com.sun.enterprise.security.auth.login.LoginContextDriver#login is
done (see
http://grepcode.com/file/repo1.maven.org/maven2/org.glassfish.security/security/3.1.1/com/sun/enterprise/security/auth/login/LoginContextDriver.java#LoginContextDriver.login%28java.lang.String%2Cchar%5B%5D%2Cjava.lang.String%29
).

From here Realm.getDefaultRealm() returns "file", which a bit further down
the call chain is used to obtain an instance of
com.sun.enterprise.security.auth.realm.file.FileRealm, which is invoked via
a JAAS LoginContext, and throws an exception if the file realm can't
authenticate the user (and thus WILL authenticate the user when credentials
are used that are NOT accepted by the JASPIC SAM, but happen to be accepted
by the default realm, which could open a huge security hole).

In JBoss AS a simular thing happens. For JASPIC support the
valve org.jboss.as.web.security.jaspi.WebJASPIAuthenticator needs to be
configured and this one is called following a call to
HttpServletRequest#login, but eventually the authenticate method in its
base class is called (see
http://grepcode.com/file/repository.jboss.org/nexus/content/repositories/releases/org.jboss.web/jbossweb/7.0.17.Final/org/apache/catalina/authenticator/AuthenticatorBase.java#AuthenticatorBase.authenticate%28org.apache.catalina.connector.Request%2Corg.apache.catalina.authenticator.HttpServletResponse%29)
which knows nothing about JASPIC and just delegates to a default realm
again.

So, is it indeed true that JASPIC does not support HttpServletRequest#login
or am I perhaps completely missing something?

Kind regards,
Arjan Tijms