/*
Transit - Remote procedure calls made simple
Copyright (c) 2012 Ulrich Hilger
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with this program. If not, see .
*/
package de.uhilger.transit.web;
import java.security.*;
import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* Ein Filter zur Pruefung von Berechtigungen zum Einsatz in einer
* Java EE konformen Webanwendung. Zum Einbau wird diese Klasse
* im Deployment Desciptor (web.xml) deklariert.
*
* @author Copyright (c) Ulrich Hilger, http://uhilger.de
* @author Published under the terms and conditions of
* the GNU Affero General Public License
*
* @version 1, September 16, 2012
*/
public class Waechter implements Filter {
/** Name, der als Benutzername verwendet wird, wenn kein Benutzer angemeldet ist */
public static final String ANONYMER_NUTZER = "anonymous";
/** Das Objekt zur Pruefung von Berechtigungen */
protected RechtePruefer rechtePruefer;
protected String className;
protected String methodName;
protected String userName;
/**
* Pruefen, ob der zur Zeit angemeldete Benutzer eine HTTP-Anfrage
* ausfuehren darf, die einen Methodenaufruf der Klassenbibliothek
* Transit enthaelt.
*
* Anfragen, die berechtigt sind, werden zur Verarbeitung weiter gereicht.
* Ist eine Anfrage nicht berechtigt, wird die Anfrage nicht weiter
* gereicht und eine Servlet Exception erzeugt.
*
* @param request die zu pruefende Anfrage
* @param response die Antowrt des Servers
* @param chain Filterkette zur Weiterleitung der Anfrage fuer den Fall, dass
* der Benutzer berechtigt ist.
*/
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws ServletException, IOException {
getParameters(request);
if(rechtePruefer == null) {
throw new ServletException("RechtePruefer konnte nicht erzeugt werden.");
} else {
if(rechtePruefer.istErlaubt(request, response, className, methodName, userName)) {
chain.doFilter(request, response);
} else {
throw new ServletException("Der Benutzer " + userName +
" darf die Methode " + className + "." + methodName + " nicht ausfuehren.");
}
}
}
protected void getParameters(ServletRequest request) throws ServletException {
className = ((HttpServletRequest) request).getParameter("c");
methodName = ((HttpServletRequest) request).getParameter("m");
userName = getUserName((HttpServletRequest) request);
if(className == null) {
throw new ServletException("Parameter c fehlt.");
} else if(methodName == null) {
throw new ServletException("Parameter m fehlt.");
} else if(userName == null) {
throw new ServletException("Name des Benutzers konnte nicht ermittelt werden.");
}
}
/**
* Den Namen des angemeldeten Benutzers ermitteln.
*
* @param req die Anfrage, deren Benutzer ermittelt werden soll
* @return Name des Benutzers oder anonymous
, wenn
* kein Benutzer angemeldet ist
*/
public static String getUserName(HttpServletRequest req) {
String userName = null;
Principal p = req.getUserPrincipal();
if(p != null) {
userName = p.getName();
}
if(userName == null) {
userName = ANONYMER_NUTZER;
}
return userName;
}
/**
* Diesen Filter initialisieren
*
* @param config die Konfiguration, die zur Initialisierung
* verwendet werden soll
*/
public void init(FilterConfig config) {
try {
String prueferKlassenName = config.getInitParameter("rechtePruefer");
if(prueferKlassenName != null) {
Class prueferKlasse = Class.forName(prueferKlassenName);
if(prueferKlasse != null) {
Object p = prueferKlasse.newInstance();
if(p != null && p instanceof RechtePruefer) {
this.rechtePruefer = (RechtePruefer) p;
} else {
rechteDbSetzen(config);
}
} else {
rechteDbSetzen(config);
}
} else {
rechteDbSetzen(config);
}
} catch(Exception e) {}
}
private void rechteDbSetzen(FilterConfig config) {
this.rechtePruefer = new RechteDb(config.getInitParameter("dataSource"));
}
/**
* Diesen Filter vernichten (vom Filter verwendete Ressourcen
* frei geben usw.)
*/
public void destroy() {
this.rechtePruefer = null;
}
}