Cache

using cache in your project

在用Cache之前 , 最好先搞清楚整個Domain logic是否穩定 , and清楚自己在作什麼

Simplest Cache

Use Map<K,V>

Origional

public class UserManager {

  private UserRepo repo;

  public User getUser(String userId){
    return repo.getUser(userId);
  }


}

Add Cache

public class UserManager {

  private UserRepo repo;
  private Map<String,User> userCache;
  ...
  public User getUser(String userId){
    User temp = userCache.get(userId);
    if(temp != null){
       return temp;
    } else{
       return repo.getUser(userId);
    }
  }
}

Why use framework?

  • eviction policies
  • max size limit
  • persistent store
  • weak references keys
  • statistics

Why use framework

http://java.dzone.com/articles/caching-best-practices

Cache Frameworks

  • JCache
  • Ehcache
  • Spring Cache
  • Guava
  • ....

Example

Guava

 

LoadingCache<Key, Graph> graphs = CacheBuilder.newBuilder()
       .maximumSize(1000)
       .build(
           new CacheLoader<Key, Graph>() {
             public Graph load(Key key) throws AnyException {
               return createExpensiveGraph(key);
             }
           });

...
try {
  return graphs.get(key);
} catch (ExecutionException e) {
  throw new OtherException(e.getCause());
}

Guava

 

@Repository
public class UserManager {
 
    @Autowired
    private UserCacheLoader cacheLoader;
    private LoadingCache<String, User> users;
 
    @PostConstruct
    void init() {
			users = CacheBuilder.newBuilder()
                .maximumSize(1000)
                .expireAfterWrite(1, TimeUnit.HOURS)
                .build(cacheLoader);
    }
 
    public User getUser(String userId) throws ExecutionException {
        return users.get(userId);
    }

    public void remove(String userId) {
		users.invalidate(userId);
    }
 
    public void removeAll() {
		users.invalidateAll();
    }
}

Guava

@Component
public class UserCacheLoader extends CacheLoader<String, User> {
 
    @Autowired
    private AuthUserManager userManager;
 
    @Override
    public User load(String key) throws Exception {
        return userManager.getUser(key);
    }
}

Spring Cache

 

@Repository
public class UserManager {

  private UserRepo repo;
  
  @Cacheable("users")
  public User getUser(String userId){
       return repo.getUser(userId);
  }

}

Spring Cache

 

@EnableCaching
@configuration
public class Application {

    @Bean
    public CacheManager cacheManager() {
        return new ConcurrentMapCacheManager("users");
    }

}

EhCache

 

@Repository
public class UserManager {

  private UserRepo repo;
  
  @Cacheable("users")
  public User getUser(String userId){
	return repo.getUser(userId);
  }
  
  @CacheEvict(value = "users", allEntries = true)
  public void updateTotpCode(String code, int userSid) {
        repo.update(code, userSid);
  }
  
}

EhCache

 

@Configuration
@EnableCaching
public class SecurityCacheConfig {

    @Autowired
    private net.sf.ehcache.CacheManager cacheManager;

    private int userTimeToIdleSeconds = 600;
    private int userTimeToLiveSeconds = 600;

    //Spring-ehcache
    @PostConstruct
    public void setUpCacheManager() {
        CacheConfiguration userConfig = 
            util.buildConf("users")
                .timeToIdleSeconds(userTimeToIdleSeconds)
                .timeToLiveSeconds(userTimeToLiveSeconds);
        Cache authUserCache = new Cache(userConfig);
        cacheManager.addCache(authUserCache);
    }

}

If your project has dependency on security , you need to use carefully.

Because crowd library has use ehcache 

At last

  • Use carefully

  • Know what you are doing

Made with Slides.com