org.hibernate.HibernateException: доступ до DialectResolutionInfo не може бути недійсним, коли параметр "hibernate.dialect" не встановлено


205

Я намагаюся запустити додаток Spring-boot, яке використовує сплячий режим через spring-jpa, але я отримую цю помилку:

Caused by: org.hibernate.HibernateException: Access to DialectResolutionInfo cannot be null when 'hibernate.dialect' not set
        at org.hibernate.engine.jdbc.dialect.internal.DialectFactoryImpl.determineDialect(DialectFactoryImpl.java:104)
        at org.hibernate.engine.jdbc.dialect.internal.DialectFactoryImpl.buildDialect(DialectFactoryImpl.java:71)
        at org.hibernate.engine.jdbc.internal.JdbcServicesImpl.configure(JdbcServicesImpl.java:205)
        at org.hibernate.boot.registry.internal.StandardServiceRegistryImpl.configureService(StandardServiceRegistryImpl.java:111)
        at org.hibernate.service.internal.AbstractServiceRegistryImpl.initializeService(AbstractServiceRegistryImpl.java:234)
        at org.hibernate.service.internal.AbstractServiceRegistryImpl.getService(AbstractServiceRegistryImpl.java:206)
        at org.hibernate.cfg.Configuration.buildTypeRegistrations(Configuration.java:1885)
        at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:1843)
        at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl$4.perform(EntityManagerFactoryBuilderImpl.java:850)
        at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl$4.perform(EntityManagerFactoryBuilderImpl.java:843)
        at org.hibernate.boot.registry.classloading.internal.ClassLoaderServiceImpl.withTccl(ClassLoaderServiceImpl.java:398)
        at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl.build(EntityManagerFactoryBuilderImpl.java:842)
        at org.hibernate.jpa.HibernatePersistenceProvider.createContainerEntityManagerFactory(HibernatePersistenceProvider.java:152)
        at org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean.createNativeEntityManagerFactory(LocalContainerEntityManagerFactoryBean.java:336)
        at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.afterPropertiesSet(AbstractEntityManagerFactoryBean.java:318)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1613)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1550)
        ... 21 more

мій файл pom.xml такий:

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>1.1.8.RELEASE</version>
</parent>

<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-web</artifactId>
       </dependency>
    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-config</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-taglibs</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-jpa</artifactId>
    </dependency>
    <dependency>
        <groupId>commons-dbcp</groupId>
        <artifactId>commons-dbcp</artifactId>
    </dependency>
</dependencies>

моя конфігурація в сплячому режимі полягає в тому, що (діалектна конфігурація знаходиться в останньому методі з цього класу):

@Configuration
@EnableTransactionManagement
@ComponentScan({ "com.spring.app" })
public class HibernateConfig {

   @Bean
   public LocalSessionFactoryBean sessionFactory() {
      LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();

      sessionFactory.setDataSource(restDataSource());
      sessionFactory.setPackagesToScan(new String[] { "com.spring.app.model" });
      sessionFactory.setHibernateProperties(hibernateProperties());

      return sessionFactory;
   }

   @Bean
   public DataSource restDataSource() {
      BasicDataSource dataSource = new BasicDataSource();

      dataSource.setDriverClassName("org.postgresql.Driver");
      dataSource.setUrl("jdbc:postgresql://localhost:5432/teste?charSet=LATIN1");
      dataSource.setUsername("klebermo");
      dataSource.setPassword("123");

      return dataSource;
   }

   @Bean
   @Autowired
   public HibernateTransactionManager transactionManager(SessionFactory sessionFactory) {
      HibernateTransactionManager txManager = new HibernateTransactionManager();
      txManager.setSessionFactory(sessionFactory);
      return txManager;
   }

   @Bean
   public PersistenceExceptionTranslationPostProcessor exceptionTranslation() {
      return new PersistenceExceptionTranslationPostProcessor();
   }

   Properties hibernateProperties() {
      return new Properties() {
         /**
         * 
         */
        private static final long serialVersionUID = 1L;

        {
            setProperty("hibernate.hbm2ddl.auto", "create");
            setProperty("hibernate.show_sql", "false");
            setProperty("hibernate.dialect", "org.hibernate.dialect.PostgreSQLDialect");
         }
      };
   }
}

