springboot单例注入——由刷新缓存引发的思考

在@service注解的 服务serviceimpl里面,有个缓存想开后门接口刷新,这个时候想把它写成静态,又担心如果是多例就会导致刷新无用。

定义的google包提供的缓存代码如下:

/**
* 本类的业务缓存,降低io
*/
public static Cache<String, Object> businessCache = CacheBuilder.newBuilder().expireAfterWrite(24, TimeUnit.HOURS).build();

对应的controller接口:

/**
 * 刷新指定统计缓存接口
 * @return
 */
@RequestMapping("/refreshCache")
public RemoteResponse<Boolean> refreshCache() {
    OrderTransactionServiceImpl.businessCache.invalidateAll();
    return RemoteResponse.success();
}

此时会有疑问,如果我们开一个接口来刷新缓存,对于一个非集群型的服务来说,各自的服务注册是注册多个实例还是单个实例?如果是单个实例则可以合理地刷新,如果是多例,则没办法清除缓存。

后来发现springboot在注入bean的时候默认就是单例,所以直接用就行;

可追踪注入代码;是从spring源码中看到的。文末附有spring源码的查看方式。

org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#getSingleton(String, boolean)

/**
 * Return the (raw) singleton object registered under the given name.
 * <p>Checks already instantiated singletons and also allows for an early
 * reference to a currently created singleton (resolving a circular reference).
 * @param beanName the name of the bean to look for
 * @param allowEarlyReference whether early references should be created or not
 * @return the registered singleton object, or {@code null} if none found
 */
@Nullable
protected Object getSingleton(String beanName, boolean allowEarlyReference) {
   // Quick check for existing instance without full singleton lock
   Object singletonObject = this.singletonObjects.get(beanName);
   if (singletonObject == null && isSingletonCurrentlyInCreation(beanName)) {
      singletonObject = this.earlySingletonObjects.get(beanName);
      if (singletonObject == null && allowEarlyReference) {
         synchronized (this.singletonObjects) {
            // Consistent creation of early reference within full singleton lock
            singletonObject = this.singletonObjects.get(beanName);
            if (singletonObject == null) {
               singletonObject = this.earlySingletonObjects.get(beanName);
               if (singletonObject == null) {
                  ObjectFactory<?> singletonFactory = this.singletonFactories.get(beanName);
                  if (singletonFactory != null) {
                     singletonObject = singletonFactory.getObject();
                     this.earlySingletonObjects.put(beanName, singletonObject);
                     this.singletonFactories.remove(beanName);
                  }
               }
            }
         }
      }
   }
   return singletonObject;
}

附带spring framework源码下载、版本、导入gradle项目的攻略:

spring源码下载及安装gradle并导入IDEA_工藤新一77的博客-CSDN博客

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值