A basic implementation of basic access authentication using JASPIC

20 April 2015, by: Arjan Tijms

Basic access authentication is a crude mechanism to authenticate that’s part of the HTTP standard. It allows both an agent to send username/password credentials and a server to request the agent to authenticate itself. This happens in a simple but standardized way.

The mechanism can be easily implemented using Java EE’s JASPIC and a sprinkle of utility code from the experimental OmniSecurity project (which is currently being discussed as one of the possible options to simplify security in Java EE 8).

A basic implementation looks as follows:

public class BasicAuthModule extends HttpServerAuthModule {
 
    @Override
    public AuthStatus validateHttpRequest(HttpServletRequest request, HttpServletResponse response, HttpMsgContext httpMsgContext) throws AuthException {
 
        String[] credentials = getCredentials(request);
        if (!isEmpty(credentials)) {
 
            UsernamePasswordIdentityStore identityStore = getReferenceOrNull(UsernamePasswordIdentityStore.class);
            if (identityStore != null) {
                if (identityStore.authenticate(credentials[0], credentials[1])) {
                    return httpMsgContext.notifyContainerAboutLogin(
                        identityStore.getUserName(), 
                        identityStore.getApplicationRoles()
                    );
                }                
            }            
        }
 
        if (httpMsgContext.isProtected()) {
            response.setHeader("WWW-Authenticate", "Basic realm=\"test realm:\"");
            return httpMsgContext.responseUnAuthorized();
        }
 
        return httpMsgContext.doNothing();
    }
 
    private String[] getCredentials(HttpServletRequest request) {
 
        String authorizationHeader = request.getHeader("Authorization");
        if (!isEmpty(authorizationHeader) && authorizationHeader.startsWith("Basic ") ) {
            return new String(parseBase64Binary(authorizationHeader.substring(6))).split(":");
        }
 
        return null;
    }
}

Full code in the OmniSecurity repo

Using injection, the example can be simplified a little and will then look as follows:

public class BasicAuthModule extends HttpServerAuthModule {
 
    @Inject
    private UsernamePasswordIdentityStore identityStore;
 
    @Override
    public AuthStatus validateHttpRequest(HttpServletRequest request, HttpServletResponse response, HttpMsgContext httpMsgContext) throws AuthException {
 
        String[] credentials = getCredentials(request);
        if (!isEmpty(credentials) && identityStore.authenticate(credentials[0], credentials[1])) {
            return httpMsgContext.notifyContainerAboutLogin(
                identityStore.getUserName(),
                identityStore.getApplicationRoles()
            );
        }
 
        if (httpMsgContext.isProtected()) {
            response.setHeader("WWW-Authenticate", "Basic realm=\"test realm:\"");
            return httpMsgContext.responseUnAuthorized();
        }
 
        return httpMsgContext.doNothing();
    }
 
    private String[] getCredentials(HttpServletRequest request) {
 
        String authorizationHeader = request.getHeader("Authorization");
        if (!isEmpty(authorizationHeader) && authorizationHeader.startsWith("Basic ") ) {
            return new String(parseBase64Binary(authorizationHeader.substring(6))).split(":");
        }
 
        return null;
    }
}

Note that the JASPIC auth module as shown here is responsible for implementing the client/server interaction details. Validating the credentials (username/password here) and obtaining the username and roles is delegated to an identity store (which can e.g. be database or LDAP based).

Arjan Tijms

One comment to “A basic implementation of basic access authentication using JASPIC”

  1. xcv says:

    I like the AuthParameters()::.rememberMe(bool) feature 🙂

Type your comment below:

Time limit is exhausted. Please reload CAPTCHA.

css.php best counter