що я тут роблю неправильно?

Відповіді:


199

Спочатку видаліть усю конфігурацію Spring Boot почне її для вас.

Переконайтеся, що у вас є application.properties ваш класний шлях і додайте наступні властивості.

spring.datasource.url=jdbc:postgresql://localhost:5432/teste?charSet=LATIN1
spring.datasource.username=klebermo
spring.datasource.password=123

spring.jpa.database-platform=org.hibernate.dialect.PostgreSQLDialect
spring.jpa.show-sql=false
spring.jpa.hibernate.ddl-auto=create

Якщо вам дійсно потрібен доступ до а, SessionFactoryі це в основному для одного і того ж джерела даних, ви можете зробити наступне (що також задокументовано тут хоча для XML, а не для JavaConfig).

@Configuration        
public class HibernateConfig {

    @Bean
    public HibernateJpaSessionFactoryBean sessionFactory(EntityManagerFactory emf) {
         HibernateJpaSessionFactoryBean factory = new HibernateJpaSessionFactoryBean();
         factory.setEntityManagerFactory(emf);
         return factory;
    }
}

Таким чином, у вас є обидва EntityManagerFactory і SessionFactory.

ОНОВЛЕННЯ: Станом на сплячку 5 SessionFactoryфактично поширюється EntityManagerFactory. Таким чином, щоб отримати a, SessionFactoryви можете просто EntityManagerFactoryпередати його або використовуватиunwrap методом, щоб отримати його.

public class SomeHibernateRepository {

  @PersistenceUnit
  private EntityManagerFactory emf;

  protected SessionFactory getSessionFactory() {
    return emf.unwrap(SessionFactory.class);
  }

}

Якщо припустити, що у вас є клас із mainметодом, @EnableAutoConfigurationвам не потрібна @EnableTransactionManagementанотація, оскільки це дозволить Spring Boot для вас. Основний клас застосування у програміcom.spring.app упаковці має бути достатньо.

@Configuration
@EnableAutoConfiguration
@ComponentScan
public class Application {


    public static void main(String[] args) throws Exception {
        SpringApplication.run(Application.class, args);
    }

} 

Щось подібного має бути достатньо, щоб усі ваші класи (включаючи сутності та сховища Spring Data) були виявлені.

ОНОВЛЕННЯ: Ці примітки можна замінити одинарними @SpringBootApplicationв останніх версіях Spring Boot.

@SpringBootApplication
public class Application {

    public static void main(String[] args) throws Exception {
        SpringApplication.run(Application.class, args);
    }
} 

Я б також запропонував видалити commons-dbcpзалежність, оскільки це дозволило б Spring Boot налаштувати більш швидку та надійну HikariCPреалізацію.


1
але чи є спосіб уникнути створення цього файлу application.propertes? Я віддаю перевагу способу, коли я роблю всю конфігурацію в класі HibernateConfig.
Клебер Мота

2
Чому? Вся мета Spring Boot полягає в тому, що вона робить автоматичну конфігурацію для вас ... Отже, ви віддаєте перевагу включити багатослівну конфігурацію Java на 7 рядків у файл властивостей ?!
М. Дейнум

2
Це може бути навіть 6 рядків у файлі властивостей. Вам не потрібно встановлювати spring.datasource.driverClassName, коли ви використовуєте Postgres, оскільки Boot буде виводити його з spring.datasource.url.
Енді Вілкінсон,

2
@AlexWorden Ні, це не так ... Замість того, щоб розміщувати випадкові коментарі, ви можете спочатку прочитати, як завантажуються властивості, особливо підтримка Spring Boot. Паролі на диску не повинні бути проблемою, якщо ви встановлюєте права файлу прямо. Помістити їх у базу даних не набагато краще ...
М. Дейнум

4
Замість використання 3 приміток, тобто конфігурації, EnableAutoConfiguration, ComponentScan. Ми можемо використовувати анотацію SpringBootApplication
Панкай

158

Я зіткнувся з подібною проблемою під час запуску програми (за допомогою Spring Boot) із запущеним сервером бази даних .

Hibernate може визначити правильний діалект, який використовуватиме автоматично, але для цього потрібно живе з'єднання з базою даних.


