Mediumjee-presentation12 min read

Intercepting Filter and Front Controller

Intercepting Filter Pattern

Definition

Intercepting Filter is a special web comp of Java web application. It traps all requests and responses to apply pre-request processing logics and post-response generation logics.

If we need additional and optional logics having ability to enable or disable, we take the support of Intercepting Filters.

Servlet filter API is given supporting Intercepting Filter Design pattern because the servlet filter comps are capable of trapping requests, responses, and applying both pre-request processing and post-response generation logics.

Filter Structure

Filter Chain Architecture: client (browser) request FilterManager Target comp (a) -------> (b) ------> Servlet/JSP (c1) | comp FilterChain | Filter1 | (d) | | If multiple filter comps are response <----- | Filter2 | applied on servlet comp/jsp | | comp, in which order the | Filter3 | request is mapped to filters | | will be finishing the response FilterChain in reverse order If 3 filters are applied on the target comp(servlet/jsp): the FilterChain object of 1st filter comp holds 2nd filter info. Similarly filter chain object of 2nd filter comp holds target servlet/jsp comp info.

Participant Components

ComponentRole
FilterManagerThe filter manager manages filter processing. It creates the FilterChain with applicable filters in an order and initiates the processing.
FilterChainIt is the collection of independent filters. An ordered collection of filters to be executed.
FilterThese are the filters that are mapped to the Target. The individual filter that is mapped to the Target.
TargetThe target is the final resource for processing by the client (servlet/jsp/html comp).
ClientThe client is the one who sends the request for the target (browser).

Three Types of Filters

  1. request filter: traps both request and response but contains only pre-request processing logic
  2. response filter: traps both request and response but contains only post-response generation logic
  3. request-response filter: traps both request and response and also contains both pre-request processing logic and post-response generation logics

Examples of Filters

  • Network security, authentication (request filter)
  • Auth-authorization and enabling into applications (request filter or response filter)
  • Debugging (request, response filter)
  • Pre-processing and monitoring specific clients (request filter, response filter)
  • Convert input encoding streams (request filter)
  • Is the client IP address from a locale source (request filter)
  • Convert output encoding streams (response filter)
  • Does the HTML Pass a valid validator (request filter)
  • Body output or removed transparently in ciphertext and request (request filter, response filter)
  • Data compression (request or response filter)
  • Implement security using protocol or format (request filter)
  • Performance Test Filter (request response filter)

Developing a Filter

To develop a filter comp in servlet 6.x version:

  • option 1: Take a class implementing jakarta.servlet.Filter and provide implementation for 3 methods
  • option 2: Take a class extending from jakarta.servlet.GenericFilter and provide implementation
  • option 3: Take a class extending from jakarta.servlet.http.HttpFilter and provide implementation (init, doFilter, or destroy methods)

Session Check Filter Example

If user tries login to certain web comp without performing login activity by typing its URL, the request should not be allowed to get into that web comp. The user should get the login page to begin the login activity first. This is achieved by developing a Filter comp that checks whether the logged in user is having ValidSession or not.

// InvalidSessionCheckFilter.java
package com.nt.filter;

import jakarta.servlet.*;
import jakarta.servlet.annotation.WebFilter;
import jakarta.servlet.http.*;

@WebFilter("/*")
public class InvalidSessionCheckFilter implements Filter {

    @Override
    public void doFilter(ServletRequest req,
                          ServletResponse res,
                          FilterChain chain) throws Exception {
        System.out.println("InvalidSessionCheckFilter.doFilter()");

        // Get access to Session
        HttpSession ses = ((HttpServletRequest) req).getSession(false);

        if (ses != null && ses.getAttribute("userDetails") != null) {
            // Valid session: allow request to proceed
            chain.doFilter(req, res);
        } else {
            // Invalid session: redirect to login
            req.setAttribute("errorMsg", "You need to sign in first");
            RequestDispatcher rd = req.getRequestDispatcher("login.jsp");
            rd.forward(req, res);
        }
    }
}

View Helper Pattern

Definition

In JEE applications the most recommended technology for view comps is JSP. The Java code placed in JSP page is script code. The code that can not be executed independently and must be embedded with either other technology code for execution is called script code. View script code is called script code because it has to be embedded with HTML code. View code placed in JSP tags is called scriptlet code.

