it-swarm.com.ru

Spring-boot: нельзя использовать постоянство

У меня есть дни в этом, и - хотя я многому учусь - начинаю отчаиваться. 

Я перепробовал все предложения по этому отличному вопросу: 

Не назван поставщик сохраняемости для EntityManager

В какой-то момент это работало с использованием вездесущего класса HibernateUtil, но мне было сказано перейти к простому стилю JPA:

Предложения по улучшению метода контроллера Spring RESTful

К сожалению, я не мог заставить инъекцию боба работать должным образом в весенней загрузке. Вот моя попытка:

Spring JPA (Hibernate) Нет подходящего компонента типа: javax.persistence.EntityManagerFactory

После долгой работы по этому пути я получил нулевого менеджера сущностей. Я нашел это и начал думать, что это не могло работать:

Использование JPA2 в Tomcat 6: @PersitenceContext не работает, EntityManager равен нулю

Мне кажется, что EntityManagerFactory абсолютно должен быть бином в любом контексте, который создает Spring-Boot, но ... в любом случае. Я думаю, что по крайней мере это будет работать:

Запуск приложения:

@Configuration
@ComponentScan
@EnableAutoConfiguration
public class Application {

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

Контроллер:

@Controller
public class GetController {

    private static final String PERSISTENCE_UNIT_NAME = "cpJpaPu";  

    @RequestMapping(value = "/user", method = RequestMethod.GET)
    public @ResponseBody User getUser(@RequestParam(value="id", required=true) int id) {
        User user = null;

        EntityManagerFactory emf = Persistence.createEntityManagerFactory(PERSISTENCE_UNIT_NAME);
        EntityManager em = emf.createEntityManager();
        UserDAO userDao = new UserDAO();
        userDao.setEntityManager(em);
        user = userDao.load(id);

        return user;
    }
}

DAO:

public class UserDAO {

    public EntityManager entityManager;

    public void setEntityManager(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public EntityManager getEntityManager() {
        return entityManager;
    }   

    public void insert(User user) {
        entityManager.persist(user);
    }

    public User load(int id) {
        return entityManager.find(User.class, id);
    }
}

/src/main/resources/persistence.xml:

<persistence xmlns="http://Java.Sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://Java.Sun.com/xml/ns/persistence http://Java.Sun.com/xml/ns/persistence/persistence_1_0.xsd" version="1.0">
  <persistence-unit name="cpJpaPu" transaction-type="RESOURCE_LOCAL">
    <provider>org.hibernate.ejb.HibernatePersistence</provider>
    <class>com.mydomain.User</class>
    <properties>
      <property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect"/>
      <property name="hibernate.connection.driver_class" value="org.postgresql.Driver"/>
      <property name="hibernate.show_sql" value="false"/>
      <property name="hibernate.connection.username" value="user"/>
      <property name="hibernate.connection.password" value=""/>
      <property name="hibernate.connection.url" value="jdbc:postgresql://localhost:5432/mydb"/>
    </properties>
  </persistence-unit>
</persistence>

И это не работает

javax.persistence.PersistenceException: No Persistence provider for EntityManager named cpJpaPu
    javax.persistence.Persistence.createEntityManagerFactory(Persistence.Java:61)
    javax.persistence.Persistence.createEntityManagerFactory(Persistence.Java:39)
    com.mydomain.GetController.getUser(GetController.Java:25)
    Sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    Sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
    Sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
    Java.lang.reflect.Method.invoke(Unknown Source)
    org.springframework.web.method.support.InvocableHandlerMethod.invoke(InvocableHandlerMethod.Java:214)
    org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.Java:132)
    org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.Java:104)
    org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandleMethod(RequestMappingHandlerAdapter.Java:748)
    org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.Java:689)
    org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.Java:83)
    org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.Java:947)
    org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.Java:878)
    org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.Java:946)
    org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.Java:837)
    javax.servlet.http.HttpServlet.service(HttpServlet.Java:621)
    org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.Java:822)
    javax.servlet.http.HttpServlet.service(HttpServlet.Java:728)
    org.springframework.web.filter.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.Java:77)
    org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.Java:108)

