职场新人第一次博客—— 记使用spring+设计模式解决大量ifelse的问题(二)

记使用设计模式解决大量ifelse的问题

本文主要以spring + 策略 + 工厂模式来进行演示

    大家好,继昨天的策略+工厂模式解决ifelse的问题后,今天我们再来加一种框架来看看。
    spring框架作为一个超级牛逼的框架我相信在座的各位应该没有不用的吧[狗头],那么我们该怎么在spring框架中应用策略+工厂模式呢,话不多说直接上手!!
咱先来创建一个springboot项目[嘿嘿]
启动类做起来

@SpringBootApplication(exclude = DataSourceAutoConfiguration.class)
public class DesignpatternsApplication {
    public static void main(String[] args) {
        SpringApplication.run(DesignpatternsApplication.class, args);
    }
}

继续将昨天的策略接口,业务类和枚举类搬过来。。
枚举类就不用动了

public enum Role {
    bussiness("Bussiness"),
    collection("Collection"),
    productino("Production");

    private String hotelCode;
    //将三个值加载进list集合
    public static List<String> getList() {
        return Arrays.asList(Role.values()).stream()
                .map(Role::getHotelCode)
                .collect(Collectors.toList());
    }

    Role(String hotelCode) {
        this.hotelCode = hotelCode;
    }
    public String getHotelCode() {
        return hotelCode;
    }
}

然后再把策略接口也拿过来

public interface getContactService {
    List<ZsBcContractDate> list(ZsBcContractDate zsBcContractDate);
}

好,再到业务类了,这就要有一些改变了,我们要将他们交给spring容器进行管理

@Component("BussinessContactServiceImpl")
public class BussinessContactServiceImpl implements getContactService {

    @Override
    public List<ZsBcContractDate> list(ZsBcContractDate zsBcContractDate) {
        return initContact(zsBcContractDate);
    }

    private List<ZsBcContractDate> initContact(ZsBcContractDate zsBcContractDate) {
        return new ArrayList<ZsBcContractDate>() {
            {
                add(new ZsBcContractDate(1L));
                add(new ZsBcContractDate(2L));
                add(new ZsBcContractDate(3L));
            }
        };
    }
}

@Component("CollectionContactServiceImpl")
public class CollectionContactServiceImpl implements getContactService {

    @Override
    public List<ZsBcContractDate> list(ZsBcContractDate zsBcContractDate) {
        return initContact(zsBcContractDate);
    }

    private List<ZsBcContractDate> initContact(ZsBcContractDate zsBcContractDate) {
        return new ArrayList<ZsBcContractDate>() {
            {
                add(new ZsBcContractDate(4L));
                add(new ZsBcContractDate(5L));
                add(new ZsBcContractDate(6L));
            }
        };
    }
}

@Component("ProductionContactServiceImpl")
public class ProductionContactServiceImpl implements getContactService {

    @Override
    public List<ZsBcContractDate> list(ZsBcContractDate zsBcContractDate) {
        return initContact(zsBcContractDate);
    }

    private List<ZsBcContractDate> initContact(ZsBcContractDate zsBcContractDate) {
        return new ArrayList<ZsBcContractDate>() {
            {
                add(new ZsBcContractDate(7L));
                add(new ZsBcContractDate(8L));
                add(new ZsBcContractDate(9L));
            }
        };
    }
}

接下来就来到我们最重要的工厂类了!!
这里我采用了applicationContext.getBeansOfType(getContactService.class);直接从容器中获取实现了这个接口的所有子类,所以说我们在上面说了要将所有的业务类交给spring容器进行管理。

@Component
public class ContactSpringFactory {
    /**
     * 服务实现后缀
     */
    private static final String CONTACT_SERVICE_SUFFIX = "ContactServiceImpl";
    private static Map<String, getContactService> CONTACT_SERVER_MAP;
    @Autowired
    private ApplicationContext applicationContext;

    public ContactSpringFactory() {
        init();
    }

    public static getContactService getContactServiceImpl(String hotelCode) {
        return CONTACT_SERVER_MAP.get(hotelCode + CONTACT_SERVICE_SUFFIX);
    }

    private void init(){
        CONTACT_SERVER_MAP = applicationContext.getBeansOfType(getContactService.class);
    }
}

搞一个controller准备启动了[旺柴]

@RestController
@RequestMapping("/test")
public class Demo01 {

    @GetMapping("/getCode")
    public void main(String code) {
        getContactService bussiness = ContactSpringFactory.getContactServiceImpl(code);
        ZsBcContractDate zsBcContractDate = new ZsBcContractDate(1L);
        List<ZsBcContractDate> list = bussiness.list(zsBcContractDate);
        System.out.println(list);
    }
}

启动gogo ????空指针

Caused by: java.lang.NullPointerException: null
	at com.example.designpatterns.Factory.ContactSpringFactory.init(ContactSpringFactory.java:40) ~[classes/:na]
	at com.example.designpatterns.Factory.ContactSpringFactory.<init>(ContactSpringFactory.java:32) ~[classes/:na]
	at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) ~[na:1.8.0_40]
	at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) ~[na:1.8.0_40]
	at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) ~[na:1.8.0_40]
	at java.lang.reflect.Constructor.newInstance(Constructor.java:422) ~[na:1.8.0_40]
	at org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:204) ~[spring-beans-5.2.11.RELEASE.jar:5.2.11.RELEASE]
	... 26 common frames omitted

人都惊呆了!!百思不得其解。。。。。
看了一下日志,在工厂类的初始化方法中爆出来的,原来是applicationContext为null,所以没有值能取出来。当时我就想,咦我不是加了@Autowired吗 ,为什么没有注入进去,百度搜了下看到了一个差不多忘了干干净净的东西了 ‘构造注入’。。

CONTACT_SERVER_MAP = applicationContext.getBeansOfType(getContactService.class);
@Component
public class ContactSpringFactory {
    /**
     * 服务实现后缀
     */
    private static final String CONTACT_SERVICE_SUFFIX = "ContactServiceImpl";
    private static Map<String, getContactService> CONTACT_SERVER_MAP;

    private ApplicationContext applicationContext;

    public ContactSpringFactory(ApplicationContext applicationContext) {
        this.applicationContext = applicationContext;
        init();
    }

    public static getContactService getContactServiceImpl(String hotelCode) {
        return CONTACT_SERVER_MAP.get(hotelCode + CONTACT_SERVICE_SUFFIX);
    }

    private void init(){
        CONTACT_SERVER_MAP = applicationContext.getBeansOfType(getContactService.class);
    }
}

用postman测试http://localhost:8080/test/getCode?code=Bussiness
这样,在他注入后我们在进行map的初始化,这样就不会爆空指针啦,项目就能正确的跑起来啦!
在这里插入图片描述
如有错误,欢迎大佬指出[拜拜]

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值