如何在使用工厂策略模式(在运行时创建)创建的对象中使用@自动有线服务?

问题描述 投票:1回答:1

考虑一个接口 Action,以及2个实现类。StupidActionSmartAction.

SmartAction 需要使用另一个服务,但由于一个 Action 是在运行时创建的。@Autowired 注解不工作(服务为空)。

使用策略模式与 春天? 这个问题有什么好的解决办法吗?

我可以把 "StupidAction "也设置为服务,而不实例化它。我也可以在方法参数中把自动连接的服务传递给 "doSomething"。但是这两种解决方案真的很脏。

一些代码例子。

public interface Action {
    void doSomething();
}

public class StupidAction implements Action{

    @Autowired
    private MyService myService;  // THIS IS NULL. because StupidAction is instanciated at runtime.

    public void doSomething(){
        myService.changeSomething()
    }
}

//Pseudo code
@RestController
@RequestMapping(path = "/")
public class WorkflowController {

    @GetMapping("")
    ResponseEntity someAPI() {  
        Action action = new SmartAction(); //create on runtime
        action.doSomething(); //NullPointerExc
    }
}
java spring nullpointerexception strategy-pattern
1个回答
0
投票

你可以通过名称动态地从上下文中获取Bean,使用 BeanFactory:

@Service
public class Service {

  @Autowired BeanFactory beanFactory;

  public void foo(){
    DynamicBean bean = beanFactory.getBean("bean_name", DynamicBean.class)
  }
}

-2
投票

你可以从ApplicationContextAware的Util服务中获取Bean。

@Service
public class BeanUtility implements ApplicationContextAware {
    private static ApplicationContext context;

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        context = applicationContext;
    }
    public static <T extends Object> T getMyBean(Class<T> beanClass) {
        return context.getBean(beanClass);
    }
}

控制器的实现如下。

@RestController
@RequestMapping(path = "/")
public class WorkflowController {

    @Autowired
    BeanUtility beanUtility;

    @GetMapping("action")
    ResponseEntity someAPI() {
        MyService myService = BeanUtility.getMyBean(MyService.class); // use the util class to get a Bean of your choice
        Action action = new SmartAction(myService); // Constructor based DI
        return new ResponseEntity<String>(action.doSomething(), HttpStatus.CREATED);
    }
}

随后是SmartAction类的实现,如下所示。

@Service
public class SmartAction implements Action{

    private MyService myService;

    public SmartAction(MyService myService){
        this.myService = myService;
    }

    @Override
    public String doSomething() {
        return "Smart action : " + myService.changeSomething();
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.