Внедрение JPA EntityManager с использованием Spring против Java EE 6 - PullRequest
1 голос
/ 09 февраля 2012

Я новичок в Java EE 6 и даже новее в Spring. Я пытаюсь внедрить EclipseLink JPA EntityManager и изучаю различные способы достижения этой цели. Я использую Glassfish и Derby. В приведенных ниже примерах я пытаюсь внедрить EntityManager непосредственно в сервлет или контроллер для простоты, на практике у меня будет класс DAO, который упаковывает EntityManager.

В Java EE 6 я могу определить сервлет следующим образом:

@WebServlet(urlPatterns="/app/*")
public class FrontController extends HttpServlet {
    private static final long serialVersionUID = 1L;

    @PersistenceContext
    private EntityManager entityManager;
}

EntityManager правильно введен без дальнейшей настройки.

Теперь я хочу использовать Spring, в идеале через аннотации. В настоящее время я могу определить контроллер следующим образом:

@Controller
@RequestMapping("/testurl.htm")
public class ExampleController {
    private EntityManager em;

    @PersistenceContext
    public void setEntityManager(EntityManager em) {
        this.em = em;
    }
}

Чтобы Spring правильно подключился, мне нужно включить следующую директиву в XML-файл контекста приложения:

<bean id="entityManagerFactory"
        class="org.springframework.orm.jpa.LocalEntityManagerFactoryBean">
    <property name="persistenceUnitName" value="myPU"/>
</bean>

Если я не включил приведенный выше фрагмент, я получаю исключение при развертывании: org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [javax.persistence.EntityManagerFactory] is defined: expected single bean but found 0

Прочитав это У меня сложилось впечатление, что мне не понадобится приведенный выше фрагмент XML. Может ли кто-нибудь подтвердить, что приведенный выше фрагмент кода всегда будет необходим?

Есть ли другой подход - если EntityManager успешно внедряется в мой сервлет FrontController с помощью контейнера Java EE, как этот же EntityManager может быть внедрен в мой контекст приложения Spring и сделан доступным для других компонентов Spring?

1 Ответ

0 голосов
/ 09 февраля 2012

Внедряйте своих в слой обслуживания, а не в свои контроллеры.

Краткий фрагмент (с использованием hibernate4):

@Controller
public class AdminController {

    @Resource(name = "companyService")
    private CompanyService companyService;

    @RequestMapping(value = "/AllCompanies", method = RequestMethod.GET)
    public String getCompanies(final Model model) {
    final List<Company> companies = companyService.getAllCompanies();
    //dostuff
    }

и обслуживание:

@Service("companyService")
@Transactional
public class CompanyService {

    @Resource(name = "sessionFactory")
    private SessionFactory sessionFactory;

    @Transactional(readOnly = true)
    public List<Company> getAllCompanies() {
    final Session session = sessionFactory.getCurrentSession();
//... do stuff
}

и соответствующий бит контекста приложения

<bean id="sessionFactory"
        class="org.springframework.orm.hibernate4.LocalSessionFactoryBean"
        p:dataSource-ref="dataSource" p:configLocation="WEB-INF/classes/hibernate.cfg.xml"
        p:packagesToScan="com.mypackage" />

    <!-- Declare a datasource that has pooling capabilities -->
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource"
        ... />

    <!-- Declare a transaction manager -->
    <bean id="transactionManager" class="org.springframework.orm.hibernate4.HibernateTransactionManager" 
                p:sessionFactory-ref="sessionFactory" />
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...