SpringCache源码分析(2) - 注解分析

SpringCache源码分析(2) - 注解分析

在上一篇中我们讲解了CacheManager和Cache源码,学会了怎样使用注解进行缓存,但是对于@CachePut、@Cacheable、@CacheEvict这些注解没有提及到,这一篇中我们将对Spring Cache中提供的注解操作做一个详细的说明。


@CachePut

@CachePut表示需要存放缓存数据,可以在类或方法上进行注解,如果注解在类上,表示这个类的所有方法都使用了@CachePut。这个注解可以设置哪些信息呢?我们直接看源代码,因为源代码能从根本说明一切。

/**
 * @CachePut可以注解类和方法,注解类时,表示整个类中的方法都注解了
 */	
@Target({ ElementType.METHOD, ElementType.TYPE })
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
public @interface CachePut {

	/**
	 * 定义存放的Cache名称,和下面的cacheNames一样
	 */
	@AliasFor("cacheNames")
	String[] value() default {};

	@AliasFor("value")
	String[] cacheNames() default {};

	/**
     * 为缓存值定义的key,默认为"",表示所有的参数都加入到key的生成中(使用默认的keyGenerator)
	 */
	String key() default "";

	/**
     * 可以使用keyGenerator来自定义key的生成,但是keyGenerator和key是排它性的,也就是说key和keyGenerator只能定义其中一个
	 */
	String keyGenerator() default "";

	/**
     * 指定设置特定的cacheManager,与cacheResolver也是排它性的。
	 * {@link org.springframework.cache.CacheManager}
	 */
	String cacheManager() default "";

	/**
     * 自定义cacheResolver
	 * {@link org.springframework.cache.interceptor.CacheResolver}
	 */
	String cacheResolver() default "";

	/**
     * 定义缓存被存放的条件,只有满足条件的方法返回值才能被存放。默认为"",也意味着方法的结果都可以被缓存。
	 */
	String condition() default "";

	/**
     * unless是在方法调用后判断是否需要进行缓存更新,如果满足unless条件就不缓存。unless具有否决权!
	 */
	String unless() default "";

}
```	

----------


### @Cacheable

@Cacheable表示从缓存中取数据,如果缓存中没有数据则执行方法,并将方法返回的结果存入到缓存中,以便下次直接从缓存中获取。@Cacheable可以在类或方法上进行注解,如果注解在类上,表示这个类的所有方法都使用了@Cacheable。由于@Cacheable和@CachePut的定义一样,就不多说明了。

@Target({ElementType.METHOD, ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Inherited @Documented public @interface Cacheable {

@AliasFor("cacheNames")
String[] value() default {};

@AliasFor("value")
String[] cacheNames() default {};

String key() default "";

String keyGenerator() default "";

String cacheManager() default "";

String cacheResolver() default "";

String condition() default "";

String unless() default "";

}


----------

### @CacheEvict

@CacheEvit表示从缓存中删除数据。和@CachePut、@Cacheable的定义基本一样,只有2个参数定义不同,allEntries和beforeInvocation。allEntries表示是否删除指定Cache名称中所有的缓存数据。beforeInvocation表示是否在方法执行前删除缓存数据,因为方法内部可能会出现异常,如果beforeInvocation=false,方法内出现异常,缓存中的数据是不会被删除的。

@Target({ElementType.METHOD, ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Inherited @Documented public @interface CacheEvict {

@AliasFor("cacheNames")
String[] value() default {};

@AliasFor("value")
String[] cacheNames() default {};

String key() default "";

String keyGenerator() default "";

String cacheManager() default "";

String cacheResolver() default "";

String condition() default "";

/**
 * 表示是否删除缓存中所有数据,默认为false,只会删除与key关联的那个缓存数据
 */
boolean allEntries() default false;

/**
 * 表示是否在方法调用之前删除数据,默认为false,表示缓存删除操作是在方法调用之后的
 */
boolean beforeInvocation() default false;

}



----------

### @Caching

@Caching是一个组合式的注解,可以组合配置@CachePut、@Cacheable、@CacheEvict集合,也可以在类或方法上进行注解。

@Target({ElementType.METHOD, ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Inherited @Documented public @interface Caching {

Cacheable[] cacheable() default {};

CachePut[] put() default {};

CacheEvict[] evict() default {};

}


----------

了解了@CachePut、@Cacheable、@CacheEvict这些注解的详细使用,那么,接下来我有一个疑惑了,这些注解到底是怎么作用到配置的方法上的呢? 怎么能够说明一个执行方法就使用了这些注解呢?对,这些注解肯定需要被解析成操作对象!那么,@CachePut、@Cacheable、@CacheEvict会被怎么解析呢? 这些问题我们在下一篇中做详细的分析。

猜你喜欢

转载自my.oschina.net/xiaoqiyiye/blog/1624330