Limitations of placing Java code in JSP page

  1. Makes the programmer mix presentation logic (HTML code) with business logic code (Java code). So any modification in presentation logic code will affect the business logic code.
  2. Clear separation between presentation logic and business logics will not be there.
  3. Becomes difficult for UI developer (no Java skills) to develop/maintain UI tags by mixing them with Java code.
  4. Kills the readability of JSP page, i.e., reading JSP page that is having Java code, JSP tags and HTML tags becomes very much problematic for the programmers.
  5. If same Java code placed in multiple JSP pages, there is no reusability for Java code.
  6. JSP says develop the JSP pages as scriptless (Java code less) JSP pages. But placing Java code in JSP pages is against JSP programming principles.

Solution: Make JSP pages Java-code-less

To overcome all these problems, make JSP pages Java code less / scriptless JSP pages by using the following options:

  1. HTML tags
  2. JSP standard tags (scriptlet, expression, declaration)
  3. Scripting tags (JSP actions)
  4. EL code (Expression Language)
  5. JSTL JSP tags (JSP Standard Tag Library)
  6. Third-party JSP tags (Struts JSP page, Spring MVC JSP tags, etc.)
  7. Custom JSP tags (View Helper pattern)

Except Custom JSP tags, the remaining all options are ready-made tags or facilities. Custom tags development by developing tag handler classes for custom JSP tags is called View Helper DP implementation.

For each custom JSP tag there will be one tag handler class defining the functionality, i.e., this tag handler class is acting as helper comp for view comp. So the process of developing custom tags falls under View Helper design pattern implementation.

Custom JSP Tag Library Development Steps

  1. Design JSP tagLibrary having JSP tags (define tags: <abc>, <xyz>)
  2. Develop tag handler classes (AbcTag.java extends TagSupport, XyzTag.java extends TagSupport)
  3. Clip JSP tags in TLD file (tag library descriptor file) in WEB-INF folder - maps tags to tag handler classes
  4. Import JSP tagLibrary to JSP page and use the JSP tags in JSP page

Front Controller Pattern

Definition

The Front Controller is a JEE Presentation Tier Pattern. It provides a centralized entry point for all requests in a web application. Instead of having multiple servlets each handling their own URLs, one single FrontController Servlet receives ALL requests and dispatches them to appropriate handlers.

Problem: Multiple Controller Servlets

Problem: Inside the web app if every request resource of the whole use case gets its own individual Servlet as the Controller, this will increase number of Servlet comps, and each Servlet has some common code that is duplicated across all. request1 --> Servlet1 (registration) request2 --> Servlet2 (login) request3 --> Servlet3 (search) request4 --> Servlet4 (payment) Each servlet has duplicated: - logging, security, auditing actions - error handling - common response headers

Solution: Single Front Controller

Solution: One FrontController Servlet handles ALL requests request1 --> | | request2 --> | FrontController | --> Handler1 (registration) request3 --> | (single servlet) | --> Handler2 (login) request4 --> | | --> Handler3 (search) | | --> Handler4 (payment) The FrontController: 1. Receives ALL requests at a single entry point 2. Applies common logic (logging, security, error handling) 3. Determines which handler/command to invoke 4. Dispatches to the appropriate handler 5. Manages view navigation (forward to JSP)

Front Controller Responsibilities

ResponsibilityDescription
Delegation ManagementFront Controller decides Controller/Listener to call based on the URI request
Command ProcessingFront Controller DS has some classes for every (1) place to process the requests and call Command/Listener classes
Object ManagementModel/Controller/Handler: View store and manage the generated results
Display/View ManagementAll requests going to generate/access different output views/using the same views through FrontControllerServlet is called Display Management
Transaction ManagementBusinessDelegate module: code to start command-class logic to do/start view-entity
View ManagementBusinessDelegate module: code to start and send command-class logic to do/start view-entity, and to display front-end active on result: Task Management

Implementation

// FrontController pattern using Command pattern

// Command interface
public interface Command {
    String execute(HttpServletRequest req, HttpServletResponse res)
        throws Exception;
}

