there's no change in h2 table (objects are not created) made by jpa intellij - jpa

i wanna create objects with intellij (jpa) system,
but after i create objects,
there's no change in h2 console.
i expect that the objects are made like this, enter image description here
(wanna make ITEM and MOVIE objects)
but what i got is this. enter image description here
these are the codes that i wrote.
package hellojpa;
import javax.persistence.Entity;
#Entity
public class Album extends Item{
private String artist;
}
package hellojpa;
import javax.persistence.Entity;
#Entity
public class Book extends Item{
private String author;
private String isbn;
}
package hellojpa;
import org.hibernate.engine.internal.JoinSequence;
import org.hibernate.mapping.Join;
import javax.persistence.*;
#Entity
#Inheritance(strategy = InheritanceType.JOINED)
public class Item {
#Id
#GeneratedValue
private Long id;
private String name;
private int price;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getPrice() {
return price;
}
public void setPrice(int price) {
this.price = price;
}
}
package hellojpa;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.EntityTransaction;
import javax.persistence.Persistence;
public class JpaMain {
public static void main(String[] args){
EntityManagerFactory emf = Persistence.createEntityManagerFactory("hello");
EntityManager em = emf.createEntityManager();
EntityTransaction tx = em.getTransaction();
tx.begin();
try{
Movie movie = new Movie();
movie.setDirector("aaaa");
movie.setActor("bbbb");
movie.setName("바람과 함께 사라지다");
movie.setPrice(10000);
tx.commit();
}catch(Exception e){
tx.rollback();
} finally{
em.close();
}
emf.close();
}
}
package hellojpa;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.OneToOne;
#Entity
public class Locker {
#Id
#GeneratedValue
private Long id;
private String name;
#OneToOne(mappedBy = "locker")
private Member member;
}
package hellojpa;
import net.bytebuddy.dynamic.TypeResolutionStrategy;
import org.hibernate.annotations.Fetch;
import javax.persistence.*;
import java.util.ArrayList;
import java.util.List;
#Entity
public class Member {
#Id #GeneratedValue
#Column(name = "MEMBER_ID")
private Long id;
#Column(name = "USERNAME")
private String username;
#ManyToOne
#JoinColumn(name = "Team_ID",insertable = false, updatable = false)
private Team team;
#OneToOne
#JoinColumn(name ="LOCKER_ID")
private Locker locker;
#OneToMany(mappedBy = "member")
private List<MemberProduct> memberProducts = new ArrayList<>();
public Long getId() {return id;}
public void setId(Long id) {this.id = id;}
public String getUsername() {return username;}
public void setUsername(String username) {this.username = username;}
}
package hellojpa;
import javax.persistence.*;
import java.time.LocalDateTime;
#Entity
public class MemberProduct {
#Id
#GeneratedValue
private Long id;
#ManyToOne
#JoinColumn(name="MEMBER_ID")
private Member member;
#ManyToOne
#JoinColumn(name = "PRODUCT_ID")
private Product product;
private int count;
private int price;
private LocalDateTime orderDateTime;
}
package hellojpa;
import javax.persistence.Entity;
#Entity
public class Movie extends Item{
private String director;
private String actor;
public String getDirector() {
return director;
}
public void setDirector(String director) {
this.director = director;
}
public String getActor() {
return actor;
}
public void setActor(String actor) {
this.actor = actor;
}
}
package hellojpa;
import javax.persistence.*;
import java.util.ArrayList;
import java.util.List;
#Entity
public class Product {
#Id
#GeneratedValue
private Long id;
private String name;
#OneToMany (mappedBy = "product")
private List<MemberProduct> memberProducts = new ArrayList<>();
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
package hellojpa;
public enum RoleType {
GUEST, USER, ADMIN
}
package hellojpa;
import javax.persistence.*;
import java.util.ArrayList;
import java.util.List;
#Entity
public class Team {
#Id #GeneratedValue
#Column(name = "TEAM_ID")
private Long id;
private String name;
#OneToMany
#JoinColumn(name = "TEAM_ID")
private List<Member> members = new ArrayList<>();
public Long getId() {return id;}
public void setId(Long id) {this.id = id;}
public String getName() {return name;}
public void setName(String name) {this.name = name;}
public List<Member> getMembers() {
return members;
}
public void setMembers(List<Member> members) {
this.members = members;
}
}
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.2"
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_2.xsd">
<persistence-unit name="hello">
<properties>
<!-- 필수 속성 -->
<property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
<property name="javax.persistence.jdbc.user" value="sa"/>
<property name="javax.persistence.jdbc.password" value=""/>
<property name="javax.persistence.jdbc.url" value="jdbc:h2:tcp://localhost/~/test"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
<!-- 옵션 -->
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hibernate.use_sql_comments" value="10"/>
<property name="hibernate.hbm2ddl.auto" value="create" />
</properties>
</persistence-unit>
</persistence>

You forgot to use the entityManager to persist your new entity. Therefore, jpa does not know about the new entity and nothing is saved.
Just add : em.persist(movie);

The screenshots you provided, in combination with <property name="hibernate.hbm2ddl.auto" value="create" />, suggests that you were not finished creating entity classes when you first run your application. Now if you use hibernate.hbm2ddl.auto = create and there is allready a schema present in your H2, it won't update the schema even though you added one or more entity classes.
The community documentation suggests that you use hibernate.hbm2ddl.auto = update in order to update the schema when the application is run.
Please note that, according to this post, it is not safe to use update in a productive environment.
Despite the best efforts of the Hibernate team, you simply cannot rely on automatic updates in production. Write your own patches, review them with DBA, test them, then apply them manually.
Theoretically, if hbm2ddl update worked in development, it should work in production too. But in reality, it's not always the case.
I hope this helps.

Related

How can I add a subselect to result in jpa query

I have an Spring boot app with an entity Person with a list of that persons events on.
Like this.
public class Person....
private Long id;
private String name;
#ElementCollection(fetch = FetchType.EAGER)
#CollectionTable(name = "person_events", joinColumns = #JoinColumn(name = "person_id"))
private List<String> personEvents = new ArrayList<>();
Now when I select I want to select the result into a dto like this.
#Query("""
select new com.....dtos.PersonDto(p.name, p.events) from Person p
where p.name = (:name)
""")
Set<PersonDto> findPersonsByName(String name);
My repository fails because it cant generate the sql. How can I achieve this?
Few things you are doing can be improved like:
Instead of constructor select you can use interface projection
Set<PersonDto> findPersonsByName(String name);
Since you are doing a select on single item the result will be single object.
so please change it to
PersonDTO findPersonsByName(String name);
Please find my complete answer below:
package com.example.demo;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;
import javax.persistence.*;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
#RestController
#RequestMapping("/person")
public class PersonController {
private final PersonService personService;
#Autowired
public PersonController(PersonService personService) {
this.personService = personService;
}
#GetMapping
public Iterable<Person> list() {
return personService.list();
}
#PostMapping
public Person create(#RequestBody Person car) {
return personService.save(car);
}
#GetMapping(path = "/by")
public PersonDTO getPersonByName(#RequestParam(value = "name") String name) {
return personService.findPersonByName(name);
}
}
#Getter
#Setter
#ToString
#Entity
class Person {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Integer id;
private String name;
#ElementCollection(fetch = FetchType.EAGER)
#CollectionTable(name = "person_events", joinColumns = #JoinColumn(name = "person_id"))
private List<String> personEvents = new ArrayList<>();
}
#Service
class PersonService {
private final PersonRepository personRepository;
#Autowired
PersonService(PersonRepository personRepository) {
this.personRepository = personRepository;
}
#Transactional
public Person save(Person person) {
return personRepository.save(person);
}
#Transactional(readOnly = true)
public Iterable<Person> list() {
return personRepository.findAll();
}
#Transactional(readOnly = true)
public PersonDTO findPersonByName(String name) {
return personRepository.findPersonsByName(name);
}
}
interface PersonDTO {
String getName();
Collection<String> getPersonEvents();
}
#Repository
interface PersonRepository extends JpaRepository<Person, Integer> {
PersonDTO findPersonsByName(String name);
}

#ManyToOne seems not working as i expect it to be

I'm working with many-to-one relationship between my two tables(Employee and Department) in which any Employee can work in more than one department. I used the #ManyToOne annotation on the Department object field which I created in Employee entity class. Now when I persist the Employee entity with a particular department, it works fine but when I try to persist another Employee entity with the same department, it creates a new Department entity with the same name and persists it with different id. What I expect it to do is that when I persist an Employee entity with already persisted department, it should just update the foriegn key of the Employee entity to point the id of that department. Sorry if I didnt got the many-to-one concept totally.
EMPLOYEE entity
package com.test.domain;
import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.TableGenerator;
#Entity
public class Employee {
#TableGenerator(name="Empl_Gen", table="ID_GEN",pkColumnName="GEN_NAME",valueColumnName="GEN_VALUE", initialValue=0, allocationSize=1)
#Id#GeneratedValue(generator="Empl_Gen",strategy=GenerationType.TABLE)
private Long id;
private String Name;
private String Country;
#ManyToOne(cascade=CascadeType.ALL)
#JoinColumn(name="DEPT_ID")
private Department department;
public Department getDepartment() {
return department;
}
public void setDepartment(Department department) {
this.department = department;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getName() {
return Name;
}
public void setName(String name) {
Name = name;
}
public String getCountry() {
return Country;
}
public void setCountry(String country) {
Country = country;
}
}
DEPARTMENT entity
package com.test.domain;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.TableGenerator;
#Entity
public class Department {
#TableGenerator(name="DEP_GEN",table="ID_GEN",pkColumnName="GEN_NAME",valueColumnName="GEN_VALUE", pkColumnValue="DEP_GEN",initialValue=0,allocationSize=1)
#Id#GeneratedValue(strategy=GenerationType.TABLE,generator="DEP_GEN")
private Long id;
private String name;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
package com.test.controllers;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import com.test.domain.Employee;
import com.test.service.EmployeeService;
/**
* Handles requests for the application home page.
*/
#Controller
#RequestMapping("/addEmployee")
public class HomeController {
#Autowired
EmployeeService service;
#RequestMapping(method=RequestMethod.GET)
public String getform(Model model)
{
model.addAttribute("employee",new Employee());
return "home";
}
#RequestMapping(method=RequestMethod.POST)
public String setform(Employee employee)
{
service.save(employee);
return"success";
}
}
package com.test.dao;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;
import com.test.domain.Employee;
#Repository
#Transactional
public class Employeedaoimpl implements Employeedao
{
#PersistenceContext
EntityManager manager;
#Override
public void save(Employee employee) {
manager.persist(employee);
}
}
Try this:
#TableGenerator(name="DEP_GEN",table="ID_GEN",pkColumnName="GEN_NAME",valueColumnName="GEN_VALUE", pkColumnValue="DEP_GEN",initialValue=0,allocationSize=1)
#Id#GeneratedValue(strategy=GenerationType.TABLE,generator="DEP_GEN")
#Column(name = "DEPT_ID")
private Long id;

Getting java.lang.NoSuchFieldError: ERRORS_IGNORED for hibernate-ogm with mongodb

I am trying to use hibernate-ogm with mongodb and getting no such fieds error
persistence.xml
<persistence-unit name="mongodb-test" transaction-type="JTA">
<provider>org.hibernate.ogm.jpa.HibernateOgmPersistence</provider>
<properties>
<property name="hibernate.ogm.datastore.provider" value="mongodb"></property>
<property name="hibernate.ogm.datastore.host" value="192.168.0.237"></property>
<property name="hibernate.ogm.datastore.create_database" value="true"></property>
<property name="hibernate.ogm.datastore.database" value="anand_test"></property>
<property name="hibernate.ogm.mongodb.connection_timeout" value="5000"></property>
<property name="hibernate.ogm.mongodb.authentication_mechanism" value="PLAIN"></property>
<property name="hibernate.ogm.datastore.document.association_storage" value="IN_ENTITY"></property>
<property name="hibernate.ogm.mongodb.association_document_storage" value="GLOBAL_COLLECTION"></property>
<property name="hibernate.ogm.mongodb.write_concern" value="ACKNOWLEDGED"></property>
<property name="hibernate.ogm.mongodb.read_preference" value="PRIMARY_PREFERRED"></property>
</properties>
</persistence-unit>
Person.java
import javax.persistence.Entity;
import javax.persistence.Id;
import org.bson.types.ObjectId;
import org.hibernate.annotations.Type;
#Entity
public class Person {
#Id
#Type(type = "objectid")
private String id;
private String firstName;
private String lastName;
public String getId() {
return id;
}
public void setId(String 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 Person(){
}
public Person(String firstName,String lastName){
this.firstName = firstName;
this.lastName = lastName;
}
}
TestMongoconnection.java
import com.mongodb.Person;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;
public class TestMongoConnection {
public static void main(String[] args) {
EntityManagerFactory entityManagerFactory = Persistence.createEntityManagerFactory("mongodb-test");
EntityManager manager = entityManagerFactory.createEntityManager();
manager.getTransaction().begin();
Person anandMohan = new Person("Anand","Mohan");
manager.persist(anandMohan);
manager.getTransaction().commit();
manager.close();
}
}
I am having mongodb version 3.0.2 and hibernate-ogm 4.2.0 final with mongodb java version 3.x jars
The problem is with the java jar version of the mongodb as 3.x version is not yet supported have to use 2.x version of it
https://forum.hibernate.org/viewtopic.php?f=31&t=1040127&p=2485319#p2485319

entity association in java

I am trying to get rid of this error:
Exception Description: [class utilisateurs.modeles.Utilisateur] uses a non-entity [class java.util.Collection] as target entity in the relationship attribute [field adresses].
at org.eclipse.persistence.exceptions.ValidationException.nonEntityTargetInRelationship(ValidationException.java:1343)
.........
org.eclipse.persistence.internal.jpa.deployment.PersistenceUnitProcessor.processORMetadata(PersistenceUnitProcessor.java:526)
at org.eclipse.persistence.internal.jpa.EntityManagerSetupImpl.predeploy(EntityManagerSetupImpl.java:1320)
... 36 more
with the following entity:
utilisateurs.modeles;
import adresses.Adresse;
import java.io.Serializable;
import java.util.Collection;
import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
#Entity(name="Utilisateur")
public class Utilisateur implements Serializable {
private static final long serialVersionUID = 1L;
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private int id;
public void setAdresses(Collection<Adresse> adresses) {
this.adresses = adresses;
}
private String firstname;
private String lastname;
private String login;
#ManyToOne(cascade=CascadeType.PERSIST)
private Collection<Adresse> adresses;
public Collection<Adresse> getAdresses() {
return adresses;
}
public Utilisateur() {
}
public Utilisateur(final String firstname, final String lastname, final String login) {
this.firstname = firstname;
this.lastname = lastname;
this.login = login;
}
//getters and setters here
#Override
public int hashCode() {
int hash = 0;
hash += (int) id;
return hash;
}
#Override
public boolean equals(Object object) {
// TODO: Warning - this method won't work in the case the id fields are not set
if (!(object instanceof Utilisateur)) {
return false;
}
Utilisateur other = (Utilisateur) object;
if (this.id != other.id) {
return false;
}
return true;
}
}
If you have any idea please.
Adresse is not an Entity, maybe you just forgot the #Entity annotation on that class?
The #ManyToOne annotation defines a relationship between entities.

Entity is not deployed

I'm learning EJB now.
When I deploy my project to glassfish server. One of my entity beans wasn't deployed. But the other 2 work properly. Here's the entity bean's code:
package com.supinfo.javapetstore.model;
import java.io.Serializable;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
#Entity
#Table(name = "Items")
public class Item implements Serializable {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private String reference;
public Item() {
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getReference() {
return reference;
}
public void setReference(String reference) {
this.reference = reference;
}
#Override
public String toString() {
return "Id: " + id + " / reference: " + reference;
}
}
No error or warning appers when deploying.
Thanks a lot.
Try enabling logging,
Assuming your using EclipseLink in Glassfish, add the property to your persistence.xml
<property name="eclipselink.logging.level" value="FINEST"/>
http://wiki.eclipse.org/EclipseLink/Examples/JPA/Logging
In general tables are not created by default, to enable table creation use the property,
<property name="eclipselink.ddl-generation" value="create-tables"/>