Spring: как создать экземпляр компонента Spring, который принимает параметр времени выполнения? - PullRequest
7 голосов
/ 24 февраля 2012

У меня есть одноэлементный компонент Spring, который создает пару задач (java.util.concurrent.Callable) во время выполнения, чтобы выполнять свою работу параллельно.В данный момент Callable определены как внутренние классы в синглтон-компоненте, и синглтон-компонент создает их просто путем создания экземпляра их с помощью new Task(in), где in - параметр, известный только во время выполнения.

Теперь я хочу извлечь внутренний класс Task в обычный класс верхнего уровня, потому что я хочу сделать метод Task * call() транзакционным, поэтому мне нужно, чтобы он был бином Spring.

Я полагаю, что яМне нужно дать моему синглтону некоторую фабрику Task s, но задачи должны быть прототипом Spring bean-компонентов, которые принимают значение времени выполнения в качестве параметра конструктора.Как мне это сделать?

Ответы [ 3 ]

4 голосов
/ 24 февраля 2012

Другой подход может заключаться в том, чтобы использовать аннотацию Spring @Configurable с ткачеством во время загрузки. Таким образом, вы можете использовать new (вместо фабрики бинов) для создания проводных Callable во время выполнения:

@Configurable
public class WiredTask implements Callable<Result> {

    @Autowired
    private TaskExecutor executor;

    public WiredTask(String in) {
        this.in = in;
    }

    public Result call() {
        return executor.run(in);
    }
}

@Bean @Scope("prototype")
public class TaskExecutor() {

    @Transactional
    public Result run(String in) {
        ...
    }
}

// Example of how you might then use it in your singleton...
ExecutorService pool = Executors.newFixedThreadPool(3);
WiredTask task = new WiredTask("payload");
Future<Result> result = pool.submit(task);

См. эту статью для получения дополнительной информации. Обратите внимание, что вы не можете использовать @ Configurable и @Transactional в одном и том же bean-компоненте , поэтому необходимо два класса. По этой причине это может быть не идеальным решением, если у вас много разных реализаций Callable (так как вам понадобится 2 класса для каждой).

3 голосов
/ 24 февраля 2012

Ваш синглтон-бин может реализовывать BeanFactoryAware и поисковые бины из фабрики пружин.

2 голосов
/ 24 февраля 2012

Фабрика бобов весны и новый являются взаимоисключающими. Вы не можете вызвать new и ожидать, что этот объект будет под контролем Spring.

Мое предложение - ввести эти Задачи в Синглтон. Сделай им и весенние бобы.

Вы должны признать, что само задание не будет транзакцией, но ее зависимости могут быть. Вставьте их в задачи и позвольте Spring управлять транзакциями.

...