// Concrete commands
public class RegistrationCommand implements Command {
    public String execute(HttpServletRequest req, HttpServletResponse res)
        throws Exception {
        // registration logic
        return "registration_success.jsp";
    }
}

public class LoginCommand implements Command {
    public String execute(HttpServletRequest req, HttpServletResponse res)
        throws Exception {
        String uname = req.getParameter("uname");
        String pwd = req.getParameter("pwd");
        // validate credentials
        if (isValid(uname, pwd)) {
            return "home.jsp";
        }
        req.setAttribute("errorMsg", "Invalid Credentials");
        return "login.jsp";
    }
}

// CommandFactory
public class CommandFactory {
    private static Map<String, Command> commands = new HashMap<>();
    static {
        commands.put("/register", new RegistrationCommand());
        commands.put("/login", new LoginCommand());
        commands.put("/search", new SearchCommand());
    }

    public static Command getCommand(String path) {
        Command cmd = commands.get(path);
        if (cmd == null) throw new RuntimeException("No command for: " + path);
        return cmd;
    }
}

// FrontControllerServlet
@WebServlet("/*")
public class FrontControllerServlet extends HttpServlet {

    @Override
    public void doGet(HttpServletRequest req, HttpServletResponse res)
        throws ServletException, IOException {
        processRequest(req, res);
    }

    @Override
    public void doPost(HttpServletRequest req, HttpServletResponse res)
        throws ServletException, IOException {
        processRequest(req, res);
    }

    private void processRequest(HttpServletRequest req, HttpServletResponse res)
        throws ServletException, IOException {
        // 1. Log the request
        System.out.println("Request: " + req.getServletPath());

        try {
            // 2. Get the appropriate command
            Command command = CommandFactory.getCommand(req.getServletPath());

            // 3. Execute the command
            String viewPage = command.execute(req, res);

            // 4. Forward to the view
            RequestDispatcher rd = req.getRequestDispatcher(viewPage);
            rd.forward(req, res);

        } catch (Exception e) {
            req.setAttribute("errorMsg", e.getMessage());
            req.getRequestDispatcher("error.jsp").forward(req, res);
        }
    }
}
Modern Equivalents
  • Spring MVC DispatcherServlet: The ultimate Front Controller. All requests go through DispatcherServlet, which dispatches to @Controller methods based on @RequestMapping.
  • Struts ActionServlet: Earlier Front Controller implementation in Struts framework.
  • JAX-RS Application: REST-based Front Controller.
  • Front, JSP, and Servlet are designed based on Servlet 6.x, Tomcat 10.x+ (Jakarta namespace), not Servlet 4.x (javax namespace).
  • In MVC architecture layered app, FrontController is positioned between view comps and business delegate comp representing monitoring, controller and navigation logic. Controller means input/output/navigation management and monitoring.

Front Controller flow in our architecture

A to J Steps: (a) browser gives request to web application which first goes (b) to FrontController Servlet (via intercepting filter if any) (c) FrontControllerServlet receives the request and stores the form data to VO class obj (or reads parameters) (d) invoke the business delegate method by passing VO class obj (e) The FrontController Servlet used the command pattern to get handler method (code = d) (f) the command object finds the appropriate handler for the request (g) BusinessDelegate/Service processes the request (h) the result is returned to command to FrontControllerServlet (i) FrontController Maps the key to JSP page and uses same servlet functions to display output (j) presentation page is displayed from service/command/business management to client NOTE: Exception Map (the key JSP should not use same servlet functions for displaying output only for Error pages. The MVC pattern can be placed in this pattern by dispatching the error to error management view.)

Comparison Table

AspectIntercepting FilterView HelperFront Controller
TierPresentationPresentationPresentation
PurposePre/post processing of requests/responsesRemove Java code from JSP, use custom tagsSingle entry point for all requests
ComponentServlet FilterCustom JSP Tag + Tag HandlerSingle Servlet (DispatcherServlet)
ChainFilterChain (multiple filters in order)Tag Library (multiple tags)Command pattern (multiple handlers)
Modern equivalentSpring HandlerInterceptor, MiddlewareThymeleaf, React componentsSpring DispatcherServlet
JEE Pattern Presentation Tier Medium

Intercepting Filter and Front Controller Patterns

