Mapper Logo
.

2. Application Architecture

Application Architecture
figure 2.1 - MapperXML Application Architecture

2.1 ServletApp

The top component in a MapperXML application is the ServletApp. All requests go through the ServletApp. The ServletApp in turn, delegates the work of servicing the request to a ServletForm.

You will typically subclass com.taursys.servlet.ServletApp to build a new application. Use of the ServletApp, however, is not required for building a MapperXML applications. You can implement your own version of the ServletApp.

The core method of the ServletApp is the doGet method. This method also services requests for the doPost method. In the doGet method, the ServletApp inspects the request's path information to decide which ServletForm should handle the request. It then invokes the doGet method of the appropriate ServletForm. The ServletApp actually uses a ServletFormFactory to do much of this work,

The following code is an extract from the ServletApp's doGet method:

  public void doGet(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {
    // Determine the Presentation Manager
    try {
      ServletForm form = factory.createServletForm(request.getPathInfo());
      try {
        form.doGet(request, response);
      }
      catch (Exception ex) {
        throw new ServletException("Unhandled Exception in ServletForm: "
            + ex.getMessage(), ex);
      } finally {
        factory.recycle(form);
      }
    }
    catch (ServletFormNotFoundException ex) {
      // throw 404
      response.sendError(HttpServletResponse.SC_NOT_FOUND,
        "The requested ServletForm was not found.  If you typed the url, please "
        + "check to be sure it is correct.  It is also possible that the system "
        + "that provides this resource is temporarily unavailable.<br/><hr/>"
        + "Internal error message: " + ex.getMessage() + ").");
    }
  }
        

The core process is very simple. The ServletApp asks the ServletFormFactory for the appropriate ServletForm. If that cannot be found, a 404 response is sent. If found, the request is sent the the ServletForm's doGet method. If an Exception occurs in the ServletForm, a ServletException is thrown with the cause attached. Finally the ServletForm is recycled (more on recycling below).

2.2 ServletFormFactory

The ServletFormFactory creates and recycles ServletForms for an application. This class was designed to be used by a ServletApp. It will typically be setup in the init method of the ServletApp. Below is an example of typical usage:

        public class MyMainServlet extends ServletApp {

          public void init(ServletConfig config) throws ServletException {
            super.init(config);
            getFactory().addPackage("/","com.taursys.examples.simpleweb");
            getFactory().setDefaultFormName("com.taursys.examples.simpleweb.ShowHidePage");
            getFactory().setDefaultClassLoader(getClass().getClassLoader());
            // Set default logging
            Debug.setLoggerAdapter(new SimpleLogger(Debug.DEBUG));
          }
        }
        

The ServletApp invokes the ServletFormFactory's createServletForm method at the beginning of a request. This method returns a ServletForm based on the given url. This method will first see if there are any recycled forms in the servletForms pool. If so, it will remove that ServletForm from the pool and return it. If none are in the pool, it will create a new one.

When the request processing is complete the ServletApp invokes the ServletFormFactory's recycle method. The recycle method will put given servletForm back into pool if servletForm supports recycling.

2.3 Sharing Application Resources

Sharing resources among the ServletForms which make up an application is accomplished through some simple means. The basic approach is to Create the resource in the ServletApp and pass it to the ServletForms through the request object. Below is an example of sharing a database connection. The datasource is first created and initialized by the ServletApp:

  ...
  private OracleConnectionPoolDataSource dataSource;
  ...
  public void init(ServletConfig config) throws ServletException {
    ...
    try {
      dataSource = new OracleConnectionPoolDataSource();
      dataSource.setURL("jdbc:oracle:thin:@192.168.5.1:1521:ORCL");
      dataSource.setUser("librarian");
      dataSource.setPassword("shelves");
    } catch (Exception ex) {
      throw new ServletException("Cannot open database connection pool", ex);
    }
  }
        

Then the request is passed to ServletForms as an attribute in the request object:

  public void doGet(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {
    // Share dataSource with ServletForms
    request.setAttribute("dataSource", dataSource);
    super.doGet(request, response);
  }
        

Finally, the ServletForms access the shared resource in their initForm or openForm method:

  protected void initForm() throws java.lang.Exception {
    ...
    dao.setDataSource(
        (DataSource)getRequest().getAttribute("dataSource"));
    ...
  }
        
.