Bootstrapping GemFire from a Java Servlet Container
search cancel

Bootstrapping GemFire from a Java Servlet Container

book

Article ID: 294175

calendar_today

Updated On:

Products

VMware Tanzu Gemfire

Issue/Introduction

This article shows you a way to bootstrap GemFire from a Java Servlet container.


Environment


Cause

Servlet instances are created or reused for each HTTP access when you have to keep a GemFire instance as a long-running service. You need to instantiate a GemFire cache when initializing your Servlet container. To establish this, you can leverage ServletContextListener to instantiate a GemFire cache and set the reference to the region object into ServletContext. Then, you can execute each region operation like gets or puts in your Servlet by getting a reference to the region via ServletContext.

Resolution

Follow the following steps to bootstrap GemFire from a Java Servlet container and execute region operations from your Servlet:

  1. Prepare web.xml to set ServletContextListener with your Servlet. Optionally, you can set some context parameters to specify paths to gemfire.properties, cache.xml and some other things (in this case, you should put your gemfire.properties and cache.xml under /WEB-INF directories with exploded war style).
    <?xml version="1.0" encoding="UTF-8"?>
    <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
     xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
     version="3.1">
    
     <display-name>MyServeltAppsOnJetty</display-name>
    
     <!-- specify your ServletContextListener class -->
     <listener>
     <listener-class>io.pivotal.gemfire.GemFireLoaderListener</listener-class>
     </listener>
    
     <!-- set your Servlet -->
     <servlet>
     <servlet-name>SessionServlet</servlet-name>
     <servlet-class>io.pivotal.gemfire.SessionServlet</servlet-class>
     </servlet>
    
     <servlet-mapping>
     <servlet-name>SessionServlet</servlet-name>
     <url-pattern>/SessionServlet</url-pattern>
     </servlet-mapping>
    
     <!-- set context parameters for specifying paths for gemfire.properties and cache.xml (optional) -->
     <context-param>
     <param-name>gemfirePropsLocation</param-name>
     <param-value>/WEB-INF/gemfire.properties</param-value>
     </context-param>
    
     <context-param>
     <param-name>gemfireCacheConfigLocation</param-name>
     <param-value>/WEB-INF/cache.xml</param-value>
     </context-param>
     </web-app>
  2. Put required GemFire Jar under /WEB-INF/lib in your war. Also, prepare gemfire.properties and cache.xml if required.
  3. Implement your region initializer class using ServletContextListener interface like the following example. In this example, it gets paths to gemfire.properties and cache.xml via context parameters in web.xml.
    package io.pivotal.gemfire;
    
    import com.gemstone.gemfire.cache.Cache;
    import com.gemstone.gemfire.cache.CacheFactory;
    
    import javax.servlet.ServletContext;
    import javax.servlet.ServletContextEvent;
    import javax.servlet.ServletContextListener;
    
    public class GemFireLoaderListener implements ServletContextListener {
    
     public static final String GEMFIRE_PROPERTIES = "gemfirePropsLocation";
     public static final String GEMFIRE_CACHE_XML = "gemfireCacheConfigLocation";
     public static final String REGION_ATTRIBUTE = "regionAttribute";
    
     public void contextInitialized(ServletContextEvent event) {
     ServletContext context = event.getServletContext();
     System.setProperty("gemfirePropertyFile", context.getRealPath(context.getInitParameter(GEMFIRE_PROPERTIES)));
     Cache cache = new CacheFactory()
     .set("name", "ServletCache")
     .set("cache-xml-file", context.getRealPath(context.getInitParameter(GEMFIRE_CACHE_XML)))
     .create();
     context.setAttribute(REGION_ATTRIBUTE, cache.getRegion("ServletRegion"));
     }
    
     public void contextDestroyed(ServletContextEvent event) {
     ServletContext context = event.getServletContext();
     // implement something if you need (e.g. closing your cache)
     }
    }
  4. Compile your ServletContextListener class and put it under /WEB-INF/classes in your war. The Java IDE may put them there automatically if you use Java IDE to develop your Web applications.
  5. You can get access to your regions via ServletContext in the do*** methods of your Servlet like the following:
    public void doPost (HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
     Region<String,Integer> region = (Region) getServletContext().getAttribute(GemFireLoaderListener.REGION_ATTRIBUTE);
     HttpSession session = request.getSession(true);
    Integer cnt = region.get(session.getId());
     cnt++;
     region.put(session.getId(),cnt);
     :


Additional Information

Environment

  • Pivotal GemFire any version (tested with version 8.2.1)
  • Servlet container any implementations (tested with Jetty 9.3.12)
  • Servlet API Version 2.3 or above (tested with version 3.1)

Bootstrapping GemFire from an Application Server- This is the original article related to this topic. While slightly old in terms of API usage, it may still prove useful for more complex use cases.