Customizing the security mechanism in JViews Web applications

In special situations where the default security mechanism does not satisfy your requirements, the JViews security mechanism can be customized by using your own validation mechanism, in which you can add or remove specific request parameters from the default parameter list for the specific request; or you can specify your own validation logic and how violation is to be handled when validation fails.

Injecting a customized parameter validation listener

There are two ways to inject a customized parameter validation listener. One is to use annotation to configure a customized parameter validation listener for a specific servlet, another is to call the setParameterValidationListener method to inject a customized parameter validation listener by using the JViews servlet support mechanism.
  1. Configure the customized parameter validation listener by using annotation on the JViews servlet class. Since JViews annotation support is provided when you configure a server action listener on a JViews servlet class as shown in the following example.
    @IlvServerActions(parameters = { 
    @IlvServerActionParam(actionName = IlvParameterValidationListener.ACTION_NAME, actionListener = MyServletParamValidationListener.class) })
    public class MyServlet extends IlvFacesDiagrammerServlet {...}
    
    This setting injects the customized MyServletParamValidationListener class for the JViews servlet of MyServlet . For more details on server action listener configuration, see Managing server action listeners.
  2. Configure the customized parameter validation listener by overriding in Servlet support class. When you are using the servlet support mechanism, you can call the setParameterValidationListener method to inject a customized parameter validation listener as shown in the following example.
    public class MyServlet extends IlvFacesDiagrammerServlet {
      public void init(ServletConfig config) throws ServletException {
        super.init(config);
      }
            
      public IlvSDMServletSupport createServletSupport(ServletContext context) {
        return new MyServletSupport(this.getServletContext());
      }
            
      class MyServletSupport extends IlvFacesDiagrammerServletSupport{
       public MyServletSupport(ServletContext context) {
          /*
           * Enable customized parameter validation by using servlet support class.
           */
          setParameterValidationListener(new MyServletParameterValidationListener());
        }
      }
      ...
    }
    This setting injects customized MyServletParamValidationListener class for JViews servlet of MyServlet by overriding the setParameterValidationListener method.

Creating a customized parameter validation listener

If you want to customize request parameters (like adding or removing some specific parameters) and use the customized validation mechanism, you must create a customized parameter validation listener to extend the provided validation listeners shipped in the product as shown in the following example.
public class MyServletParamValidationListener extends IlvManagerServletParameterValidationListener {...}

Customizing the request parameters

