借助@Conditional实现自定义初始化Spring Bean

本项目使用传统的Spring MVC框架进行搭建,未使用Spring Boot,而需要实现根据用户配置自动选择TCP、UDP、串口等不同协议进行数据获取,还有用户若在内网,实现短信服务动态关闭(wsimport 方式实现的,用户配置修改后Spring不加载相应的短信服务)。若使用Spring Boot,Spring Boot提供了一系列根据条件初始化Spring Bean的注解,非常方便的进行此等操作,在传统Spring MVC项目中,可自己借助@Conditional实现以上操作。

  • 协议动态选择

    • 首先定义不同协议的注解

      /**
      * @类名 ServerType
      * @描述 不同协议初始化不同服务器(0:TCP,1:UDP,2:串口)
      * @作者 zhuxl
      * @创建时间 2017-3-28下午04:50:55
      */
      public class ServerType {
      /**
       * @类名 TCP
       * @描述 TCP
       * @作者 zhuxl
       * @创建时间 2017-3-28下午04:55:38
       */
      public @interface TCP {
      
      }
      
      /**
       * @类名 UDP
       * @描述 UDP
       * @作者 zhuxl
       * @创建时间 2017-3-28下午04:55:43
       */
      public @interface UDP {
      
      }
      
      /**
       * @类名 Serial
       * @描述 串口
       * @作者 zhuxl
       * @创建时间 2017-3-28下午04:55:48
       */
      public @interface Serial {
      
      }
      }
    • 根据配置文件中不同的配置,实现对不同协议的处理

    /**
     * @类名 ServerCondition
     * @描述 服务器条件初始化(根据配置自动初始化不同的服务器)
     * @作者 zhuxl
     * @创建时间 2017-4-1下午01:30:48
     */
    public class ServerCondition implements Condition{
    
        @Override
        public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
            int type=PropUtil.getInt(Constant.SETTING_PATH, "transport.type", 0);
            switch(type){
                case 1:{//UDP
                    return metadata.isAnnotated(UDP.class.getName());
                }
                case 2:{//串口
                    return metadata.isAnnotated(Serial.class.getName());
                }
                default:{//TCP
                    return metadata.isAnnotated(TCP.class.getName());
                }
            }       
        }
    }
    
    • 对于不同的协议类型,初始化不同的Bean
      //串口处理
      @Component("minaServer")
      @Conditional(value=ServerCondition.class)
      @Serial
      public class SerialServer implements Server {
      }
      // TCP处理
      @Component("minaServer")
      @Conditional(value=ServerCondition.class)
      @TCP
      public class TCPServer implements Server {
      }
  • 短信服务动态关闭:根据配置,能够实现短信服务动态加载(短信服务时wsimport加载的)

    • 短信服务条件初始化
      /**
      * @类名 SmsCondition
      * @描述 短信服务条件初始化
      * @作者 zhuxl
      * @创建时间 2017-6-12下午04:58:58
      */
      public class SmsCondition implements Condition{
          @Override
          public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
              int flag=PropUtil.getInt(Constant.SETTING_PATH, "sms.use", 0);
              return flag==1?true:false;
          }
      }
  • 短信服务Bean动态加载
/**
 * @类名 SmsConfig
 * @描述 短信条件初始化
 * @作者 zhuxl
 * @创建时间 2017-6-12下午05:13:14
 */
@Configuration
@Conditional(SmsCondition.class)
public class SmsConfig {
    @Bean 
    public SmSWebService smSWebService(){
        return new SmSWebService();
    }
    @Bean
    public SmSWebServiceSoap smSWebServiceSoap(SmSWebService smSWebService){
        return smSWebService.getSmSWebServiceSoap();
    }
} 
  • 在需要短信的地方使用以下代码加入短信服务,但使用前需要判断短信服务是否为空,为空则为加载。
    @Autowired(required=false) @Qualifier("smSWebServiceSoap")
    private SmSWebServiceSoap smSWebServiceSoap;

    public String sendSms(Sms sms) {
        if(smSWebServiceSoap==null){
            return "短信功能不可用,请确定短信服务可用";
        }
        if(sms==null){
            return "短信参数错误";
        }
        try{
            WsSendResponse response=smSWebServiceSoap.sendSms(smsAccount.getUserId(), smsAccount.getAccount(), smsAccount.getPassword(), sms.getMobile(), sms.getContent(), sms.getSendTime(), sms.getExtno());
            logger.info("短信发送:"+response.getMessage()+","+response.getReturnStatus());
            return response.getMessage();
        }catch(Exception ex){
            ex.printStackTrace();
            return "短信发送失败";
        }
    }

你可能感兴趣的:(Java,Spring)