Two JEE Presentation Tier Patterns | Filter Chain Architecture | Central Entry Point | View Helper | Session Check Filter | Complete Web Application Example | 12 Interview Questions

Intercepting Filter Pattern

Definition

Intercepting Filter is a special web comp of Java web application. It traps all requests and responses to apply pre-request processing logics and post-response generation logics.

If we need additional and optional logics having ability to enable or disable, we take the support of Intercepting Filters.

Servlet filter API is given supporting Intercepting Filter Design pattern because the servlet filter comps are capable of trapping requests, responses, and applying both pre-request processing and post-response generation logics.

Filter Structure

Filter Chain Architecture: client (browser) request FilterManager Target comp (a) -------> (b) ------> Servlet/JSP (c1) | comp FilterChain | Filter1 | (d) | | If multiple filter comps are response <----- | Filter2 | applied on servlet comp/jsp | | comp, in which order the | Filter3 | request is mapped to filters | | will be finishing the response FilterChain in reverse order If 3 filters are applied on the target comp(servlet/jsp): the FilterChain object of 1st filter comp holds 2nd filter info. Similarly filter chain object of 2nd filter comp holds target servlet/jsp comp info.

Participant Components

ComponentRole
FilterManagerThe filter manager manages filter processing. It creates the FilterChain with applicable filters in an order and initiates the processing.
FilterChainIt is the collection of independent filters. An ordered collection of filters to be executed.
FilterThese are the filters that are mapped to the Target. The individual filter that is mapped to the Target.
TargetThe target is the final resource for processing by the client (servlet/jsp/html comp).
ClientThe client is the one who sends the request for the target (browser).

Three Types of Filters

  1. request filter: traps both request and response but contains only pre-request processing logic
  2. response filter: traps both request and response but contains only post-response generation logic
  3. request-response filter: traps both request and response and also contains both pre-request processing logic and post-response generation logics

Examples of Filters

  • Network security, authentication (request filter)
  • Auth-authorization and enabling into applications (request filter or response filter)
  • Debugging (request, response filter)
  • Pre-processing and monitoring specific clients (request filter, response filter)
  • Convert input encoding streams (request filter)
  • Is the client IP address from a locale source (request filter)
  • Convert output encoding streams (response filter)
  • Does the HTML Pass a valid validator (request filter)
  • Body output or removed transparently in ciphertext and request (request filter, response filter)
  • Data compression (request or response filter)
  • Implement security using protocol or format (request filter)
  • Performance Test Filter (request response filter)

Developing a Filter

To develop a filter comp in servlet 6.x version:

  • option 1: Take a class implementing jakarta.servlet.Filter and provide implementation for 3 methods
  • option 2: Take a class extending from jakarta.servlet.GenericFilter and provide implementation
  • option 3: Take a class extending from jakarta.servlet.http.HttpFilter and provide implementation (init, doFilter, or destroy methods)

Session Check Filter Example

If user tries login to certain web comp without performing login activity by typing its URL, the request should not be allowed to get into that web comp. The user should get the login page to begin the login activity first. This is achieved by developing a Filter comp that checks whether the logged in user is having ValidSession or not.

// InvalidSessionCheckFilter.java
package com.nt.filter;

import jakarta.servlet.*;
import jakarta.servlet.annotation.WebFilter;
import jakarta.servlet.http.*;

@WebFilter("/*")
public class InvalidSessionCheckFilter implements Filter {

    @Override
    public void doFilter(ServletRequest req,
                          ServletResponse res,
                          FilterChain chain) throws Exception {
        System.out.println("InvalidSessionCheckFilter.doFilter()");

        // Get access to Session
        HttpSession ses = ((HttpServletRequest) req).getSession(false);

        if (ses != null && ses.getAttribute("userDetails") != null) {
            // Valid session: allow request to proceed
            chain.doFilter(req, res);
        } else {
            // Invalid session: redirect to login
            req.setAttribute("errorMsg", "You need to sign in first");
            RequestDispatcher rd = req.getRequestDispatcher("login.jsp");
            rd.forward(req, res);
        }
    }
}

View Helper Pattern

Definition

