spring-context提供了Cache集成抽象組件方式, 如: CacheManager接口、 Cache接口, @Cacheable 、 @EnableCaching 等。java
spring-context-support則提供了多種具體緩存實現。git
key自定義策略是指: github
@Cacheable(value="users", key="#id") public User find(Integer id) { return null; } @Cacheable(value="users", key="#p0") public User find(Integer id) { return null; } @Cacheable(value="users", key="#user.id") public User find(User user) { return null; } @Cacheable(value="users", key="#p0.id") public User find(User user) { return null; }
屬性名稱spring |
描述數組 |
示例緩存 |
methodNameless |
當前方法名ide |
#root.methodNamespring-boot |
method測試 |
當前方法 |
#root.method.name |
target |
當前被調用的對象 |
#root.target |
targetClass |
當前被調用的對象的class |
#root.targetClass |
args |
當前方法參數組成的數組 |
#root.args[0] |
caches |
當前被調用的方法使用的Cache |
#root.caches[0].name |
當要使用root對象的屬性做爲key時咱們也能夠將「#root」省略,由於Spring默認使用的就是root對象的屬性。
@Cacheable(value={"users", "xxx"}, key="caches[1].name") public User find(User user) { return null; }
本文以CaffeineCache接入爲例。
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-cache</artifactId> </dependency> <dependency> <groupId>com.github.ben-manes.caffeine</groupId> <artifactId>caffeine</artifactId> </dependency>
import org.springframework.cache.CacheManager; import org.springframework.cache.caffeine.CaffeineCacheManager; import com.github.benmanes.caffeine.cache.CacheLoader; import com.github.benmanes.caffeine.cache.Caffeine; @Bean public CacheManager cacheManager() { CaffeineCacheManager cacheManager = new CaffeineCacheManager(); Caffeine caffeine = Caffeine.newBuilder() // cache的初始容量值 .initialCapacity(100) // maximumSize用來控制cache的最大緩存數量,maximumSize和maximumWeight不能夠同時使用, .maximumSize(200).expireAfterWrite(5, TimeUnit.SECONDS); // 使用refreshAfterWrite必需要設置cacheLoader,可是不能用,由於每一個cacheLoader要有差別 //.refreshAfterWrite(2, TimeUnit.SECONDS); // cacheManager.setCacheLoader(cacheLoader()); // cacheManager.setAllowNullValues(false); cacheManager.setCaffeine(caffeine); cacheManager.setCacheNames(Arrays.asList("activityCache", "propCache", "eventCache")); return cacheManager; } /** * 必需要指定這個Bean,refreshAfterWrite這個配置屬性才生效 */ private CacheLoader<Object, Object> cacheLoader() { CacheLoader<Object, Object> cacheLoader = new CacheLoader<Object, Object>() { @Override public Object load(Object key) throws Exception { return null; } // 重寫這個方法將oldValue值返回,進而刷新緩存 @Override public Object reload(Object key, Object oldValue) throws Exception { return oldValue; } }; return cacheLoader; }
@Cacheable(value = "activityCache", key = "#actId" , condition ="#actId != '' ", unless = "#result == null") public Activity findById(String actId) { return mongoTemplate.findById(actId, Activity.class); }
@Cacheable 不能配置 condition = "#result != null" ,由於這個註解在進入方法前去檢測condition,而這時尚未result,確定爲null;形成一直不能緩存的狀況。-----測試正確
想要達到參數爲空和返回值爲空不緩存(後者會出現緩存穿透的現象)當設置cacheManager.setAllowNullValues(false)時<默認true>,targetMethod返回null直接報錯:
因此只能使用unless :