Realm.authenticate() doesn't register Principal in Session.. use Authenticator instead?

2006-01-18 Thread Ken Johanson

Hi all,

I am able to access the current context's org.apache.catalina.Realm
object using Yoav Shapira's Tomcat-Realm example; however, when I call
Realm.authenticate(String user, String pass), the Principal object that
it returns is not being registered with the session (subsequent requests 
have a null Principal)..


Apparently this is because that method is normally invoked by 
AuthenticatorBase, which handles the registering of Principal with 
Session. However I can't find a way to get the Authenticator object. 
Moreover, AuthenticatorBase's register(req, res, login) method is 
protected which also complicates things slightly (given that the impl 
must be cast-to or reflection used)


My question is, what is the most straight-forward way to authenticate 
(using one or both of (String user, String pwd) or (X509Certificate 
cert)) and then register the Principal, using the currently defined 
Realm/Authenticator?


Also, is there any facility to implicitly login a user using only a void 
doLogin(Principal p)? This would allow me to completely abstract the 
authentication process and rules (especially into schemes that don't fit 
Realm's interface definition), and without having to extend Realm or 
Authenticator.


Thank,
ken



-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]







-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Proposal: void AuthenticatorBase.doLogin(request, response, principal)

2006-02-13 Thread Ken Johanson
These 3 new (proposed) methods allow webapps (with classloader access to 
the server APIs) to implicitly register a Principal with a HttpSession 
(e.g to implement or use-existing 3rd party Authenticator/Realm systems):


Add to org.apache.catalina.connector.ResponseFacade:
public Response getResponse() {
  return resp;
}

Add to org.apache.catalina.connector.RequestFacade:
public Request getRequest() {
  return (Request)request;
}

Add to org.apache.catalina.authenticator.AuthenticatorBase:
public void doLogin(HttpServletRequest request,
  HttpServletResponse response, Principal principal)
{
  register(
(HttpRequest)((RequestFacade)request).getRequest(),
(HttpResponse)((ResponseFacade)response).getResponse(),
principal, "FORM", null, null);
}

I have tested these but in a limited way, and am not certain of the 
absence of potential ClassCastExceptions.


Example usage, querying an existing config'd Authenticator:

/** query an existing plain-password (custom form-based login) 
authenticator/realm, if success login: **/
public static boolean tryLogin(HttpServletRequest request, 
HttpServletRequest response, String user, String pass)

  throws Exception
{
  Server server = ServerFactory.getServer();
  Service service = server.findService("Catalina");
  if (service==null)
throw new NullPointerException("login: Cannot load Service 
'Catalina'");

  Engine engine = (Engine) service.getContainer();
  if (engine==null)
throw new NullPointerException("login: Cannot load Container for 
Service 'Catalina'");


  Host host = null;
  String hostname = Strings.norm(request.getHeader("Host"));
  Object[] o = engine.findChildren();
  for (int i=0; ithrow new NullPointerException("login: Cannot load Host 
'"+hostname+"'");

  String reqbase  = Strings.norm(req.getContextPath())+"/";
  Context context = (Context) host.findChild(reqbase);
  if (context==null)
  {
context = (Context) host.findChild(Strings.clip(reqbase,-1));
  }
  if (context==null)
throw new NullPointerException("login: Cannot load Context 
'"+reqbase+"'");

  Manager manager = context.getManager();
  HttpSession hses = request.getSession(true);
  Session session = null;
  try {
session = manager.findSession(hses.getId());
  } catch (IOException e) {}
  if (session==null)
throw new NullPointerException("login: Cannot load Session 
'"+reqbase+"'");

  Realm realm = context.getRealm();
  LoginConfig config = context.getLoginConfig();
  FormAuthenticator auth = null;
  Pipeline pipe = context.getPipeline();
  Valve[] v = pipe.getValves();
  for (int i=0; ithrow new NullPointerException("login: Cannot load Authenticator 
'"+reqbase+"'");

  Principal principal = realm.authenticate(user, pass);
  if (principal==null)
return false;
  session.setNote(Constants.FORM_PRINCIPAL_NOTE, principal);
  session.setNote(Constants.SESS_USERNAME_NOTE, user);
  session.setNote(Constants.SESS_PASSWORD_NOTE, pass);
  auth.doLogin(request, response, principal);
  return true;
}



-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]