Доступ как к аргументу времени выполнения, так и к другим компонентам в конструкторе spring bean

#java #spring #spring-boot

#java #spring #spring-boot

Вопрос:

У меня есть два компонента в приложении с весенней загрузкой:

 @Component
@Scope(BeanDefinition.SCOPE_PROTOTYPE)
public class Shape {

    @Resource
    private ShapeService shapeService;

    private String name;
    private String description;

    public Shape(String name) {
        this.name = name;
        this.description = shapeService.getDescription();
    }
}
  
 @Service
public class ShapeService {

    public String getDescription() {
        return "This is a shape.";
    }
}

  

Я создал Shape экземпляр, используя следующий код:

 Shape shape = beanFactory.getBean(Shape.class, "shape");
  

Но я получил a NullPointerException в следующей строке:

 this.description = shapeService.getDescription();
  

shapeService равно нулю. Есть ли какой-либо способ использовать shapeService конструктор inside Shape ?

Ответ №1:

Проблема в том, что Spring должен создать объект, прежде чем он сможет выполнить над ним внедрение поля. Таким образом, поле, на которое вы ссылаетесь, еще не было установлено Spring, но будет установлено позже, после того, как объект будет полностью сконструирован. Если бы эта строка была в обычном методе, она бы работала.

Чтобы исправить это, вы должны заставить Spring передать ссылку на ваш ShapeService конструктор вашему конструктору через аргумент конструктора. Измените свой код для вашего Shape класса, чтобы он выглядел следующим образом:

 @Component
@Scope(BeanDefinition.SCOPE_PROTOTYPE)
public class Shape {

    private ShapeService shapeService;

    private String name;
    private String description;

    public Shape(String name, ShapeService shapeService) {
        this.name = name;
        this.shapeService = shapeService;
        this.description = shapeService.getDescription();
    }
}
  

Я предпочитаю ввод аргумента конструктора вместо автозапуска, даже если в этом нет необходимости, как в вашем случае. Внедрение конструктора обычно считается лучшей формой. Вот статья, в которой объясняется, почему