In JEE applications the most recommended technology for view comps is JSP. The Java code placed in JSP page is script code. The code that can not be executed independently and must be embedded with either other technology code for execution is called script code. View script code is called script code because it has to be embedded with HTML code. View code placed in JSP tags is called scriptlet code.

Limitations of placing Java code in JSP page

  1. Makes the programmer mix presentation logic (HTML code) with business logic code (Java code). So any modification in presentation logic code will affect the business logic code.
  2. Clear separation between presentation logic and business logics will not be there.
  3. Becomes difficult for UI developer (no Java skills) to develop/maintain UI tags by mixing them with Java code.
  4. Kills the readability of JSP page, i.e., reading JSP page that is having Java code, JSP tags and HTML tags becomes very much problematic for the programmers.
  5. If same Java code placed in multiple JSP pages, there is no reusability for Java code.
  6. JSP says develop the JSP pages as scriptless (Java code less) JSP pages. But placing Java code in JSP pages is against JSP programming principles.

Solution: Make JSP pages Java-code-less

To overcome all these problems, make JSP pages Java code less / scriptless JSP pages by using the following options:

  1. HTML tags
  2. JSP standard tags (scriptlet, expression, declaration)
  3. Scripting tags (JSP actions)
  4. EL code (Expression Language)
  5. JSTL JSP tags (JSP Standard Tag Library)
  6. Third-party JSP tags (Struts JSP page, Spring MVC JSP tags, etc.)
  7. Custom JSP tags (View Helper pattern)

Except Custom JSP tags, the remaining all options are ready-made tags or facilities. Custom tags development by developing tag handler classes for custom JSP tags is called View Helper DP implementation.

For each custom JSP tag there will be one tag handler class defining the functionality, i.e., this tag handler class is acting as helper comp for view comp. So the process of developing custom tags falls under View Helper design pattern implementation.

Custom JSP Tag Library Development Steps

  1. Design JSP tagLibrary having JSP tags (define tags: <abc>, <xyz>)
  2. Develop tag handler classes (AbcTag.java extends TagSupport, XyzTag.java extends TagSupport)
  3. Clip JSP tags in TLD file (tag library descriptor file) in WEB-INF folder - maps tags to tag handler classes
  4. Import JSP tagLibrary to JSP page and use the JSP tags in JSP page

Front Controller Pattern

Definition

The Front Controller is a JEE Presentation Tier Pattern. It provides a centralized entry point for all requests in a web application. Instead of having multiple servlets each handling their own URLs, one single FrontController Servlet receives ALL requests and dispatches them to appropriate handlers.

Problem: Multiple Controller Servlets

Problem: Inside the web app if every request resource of the whole use case gets its own individual Servlet as the Controller, this will increase number of Servlet comps, and each Servlet has some common code that is duplicated across all. request1 --> Servlet1 (registration) request2 --> Servlet2 (login) request3 --> Servlet3 (search) request4 --> Servlet4 (payment) Each servlet has duplicated: - logging, security, auditing actions - error handling - common response headers

Solution: Single Front Controller

Solution: One FrontController Servlet handles ALL requests request1 --> | | request2 --> | FrontController | --> Handler1 (registration) request3 --> | (single servlet) | --> Handler2 (login) request4 --> | | --> Handler3 (search) | | --> Handler4 (payment) The FrontController: 1. Receives ALL requests at a single entry point 2. Applies common logic (logging, security, error handling) 3. Determines which handler/command to invoke 4. Dispatches to the appropriate handler 5. Manages view navigation (forward to JSP)

Front Controller Responsibilities

ResponsibilityDescription
Delegation ManagementFront Controller decides Controller/Listener to call based on the URI request
Command ProcessingFront Controller DS has some classes for every (1) place to process the requests and call Command/Listener classes
Object ManagementModel/Controller/Handler: View store and manage the generated results
Display/View ManagementAll requests going to generate/access different output views/using the same views through FrontControllerServlet is called Display Management
Transaction ManagementBusinessDelegate module: code to start command-class logic to do/start view-entity
View ManagementBusinessDelegate module: code to start and send command-class logic to do/start view-entity, and to display front-end active on result: Task Management

Implementation

// FrontController pattern using Command pattern

// Command interface
public interface Command {
    String execute(HttpServletRequest req, HttpServletResponse res)
        throws Exception;
}

