10-1. Cluster Object State Using Terracotta
You want to share object state across multiple virtual machines. For example, you'd like to be able to
load all the cities in the United States into memory for faster lookup. Any other nodes in the cluster that
need access to those objects should be able to get them from the cache, and not reload them.
You can use Terracotta to build such a solution. Terracotta works like many other clustered caches,
except that it, in addition to being a good Hibernate clustered cache, also works as a mostly
unnoticeable engine to enable API-free shared state across a cluster.
How It Works
Terracotta works as a JVM agent that monitors the object graph of a given JVM instance and ensures
replication of object state across a cluster. It does this by deferring to a configuration file in which you
specify which classes, methods, and fields should be clustered.
It does this for any object in the JVM, not just Hibernate entities or session entries, or objects
otherwise updated by some caching API.
It's as simple as using a property on an object or updating a shared variable on an object. Instantly,
across as many nodes as you want, that updated state is reflected in reads to that property on other
To illustrate it, it's best to imagine a threaded application. Imagine a shared integer value in a
threaded application. Three threads increment the value of an integer in lockstep, delayed every five
seconds. Each thread acquires the lock, increments the integer, and then releases the lock. Other threads
see the updated value and print it out. Eventually, as this goes on, the number rises and rises until some
condition is met (you exit the program, for example.) to stop it. This is a very effective example of where
Java's support for threading is useful, because it guarantees state through concurrent access. Now,
imagine perhaps that you have that same integer, and each time a server hits a page, that integer is
accessed and incremented. This page is deployed across several nodes, so that hitting the page on each
of the nodes causes the integer, and thus the state, to change. Other servers see the new value on refresh,
even though the change was last made on another server. The state is visible to all nodes in the cluster,
and at the same times as the state would be visible to threads. This is what Terracotta does: it clusters
object state. On the whole, your code will remain simple code (perhaps multithreaded in nature) that
works across multiple VMs.
This is different than most clustered caches today because it has no visible API, and because it's far
more efficient in conveying the changed state to nodes across the cluster. Most systems use some sort of
Java serialization or broadcast mechanism, wherein each other node is given the entire object, or object
graph, that's changed, regardless of whether they even they need to be aware of the new state. Terracotta
does it differently: it deltas the memory of the object graphs itself and synchronizes other nodes in the
cluster as they need a consistent view of the object state. Succinctly, it can do something tantamount to
transmitting just one updated variable in an object, and not the entire object.
Deploying a Simple Example with Terracotta
You want to deploy Terracotta, and want to see what a simple application looks like, without Spring.
We will walk through an example of how to do this, without using Spring. The example is a simple
application that prompts for input and uses a service class that in turn keeps state. We cluster this state