Java 需要一个无法找到的“org.hibernate.SessionFactory”类型的 bean
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/43533691/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
required a bean of type 'org.hibernate.SessionFactory' that could not be found
提问by kapil joshi
I am getting following error whenever started application spring boot.
每当启动应用程序 spring 启动时,我都会收到以下错误。
APPLICATION FAILED TO START
应用程序无法启动
Description:
描述:
Field session in com.base.model.AbstractDao required a bean of type 'org.hibernate.SessionFactory' that could not be found.
com.base.model.AbstractDao 中的字段会话需要一个无法找到的“org.hibernate.SessionFactory”类型的 bean。
Action:
行动:
Consider defining a bean of type 'org.hibernate.SessionFactory' in your configuration.
考虑在您的配置中定义一个“org.hibernate.SessionFactory”类型的 bean。
I have added implementation of my application:
我添加了我的应用程序的实现:
POM.xml
POM文件
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.example</groupId>
<artifactId>demo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>demo</name>
<description>Demo project for Spring Boot</description>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.5.2.RELEASE</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- Spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>4.2.2.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- Hibernate dependency -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>5.1.5.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>5.0.3.Final</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
application.property
应用程序属性
spring.datasource.driver-class-name=com.mysql.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/test
spring.datasource.username = root
spring.datasource.password = root
hibernate.dialect = org.hibernate.dialect.MySQLDialect
spring.jpa.properties.hibernate.current_session_context_class=org.springframework.orm.hibernate4.SpringSessionContext
Configuration class
配置类
@Configuration
@EnableTransactionManagement
@ComponentScan({"configure"})
@PropertySource({"classpath:application.properties"})
public class HibernateConfiguration {
@Autowired
private Environment environment;
@Bean
public LocalSessionFactoryBean sessionFactory(){
LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();
sessionFactory.setDataSource(dataSource());
sessionFactory.setPackagesToScan(new String[]{"com.base","com.base.model"});
sessionFactory.setMappingResources(new String[]{"Employee.hbm.xml"});
sessionFactory.setHibernateProperties(hibernateProperties());
return sessionFactory;
}
@Bean
public Properties hibernateProperties() {
Properties properties = new Properties();
properties.put("hibernate.dialect", environment.getRequiredProperty("hibernate.dialect"));
properties.put("hibernate.show_sql", environment.getRequiredProperty("hiberante.show_sql"));
properties.put("hibernate.format_sql", environment.getRequiredProperty("hibernate.format_sql"));
return properties;
}
@Bean
public DataSource dataSource() {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setDriverClassName(environment.getRequiredProperty("jdbc.driverClassName"));
dataSource.setUrl(environment.getRequiredProperty("jdbc.url"));
dataSource.setUsername(environment.getRequiredProperty("jdbc.userName"));
dataSource.setUsername(environment.getRequiredProperty("jdbc.password"));
return dataSource;
}
@Bean
public SessionFactory sessionFactory(HibernateEntityManagerFactory hemf){
return hemf.getSessionFactory();
}
}
Employee.java
雇员.java
public class Employee implements Serializable{
/**
*
*/
private static final long serialVersionUID = 1L;
private int id;
private String name;
private String country;
public int getId(){
return this.id;
}
public void setId(int id){
this.id = id;
}
public String getName(){
return this.name;
}
public void setName(String name){
this.name = name;
}
public void setCountry(String country){
this.country = country;
}
public String getCountry(){
return this.getCountry();
}
@Override
public String toString() {
return "Employee [id=" + id + ", name=" + name + ", country="
+ country + "]";
}
}
Employee.hbm.xml
员工.hbm.xml
<?xml version='1.0' encoding='UTF-8'?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name="com.base.model.Employee" table="Person">
<id name="id" type="java.lang.Integer">
<generator class="native"></generator>
</id>
<property name="name" type="java.lang.String">
<column name="name" not-null="true"></column>
</property>
<property name="country" type="java.lang.String">
<column name="country"></column>
</property>
</class>
</hibernate-mapping>
EmployeeDaoImpl
EmployeeDaoImpl
@Component
public class EmployeeDataDaoImpl {
@Autowired
SessionFactory sessionFactory;
public List<Employee> findAllEmployee(){
//// Criteria cri = getSession().createCriteria(Employee.class);
// List<Employee> dbList = cri.list();
// for (Employee employee : dbList) {
// System.out.println(employee.getCountry());
// }
return null;
}
}
I have looked up the same error code on stackoverflow but none of the solutions worked and thus posting it here again with my code. Hoping someone else can point out where I am going wrong.
我在 stackoverflow 上查找了相同的错误代码,但没有一个解决方案有效,因此用我的代码再次发布在这里。希望其他人能指出我哪里出错了。
采纳答案by M. Deinum
For starters there are a couple of things of with your configuration
对于初学者来说,您的配置有几件事
- Mixing jars from different Spring and Hibernate versions
- Too may already managed dependencies
- Trying to be smarter then Spring Boot.
- 混合来自不同 Spring 和 Hibernate 版本的 jars
- 太可能已经管理依赖项
- 试图比 Spring Boot 更聪明。
For 1. and 2. just remove the <version>
tag for spring-orm
and the hibernate-core
and hibernate-entitymanager
manager dependencies. Spring Boot is already managing those. You can actually remove all the org.springframework
dependencies those are already pulled in by the starters (and actually the hibernate ones also).
对于1和2只是删除<version>
了标签spring-orm
和hibernate-core
和hibernate-entitymanager
经理的依赖。Spring Boot 已经在管理这些。您实际上可以删除org.springframework
启动器已经引入的所有依赖项(实际上也可以删除休眠的依赖项)。
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
</dependencies>
Next in your configuration you have at least 2 SessionFactory
's configured. I would suggest to use annotations to define your entities instead of hbm.xml
files.
接下来在您的配置中,您至少SessionFactory
配置了2 个。我建议使用注释来定义您的实体而不是hbm.xml
文件。
@Entity
@Table("person")
public class Employee implements Serializable{
/**
*
*/
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue
private int id;
@Column(nullable=false)
private String name;
private String country;
}
When using JPA annotations Hibernate will automatically detect your entities (especially combined with Spring Boot) which makes it very powerful. Ofcourse you can now remove your Employee.hbm.xml
.
使用 JPA 注释时,Hibernate 会自动检测您的实体(尤其是与 Spring Boot 结合使用),这使得它非常强大。当然,您现在可以删除您的Employee.hbm.xml
.
Next your EmployeeDataDaoImpl
I strongly suggest to use plain JPA over plain Hibernate. Generally that provides enough for you to work with.
接下来,EmployeeDataDaoImpl
我强烈建议在普通 Hibernate 上使用普通 JPA。通常,这为您提供了足够的工作。
@Repository
public class EmployeeDataDaoImpl {
@PersistenceContext
private EntityManager entityManger;
public List<Employee> findAllEmployee(){
return em.createQuery("select e from Employee e", Employee.class).getResultList();
}
}
With this setup you can basically completely remove your HibernateConfiguration
. Yes you can as Spring Boot detects Hibernate and automatically creates a JpaTransactionManager
, enables transactions and preconfigured a EntityManagerFactory
.
通过此设置,您基本上可以完全删除您的HibernateConfiguration
. 是的,你可以,因为 Spring Boot 检测到 Hibernate 并自动创建一个JpaTransactionManager
,启用事务并预先配置一个EntityManagerFactory
.
If you really want to use plain hibernate with a SessionFactory
just use a HibernateJpaSessionFactoryBean
to expose the underlying SessionFactory
of the EntityManagerFactory
.
如果你真的想使用纯休眠与SessionFactory
只使用一个HibernateJpaSessionFactoryBean
,露出底层SessionFactory
的EntityManagerFactory
。
@Bean
public HibernateJpaSessionFactoryBean sessionFactory(EntityManagerFactory emf) {
HibernateJpaSessionFactoryBean factory = new HibernateJpaSessionFactoryBean();
factory.setEntityManagerFactory(emf);
return factory;
}
However as mentioned I would strongly suggest to use plain JPA as that is a lot easier to setup and with the current state of JPA it offers almost as much of the functionality as plain Hibernate does.
然而,正如前面提到的,我强烈建议使用普通 JPA,因为它更容易设置,而且在 JPA 的当前状态下,它提供的功能几乎与普通 Hibernate 一样多。
Pro TipYou have a dependency on spring-boot-starter-data-jpa
which means you are having a dependency on Spring Data JPA. Which would make things even easier if you would use JPA. You can remove your EmployeeDataDaoImpl
and just create an interface and use that.
专业提示您依赖,spring-boot-starter-data-jpa
这意味着您依赖 Spring Data JPA。如果您使用 JPA,这将使事情变得更加容易。您可以删除您的EmployeeDataDaoImpl
,只需创建一个界面并使用它。
public interface EmployeeRepository extends JpaRepository<Employee, Long> {}
That is it, all the CRUD methods (findOne
, findAll
, save
etc.) are provided for you without you having to create an implementation.
这就是它,所有的CRUD方法(findOne
,findAll
,save
提供等)为您无需您创建一个实现。
回答by Monzurul Haque Shimul
Your SessionFactory configuration is wrong. From your pom.xml I see you are using hibernate version 5, so your configuration should be:
您的 SessionFactory 配置错误。从你的 pom.xml 我看到你使用的是休眠版本 5,所以你的配置应该是:
spring.jpa.properties.hibernate.current_session_context_class=org.springframework.orm.hibernate5.SpringSessionContext
And also you have different versions of hibernate jars in your pom.xml, try to use same versions.
而且您的 pom.xml 中有不同版本的休眠 jar,请尝试使用相同的版本。