I'm new in jpa and hibernate, and it took me a while to set up the xml file(it might not be whole), lower the errors, and try to figure it all out. I'm using mariadb and have a database called jpadb, which im trying create and pass an "Employee" object from java. I get the error
:org.hibernate.PersistentObjectException: detached entity passed to
persist: model.Employee
my code is as follows:
persistence.xml
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" 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_2_0.xsd">
<persistence-unit name="sample" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<class>model.Employee</class>
<properties>
<property name="javax.persistence.jdbc.driver" value="org.mariadb.jdbc.Driver" />
<property name="javax.persistence.jdbc.url" value="jdbc:mariadb://localhost:3306/jpadb" />
<property name="javax.persistence.jdbc.user" value="root" />
<property name="javax.persistence.jdbc.password" value="root" />
</properties>
</persistence-unit>
</persistence>
pom.xml
<?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>sqlDemo</groupId>
<artifactId>demo</artifactId>
<version>1.0</version>
<packaging>jar</packaging>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<configuration>
<archive>
<manifest>
<mainClass>loader.MainApp</mainClass>
</manifest>
</archive>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
<groupId>org.mariadb.jdbc</groupId>
<artifactId>mariadb-java-client</artifactId>
<version>2.2.3</version>
</dependency>
<dependency>
<groupId>javax.persistence</groupId>
<artifactId>persistence-api</artifactId>
<version>1.0.2</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>5.2.17.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-c3p0</artifactId>
<version>5.2.17.Final</version>
</dependency>
</dependencies>
</project>
Employee.java
package model;
import javax.persistence.*;
#Entity
#Table (name="user")
public class Employee {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(name = "id")
private int eid;
#Column(name = "ename")
private String ename;
#Column(name = "salary")
private double salary;
#Column(name = "deg")
private String deg;
public Employee(int eid, String ename, double salary, String deg) {
super( );
this.eid = eid;
this.ename = ename;
this.salary = salary;
this.deg = deg;
}
public Employee( ) {
super();
}
public int getEid( ) {
return eid;
}
public void setEid(int eid) {
this.eid = eid;
}
public String getEname( ) {
return ename;
}
public void setEname(String ename) {
this.ename = ename;
}
public double getSalary( ) {
return salary;
}
public void setSalary(double salary) {
this.salary = salary;
}
public String getDeg( ) {
return deg;
}
public void setDeg(String deg) {
this.deg = deg;
}
#Override
public String toString() {
return "Employee [eid=" + eid + ", ename=" + ename + ", salary=" + salary + ", deg=" + deg + "]";
}
}
CreateEmployee.java
package service;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;
import model.Employee;
public class CreateEmployee {
public static void main( String[ ] args ) {
EntityManagerFactory emfactory = Persistence.createEntityManagerFactory( "sample" );
EntityManager entitymanager = emfactory.createEntityManager( );
entitymanager.getTransaction( ).begin( );
Employee employee = new Employee( );
employee.setEid( 1201 );
employee.setEname( "Maria" );
employee.setSalary( 40000 );
employee.setDeg( "Technical Manager" );
entitymanager.persist( employee );
entitymanager.getTransaction( ).commit( );
entitymanager.close( );
emfactory.close( );
}
}
I'm trying to go through tutorials, but due to hibernate-property version mismatches I'm having a really hard time. It took me a while to find the properties for mariadb in order for this to work. Thanks in advance.
set #GeneratedValue(strategy=GenerationType.IDENTITY) and remove the line employee.setEid( 1201 );
Your id is auto generated, you don't have to pass it when inserting a new row.
Remove the line employee.setEid( 1201 ); and it should do it. You should take a look at entity lifecycle. https://www.javabullets.com/jpa-entity-lifecycle/
Related
I am trying to setup my first Java Hibernate project and decided to follow the instructions on this YouTube video: https://www.youtube.com/watch?v=QJddHc41xrM&t=535s I made it to #08:50 where "jpa" was entered and the entitymanager setup was compiled. I can't get intellij to recognize this input and compile the code like in the video. What would be the next step to get this application working so I can simply enter 1 row into my database. Attached to this question are pictures of my class file setup and structure. I will also attach code to show how my entities, pom.xml, and persistence.xml file is setup. My main class that would start the transaction is empty and I want to know how I can make this work or what additional information I need to make it work. Any help would be much appreciated.
The code below is from my pom.xml file:
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.example</groupId>
<artifactId>HibernateJPA</artifactId>
<version>1.0-SNAPSHOT</version>
<name>HibernateJPA</name>
<packaging>war</packaging>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.target>11</maven.compiler.target>
<maven.compiler.source>11</maven.compiler.source>
<junit.version>5.9.1</junit.version>
</properties>
<dependencies>
<dependency>
<groupId>jakarta.servlet</groupId>
<artifactId>jakarta.servlet-api</artifactId>
<version>5.0.0</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.hibernate.orm</groupId>
<artifactId>hibernate-core</artifactId>
<version>6.0.2.Final</version>
</dependency>
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>3.0.2</version>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
<version>8.0.32</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>3.3.2</version>
</plugin>
</plugins>
</build>
</project>
The code below is from my persistence.xml file:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<persistence xmlns="https://jakarta.ee/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="https://jakarta.ee/xml/ns/persistence https://jakarta.ee/xml/ns/persistence/persistence_3_0.xsd"
version="3.0">
<persistence-unit name="default">
<class>entity.EmployeeEntity</class>
<properties>
<property name="hibernate.connection.url" value="jdbc:mysql://localhost:3306/testDB"/>
<property name="hibernate.connection.driver_class" value="com.mysql.cj.jdbc.Driver"/>
<property name="hibernate.connection.username" value="root"/>
<property name="hibernate.connection.password" value=""/>
</properties>
</persistence-unit>
</persistence>
The code below is from my Entity Employee class:
package entity;
import jakarta.persistence.*;
import java.util.Objects;
#Entity
#Table(name = "employee", schema = "testdb", catalog = "")
public class EmployeeEntity {
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Id
#Column(name = "id")
private int id;
#Basic
#Column(name = "first_name")
private String firstName;
#Basic
#Column(name = "last_name")
private String lastName;
#Basic
#Column(name = "salary")
private Integer salary;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public Integer getSalary() {
return salary;
}
public void setSalary(Integer salary) {
this.salary = salary;
}
#Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
EmployeeEntity that = (EmployeeEntity) o;
return id == that.id && Objects.equals(firstName, that.firstName) && Objects.equals(lastName, that.lastName) && Objects.equals(salary, that.salary);
}
#Override
public int hashCode() {
return Objects.hash(id, firstName, lastName, salary);
}
}
My project 's structure is as follow:
+--Main POM project: MyschoolKarafOSGI
+----Bundle project: KarafDataAPI
+----Bundle project: KarafDataAPI/resources/META-INF/persistence.xml
+----Bundle project: KarafDataAPI/resources/OSGI-INF/blueprint/blueprint.xml
My persistence.xml file:
<?xml version="1.0" encoding="UTF-8" ?>
<persistence version="2.0" 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_2_0.xsd">
<persistence-unit name="default" transaction-type="JTA">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<jta-data-source>osgi:service/javax.sql.DataSource/(osgi.jndi.service.name=myschool-ds)</jta-data-source>
<non-jta-data-source>osgi:service/javax.sql.DataSource/(osgi.jndi.service.name=myschool-ds)</non-jta-data-source>
<class>myschool.com.Entity.Student</class>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL8Dialect"/>
<property name="hibernate.hbm2ddl.auto" value="create-drop"/>
</properties>
</persistence-unit>
</persistence>
My blueprint.xml file:
<?xml version="1.0" encoding="UTF-8" ?>
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:jpa="http://aries.apache.org/xmlns/jpa/v2.0.0"
xmlns:tx="http://aries.apache.org/xmlns/transactions/v1.2.0"
xsi:schemaLocation="http://www.osgi.org/xmlns/blueprint/v1.0.0 http://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd">
<jpa:enable />
<tx:enable-annotations />
<bean id="persistenceUtil" class="myschool.com.Persistence.PersistenceUtil" />
<bean id="studentDataServiceImpl" class="myschool.com.DAO.StudentDataServiceImpl">
<argument ref="persistenceUtil" />
</bean>
<bean id="studentPersistenceService" class="myschool.com.DAO.StudentPersistenceServiceImpl" >
<argument ref="studentDataServiceImpl" />
</bean>
<service ref="studentPersistenceService" interface="myschool.com.PersistenceService.StudentPersistenceService" />
</blueprint>
My StudentPersistenceService interface:
package myschool.com.PersistenceService;
import myschool.com.Service.StudentDataService;
public interface StudentPersistenceService extends StudentDataService {
}
My StudentDataService interface:
package myschool.com.Service;
import myschool.com.Entity.Student;
import java.util.List;
public interface StudentDataService {
List<Student> getStudentList();
Student getStudentById(Long id);
int addStudent(Student student);
int updateStudent(Student student);
int deleteStudent(Long id);
}
My PersistenceUtil class:
package myschool.com.Persistence;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.transaction.Transactional;
#Transactional
public class PersistenceUtil {
#PersistenceContext(unitName = "default")
private EntityManager entityManager;
public EntityManager getEntityManager() {
return entityManager;
}
public void setEntityManager(EntityManager entityManager) {
this.entityManager = entityManager;
}
}
My Entity class:
package myschool.com.Entity;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlRootElement;
import java.util.Date;
#XmlRootElement(name = "Student")
#XmlAccessorType(XmlAccessType.FIELD)
#Entity
#Table(name = "STUDENTS")
public class Student {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "Id")
private Long id;
#Column(name = "LastName")
private String lastname;
#Column(name = "FirstName")
private String firstname;
#Column(name = "DateOfEnrollment")
private Date dateOfEnrollment;
public Student() {
}
public Student(Long id, String lastname, String firstname, Date dateofenrollment) {
this.id = id;
this.lastname = lastname;
this.firstname = firstname;
this.dateOfEnrollment = dateofenrollment;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getLastName() {
return lastname;
}
public void setLastName(String lastname) {
this.lastname = lastname;
}
public String getFirstName() {
return firstname;
}
public void setFirstName(String firstname) {
this.firstname = firstname;
}
public Date getDateOfEnrollment() {
return dateOfEnrollment;
}
public void setDateOfEnrollment(Date enrollment) {
this.dateOfEnrollment = enrollment;
}
}
My feature.xml file:
<?xml version="1.0" encoding="UTF-8" ?>
<features name="KarafFeatures-${project.version}" xmlns="http://karaf.apache.org/xmlns/features/v1.4.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://karaf.apache.org/xmlns/features/v1.4.0 ">
<repository>mvn:org.apache.karaf.features/standard/4.2.11/xml/features</repository>
<repository>mvn:org.apache.cxf.karaf/apache-cxf/3.4.4/xml/features</repository>
<repository>mvn:org.ops4j.pax.jdbc/pax-jdbc-features/1.5.0/xml/features</repository>
<feature name="KarafCommonAPI" version='${project.version}'>
<bundle>mvn:myschool.com/KarafCommonAPI/${project.version}</bundle>
</feature>
<feature name="KarafDataAPI" version='${project.version}'>
<bundle>mvn:myschool.com/KarafDataAPI/${project.version}</bundle>
</feature>
<feature name="KarafCommandLine" version='${project.version}'>
<bundle>mvn:myschool.com/KarafCommandLine/${project.version}</bundle>
</feature>
<feature name="KarafDataProvider" version='${project.version}'>
<config name="org.ops4j.datasource-myschool">
osgi.jdbc.driver.class=org.maria.jdbc.Driver
osgi.jdbc.driver.name=mariadb
pool=dbcp2
databaseName=myschool
user=admindb
password=welcome
url=jdbc:mysql://localhost:3306/myschool
dataSourceName=myschool-ds
org.apache.karaf.features.configKey=org.ops4j.datasource-myschool
</config>
<capability>
osgi.service;objectClass=javax.sql.DataSource;effective:=active;osgi.jndi.service.name=myschool-ds
</capability>
<feature>transaction</feature>
<feature>jndi</feature>
<feature dependency="true">aries-blueprint</feature>
<feature>jpa</feature>
<feature>hibernate</feature>
<feature>jdbc</feature>
<feature>pax-jdbc-spec</feature>
<bundle>mvn:org.ops4j.pax.jdbc/pax-jdbc-mariadb/1.5.0</bundle>
<bundle>mvn:org.mariadb.jdbc/mariadb-java-client/2.4.4</bundle>
<feature>pax-jdbc-config</feature>
<feature>pax-jdbc-mariadb</feature>
<feature>pax-jdbc-pool-dbcp2</feature>
</feature>
<feature name="KarafFeatures" version='${project.version}'>
<feature version='${project.version}'>KarafDataProvider</feature>
<feature version='${project.version}'>KarafCommonAPI</feature>
<feature version='${project.version}'>KarafDataAPI</feature>
<feature version='${project.version}'>KarafCommandLine</feature>
</feature>
</features>
My POM file:
<?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">
<parent>
<artifactId>MyschoolKarafOSGI</artifactId>
<groupId>myschool.com</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>KarafDataAPI</artifactId>
<packaging>bundle</packaging>
<name>KarafDataAPI</name>
<!-- FIXME change it to the project's website -->
<url>http://www.example.com</url>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>myschool.com</groupId>
<artifactId>KarafCommonAPI</artifactId>
<version>1.0-SNAPSHOT</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.eclipse.persistence</groupId>
<artifactId>javax.persistence</artifactId>
<version>2.1.0</version>
</dependency>
<dependency>
<groupId>javax.transaction</groupId>
<artifactId>javax.transaction-api</artifactId>
<version>1.2</version>
</dependency>
<dependency>
<groupId>javax.interceptor</groupId>
<artifactId>javax.interceptor-api</artifactId>
<version>1.2.2</version>
</dependency>
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf-rt-frontend-jaxrs</artifactId>
<version>${cxf.version}</version>
<scope>provided</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<extensions>true</extensions>
<configuration>
<instructions>
<Meta-Persistence>META-INF/persistence.xml</Meta-Persistence>
<Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
<Bundle-Version>${project.version}</Bundle-Version>
<Export-Package>myschool.com.DAO;myschool.com.DAO.*;myschool.com.PersistenceService.*;myschool.com.Persistence.*</Export-Package>
<Private-Package/>
<Import-Package>
javax.persistence;version="[2,3)",myschool.com.Entity.*,myschool.com.Service.*,*
</Import-Package>
</instructions>
</configuration>
</plugin>
</plugins>
</build>
</project>
I got the error:
GracePeriod Missing
Dependencies:(&(osgi.unit.name-default)(objectClass=javax.persistence.Entity
Manager)) Declarative Services
I tried to fix by many ways but none of them works.
Could anyone help me on this issue?
I am studying Spring Boot and I want to create a Rest Controller, and using a sql database, but there is a problem when I start the project :
Error:
(the error text is great I will leave the link)
And code:
OrderController.java
package ***;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.List;
import java.util.Map;
import java.util.Optional;
#RestController
public class OrderController {
#Autowired
private OrderRepository orderRep;
#GetMapping("/")
public List<Order> index(){
return (List<Order>) orderRep.findAll();
}
#GetMapping("/{id}")
public Order show(#PathVariable int id){
Optional<Order> orderId= orderRep.findById(id);
Order order = orderId.get();
return order;
}
#PostMapping("/search")
public List<Order> search(#RequestBody Map<String, String> body){
String searchItem = body.get("item");
return orderRep.findByTitleContainingOrContentContaining(searchItem);
}
#PostMapping("/")
public Order create(#RequestBody Map<String, String> body){
String item = body.get("item");
int price = Integer.parseInt(body.get("price"));
int quantity = Integer.parseInt(body.get("quantity"));
return orderRep.save(new Order(item, price,quantity));
}
#PutMapping("/{id}")
public Order update(#PathVariable String id, #RequestBody Map<String, String> body){
int orderId = Integer.parseInt(id);
// getting blog
Optional<Order> order = orderRep.findById(orderId);
order.get().setItem(body.get("item"));
order.get().setPrice(Integer.parseInt(body.get("price")));
order.get().setQuantity(Integer.parseInt("quantity"));
return orderRep.save(order.get());
}
#DeleteMapping("/{id}")
public boolean delete(#PathVariable int id){
//int orderId = Integer.parseInt(id);
orderRep.deleteById(id);
return true;
}
}
Order.java
package ***;
import javax.persistence.*;
#Entity
#Table(name = "orders")
public class Order {
//Fields
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private int id;
#Column(name = "item")
private String item;
#Column(name = "price")
private int price;
#Column(name = "quantity")
private int quantity;
//Constructors
public Order() { }
public Order(String item, int price, int quantity) {
this.setItem(item);
this.setPrice(price);
this.setQuantity(quantity);
}
public Order(int id, String item, int price, int quantity) {
this.setId(id);
this.setItem(item);
this.setPrice(price);
this.setQuantity(quantity);
}
//Object to string data
#Override
public String toString() {
return "Order{" +
"id=" + getId() +
", item='" + getItem() + '\'' +
", price='" + getPrice() + '\'' +
", price='" + getQuantity() + '\'' +
'}';
}
//Getters & Setters
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getItem() {
return item;
}
public void setItem(String item) {
this.item = item;
}
public int getPrice() {
return price;
}
public void setPrice(int price) {
this.price = price;
}
public int getQuantity() {
return quantity;
}
public void setQuantity(int quantity) {
this.quantity = quantity;
}
}
OrderRepository.java
package ***;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.repository.CrudRepository;
import org.springframework.stereotype.Repository;
import java.util.List;
#Repository
public interface OrderRepository extends CrudRepository<Order, Integer> {
// custom query to search to blog post by title or content
List<Order> findByTitleContainingOrContentContaining(String item);
}
application.properties
spring.jpa.hibernate.ddl-auto=update
spring.datasource.url=jdbc:mysql://${MYSQL_HOST:localhost}:3306/testvoy?useUnicode=true&serverTimezone=UTC&useSSL=true&verifyServerCertificate=false
spring.datasource.username=root
spring.datasource.password=
spring.datasource.driver-class-name =com.mysql.jdbc.Driver
#spring.jpa.show-sql: true
pom.xml
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.5</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.test</groupId>
<artifactId>project</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>project</name>
<description>project</description>
<properties>
<java.version>11</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.restdocs</groupId>
<artifactId>spring-restdocs-mockmvc</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.asciidoctor</groupId>
<artifactId>asciidoctor-maven-plugin</artifactId>
<version>1.5.8</version>
<executions>
<execution>
<id>generate-docs</id>
<phase>prepare-package</phase>
<goals>
<goal>process-asciidoc</goal>
</goals>
<configuration>
<backend>html</backend>
<doctype>book</doctype>
</configuration>
</execution>
</executions>
<dependencies>
<dependency>
<groupId>org.springframework.restdocs</groupId>
<artifactId>spring-restdocs-asciidoctor</artifactId>
<version>${spring-restdocs.version}</version>
</dependency>
</dependencies>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
I would be grateful for any help, thanks in advance
If you check the error, you can see that it comes from there:
List<Order> findByTitleContainingOrContentContaining(String item);
and if you read more closely to the error, you will see:
No property title found for type Order!;
inside here:
Caused by: org.springframework.data.repository.query.QueryCreationException: Could not create query for public abstract java.util.List com.test.project.OrderRepository.findByTitleContainingOrContentContaining(java.lang.String)! Reason: Failed to create query for method public abstract java.util.List com.test.project.OrderRepository.findByTitleContainingOrContentContaining(java.lang.String)! No property title found for type Order!; nested exception is java.lang.IllegalArgumentException: Failed to create query for method public abstract java.util.List com.test.project.OrderRepository.findByTitleContainingOrContentContaining(java.lang.String)! No property title found for type Order!
Infact, if you check your model, there is no title property
I have a table with a composite primary key - groupId and batchId. Entity class looks like:
#Entity(name="EMPLOYEE")
public class Employee {
#EmbeddedId
private EmployeePK employeePK;
//Other columns and their getters and setters
//Getters and setters
}
Composite PK:
#Embeddable
public class EmployeePK implements Serializable {
private long groupId;
private long batchId;
#GeneratedValue(strategy=GenerationType.AUTO)
public long getBatchId() {
return batchId;
}
public void setBatchId(long batchId) {
this.batchId = batchId;
}
}
I'm trying to auto increment the batch Id, for a new record to be inserted.
//For saving
Employee employee = new Employee();
EmployeePK pk = new IRAmendmentBatchesPK();
pk.setBatchId(0);
pk.setGroupId(4388);
Employee employee = employeeRepository.save(employee);
//Repository Interface
public interface EmployeeRepository extends JpaRepository<Employee, EmployeePK>{
}
I'm explicity setting batchId as 0, in hopes that the auto-incremented value is set in the batchId during save(insert). As of now, this code will save a new entry with batchId as 0.
As I have mentioned in comment, I have used #IdClass it worked while I have tried in hsqldb in-memory database, but failed to work in mysql.
Please note I am using hibernate 5
You may give a try with oracle, I couldn't recollect but it should work. But please check for if any drawbacks with the approach if any.
pom.xml
<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.techdisqus</groupId>
<artifactId>spring5-mvc-hibernate-example</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>war</packaging>
<properties>
<failOnMissingWebXml>false</failOnMissingWebXml>
<spring.version>5.0.0.RELEASE</spring.version>
<hibernate.version>5.2.11.Final</hibernate.version>
<hibernate.validator>5.4.1.Final</hibernate.validator>
<c3p0.version>0.9.5.2</c3p0.version>
<jstl.version>1.2.1</jstl.version>
<tld.version>1.1.2</tld.version>
<servlets.version>3.1.0</servlets.version>
<jsp.version>2.3.1</jsp.version>
<hsqldb.version>1.8.0.10</hsqldb.version>
</properties>
<dependencies>
<!-- Spring MVC Dependency -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- Spring ORM -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- Hibernate ORM -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>${hibernate.version}</version>
</dependency>
<!-- Hibernate-C3P0 Integration -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-c3p0</artifactId>
<version>${hibernate.version}</version>
</dependency>
<!-- c3p0 -->
<dependency>
<groupId>com.mchange</groupId>
<artifactId>c3p0</artifactId>
<version>${c3p0.version}</version>
</dependency>
<!-- Hibernate Validator -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator</artifactId>
<version>${hibernate.validator}</version>
</dependency>
<!-- JSTL Dependency -->
<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>javax.servlet.jsp.jstl-api</artifactId>
<version>${jstl.version}</version>
</dependency>
<dependency>
<groupId>taglibs</groupId>
<artifactId>standard</artifactId>
<version>${tld.version}</version>
</dependency>
<!-- Servlet Dependency -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>${servlets.version}</version>
<scope>provided</scope>
</dependency>
<!-- JSP Dependency -->
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>javax.servlet.jsp-api</artifactId>
<version>${jsp.version}</version>
<scope>provided</scope>
</dependency>
<!-- HSQL Dependency -->
<dependency>
<groupId>hsqldb</groupId>
<artifactId>hsqldb</artifactId>
<version>${hsqldb.version}</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.12</version>
</dependency>
</dependencies>
<build>
<sourceDirectory>src/main/java</sourceDirectory>
<resources>
<resource>
<directory>src/main/resources</directory>
</resource>
</resources>
<plugins>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.5.1</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
<!-- Embedded Apache Tomcat required for testing war -->
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.2</version>
<configuration>
<path>/</path>
</configuration>
</plugin>
</plugins>
</build>
</project>
Book.java
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.IdClass;
import javax.persistence.Table;
#Entity(name = "Book")
#Table(name = "book")
#IdClass( PK.class )
public class Book {
#Id
#Column(name = "registration_number")
#GeneratedValue(strategy = GenerationType.AUTO)
private Long registrationNumber;
#Id
#Column(name = "publisher_id")
private Integer publisherId;
private String title;
public Long getRegistrationNumber() {
return registrationNumber;
}
public void setRegistrationNumber(Long registrationNumber) {
this.registrationNumber = registrationNumber;
}
public Integer getPublisherId() {
return publisherId;
}
public void setPublisherId(Integer publisherId) {
this.publisherId = publisherId;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
#Override
public String toString() {
return "Book [registrationNumber=" + registrationNumber + ", publisherId=" + publisherId + ", title=" + title
+ "]";
}
}
PK.java
import java.io.Serializable;
import java.util.Objects;
public class PK implements Serializable {
/**
*
*/
private static final long serialVersionUID = 2371758145387850080L;
private Long registrationNumber;
private Integer publisherId;
public PK(Long registrationNumber, Integer publisherId) {
this.registrationNumber = registrationNumber;
this.publisherId = publisherId;
}
public PK() {
}
#Override
public boolean equals(Object o) {
if ( this == o ) {
return true;
}
if ( o == null || getClass() != o.getClass() ) {
return false;
}
PK pk = (PK) o;
return Objects.equals( registrationNumber, pk.registrationNumber ) &&
Objects.equals( publisherId, pk.publisherId );
}
#Override
public int hashCode() {
return Objects.hash( registrationNumber, publisherId );
}
}
hibernate.cfg.xml
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.archive.autodetection">class,hbm</property>
<property name="hibernate.dialect">org.hibernate.dialect.HSQLDialect</property>
<property name="hibernate.show_sql">true</property>
<property name="hibernate.connection.driver_class">org.hsqldb.jdbcDriver</property>
<property name="hibernate.connection.username">sa</property>
<property name="hibernate.connection.password"></property>
<property name="hibernate.connection.url">jdbc:hsqldb:mem:test</property>
<property name="hibernate.hbm2ddl.auto">create</property>
<property name="hibernate.c3p0.min_size">5</property>
<property name="hibernate.c3p0.max_size">20</property>
<property name="hibernate.c3p0.acquire_increment">2</property>
<property name="hibernate.c3p0.acquire_increment">1800</property>
<property name="hibernate.c3p0.max_statements">150</property>
</session-factory>
</hibernate-configuration>
HibernateConfig.java
#Configuration
#EnableTransactionManagement
#ComponentScans(value = { #ComponentScan("com.techdisqus")})
public class HibernateConfig {
#Autowired
private ApplicationContext context;
#Bean
public LocalSessionFactoryBean getSessionFactory() {
LocalSessionFactoryBean factoryBean = new LocalSessionFactoryBean();
factoryBean.setConfigLocation(context.getResource("classpath:hibernate.cfg.xml"));
factoryBean.setAnnotatedClasses(Book.class);
return factoryBean;
}
#Bean
public HibernateTransactionManager getTransactionManager() {
HibernateTransactionManager transactionManager = new HibernateTransactionManager();
transactionManager.setSessionFactory(getSessionFactory().getObject());
return transactionManager;
}
}
BookDAOImpl.java
#Repository
public class BookDAOImpl implements BookDAO {
#Autowired
private SessionFactory sessionFactory;
public void setSessionFactory(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
public void save(Book book) {
Session session = this.sessionFactory.openSession();
Transaction tx = session.beginTransaction();
session.persist(book);
tx.commit();
session.close();
}
}
client code:
public class SpringHibernateMain2 {
public static void main(String[] args) {
ApplicationContext appContext = new AnnotationConfigApplicationContext(HibernateConfig.class);
BookDAO personDAO = appContext.getBean(BookDAO.class);
Book book = new Book();
book.setPublisherId(12);
book.setTitle("t 1");
//book.setRegistrationNumber(2l);
personDAO.save(book);
System.out.println("book::"+book);
//context.close();
}
}
from logs while using with H:
Hibernate: call next value for hibernate_sequence Hibernate: insert
into book (title, publisher_id, registration_number) values (?, ?, ?)
book::Book [registrationNumber=1, publisherId=12, title=t 1]
The below is the error I get while I try with MySql
Hibernate: select next_val as id_val from hibernate_sequence for
update Dec 04, 2018 6:24:53 PM
org.hibernate.id.enhanced.TableStructure$1$1 execute ERROR: could not
read a hi value java.sql.SQLSyntaxErrorException: Table
'security.hibernate_sequence' doesn't exist
I have tried with accepted answer in the post
Hibernate insert failing when embedded key contains identity column on SQL Server
but no luck with it.
#Embeddable
public class EmployeePK implements Serializable {
private long groupId;
#GeneratedValue(strategy = GenerationType.AUTO)
private long batchId;
public long getBatchId() {
return batchId;
}
public void setBatchId(long batchId) {
this.batchId = batchId;
}
//implements equals and hashcode
}
It's precised in the Javadoc of oracle that is not possible and not in the spec : https://docs.oracle.com/javaee/6/api/javax/persistence/GeneratedValue.html
Use of the GeneratedValue annotation is not supported for derived primary keys.
And I found nothing about how to do it with build in tools. So you need to do yours own implementation of that.
I am trying to generate schema tables based on entities. The application starts correctly, the SQL is generated but there is no result - none of tables are created. What's wrong? I have used the same settings in plain Spring MVC + Hibernate JPA without Spring Boot and everything was working correctly.
Here is my pom.xml:
<?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.agileplayers</groupId>
<artifactId>applicationname</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>ApplicationName</name>
<description>Application Name</description>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.3.5.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</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-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<!--<scope>runtime</scope>-->
<version>9.4-1201-jdbc41</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
application.properties:
spring.datasource.url = jdbc:postgresql://localhost:5432/postgres
spring.datasource.driverClassName = org.postgresql.Driver
spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.PostgreSQL82Dialect
spring.datasource.schema=schemaName
spring.datasource.username=userName
spring.datasource.password=userPassword
spring.jpa.hibernate.ddl-auto=create
spring.jpa.show-sql=true
spring.jpa.generate-ddl=true
BaseEntity.java:
package com.agileplayers.applicationname.core.domain;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.MappedSuperclass;
import java.util.Date;
#MappedSuperclass
public class BaseEntity {
#Id
#GeneratedValue
private int id;
private Date createdOn;
public String description;
public BaseEntity() {
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public Date getCreatedOn() {
return createdOn;
}
public void setCreatedOn(Date createdOn) {
this.createdOn = createdOn;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
}
example of Entity which extends BaseEntity - Entry.java:
package com.agileplayers.applicationname.core.domain;
import javax.persistence.Entity;
import javax.persistence.ManyToOne;
import java.util.Date;
#Entity
public class Entry extends BaseEntity{
private String type;
#ManyToOne
private Account account;
public Entry() {
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public Account getAccount() {
return account;
}
public void setAccount(Account account) {
this.account = account;
}
}
I have fixed the issue. Instead of spring.datasource.schema=schemaName there should be spring.jpa.properties.hibernate.default_schema=schemaName.
The set of necessary properties required for generating tables in my case is the following:
spring.datasource.url = jdbc:postgresql://localhost:5432/postgres
spring.jpa.properties.hibernate.default_schema = schemaName
spring.datasource.username = userName
spring.datasource.password = userPassword
spring.jpa.hibernate.ddl-auto = create-drop
spring.jpa.show-sql = true