Problem with integration of JPA + Hibernate

Discussion in 'Programming' started by AzRoDoRzA, Mar 19, 2020.

  1. Hello everyone,

    I'm having trouble integrating JPA and Hibernate to my plugin.
    I followed this tutorial but I still get the error :
    Code (Text):
    No Persistence provider for EntityManager named persistence-unit
    I have been searching for like 5-6 hours but I did not find any solution. I don't know what I'm doing wrong.

    I'm doing my plugin with gradle, this is my build.gradle :

    Code (Text):
    plugins {
        id 'java'
    }

    repositories {
        mavenCentral()
        maven {
            url "https://hub.spigotmc.org/nexus/content/repositories/snapshots"
        }
        maven {
            url = "https://oss.sonatype.org/content/repositories/snapshots/"
        }
    }


    dependencies {
        compile 'javax.servlet:javax.servlet-api:3.1.0'
        compile 'org.slf4j:slf4j-simple:1.7.7'
        compile 'org.javassist:javassist:3.15.0-GA'
        compile 'mysql:mysql-connector-java:5.1.31'
        compile "org.hibernate:hibernate-core:5.4.11.Final"
        compile "org.spigotmc:spigot-api:1.11.2-R0.1-SNAPSHOT"
    }

    jar {
        baseName = 'ServerSync'
        version =  '1.0.0'
    }

    task copyJar(type: Copy) {
        from jar // here it automatically reads jar file produced from jar task
        into serverPath + "/plugins"
    }


    task runSpigot(type: JavaExec, dependsOn: copyJar) {
        main = '-jar'
        args new File("/" + serverPath, serverJarName), "nogui"
        workingDir = serverPath
    }
    build.dependsOn {
        runSpigot
    }

    This is my persistence.xml (the exact same as the tutorial, except for the <class> and the database information) which is placed under src/main/resources/META-INF :
    Code (Text):
    <?xml version="1.0" encoding="UTF-8" ?>
    <persistence xmlns="http://xmlns.jcp.org/xml/ns/persistence"
                 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                 xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence
                        http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd"
                 version="2.1">
        <persistence-unit name="persistence-unit" transaction-type="RESOURCE_LOCAL">

            <class>serversync.Players</class>
            <exclude-unlisted-classes>true</exclude-unlisted-classes>
            <properties>
                <property name="javax.persistence.jdbc.driver" value="com.mysql.jdbc.Driver" />
                <property name="javax.persistence.jdbc.url" value="jdbc:mysql://yourdatabase.com:3306" />
                <property name="javax.persistence.jdbc.user" value="yourusername" />
                <property name="javax.persistence.jdbc.password" value="yourpassword" />
                <property name="javax.persistence.schema-generation.database.action" value="create" />
                <!-- Hibernate Specific -->
                <property name="hibernate.show_sql" value="true" />
            </properties>
        </persistence-unit>
    </persistence>
    This is my entity class named Players :
    Code (Java):
    package serversyncspigot.hibernate;

    import javax.persistence.*;

    @Table(name = "players")
    @javax.persistence.Entity
    public class Players {

        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        @Column(name = "id")
        private int id;

        @Column(name = "uuid")
        private String uuid;

        public int getId() {
            return id;
        }

        public void setId(int id) {
            this.id = id;
        }

        public String getUuid() {
            return uuid;
        }

        public void setUuid(String uuid) {
            this.uuid = uuid;
        }
    }
    This is my database class :
    Code (Java):
    package serversyncspigot.database;

    import org.bukkit.entity.Entity;
    import serversyncspigot.Main;
    import serversyncspigot.hibernate.Players;

    import javax.persistence.EntityManager;
    import javax.persistence.EntityManagerFactory;
    import javax.persistence.EntityTransaction;
    import javax.persistence.Persistence;
    import java.sql.Connection;
    import java.sql.DriverManager;
    import java.sql.SQLException;
    import java.sql.Statement;

    public class Database {
        public static void write() {
            EntityManagerFactory emf = Persistence.createEntityManagerFactory("persistence-unit");
            EntityManager em = emf.createEntityManager();
            EntityTransaction tx = em.getTransaction();
            tx.begin();

            Players data = new Players();
            data.setUuid("test");

            em.persist(data);

            tx.commit();
            em.close();
            emf.close();

        }

        public static void read() {
            EntityManagerFactory emf = Persistence.createEntityManagerFactory("persistence-unit");
            EntityManager em = emf.createEntityManager();
            EntityTransaction tx = em.getTransaction();
            tx.begin();

            Entity data = em.find(Entity.class, 1);

            System.out.println("entity ="+ data);

            tx.commit();
            em.close();
            emf.close();
        }
    }
    and i'm calling this in my onEnable() :

    Code (Java):
    Thread.currentThread().setContextClassLoader(getClass().getClassLoader());
    database = new Database();
    database.write();
    database.read();

    The error is triggering on the first line of the write method.

    I'm for sure missing something but I can't figure out what..

    I attached my project structure.

    Thank you in advance for you help.
     

    Attached Files:

  2. Perhaps I'm wrong because I'm just a Java dev getting into Spigot, but why don't you use JPA repository to do this? It provides the same functionality. It's there for heightened security and it's much easier to use. It creates an EntityManager for you and does queries without you having to create any transactional business code manually.
     
  3. When I use hibernate, I just create a Configuration object, use the provided methods to configure it and then use #buildSessionFactory. Clean, no config files needed.
     
  4. Hello!
    Sorry for the late answer I was busy those days..

    Thank you for your answer guys.

    Unfortunately, we can't use JPA repository with Spigot..

    I ended up on not using Hibernate at all. But i'll try that one day when I will have time!

    I keep this thread open in case someone is facing the same issue and someone else provide a solution!