--- Добавлена ​​информация ---

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.mygroup</groupId>
    <artifactId>myartifact</artifactId>
    <version>0.1.0</version>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>0.5.0.M6</version>
    </parent>

    <dependencies>
        <!--  Spring framework -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!--  Hibernate -->
        <dependency>
            <groupId>org.hibernate</groupId>
            <artifactId>hibernate-core</artifactId>
            <version>4.3.0.Final</version>
        </dependency>

        <dependency>
            <groupId>org.hibernate</groupId>
            <artifactId>hibernate-entitymanager</artifactId>
            <!-- Must override version or face stack traces -->
            <version>4.3.0.Final</version>
        </dependency>

        <!-- Spring ORM, works with Hibernate -->   
        <dependency>
           <groupId>org.springframework</groupId>
           <artifactId>spring-orm</artifactId>
        </dependency>

        <!--  Spring implementation of Jackson for RESTful JSON -->
        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-databind</artifactId>         
        </dependency>

        <!--  JDBC -->
        <dependency>
            <groupId>postgresql</groupId>
            <artifactId>postgresql</artifactId>
            <version>9.1-901.jdbc4</version>
        </dependency>

        <!-- Logging -->
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-log4j12</artifactId>
        </dependency>

        <!-- Prevent logging conflicts -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-logging</artifactId>
            <scope>compile</scope>
            <exclusions>                
                <exclusion>
                    <groupId>ch.qos.logback</groupId>
                    <artifactId>logback-classic</artifactId>
                </exclusion>
            </exclusions> 
        </dependency>
    </dependencies>

    <properties>
        <start-class>com.cloudfordev.controlpanel.Application</start-class>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    </properties>

    <build>
        <plugins>   
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>

            <plugin>
                <groupId>org.Apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>          
                <configuration>
                    <source>1.7</source>
                    <target>1.7</target>
                </configuration>
            </plugin>
        </plugins>
    </build>

    <repositories>
        <repository>
            <id>spring-snapshots</id>
            <url>http://repo.spring.io/libs-snapshot</url>
            <snapshots><enabled>true</enabled></snapshots>
        </repository>
    </repositories>

    <pluginRepositories>
        <pluginRepository>
            <id>spring-snapshots</id>
            <url>http://repo.spring.io/libs-snapshot</url>
            <snapshots><enabled>true</enabled></snapshots>
        </pluginRepository>
    </pluginRepositories>
</project>
12
Lurk21

На этот вопрос ответили с гораздо лучшей архитектурой здесь:

Spring JPA (Hibernate) Нет подходящего компонента типа: javax.persistence.EntityManagerFactory

1
Lurk21

spring boot не читает файл persistence.xml по умолчанию, см. документ здесь

https://docs.spring.io/spring-boot/docs/current/reference/html/howto-data-access.html

так что если вы хотите продолжать использовать файл persistence.xml, просто добавьте приведенный ниже код в ваш класс AppConfig

@Bean
public LocalEntityManagerFactoryBean entityManagerFactory(){
     LocalEntityManagerFactoryBean factoryBean = new LocalEntityManagerFactoryBean();
    factoryBean.setPersistenceUnitName("cpJpaPu");
    return factoryBean;
}
6
vedat

Некоторые функции JPA, к сожалению, работают только в конфигурации XML, но я не вижу ничего подобного в вашей. Я не думаю, что persistence.xml загружается по умолчанию, так что, вероятно, это проблема. Так почему бы вам не использовать поток и не использовать Java и application.properties для настройки менеджера сущностей? Образец JPA из Spring Boot содержит все необходимое для начала работы. Он использует Spring Data JPA, тогда как ваш код использует только API JPA, но вы можете легко вернуться к этому уровню, просто удалив зависимости Spring Data в образце.

Недавние снимки Spring Boot имеют функцию, которая позволяет вам создать свою собственную LocalEntityManagerFactoryBean, чтобы вы могли добавить пользовательскую конфигурацию XML, но до M7 вам пришлось бы выполнять всю конфигурацию JPA вручную, как только вам потребовалась пользовательская EntityManager.

Нотабене вы на самом деле не очень эффективно используете внедрение зависимостей в своем контроллере - почему бы вам просто не внедрить UserDao?

1
Dave Syer

Файл persistence.xml должен находиться в каталоге META-INF

/src/main/resources/META-INF/persistence.xml

1
xi.lin

Я решил эту проблему после удаления всех папок hibernate-core в каталоге ниже: .m2\repository\org\hibernate\hibernate-core

и перестроил мои проекты.

Теперь он отлично работает под Spring Boot 2.0.4.RELEASE. И я уверен, что он загружает main/resources/META-INF/persistence.xml без внедрения LocalEntityManagerFactoryBean Bean.

Прежде чем удалить их, в указанной выше папке есть 4 версии hibernate-core. Это «4.3.6»/«5.0.12»/«5.2.17»/«5.3.4».

После того как я удалил их, после перестройки моих проектов появилось «5.0.12»/«5.2.17»/«5.3.4».

И когда я углубился в эту проблему, я обнаружил, что папка «hibernate-core-5.2.17.Final.jar» в предыдущей папке «5.2.17» больше обычной и не имеет «hibernate-core-5.2.17». .Final.jar.sha1" .

Таким образом, это может быть вызвано плохой сетью или плохим зеркалом.

0
capcom923