2017-06-20 47 views
0

我有一个类使用静态缓存,该静态缓存在类的所有实例之间共享。我希望能够在运行时设置缓存超时。使用命令行参数初始化静态缓存

提供一个具体的用例:我缓存从云存储中获取的值。我想在开发环境中比在prod中更快地刷新值。部署代码时,它会为与该环境相对应的配置文件提供参数。此配置文件可以包含缓存刷新时间的值。

public class Pipeline { 
    private static final LoadingCache<BlobId, Definitions> CACHE = 
     CacheBuilder.newBuilder() 
        .refreshAfterWrite(VALUE, TimeUnit.MINUTES) // <-- how do I set VALUE from a config file? 
        .build(
       new CacheLoader<BlobId, Definitions>() { 
        public Definitions load(BlobId key) throws Exception { 
         return DefinitionsLoader.load(key); 
        } 
       }); 
... 
} 

回答

0

在运行时动态加载不同的配置,你可以使用一个的.properties文件。在下面的示例中,我将属性文件加载到静态块中,但您也可以在初始化缓存的静态方法中实现逻辑。在他们的声明中初始化

https://docs.oracle.com/javase/tutorial/essential/environment/properties.html

private static final LoadingCache<BlobId, Definitions> CACHE; 
static { 
    Properties prop = new Properties(); 
    try { 
     prop.load(new FileInputStream("config.properties")); 
    } catch (IOException e) { 
     // handle exception 
    } 

    Long value = Long.parseLong(prop.getProperty("value", "5")); 
    CACHE = CacheBuilder.newBuilder() 
      .refreshAfterWrite(value, TimeUnit.MINUTES) 
      .build(new CacheLoader<Integer, Definitions>() { 
       public Definitions load(BlobId key) throws Exception { 
        return DefinitionsLoader.load(key); 
       } 
      }); 

} 
0

静态字段,你想要做的不是设计来进行参数设置。

此外,您的缓存加载不灵活。
如果明天你改变了主意,或者你想使用它们中的多个,你不能。
最后,它也是不可测试的。

如果要为缓存加载提供特定行为,最自然的方法是更改​​包含该字段的类的API。

您可以提供一个Pipeline构造函数,其参数long delayInMnToRefresh,您可以使用此参数设置缓存的刷新时间。

public Pipeline(int delayInMnToRefresh){ 
     CacheBuilder.newBuilder() 
        .refreshAfterWrite(delayInMnToRefresh, TimeUnit.MINUTES) 
     .... 
} 

如果你使用Spring,你可以用一个@Autowired构造函数,在运行时使用定义的属性时,Spring上下文加载:

@Autowired 
public Pipeline(@Value("${clould.cache.delayInMnToRefresh}") int delayInMnToRefresh){ 

     .... 
} 

随着这种方式,例如在定义的属性ENV:

clould.cache.delayInMnToRefresh = 5

而且在督促以这种方式定义,例如另一个属性:

clould.cache.delayInMnToRefresh = 15

当然,你可以实现无春(春季启动)这一要求,但你应该简单地执行更多的锅炉板任务(在调用此方法之前加载属性文件并处理环境概念)。