2
Моя проблема була подібною до цієї в тому, що pg_hba.conf на сервері не був налаштований для віддаленого з'єднання, що дало мені цю помилку.
Брайан

8
Якщо база даних, до якої ви намагаєтеся підключитися, не існує, ви також бачите цю помилку.
Йонас Педерсен

12
Отримала таку ж проблему, у моєму випадку БД була налаштована, але облікові дані були помилковими. +1
Федеріко П'яцца

дивно, що я почав отримувати цю проблему, коли скинута схема очікувала hbm2ddl.auto = true створить db та таблиці. проте це не вдалося. але Вень я створив порожню схему hbm2ddl працював над створенням таблиць
Saurabh

IP машини бази даних була змінена , але DNS вирішувала до старого :-(
Іллідан

24

додати spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.MySQLDialectу файл application.properties


Це чудова відповідь - дозволяє мені використовувати MockBean для мого класу баз даних і не мати реальної інформації про з'єднання в моєму профілі властивостей
Тейлор

Додавання spring.jpa.properties.hibernate.dialect до програми.properties допомогло мені. Дякую)
Макс

22

Я отримав цю помилку, коли моя база даних не була створена. Після створення БД вручну він працював чудово.


1
Зазвичай ви можете уникнути створення вручну, використовуючи "spring.jpa.hibernate.ddl-auto = create"
Андрій

@Andrei - як / де я б зазначив "spring.jpa.hibernate.ddl-auto = create"?
Алекс Worden

2
@AlexWorden, Андрій мав на увазі, що ви можете помістити його у application.properties, якщо це Spring Boot. Має бути еквівалент для конфігурації Spring на основі xml.
ACV

Чи з’являється ця помилка лише тоді, коли база даних не існує, а також коли таблиць всередині бази даних немає?
зигімантус

1
Я вказав неправильний пароль, і я зіткнувся з тією ж помилкою. Дякую ACV, ти мені дуже допоміг.
Санту

17

Я також зіткнувся з подібним питанням. Але це було пов’язано з наданим недійсним паролем. Також хотілося б сказати, що ваш код виглядає як старий код із використанням весни. Ви вже згадували, що ви використовуєте весняний завантажувач, що означає, що більшість речей буде налаштована автоматично для вас. hibernate dialect буде автоматично обраний на основі драйвера DB, доступного на classpath, а також дійсних облікових даних, які можна використовувати для перевірки належного з'єднання. Якщо з підключенням виникнуть проблеми, ви знову зіткнетеся з тією ж помилкою. У програмі application.properties потрібні лише 3 властивості

# Replace with your connection string
spring.datasource.url=jdbc:mysql://localhost:3306/pdb1

# Replace with your credentials
spring.datasource.username=root
spring.datasource.password=

8

Я зіткнувся з тією ж проблемою, і моя проблема полягала в тому, що БД, до якої я намагався підключитися, не існувала.

Я створив БД, перевірив URL / рядок з'єднання та перезавантажив і все працював так, як очікувалося.


Дякую, що ваш коментар змусив мене перевірити порт підключення, який був неправильним
Feras

4

це відбувається тому, що ваш код не є тюком для підключення бази даних. Переконайтесь, що у вас є драйвер та ім'я користувача mysql, пароль правильний.


4

Переконайтеся , що ваш application.propertiesмає все правильно інформацію: (я змінив дб порт від 8889до 3306він працював)

 db.url: jdbc:mysql://localhost:3306/test

4

У весняному завантаженні jpa java config потрібно розширити JpaBaseConfiguration і реалізувати його абстрактні методи.

@Configuration
public class JpaConfig extends JpaBaseConfiguration {

    @Override
    protected AbstractJpaVendorAdapter createJpaVendorAdapter() {
        final HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
        return vendorAdapter;
    }

    @Override
    protected Map<String, Object> getVendorProperties() {
        Map<String, Object> properties = new HashMap<>();
        properties.put("hibernate.dialect", "org.hibernate.dialect.PostgreSQLDialect");
    }

}

у деяких випадках application.properties не може побачити зміни властивостей. І я додав Properties.put, як вище, і працював нормально.Thx для відповіді.
fatih yavuz

4

Видаліть зайву конфігурацію в сплячому режимі

Якщо ви використовуєте Spring Boot, вам не потрібно чітко вказувати конфігурацію JPA та Hibernate, оскільки Spring Boot може це зробити для вас.

