Introduktion till Ehcache

1. Översikt

I den här artikeln presenterar vi Ehcache, ett allmänt använt Java-baserat cache-minne med öppen källkod. Den har minne och diskbutiker, lyssnare, cacheladdare, RESTful och SOAP API: er och andra mycket användbara funktioner.

För att visa hur cachning kan optimera vår applikation skapar vi en enkel metod som beräknar kvadratvärden för angivna nummer. Vid varje samtal kommer metoden att anropa metoden CalcSquareOfNumber (int number) och skriva ut informationsmeddelande till konsolen.

Med det här enkla exemplet vill vi visa att beräkning av kvadratvärden endast görs en gång, och vartannat samtal med samma ingångsvärde returnerar resultatet från cachen.

Det är viktigt att lägga märke till att vi fokuserar helt på själva Ehcache (utan vår); om du vill se hur Ehcache fungerar med Spring, ta en titt på läs den här artikeln.

2. Maven Beroenden

För att kunna använda Ehcache måste vi lägga till detta Maven-beroende:

 org.ehcache ehcache 3.1.3 

Den senaste versionen av Ehcache-artefakten finns här.

3. Cache-konfiguration

Ehcache kan konfigureras på två sätt:

  • Det första sättet är genom Java POJO där alla konfigurationsparametrar konfigureras via Ehcache API
  • Det andra sättet är konfiguration genom XML-fil där vi kan konfigurera Ehcache enligt den angivna schemadefinitionen

I den här artikeln visar vi båda metoderna - Java såväl som XML-konfiguration.

3.1. Java-konfiguration

Detta underavsnitt visar hur enkelt det är att konfigurera Ehcache med POJO. Vi kommer också att skapa en hjälpklass för enklare cache-konfiguration och tillgänglighet:

public class CacheHelper { private CacheManager cacheManager; private Cache squareNumberCache; public CacheHelper() { cacheManager = CacheManagerBuilder .newCacheManagerBuilder().build(); cacheManager.init(); squareNumberCache = cacheManager .createCache("squaredNumber", CacheConfigurationBuilder .newCacheConfigurationBuilder( Integer.class, Integer.class, ResourcePoolsBuilder.heap(10))); } public Cache getSquareNumberCacheFromCacheManager() { return cacheManager.getCache("squaredNumber", Integer.class, Integer.class); } // standard getters and setters }

För att initialisera vår cache måste vi först definiera Ehcache CacheManager- objekt. I det här exemplet skapar vi ett standardcache squaredNumber ” med newCacheManagerBuilder () API .

Cachen cappar helt enkelt heltalstangenter till heltalvärden .

Lägg märke till hur vi, innan vi börjar använda den definierade cachen, måste initiera CacheManager- objektet med init () -metoden.

Slutligen, för att få vår cache, kan vi bara använda getCache () API med det angivna namnet, nyckeln och värdetyperna för vår cache.

Med de få raderna skapade vi vår första cache som nu är tillgänglig för vår applikation.

3.2. XML-konfiguration

Konfigurationsobjektet från underavsnitt 3.1. är lika med att använda denna XML-konfiguration:

