0

The example at https://spring.io/guides/gs/caching-gemfire/ shows that if there is a cache miss, we have to fetch the data from a server and store in the cache.

Is this an example of Gemfire running as the Gemfire server or is it a Gemfire client? I thought a client would automatically fetch the data from a Server if there is a cache miss. If that is the case, would there ever be a cache miss for the client?

Regards,
Yash

Yash
  • 946
  • 1
  • 13
  • 28

1 Answers1

2

First, I think you are missing the point of the core Spring Framework's Cache Abstraction. I encourage you to read more about the Cache Abstraction's intended purpose here.

In a nutshell, if one of your application objects makes a call to some "external", "expensive" service to access a resource, then caching maybe applicable, especially if the inputs passed result in the exact same output every single time.

So, for a moment, lets imagine your application makes a call to the Geocoding API in the Google Maps API to translate a addresses and (the inverse,) latitude/longitude coordinates.

You might have a application Spring @Service component like so...

@Service("AddressService")
class MyApplicationAddressService {

  @Autowired
  private GoogleGeocodingApiDao googleGeocodingApiDao;

  @Cacheable("Address")
  public Address getAddressFor(Point location) {
    return googleGeocodingApiDao.convert(location);
  }
}

@Region("Address")
class Address {

  private Point location;

  private State state;

  private String street;
  private String city;
  private String zipCode;

  ...
}

Clearly, given a latitude/longitude (input), it should produce the same Address (result) everytime. Also, since making a (network) call to an external API like Google's Geocoding service can be very expensive, to both access the resource and perform the conversion, then this type of service call is a perfect candidate for use to cache in our application.

Among many other caching providers (e.g. EhCache, Hazelcaset, Redis, etc), you can, of course, use Pivotal GemFire, or the open source alternative, Apache Geode to back Spring's Caching Abstraction.

In your Pivotal GemFire/Apache Geode setup, you can of course use either the peer-to-peer (P2P) or client/server topology, it doesn't really matter, and GemFire/Geode will do the right thing, once "called upon".

But, the Spring Cache Abstraction documentation states, when you make a call to one of your application components methods (e.g. getAddressFor(:Point)) that support caching (with @Cacheable) the interceptor will first "consult" the cache before making the method call. If the value is present in the cache, then that value is returned and the "expensive" method call (e.g. getAddressFor(:Point)) will not be invoked.

However, if there is a cache miss, then Spring will proceed in invoking the method, and upon successful return from the method invocation, cache the result of the call in the backing cache provider (such as GemFire/Geode) so that the next time the method call is invoked with the same input, the cached value will be returned.

Now, if your application is using the client/sever topology, then of course, the client cache will forward the request onto the server if...

  1. The corresponding client Region is a PROXY, or...

  2. The corresponding client Region is a CACHING_PROXY, and the client's local client-side Region does not contain the requested Point for the Address.

I encourage you to read more about different client Region data management policies here.

To see another working example of Spring's Caching Abstraction backed by Pivotal GemFire in Action, have a look at...

caching-example

I used this example in my SpringOne-2015 talk to explain caching with GemFire/Geode as the caching provider. This particular example makes a external request to a REST API to get the "Quote of the Day".

Hope this helps!

Cheers, John

Community
  • 1
  • 1
John Blum
  • 7,381
  • 1
  • 20
  • 30
  • I am aware of Caching Abstraction. My question is: If the getAddressFor function is running inside a client program in a client/server deployment model of Gemfire, will the googleGeocodingApiDao.convert ever be called? I believe it will not be, because if there is a cache miss, the cache request will be forwarded to the server. The googleGeocodingApiDao will never be given the chance to fetch the data. Kindly correct me if I am wrong. – Yash Jul 30 '16 at 21:04
  • Whether or not you are using client/server or p2p, the behavior is the same. Spring will first "ask" the caching provider (i.e. GemFire) if the input has been cached.. The client, if a `PROXY` (or even a `CACHING_PROXY`), will immediately forward the request to the Server. If the corresponding Server-side Region (e.g. "Address") does not contain a entry, then GemFire will return **null**, and Spring's Cache abstraction will flag the **null** as a "cache miss" and "proceed" to invoke the method, resulting in a invocation to `googleGeocodingApiDao.convert(:Point)`. The result of that call... – John Blum Aug 01 '16 at 17:28
  • … will be cached, which means the cache client (again, a `PROXY`) will forward the value to the Server Region ("Address") to be stored. Subsequent calls to the `MyApplicationAddressService.getAddressFor(:Point)`, given the same coordinates, will lead to the result being pulled out of GemFire, and then the `googleGeocodingApiDao.convert(:Point)` method will **not** be called. – John Blum Aug 01 '16 at 17:28