apache > cocoon
 

Authentication Framework: Authenticating a User

Usually, the redirect-to document of a handler contains a form for the user to authenticate. But of course, you are not limited to this. No matter how the redirect-to document looks like, the user has "somewhere" the abilitiy to authenticate, so in most cases the user has a form where he can enter his information (e.g. user name and password). You have to write a pipeline presenting this form to the user. When the form is submitted, the authentication process has to be started inside the authentication framework. As a submit of a form invokes a request to Cocoon, a pipeline in the sitemap is triggered. We refer to this pipeline as a login pipeline.

The Login Process

The authentication process is started by invoking the auth-login action. So, the login pipeline has to contain this action:

<map:match pattern="login">
  <map:act type="auth-login">
    <map:parameter name="handler" value="portalhandler"/>
    <map:parameter name="parameter_userid" value="{request-param:name}"/>
    <map:parameter name="parameter_password" value="{request-param:password}"/>
    <map:redirect-to uri="authentication-successful"/>
  </map:act>
  <!-- authentication failed: -->
  <map:generate src="auth_failed.xml"/>
  <map:transform src="tohtml.xsl"/>
  <map:serialize/>
</map:match>

The auth-login action uses the handler parameter to call the authentication resource of this handler. This authentication resource needs to know the information provided by the user, e.g. in the form. For each piece of information a separate parameter is created. The name of this parameter has to start with "parameter_". So in the example above, the authentication resource gets two parameters: userid and password. Since the values of these parameters were sent by a form, they need to be passed on to the authentication resource. If you use "{request-param:...}" for the value of a parameter, the auth-login action will pass the actual value of that request parameter to the authentication resource by using the input modules concept of Cocoon.

Note
You might be wondering why we explicitly pass the request parameters on to the internal pipeline call. Note that the authentication resource of the portalhandler is defined by cocoon:raw. By using this, no request parameter of the original request is passed on to the internal pipeline by default and therefore we have to define them explicitly. If you use cocoon: then the parameters of the form are by default passed on to the authentication resource and we could omit the parameter definition from above. But we feel that it is safer to explicitly define them.

If the user is not already authenticated with this handler, the framework calls the authentication resource and passes the parameters to it. If this authentication is successful, the action returns a map and the sitemap commands inside the map:act are executed. If not already done, a session is created on the server as well.

If the authentication fails, the action does not deliver a map and therefore the commands inside the map:act are skipped. The error information delivered by the authentication resource is stored in the temporary context. So you can get the information using either the session transformer or the session-context input module.

Note
As you can see from the example above, you are not limited in defining the information the user has to provide. This can be as many fields as you need.

The authentication resource

The last chapter described the authentication process but left out details about the authentication itself. This chapter closes this gap.

The authentication can be done by different components:

  • A sitemap resource (pipeline).
  • A distant resource, e.g. requested via HTTP.
  • A java class.

The first two are actually similar as in both cases a URI is called. So we will talk about them in the next chapter. Authentication using a java class is the topic of the following chapter.

Using a URI as the authentication resource

Using this flexible approach nearly any kind of authentication is possible (e.g. database, LDAP). The authentication resource is a mandatory configuration of the authentication handler:

<autentication-manager>
  <handlers>
    <!-- Now follows the handlers configuration -->
    <handler name="portalhandler">
      <!-- The login resource -->
      <redirect-to uri="cocoon:/sunspotdemoportal"/>
      <authentication uri="cocoon:raw:/sunrise-authuser"/>
    </handler>
  </handlers>
</autentication-manager>

If the authentication resource is a sitemap resource or a remote resource, this resource is requested by the framework with the given parameters from the auth-login action (see previous section). In addition, all parameters inside the authentication tag of the handler configuration are passed to the resource. The response of this resource must contain XML conforming to the following scheme:

<authentication>
    <ID>Unique ID of the user in the system</ID>
    <role>rolename</role> <!-- optional -->
    <data>
        Any additional optional information can be supplied here. 
        This will be stored in the session for later retrieval
    </data>
</authentication>

The XML is very simply, only the root element authentication and the ID element with a valid unique ID for the user in this handler is required. Everything else is optional.

The framework checks the response of the authentication resource for the given scheme: the root node must be named authentication and one child called ID must be present. In this case the authentication is successfull and the framework creates an authentication session context and stores the XML inside.

The mandatory ID tag is an unique identification for the user inside the web application or more precisly inside this handler. The role is optional and can be used for categorizing users and displaying different functionality inside the Cocoon portal engine.

Note
The role element is optional; you can use your own categorization and exchange it with a roles element or a group element or leave it out, if you don't need it. In addition you can add any other element there as well and access the information later on.

Using the data node, the authentication resource can pass any information of the user to the session. You can retrieve the information as long as the session is valid.

If the authentication is not successful, the resource must create an XML with the root node authentication, without the ID tag. In addition a data node can be added containing more information about the unsuccessful attempt. This data node is then stored into the temporary context (see previous section).

Note
It is advisable to make an internal pipeline for the authentication resource. An internal pipeline is not directly accessible by a user.

Using a Java class as the authentication resource

Using a class is an alternative for using a pipeline. You can define this class in the handler configuration as an attribute authenticator of the authentication element, e.g.:

<autentication-manager>
  <handlers>
    <!-- Now follows the handlers configuration -->
    <handler name="portalhandler">
      <!-- The login resource -->
      <redirect-to uri="cocoon:/sunspotdemoportal"/>
      <authentication authenticator="mypkg.MyAuthenticator"/>
    </handler>
  </handlers>
</autentication-manager>

This class must conform to the Authenticator interface. This interface provides a method that tries to authenticate a User and delivers XML that is stored in the session on success. So, the behaviour is similar to the pipeline.

Logging out

The logout process is triggered by the "auth-logout" action:

<map:act type="auth-logout">
  <map:parameter name="handler" value="unique"/>
</map:act>

This action logs the user out of the given handler and removes all the information about this handler that is stored in the session.