Додати властивості конфігурації бази даних

У application.propertiesфайлі конфігурації Spring Boot ви можете додати властивості конфігурації бази даних:

spring.datasource.driverClassName = "org.postgresql.Driver
spring.datasource.url = jdbc:postgresql://localhost:5432/teste?charSet=LATIN1
spring.datasource.username = klebermo
spring.datasource.password = 123

Додайте специфічні властивості в сплячку

У цьому ж application.propertiesфайлі конфігурації ви також можете встановити власні властивості в сплячому режимі:

# Log SQL statements
spring.jpa.show-sql = false

# Hibernate ddl auto for generating the database schema
spring.jpa.hibernate.ddl-auto = create

# Hibernate database Dialect
spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect

Це воно!


Додавання spring.jpa.properties.hibernate.dialect до програми.properties допомогло мені. Дякую)
Макс

3

У мене був такий самий випуск. додавши це до application.properties вирішив проблему:

spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.MySQLDialect

Додавання spring.jpa.properties.hibernate.dialect до програми.properties допомогло мені. Дякую)
Макс

2

У моєму випадку користувач не зміг підключитися до бази даних. Якщо виникла проблема, якщо журнал містить попередження перед винятком:

WARN HHH000342: Could not obtain connection to query metadata : Login failed for user 'my_user'.

2

Переконайтеся, що у вас є база даних в такому плані, як це зробили ОП Це була моя проблема.


Чи можете ви детальніше розробити? Що ви маєте на увазі під цією відповіддю?
Тунакі

Мені просто потрібно було додати залежності mysql.
obesechicken13

2

Моя проблема полягала в тому, що вбудована база даних вже була підключена. тісний зв’язок


1
Я можу підтвердити, що існує якась проблема в сплячому режимі, яка повідомляє про цю помилку, коли не вдається підключитися. Я міг відтворити проблему з включенням та вимиканням мережі.
borjab

2

У мене виникло це питання, коли Eclipse не зміг знайти драйвер JDBC. Щоб отримати цю роботу, довелося зробити градус оновлення від затемнення.


2

Нижче наведено деякі причини hibernate.dialectне встановленого питання. Більшість із цих винятків відображаються в журналі запуску, після якого нарешті слідує згадана проблема.

Приклад: Весняний завантажувальний додаток з БД Postgres

1. Перевірте, чи база даних фактично встановлена ​​та її сервер запущений.

  • org.postgresql.util.PSQLException: Підключення до localhost: 5432 відмовлено. Переконайтесь, що ім'я хоста та порт правильні та чи поштовий майстер приймає TCP / IP-з'єднання.
  • java.net.ConnectException: Підключення відмовлено: підключити
  • org.hibernate.service.spi.ServiceException: неможливо створити запитувану службу [org.hibernate.engine.jdbc.env.spi.JdbcEnvironment]

2. Перевірте, чи правильно вказано ім'я бази даних.

  • org.postgresql.util.PSQLException: FATAL: база даних "foo" не існує

    У application.propertiesфайлі

    spring.datasource.url = jdbc:postgresql://localhost:5432/foo

    але fooне існувало Тому я створив базу даних з pgAdmin для postgres

    CREATE DATABASE foo;

3. Перевірте, чи доступні ім'я хосту та порт сервера.

  • org.postgresql.util.PSQLException: Підключення до localhost: 5431 відмовлено. Переконайтесь, що ім'я хоста та порт правильні та чи поштовий майстер приймає TCP / IP-з'єднання.
  • java.net.ConnectException: Підключення відмовлено: підключити

4. Перевірте правильність облікових даних бази даних.

  • як згадував @Pankaj
  • org.postgresql.util.PSQLException: FATAL: помилка автентифікації пароля для користувача "postgres"

    spring.datasource.username= {DB USERNAME HERE}

    spring.datasource.password= {DB PASSWORD HERE}


1

Якщо ви використовуєте цей рядок:

sessionFactory.getHibernateProperties().put("hibernate.dialect", env.getProperty("hibernate.dialect"));

переконайтеся, що env.getProperty("hibernate.dialect")це не нуль.


1

Те саме, але в JBoss WildFly AS .

Вирішено з властивостями в моїх META-INF/persistence.xml

