Using Spring to configure space

Spring can be used for configuration. Remember that this configuration is not interchangeable with other configuration options, due to reasons explained in the Terracotta configuration chapter.

Notice that this description is not complete, as there are several elements to configure and take into consideration. The easiest way of working with this, is probably to start with the sources for semispace-war, run the application with mvn jetty:run and examine the result(s).

Configure your webapp's beans for spring

As of Terracotta 3.2, you do not need to add anything particular in your tc-config.xml file.

The part you need, is the configuration in Spring's application-context.xml

	<!-- 
		The space itself. It may be distributed with terracotta, or
		be stand alone.
	-->
	<bean id="semispace" class="org.semispace.SemiSpace" scope="singleton"
		factory-method="retrieveSpace" />

The bean is used in the "normal" way, which is to say that it is either injected into a controller, or retrieved as a bean. Notice that you do not need to configure SemiSpace for Spring, as the other parts of the tc-config.xml covers those classes, even when they are instantiated with spring.

Exposing the web service in spring

The webservices configuration needs some more configuration in applicationContext.xml:

	<import resource="classpath:META-INF/cxf/cxf.xml" />
	<import resource="classpath:META-INF/cxf/cxf-extension-soap.xml" />
	<import resource="classpath:META-INF/cxf/cxf-servlet.xml" />

	<!--
		Definition of an unauthenticated space. Useful if you are
		within a firewall, or otherwise do not expose the
		service to the world. 
	-->
	<jaxws:endpoint id="space" implementor="#spaceproxy"
		address="/space" />

	<bean id="spaceproxy"
		class="org.semispace.ws.WsSpaceImpl">
		<property name="space">
			<ref bean="semispace" />
		</property>
	</bean>

Running the CXF servlet

In addition to setting up the spring controller servlet, you need to start the CXF servlet in web.xml:

  <servlet>
    <servlet-name>CXFServlet</servlet-name>
    <servlet-class>
        org.apache.cxf.transport.servlet.CXFServlet
    </servlet-class>
  </servlet>

  <servlet-mapping>
    <servlet-name>CXFServlet</servlet-name>
    <url-pattern>/services/*</url-pattern>
  </servlet-mapping>

This will interface with the CXF configuration you performed in applicationContext.xml.

JMX exposure

The application context for semispace-war is configured to expose statistical data to a JMX client. In order to avoid setting up alternate strategies for injection of the statistical object, the data is exposed through the SemiSpace instance itself. The problem is that it is difficult (but not impossible) to successfully use different wiring strategies together with terracotta. SemiSpace uses the easiest approach...

The following spring MBean configuration is used for exposing the statistic:

	<bean id="mbeanServer"
		class="org.springframework.jmx.support.MBeanServerFactoryBean">
		<!-- indicate to first look for a server -->
		<property name="locateExistingServerIfPossible" value="true" />
	</bean>
	<!--
		this bean needs to be eagerly pre-instantiated in order for the exporting to occur;
		this means that it must not be marked as lazily initialized
	-->
	<bean id="exporter"
		class="org.springframework.jmx.export.MBeanExporter">
		<property name="beans">
			<map>
				<entry key="bean:name=semiSpaceStatistics"
					value-ref="semispace" />
			</map>
		</property>
		<property name="server" ref="mbeanServer" />
	    <property name="assembler">
      	<bean class="org.springframework.jmx.export.assembler.MethodNameBasedMBeanInfoAssembler">
        	<property name="managedMethods">
          		<value>numberOfSpaceElements,numberOfBlockingRead,numberOfBlockingTake,numberOfMissedRead,numberOfMissedTake,numberOfNumberOfListeners,,numberOfRead,numberOfTake,numberOfWrite
			    </value>
        	</property>
      	</bean>
    </property>
	</bean>

You need either a container which registers and presents the JMX data, or SDK-1.6.

Examine JMX data with JConsole

With SDK-1.6 (or greater), you have jconsole available, and can connect to the bean for obtaining statistical information.