«1. Обзор

В этой статье мы создадим приложение Spring, используя Hibernate/JPA с источником данных JNDI.

Если вы хотите заново открыть для себя основы Spring и Hibernate, ознакомьтесь с этой статьей.

2. Объявление источника данных

2.1. Система

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

В этом примере мы будем использовать Tomcat версии 8.5.x и базу данных PostgreSQL версии 9.5.x.

Вы должны быть в состоянии воспроизвести те же шаги, используя любой другой контейнер приложения Java и базу данных по вашему выбору (при условии, что у вас есть для этого подходящие файлы jar JDBC!).

2.2. Объявление источника данных в контейнере приложения

Мы объявим наш источник данных в файле \u003ctomcat_home\u003e/conf/server.xml внутри элемента \u003cGlobalNamingResources\u003e.

Если предположить, что сервер базы данных работает на том же компьютере, что и контейнер приложения, и предполагаемая база данных называется postgres, а имя пользователя baeldung с паролем pass1234, ресурс будет выглядеть так:

<Resource name="jdbc/BaeldungDatabase" 
  auth="Container"
  type="javax.sql.DataSource" 
  driverClassName="org.postgresql.Driver"
  url="jdbc:postgresql://localhost:5432/postgres"
  username="baeldung" 
  password="pass1234" 
  maxTotal="20" 
  maxIdle="10" 
  maxWaitMillis="-1"/>

~~ ~ Обратите внимание, что мы назвали наш ресурс jdbc/BaeldungDatabase. Это имя будет использоваться при ссылке на этот источник данных.

Нам также пришлось указать его тип и имя класса драйвера базы данных. Чтобы это работало, вы также должны поместить соответствующий jar-файл в \u003ctomcat_home\u003e/lib/ (в данном случае это jar-файл JDBC PostgreSQL).

Остальные параметры конфигурации:

    auth=“Container” – означает, что контейнер будет входить в диспетчер ресурсов от имени приложения. maxTotal, maxIdle и maxWaitMillis – это конфигурация подключения к пулу. параметры

Мы также должны определить ResourceLink внутри элемента \u003cContext\u003e в \u003ctomcat_home\u003e/conf/context.xml, который будет выглядеть так:

<ResourceLink 
  name="jdbc/BaeldungDatabase" 
  global="jdbc/BaeldungDatabase" 
  type="javax.sql.DataSource"/>

Обратите внимание, что мы используем имя, которое мы определили в нашем Resource в сервер.xml.

3. Использование ресурса

3.1. Настройка приложения

Теперь мы собираемся определить простое приложение Spring + JPA + Hibernate, используя чистую конфигурацию Java.

Мы начнем с определения конфигурации контекста Spring (имейте в виду, что здесь мы фокусируемся на JNDI и предполагаем, что вы уже знакомы с основами конфигурации Spring):

@Configuration
@EnableTransactionManagement
@PropertySource("classpath:persistence-jndi.properties")
@ComponentScan("com.baeldung.hibernate.cache")
@EnableJpaRepositories(basePackages = "com.baeldung.hibernate.cache.dao")
public class PersistenceJNDIConfig {

    @Autowired
    private Environment env;

    @Bean
    public LocalContainerEntityManagerFactoryBean entityManagerFactory() 
      throws NamingException {
        LocalContainerEntityManagerFactoryBean em 
          = new LocalContainerEntityManagerFactoryBean();
        em.setDataSource(dataSource());
        
        // rest of entity manager configuration
        return em;
    }

    @Bean
    public DataSource dataSource() throws NamingException {
        return (DataSource) new JndiTemplate().lookup(env.getProperty("jdbc.url"));
    }

    @Bean
    public PlatformTransactionManager transactionManager(EntityManagerFactory emf) {
        JpaTransactionManager transactionManager = new JpaTransactionManager();
        transactionManager.setEntityManagerFactory(emf);
        return transactionManager;
    }

    // rest of persistence configuration
}

Обратите внимание, что у нас есть полный пример конфигурации в статье Spring 4 и JPA с Hibernate.

Чтобы создать наш bean-компонент dataSource, нам нужно найти ресурс JNDI, который мы определили в контейнере нашего приложения. Мы сохраним это в ключе persistence-jndi.properties (среди других свойств):

jdbc.url=java:comp/env/jdbc/BaeldungDatabase

Обратите внимание, что в свойстве jdbc.url мы определяем корневое имя для поиска: java:comp/env/ ( это значения по умолчанию, соответствующие компоненту и среде), а затем то же имя, которое мы использовали в server.xml: jdbc/BaeldungDatabase.

3.2. Конфигурация JPA — модель, DAO и сервис

Мы собираемся использовать простую модель с аннотацией @Entity со сгенерированным идентификатором и именем:

@Entity
public class Foo {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "ID")
    private Long id;
 
    @Column(name = "NAME")
    private String name;

    // default getters and setters
}

Давайте определим простой репозиторий:

@Repository
public class FooDao {

    @PersistenceContext
    private EntityManager entityManager;

    public List<Foo> findAll() {
        return entityManager
          .createQuery("from " + Foo.class.getName()).getResultList();
    }
}

И, наконец, давайте создадим простую службу:

@Service
@Transactional
public class FooService {

    @Autowired
    private FooDao dao;

    public List<Foo> findAll() {
        return dao.findAll();
    }
}

Благодаря этому у вас есть все необходимое для использования вашего источника данных JNDI в вашем приложении Spring.

4. Заключение

В этой статье мы создали пример приложения Spring с настройкой JPA + Hibernate, работающего с источником данных JNDI.

Обратите внимание, что наиболее важными частями являются определение ресурса в контейнере приложения и поиск ресурса JNDI в конфигурации.

И, как всегда, полный проект можно найти на GitHub.