2015-03-08 5 views
7

Мне нужно ввести @Autouired конкретную реализацию класса обслуживания.Весна - как реализовать реализацию интерфейса бетона?

Сервисный интерфейс:

public interface PostService { 
... 
} 

Реализация:

@Service("postServiceImpl") 
public class PostServiceImpl implements PostService { 
... 
} 

метода в службе есть с @ транзакционной аннотацией

А теперь я хочу, чтобы ввести postServiceImpl в мой контроллер - потому что мне нужно использовать один метод из реализации, который отсутствует в интерфейсе:

@Autowired 
@Qualifier("postServiceImpl") 
private PostServiceImpl postService; 

Я получаю NoSuchBeanDefinitionException со следующим сообщением:

Нет квалификационная рожкового типа [(...) .PostServiceImpl] нашел для зависимости: ожидается, по крайней мере, один боб, который квалифицируется как autowire кандидат на эту зависимость.

при изменении поля в моем контроллере:

private PostService postService 

это работает, но я не могу использовать конкретный метод из PostServiceImpl.

+3

Затем добавьте его в интерфейс. Какой смысл объявлять интерфейсы, если вы вводите конкретный тип? –

+0

У вас есть некоторые аспекты, применяемые к этому бонусу? Или прокси-серверы на основе интерфейса? – fcracker79

+1

@ fcracker79 Я думаю, что у меня есть, потому что методы в сервисе связаны с аннотацией @ Transactional. – tomdavies

ответ

9

Поскольку ваши методы аннотируются @Transactional, весна создаст прокси во время выполнения, чтобы ввести код управления транзакциями. По умолчанию Spring использует JDK Dynamic Proxy для прокси-механизма, который использует прокси на основе интерфейсов.

Таким образом, весна создает в этом случае еще один класс, который реализует интерфейс PostService и создает компоненты этого класса. Определенно, это невозможно сделать для PostServiceImpl, так как это братья и сестры. Однако, если вы действительно хотите использовать autowire на классе, вы можете заставить Spring использовать прокси-сервер CGLib, который использует прокси с помощью подкласса. Это можно сделать, установив proxyTargetClass=true в аннотацию @EnableTransactionManagement, если вы используете конфигурацию на основе Java.

Смежные вопросы