For each request, a list of request parameters are supported by default. For more details on supported parameters see Introducing JViews Web application exchange protocols and securities. Under some circumstances, you might need to customize the request parameters: for example, to add or to remove some parameters for a specific request in the application. You can perform such customization by using a request parameter handler. The following example shows how to add a customized request parameter called testParameter for an image request by overriding the getServletParametersHandler method in the parent class.
public class MyServletParamValidationListener extends
  IlvManagerServletParameterValidationListener {
      ...
    public IlvServletParameterHandler getServletParametersHandler(
      ServletRequest request) {
      String type = request.getParameter("request");
      IlvServletParameterHandler handler = null;
      // if you want to add more customized parameters for specific 
      // request types such as "image"
      if ("image".equals(type)) {
        // get the default parameter handler for the image request 
        // by using the factory class.
        handler = IlvManagerServletParameterHandlerFactory.getInstance()
          .getServletParametersHandler(request);
        // add a non-mandatory testing paramter called "testParameter" 
        // and an expected value of "expectedValue" under the specific 
        // comparator "List"
        handler.addParameter("testParameter", false, "expectedValue", 
          true,IlvRequestParameter.Comparator.LIST);
      } else {
        handler = super.getServletParametersHandler(request);
      }
    return handler;
  }
}
For the image request, you must get the default parameter handler by using parameter handler factory class, then you must add a non-mandatory testing parameter called testParameter and the expected value called expectedValue under the specific comparator List . This comparator will compare the list of expected values with the requested parameter for validation.
For each request, the parameter handler is provided by default, which support parameters operations such as adding or removing some parameters. For more details on supported operations, see IlvServletParameterHandler. To customize your request parameter, you must first get the default parameter handler. You can use the parameter handler factory classes to get the specific parameter handler for your specific request.
To get the default parameter handler:
To get the default parameter handler, use the IlvManagerServletParameterHandlerFactory class.
If you want to get the parameter handler in resource loading, use IlvResourceParameterHandlerFactory
To specify the comparator:
You can also specify how to compare the parameter value by setting a specific comparator to true . The default comparator is EQUALS which means that the requested parameter value should be equal to expected value. Here is a list of supported comparators and sample code fragments to show you how to use them. For more details on supported comparators see IlvRequestParameter.
Name Description Example code
EQUALS The parameter value is equal to the expected value. addParameter("format", true, "json", true, IlvRequestParameter.Comparator.EQUALS);
CONTAINS The parameter value contains the expected value. addParameter("res", false, "data", true, IlvRequestParameter.Comparator.CONTAINS);
NOT_CONTAINS The parameter value does not contain the expected value. addParameter("image", false, "script", true, IlvRequestParameter.Comparator.NOT_CONTAINS);
STARTS_WITH The parameter value starts with one of the listed expected values, the value is separated by a semicolon in the string. addParameter("res", true, "ilog", true, IlvRequestParameter.Comparator.STARTS_WITH);
ENDS_WITH The parameter value ends with one of the listed expected values, the value is separated by semicolon in the string. addParameter("res", true, ".gif;.jpg;.jpeg;.png;.js;.css", true, IlvRequestParameter.Comparator.ENDS_WITH);
LIST The parameter value is one in the list of expected values, the value is separated by semicolon in the string. addParameter("format", true, "JPEG;PNG;GIF;JPG", true, IlvRequestParameter.Comparator.LIST);

Customizing the validation logic

When the parameter validation mechanism is enabled, the parameter value for each request is compared with the expected one using the default validation logic. If you want to change the default validation logic, for example, to exempt or to add stricter rules on specific requests, you must customize the logic. The following example shows you how to add a customized validation logic for the image request by overriding the validate method in the parent class.
public class MyServletParamValidationListener extends
  IlvManagerServletParameterValidationListener {
      ...
    public boolean validate(HttpServletRequest request,
      HttpServletResponse response){
      String type = request.getParameter("request");
      //if you want to validate specific request type.
      if ("specificType".equals(type)) {
        /*
         * If you put error messages in request scope under the namespace of ERROR_MESSAGE.
         * the default handleViolation method can retrieve it and put it in the response. And 
         * the type of response is based on your request type.  
         */
        String errorMsg = "some error messages";      
        request.setAttribute(ERROR_MESSAGES, errorMsg);
        return false;
      } else {
        return super.validate(request, response);
      }
  }
   ...  
} 
The error message is placed under the namespace of ERROR_MESSAGES in the request scope, so that the default violation handling method can retrieve it and put it in the response.

Customizing violation handling

If any parameters sent by a request fails the parameter validation the default process for violation handling is applied. By default, the response format is the same as the request expected. For example, if the request expects an image, the image containing the error message is returned. If you want to change the default process, for example by adding more information or taking other actions, you must customize the violation handling. The following example shows how to customize violation handling by overriding the handleViolation method in the parent class.
public class MyServletParamValidationListener extends
  IlvManagerServletParameterValidationListener {
      ...
  public void handleViolation(HttpServletRequest request,
    HttpServletResponse response) throws IOException {
    // gets error message from request attribute
    Object obj = request.getAttribute(ERROR_MESSAGES);
    String messages = obj == null ? "" : obj.toString();     
    String type = request.getParameter("request");
    if (type.equals("image")) {
      // perfom your customized action 
    }
  }
}
In this example, the error message is obtained from the namespace of ERROR_MESSAGES in the request scope.

Example

For a reference example, see:
file://../jviews-diagrammer89/codefragments/jsf-diagrammer-ice/index.html <installdir> /jviews-diagrammer89/codefragments/jsf-diagrammer-ice/index.html .