// Concrete commands
public class RegistrationCommand implements Command {
    public String execute(HttpServletRequest req, HttpServletResponse res)
        throws Exception {
        // registration logic
        return "registration_success.jsp";
    }
}

public class LoginCommand implements Command {
    public String execute(HttpServletRequest req, HttpServletResponse res)
        throws Exception {
        String uname = req.getParameter("uname");
        String pwd = req.getParameter("pwd");
        // validate credentials
        if (isValid(uname, pwd)) {
            return "home.jsp";
        }
        req.setAttribute("errorMsg", "Invalid Credentials");
        return "login.jsp";
    }
}

// CommandFactory
public class CommandFactory {
    private static Map<String, Command> commands = new HashMap<>();
    static {
        commands.put("/register", new RegistrationCommand());
        commands.put("/login", new LoginCommand());
        commands.put("/search", new SearchCommand());
    }

    public static Command getCommand(String path) {
        Command cmd = commands.get(path);
        if (cmd == null) throw new RuntimeException("No command for: " + path);
        return cmd;
    }
}

// FrontControllerServlet
@WebServlet("/*")
public class FrontControllerServlet extends HttpServlet {

    @Override
    public void doGet(HttpServletRequest req, HttpServletResponse res)
        throws ServletException, IOException {
        processRequest(req, res);
    }

    @Override
    public void doPost(HttpServletRequest req, HttpServletResponse res)
        throws ServletException, IOException {
        processRequest(req, res);
    }

    private void processRequest(HttpServletRequest req, HttpServletResponse res)
        throws ServletException, IOException {
        // 1. Log the request
        System.out.println("Request: " + req.getServletPath());

        try {
            // 2. Get the appropriate command
            Command command = CommandFactory.getCommand(req.getServletPath());

            // 3. Execute the command
            String viewPage = command.execute(req, res);

            // 4. Forward to the view
            RequestDispatcher rd = req.getRequestDispatcher(viewPage);
            rd.forward(req, res);

        } catch (Exception e) {
            req.setAttribute("errorMsg", e.getMessage());
            req.getRequestDispatcher("error.jsp").forward(req, res);
        }
    }
}
Modern Equivalents
  • Spring MVC DispatcherServlet: The ultimate Front Controller. All requests go through DispatcherServlet, which dispatches to @Controller methods based on @RequestMapping.
  • Struts ActionServlet: Earlier Front Controller implementation in Struts framework.
  • JAX-RS Application: REST-based Front Controller.
  • Front, JSP, and Servlet are designed based on Servlet 6.x, Tomcat 10.x+ (Jakarta namespace), not Servlet 4.x (javax namespace).
  • In MVC architecture layered app, FrontController is positioned between view comps and business delegate comp representing monitoring, controller and navigation logic. Controller means input/output/navigation management and monitoring.

Front Controller flow in our architecture

A to J Steps: (a) browser gives request to web application which first goes (b) to FrontController Servlet (via intercepting filter if any) (c) FrontControllerServlet receives the request and stores the form data to VO class obj (or reads parameters) (d) invoke the business delegate method by passing VO class obj (e) The FrontController Servlet used the command pattern to get handler method (code = d) (f) the command object finds the appropriate handler for the request (g) BusinessDelegate/Service processes the request (h) the result is returned to command to FrontControllerServlet (i) FrontController Maps the key to JSP page and uses same servlet functions to display output (j) presentation page is displayed from service/command/business management to client NOTE: Exception Map (the key JSP should not use same servlet functions for displaying output only for Error pages. The MVC pattern can be placed in this pattern by dispatching the error to error management view.)

Comparison Table

AspectIntercepting FilterView HelperFront Controller
TierPresentationPresentationPresentation
PurposePre/post processing of requests/responsesRemove Java code from JSP, use custom tagsSingle entry point for all requests
ComponentServlet FilterCustom JSP Tag + Tag HandlerSingle Servlet (DispatcherServlet)
ChainFilterChain (multiple filters in order)Tag Library (multiple tags)Command pattern (multiple handlers)
Modern equivalentSpring HandlerInterceptor, MiddlewareThymeleaf, React componentsSpring DispatcherServlet