io.continual.http.app.servers.endpoints.AuthList Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of continualHttp Show documentation
Show all versions of continualHttp Show documentation
Continual's HTTP service library.
package io.continual.http.app.servers.endpoints;
import java.util.LinkedList;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import io.continual.http.app.servers.endpoints.TypicalRestApiEndpoint.Authenticator;
import io.continual.http.service.framework.context.CHttpRequestContext;
import io.continual.iam.IamAuthLog;
import io.continual.iam.IamService;
import io.continual.iam.credentials.ApiKeyCredential;
import io.continual.iam.credentials.JwtCredential;
import io.continual.iam.credentials.JwtCredential.InvalidJwtToken;
import io.continual.iam.credentials.UsernamePasswordCredential;
import io.continual.iam.exceptions.IamSvcException;
import io.continual.iam.identity.Identity;
import io.continual.iam.impl.common.ApiKeyAuthHelper;
import io.continual.iam.impl.common.BasicAuthHelper;
import io.continual.iam.impl.common.HeaderReader;
/**
* A list of authenticators which is itself an authenticator.
*
* @param
*/
class AuthList implements Authenticator
{
public static final String kSetting_ContinualProductTag = "apiKeyProductTag";
public static final String kContinualProductTag = "continual";
/**
* Instantiate the standard auth list
* @param settings Settings used to configure the authenticators
*/
public AuthList ( JSONObject settings )
{
fAuthenticators = new LinkedList<>();
// API key...
addAuthenticator ( new Authenticator ()
{
@Override
public I authenticate ( IamService am, final CHttpRequestContext context ) throws IamSvcException
{
final String systag = settings.optString ( kSetting_ContinualProductTag, kContinualProductTag );
I authUser = null;
final ApiKeyCredential creds = ApiKeyAuthHelper.readApiKeyCredential ( settings, new CHttpHeaderReader ( context ), systag );
if ( creds != null )
{
authUser = am.getIdentityDb ().authenticate ( creds );
if ( authUser != null )
{
IamAuthLog.authenticationEvent ( authUser.getId (), "API Key", context.request ().getBestRemoteAddress () );
}
}
return authUser;
}
} );
// JWT...
addAuthenticator ( new Authenticator ()
{
@Override
public I authenticate ( IamService am, final CHttpRequestContext context ) throws IamSvcException
{
I authUser = null;
try
{
JwtCredential cred = null;
// we normally pick up the JWT token from the Auth/bearer header.
final String authHeader = context.request ().getFirstHeader ( "Authorization" );
if ( authHeader != null && authHeader.startsWith ( "Bearer " ) )
{
final String[] parts = authHeader.split ( " " );
if ( parts.length == 2 )
{
cred = JwtCredential.fromHeader ( authHeader );
}
}
// ... but we also support the token as a parameter to support some REST API
// use cases, like background data loads
if ( cred == null )
{
final String queryParam = context.request ().getParameter ( "jwt", null );
if ( queryParam != null )
{
cred = new JwtCredential ( queryParam );
}
}
if ( cred != null )
{
authUser = am.getIdentityDb ().authenticate ( cred );
if ( authUser != null )
{
IamAuthLog.authenticationEvent ( authUser.getId (), "JWT", context.request ().getBestRemoteAddress () );
}
}
}
catch ( InvalidJwtToken e )
{
// ignore, can't authenticate this way
log.info ( "Invalid token: " + e.getMessage () );
}
return authUser;
}
} );
// username/password...
addAuthenticator ( new Authenticator ()
{
@Override
public I authenticate ( IamService am, final CHttpRequestContext context ) throws IamSvcException
{
I authUser = null;
final UsernamePasswordCredential upc = BasicAuthHelper.readUsernamePasswordCredential ( new CHttpHeaderReader ( context ) );
if ( upc != null )
{
authUser = am.getIdentityDb().authenticate ( upc );
if ( authUser != null )
{
IamAuthLog.authenticationEvent ( authUser.getId (), "Username/Password", context.request ().getBestRemoteAddress () );
}
}
return authUser;
}
} );
}
/**
* Add an authenticator to this authenticator list
* @param a an authenticator
* @return this authenticator list
*/
public synchronized AuthList addAuthenticator ( Authenticator a )
{
fAuthenticators.add ( a );
return this;
}
/**
* authenticate
*/
@Override
public synchronized I authenticate ( IamService am, CHttpRequestContext context ) throws IamSvcException
{
for ( Authenticator inner : fAuthenticators )
{
I result = inner.authenticate ( am, context );
if ( result != null ) return result;
}
return null;
}
private final LinkedList> fAuthenticators;
private static class CHttpHeaderReader implements HeaderReader
{
public CHttpHeaderReader ( CHttpRequestContext context )
{
fContext = context;
}
@Override
public String getFirstHeader ( String header )
{
return fContext.request ().getFirstHeader ( header );
}
private final CHttpRequestContext fContext;
}
private static final Logger log = LoggerFactory.getLogger ( AuthList.class );
}