 java.lang.Integer java.lang.Integer 10 

Och för att inkludera denna cache i vår Java-applikation måste vi läsa XML-konfigurationsfilen i Java:

URL myUrl = getClass().getResource(xmlFile); XmlConfiguration xmlConfig = new XmlConfiguration(myUrl); CacheManager myCacheManager = CacheManagerBuilder .newCacheManager(xmlConfig);

4. Ehcache-test

I avsnitt 3. visade vi hur du kan definiera enkel cache för dina ändamål. För att visa att cachning faktiskt fungerar skapar vi SquaredCalculator- klassen som beräknar kvadratvärdet för den angivna ingången och lagrar beräknat värde i en cache.

Om cache redan innehåller beräknat värde returnerar vi naturligtvis cachat värde och undviker onödiga beräkningar:

public class SquaredCalculator { private CacheHelper cache; public int getSquareValueOfNumber(int input) { if (cache.getSquareNumberCache().containsKey(input)) { return cache.getSquareNumberCache().get(input); } System.out.println("Calculating square value of " + input + " and caching result."); int squaredValue = (int) Math.pow(input, 2); cache.getSquareNumberCache().put(input, squaredValue); return squaredValue; } //standard getters and setters; }

För att slutföra vårt testscenario behöver vi också koden som beräknar kvadratvärden:

@Test public void whenCalculatingSquareValueAgain_thenCacheHasAllValues() { for (int i = 10; i < 15; i++) { assertFalse(cacheHelper.getSquareNumberCache().containsKey(i)); System.out.println("Square value of " + i + " is: " + squaredCalculator.getSquareValueOfNumber(i) + "\n"); } for (int i = 10; i < 15; i++) { assertTrue(cacheHelper.getSquareNumberCache().containsKey(i)); System.out.println("Square value of " + i + " is: " + squaredCalculator.getSquareValueOfNumber(i) + "\n"); } }

Om vi ​​kör vårt test får vi detta resultat i vår konsol:

Calculating square value of 10 and caching result. Square value of 10 is: 100 Calculating square value of 11 and caching result. Square value of 11 is: 121 Calculating square value of 12 and caching result. Square value of 12 is: 144 Calculating square value of 13 and caching result. Square value of 13 is: 169 Calculating square value of 14 and caching result. Square value of 14 is: 196 Square value of 10 is: 100 Square value of 11 is: 121 Square value of 12 is: 144 Square value of 13 is: 169 Square value of 14 is: 196

Som du kan märka, beräkna () metoden var att göra beräkningar endast vid första samtalet. Vid det andra samtalet hittades alla värden i cachen och returnerades från den.

5. Andra Ehcache-konfigurationsalternativ

När vi skapade vår cache i föregående exempel var det en enkel cache utan några speciella alternativ. Det här avsnittet visar andra alternativ som är användbara vid skapande av cache.

5.1. Diskuthållighet

Om det finns för många värden att lagra i cachen kan vi lagra några av dessa värden på hårddisken.

PersistentCacheManager persistentCacheManager = CacheManagerBuilder.newCacheManagerBuilder() .with(CacheManagerBuilder.persistence(getStoragePath() + File.separator + "squaredValue")) .withCache("persistent-cache", CacheConfigurationBuilder .newCacheConfigurationBuilder(Integer.class, Integer.class, ResourcePoolsBuilder.newResourcePoolsBuilder() .heap(10, EntryUnit.ENTRIES) .disk(10, MemoryUnit.MB, true)) ) .build(true); persistentCacheManager.close();

Istället för standard CacheManager använder vi nu PersistentCacheManager som kommer att bestå alla värden som inte kan sparas i minnet.

Från konfigurationen kan vi se att cache sparar 10 element i minnet och det kommer att allokera 10 MB på hårddisken för beständighet.

5.2. Data upphör att gälla

Om vi ​​cachar mycket data är det naturligt att vi sparar cachad data under en viss tid så att vi kan undvika stor minnesanvändning.

Ehcache styr datafriskhet genom utgångsgränssnitt :

CacheConfiguration cacheConfiguration = CacheConfigurationBuilder .newCacheConfigurationBuilder(Integer.class, Integer.class, ResourcePoolsBuilder.heap(100)) .withExpiry(Expirations.timeToLiveExpiration(Duration.of(60, TimeUnit.SECONDS))).build();

I denna cache kommer all data att leva i 60 sekunder och efter den tiden raderas den från minnet.

6. Sammanfattning

I den här artikeln visade vi hur man använder enkel Ehcache-cachning i ett Java-program.

I vårt exempel såg vi att även en enkelt konfigurerad cache kan spara många onödiga åtgärder. Vi visade också att vi kan konfigurera cachar via POJOs och XML och att Ehcache har ganska bra funktioner - som uthållighet och utgångsdatum.

Som alltid finns koden från den här artikeln på GitHub.