How to write a simple foaf+ssl authentication servlet

After having set up a web server so that it listens to an https socket that accepts certificates signed by any Certification Authority (CA) (see the Tomcat post), we can write a servlet that uses these retrieved certificates to authenticate the user. I will detail one simple way of doing this here.

Retrieving the certificate from the servlet

In Tomcat compatible servlets it is possible to retrieve the certificates used in a connection with the following code:

import java.security.cert.X509Certificate;
protected void doGet(HttpServletRequest request, HttpServletResponse response)
             throws ServletException, IOException {
       //...
       X509Certificate[] certificates = (X509Certificate[]) request
                       .getAttribute("javax.servlet.request.X509Certificate");
       //...
 }

Verifying the WebId

This can be done very easily by using a class such as DereferencingFoafSslVerifier (see source), available as a maven project from so(m)mer repository (in the foafssl/ directory).

Use it like this:

  Collection<? extends FoafSslPrincipal> verifiedWebIDs = null;

  try {
     FoafSslVerifier FOAF_SSL_VERIFIER = new DereferencingFoafSslVerifier();
     verifiedWebIDs = FOAF_SSL_VERIFIER.verifyFoafSslCertificate(foafSslCertificate);
  } catch (Exception e) {
     redirect(response,...); //redirect appropriately
     return;
  }

If the certificate is authenticated by the WebId, you will then end up with a collection of FoafSslPrincipals, which can be used for as an identifier for the user who just logged in. Otherwise you should redirect the user to a page enabling him to login with either OpenId, or the usual username/password pair, or point him to a page such as this one where he can get a foaf+ssl certificate.

For a complete example application that uses this code, have a look at the Identity Provider Servlet, which is running at https://foafssl.org/srv/idp (note this servlet was trying to create a workaround for an iPhone bug. Ignore that code for the moment).

Todo

The current library is too simple and has a few gaping usability holes. Some of the most evident are:

  • No support for rdfa or turtle formats.
  • The Sesame RDF framework/database should be run as a service, so that it can be queried directly by the servlet. Currently the data gathered by the foaf file is lost as soon as the FOAF_SSL_VERIFIER.verifyFoafSslCertificate(foafSslCertificate); method returns. This is ok for a Identity Provider Servlet, but not for most other servers. A Java/RDF mapper such as the So(m)mer mapper would then make it easy for Java programmers to use the information in the database to personalize the site with the information given by the foaf file.
  • develop an access control library that makes it easy to specify which resources can be accessed by which groups of users, specified declaratively. It would be useful for example to be able to specify that a number of resources can be accessed by friends of someone, or friends of friends of someone, or family members, ....

But this is good enough to get going. If you have suggestions on the best way to architect some of these improvements so that we have a more flexible and powerful library, please contact me. I welcome all contributions. :-)

Comments:

Post a Comment:
Comments are closed for this entry.
About

bblfish

Search

Archives
« April 2014
MonTueWedThuFriSatSun
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
    
       
Today