创建普通缓存很简单,但是如果数据的数据结构很复杂,我们需要一个Cache来缓存。
在云原生应用开发中,微服务对于某些主数据是相互依赖的。获取信息意味着发送HTTP请求,当客户端微服务非常频繁地需要数据并且数据源是另一个微服务时,必须进行非常频繁的HTTP请求。这会导致客户端微服务中的处理延迟。由于这些原因,将主数据缓存在不经常更改的客户端微服务中是有意义的。虽然这种实现不仅适用于云原生开发中的微服务,而且可以用于任何类型的应用程序。
在这篇文章中,我将展示如何实现缓存的缓存。缓存的缓存是一个通用的番石榴缓存,其中键是字符串,值是其他番石榴缓存。这些作为值的番石榴缓存也有键值对。键和值可以是任何类型。这里缓存的缓存是 CacheManager 中的 cacheMap。内部缓存定义为 Cache<K,V>。这就是为什么缓存管理器是通用的,可以用来保存任何类型的键值对。 CacheManager 中的 getEntityCache() 方法从 cacheMap 中检索缓存。如果给定 entityId 的缓存不存在,则创建它并将其添加到 cacheMap 然后返回。
import com.google.common.cache.Cache;
import com.google.common.cache.CacheBuilder;
/** manages a set of caches where each instance of cache belongs to exactly one entity=manager
* @param <K> - type of key
* @param <V> - type of cache object
*/
public class **CacheManager****<****K****,****V****>** {
public static final int maxSize = 1024;
protected final Cache<String , Cache<K,V>> cacheMap;
private boolean isWeekKeys;
public CacheManager() { this(false);}
public CacheManager(boolean isWeekKeys) { this. isWeekKeys = isWeekKeys ;}
/** returns a user/manager specific instance of cache
* @param entityId user/manager
*/
public Cache<K,V> getEntityCache(String entityId) {
Cache<K,V> entityCache = cacheMap.getIfpresent( entityId );
if( entityCache == null) {
entityId = entityId.intern() //do not remove inturn()
synchronized(entityId) {
entityCache = cacheMap.getIfPresent(entityId);
if( entityCache == null ) {
final CacheBuilder builder = CacheBuilder.newbuilder().maximumsize(256);
if(isWeekKeys) {
builder.weakKeys();
}
entityCache = builder.build();
cacheMap.put(entityId, entityCache);
}
}
}
return entityCache;
}
}
现在我们将使用这个通用的 CacheManager 来实现一个 EmployeeCacheManager。 EmployeeCacheManager 代表组织中的经理列表。缓存中的每个经理都拥有为他们工作的员工列表。管理者由缓存的缓存的键表示,它是字符串,员工是缓存的缓存的值。内部缓存(员工)中的每个元素都由一个 Sting 键表示,该键是employeeId,内部缓存的值是员工对象。
import com.google.common.cache.Cache;
import EmployeeCacheManager.Employee;
public class **EmployeeCacheManager** extends CacheManager<String, Employee> {
public String getEmployeeAddress(String managerId, String employeeId) {
Cache< String, Employee > employeeCache = getEntityCache(managerId);
Employee employee = getEmployee(employeeCache, employeeId);
String address = getEmployeeAddress(employee);
return address;
}
public void setEmployeeAddress(String managerId, String employeeId, String address) {
Cache< String, Employee > employeeCache = getEntityCache(managerId);
Employee employee = getEmployee(employeeCache, employeeId);
setEmployeeAddress(employee, address);
}
public Employee getEmployee(Cache< String, Employee > employeeCache,
String employeeId) {
Employee employee = employeeCache.getIfPresent( employeeId );
if( employee == null) {
synchronized( employee ) {
employee = employeeCache.getIfPresent( employeeId );
if( employee == null) {
employee = new Employee(employeeId);
employeeCache.put( employeeId , employee);
}
}
}
return employee;
}
public String getEmployeeAddress(Employee employee) {
return employee.getAddress();
}
public void setEmployeeAddress( Employee employee, String address ) {
employee.setAddress(address);
}
public class **Employee** {
String name;
String address;
String id;
public class Employee(id) { this.id = id;}
public String getName() {return this.name;}
public String getAddress() {return this.address;}
public String getId() {this.id;}
public void setName(String name) {this.name = name;}
public void setAddress(String address) {this.address = address;}
}
}
此类创建 EmployeeCacheManager 的一个实例。
public class **EmployeeCachecreator** {
public static void main(String[] args) {
EmployeeCacheManager cacheManager = new EmployeeCacheManager();
cacheManager.setEmployeeAddres("M111", "E111", "adress");
String address = cacheManager.getEmployeeAddres("M111", "E111");
}
}
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://www.cloudnativemaster.com/post/how-to-create-cache-of-caches-using-google-guava-cache
内容来源于网络,如有侵权,请联系作者删除!