<properties>
            <property name="hibernate.transaction.jta.platform"
                value="org.hibernate.service.jta.platform.internal.JBossAppServerJtaPlatform" />
            <property name="spring.jpa.database-platform" value="org.hibernate.dialect.PostgreSQLDialect" />
            <property name="spring.jpa.show-sql" value="false" />
</properties>

1

Для тих, хто працює з AWS MySQL RDS, це може статися, коли ви не можете підключитися до бази даних. Перейдіть до налаштування груп безпеки AWS для MySQL RDS та відредагуйте вхідне правило IP, оновивши MyIP.

Я зіткнувся з цією проблемою, і робивши вище, я вирішив проблему.


Я дозволив увесь трафік групі безпеки RDS Aurora MySQL, це зробило для мене трюк. Якщо ви хочете бути більш конкретними або для prod env, додайте лише дозволені ips
AleksandarT

1

У мене теж була ця проблема. У моєму випадку це було тому, що користувачеві MySQL не було призначено грантів. Призначення грантів користувачеві MySQL, який використовує моя програма, вирішив проблему:

grant select, insert, delete, update on my_db.* to 'my_user'@'%';

1

У мене був такий самий випуск, і після налагодження виявляється, що Spring application.properties мав неправильну IP-адресу для сервера DB

spring.datasource.url=jdbc:oracle:thin:@WRONG:1521/DEV

1

Я відтворив це повідомлення про помилку в наступних трьох випадках:

  • Не існує користувача бази даних з ім’ям користувача, записаним у файлі application.properties або файлом persistent.properties або, як у вашому випадку, у файлі HibernateConfig
  • Розгорнута база даних має цього користувача, але користувач ідентифікується іншим паролем, ніж той, що знаходиться в одному з вищезазначених файлів
  • База даних містить цього користувача та паролі, але користувач не має всіх привілеїв, необхідних для виконання всіх завдань із бази даних, які виконує ваш додаток Spring-boot.

Очевидним рішенням є створення нового користувача бази даних з тим же ім’ям користувача та паролем, що і у програмі Spring-boot, або змінити ім’я користувача та пароль у файлах додатка Spring-boot, щоб відповідати існуючому користувачеві бази даних та надавати достатній привілей цьому користувачеві бази даних. У випадку з базою даних MySQL це можна зробити, як показано нижче:

mysql -u root -p 
>CREATE USER 'theuser'@'localhost' IDENTIFIED BY 'thepassword';
>GRANT ALL ON *.* to theuser@localhost IDENTIFIED BY 'thepassword';
>FLUSH PRIVILEGES;

Очевидно, що в Postgresql є подібні команди, але я не перевіряв, чи у випадку Postgresql це повідомлення про помилку може бути відтворене в цих трьох випадках.


0

У мене була така ж проблема, і це було викликано тим, що не вдалося підключитися до екземпляра бази даних. Шукайте в журналі над цією помилкою хибернальну помилку HHH000342, вона повинна дати вам уявлення про те, де збій db-з'єднання (неправильне ім’я користувача / пароль, URL тощо)


0

Це сталося зі мною, тому що я не додав conf.configure();попереднього початку сеансу:

Configuration conf = new Configuration();
conf.configure();

0

Переконайтеся, що ви ввели дійсні деталі в application.properties та чи є ваш сервер баз даних. Як приклад під час підключення до MySQL перевірте, чи правильно працює XAMPP .


0

Я зіткнувся з тим же питанням: db, з яким я намагався підключитися, не існував. Я використовував jpa.database=default(що, мабуть, означає, що він спробує підключитися до бази даних, а потім автоматично вибрати діалект). Після того, як я запустив базу даних, вона працювала нормально без будь-яких змін.


0

Я зіткнувся з цим питанням через повернення версії Mysql 8.0.11 назад до 5.7, вирішеної для мене




0

У мене була та сама помилка,

 Caused by: org.hibernate.HibernateException: Access to DialectResolutionInfo cannot be null when 'hibernate.dialect' not set

у моєму випадку WAR мав application.properties всередині, який вказував на сервер розробки,
де зовнішні application.properties вказували на правильний сервер БД.

переконайтеся, що у вас немає жодного іншого application.properties на classpath / jars ...

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.