Hibernate COUNT function can't find column - postgresql

Currently trying to run a COUNT function in Hibernate that simply returns a count of all platforms in the table.
Query<?> intQuery = session.createQuery("select count(platform) from
UserPlatform");`
Hibernate output in console:
Hibernate: select count(userplatfo0_.PLATFORM) as col_0_0_ from OTS_SCHEMA.OTS_USER_PLATFORM_TBL userplatfo0_
However, I am continually met with the following error when I run the code:
Exception in thread "Thread-9" javax.persistence.PersistenceException: org.hibernate.exception.GenericJDBCException: could not execute query
at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:154)
at org.hibernate.query.internal.AbstractProducedQuery.list(AbstractProducedQuery.java:1535)
at org.hibernate.query.internal.AbstractProducedQuery.getSingleResult(AbstractProducedQuery.java:1574)
at com.ots.Utilities.getPrimaryUserPlatformFromWrapper(Utilities.java:677)
at com.ots.Processor$3.run(Processor.java:194)
Caused by: org.hibernate.exception.GenericJDBCException: could not execute query
Caused by: java.sql.SQLException: Column not found: col_0_0_
The Hibernate model class:
#Repository
#Entity
#Table(name="OTS_USER_PLATFORM_TBL")
#Scope("prototype")
public class UserPlatform {
#Id
#Column(name="ID")
private int id;
#Column(name="CWSID")
private String cwsid;
#Column(name="PLATFORM")
private String platform;
#Autowired
public UserPlatform(String cwsid, String platform) {
this.cwsid = cwsid;
this.platform = platform;
}
public UserPlatform() {
}
//getters&setters
}
I suspect Hibernate is looking for a mapping to col_0_0, but as col_0_0 is not a 'real' column, there is no mapping for it. How do we handle this problem in Hibernate?

Your Hibernate model class is way off:
Delete: #Repository
Delete: #Scope
Delete: #Autowired Constructor
You need to show your real service code, i.e. where you execute the query.

Related

Rapository can not connect to Postgres (testcontainers) in integration tests with KafkaListener

I run integrations tests using test containers with Postgres DB. When I send json message to a kafka topic using KafkaTemplate I getting SQL exception:
[W] SqlExceptionHelper - SQL Error: 0, SQLState: 42P01
[E] SqlExceptionHelper - ERROR: relation "test_db.test_schema" does not exist
could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
org.springframework.dao.InvalidDataAccessResourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
My test looks like this:
#Autowired
TestRepository repository;
#Autowired
KafkaTemplate<String, String> kafkaTemplate;
private void publishFile(String fileName) {
kafkaTemplate.send("test.topic", "1", readFile(fileName));
}
#Test
public void test_1() {
publishFile("json/test_1.json");
await().atMost(5, SECONDS).until(()-> repository.findAll().size() == 1);
}
When I call publishFile message arrives to a #KafkaListener
#KafkaListener(topics = "test.topic")
public void onRecieve(#Payload String json, #Header(name = RECIEVED_MESSAGE_KEY) String key) {
TestEntity entity = mapper.readValue(json, TestEntity.class);
repository.save(entity);
}
But when I use repository directly in test like this:
#Test
public void test_1() {
repository.findAll();
}
Everything ok. I can write to and read from repository.
Also I have access to a repository in this test:
#Test
public void test_1() {
TestEntity entity = mapper.readValue(readFile("json/test_1.json"), TestEntity.class);
repository.save(entity);
publishFile("json/test_1.json");
log.info(repository.findAll());
await().atMost(5, SECONDS).until(()-> repository.findAll().size() == 1);
}
In main thread I can write to a repository and after sendig message to a #KafkaListener I can read from repository. But In #KafkaListener thread I can not. I suppose there should be the same test context but looks like its not. How can I use repository to interract with Postgres container in #KafkaListener thread?

Issue with uploading pdf into Postgres

I am trying to save a pdf doc into my postgres 10.1 database using Hibernate.
Below is my entity class.
#Entity
#Table(name = "FILEUPLOADS", schema="SomeSchema")
public class FileUploads{
//skipping other columns
#Lob
#Column(name="DOCDATA")
private byte[] docData;
}
This column is op type bytea in the postgres database.
As suggested by Authur here : similar issue, I created my custom implementation of postgres dialect like below.
#Configuration
public class TestDialect extends PostgreSQLDialect{
public TestDialect() {
super();
registerColumnType(Types.BLOB, "bytea");
}
}
Then inside my persistence.xml file , I am using this custom dialect
<property name="hibernate.dialect" value="com.digital.repository.TestDialect" />
Even after doing all this, I am getting below error
ERROR: column "DOCDATA" is of type bytea but expression is of type bigint
Hint: You will need to rewrite or cast the expression.
Position: 251
at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:2468)
at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:2211)
at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:309)
at org.postgresql.jdbc.PgStatement.executeInternal(PgStatement.java:446)
at org.postgresql.jdbc.PgStatement.execute(PgStatement.java:370)
at org.postgresql.jdbc.PgPreparedStatement.executeWithFlags(PgPreparedStatement.java:149)
at org.postgresql.jdbc.PgPreparedStatement.executeUpdate(PgPreparedStatement.java:124)
at org.apache.tomcat.dbcp.dbcp.DelegatingPreparedStatement.executeUpdate(DelegatingPreparedStatement.java:105)
at org.apache.tomcat.dbcp.dbcp.DelegatingPreparedStatement.executeUpdate(DelegatingPreparedStatement.java:105)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at org.hibernate.engine.jdbc.internal.proxy.AbstractStatementProxyHandler.continueInvocation(AbstractStatementProxyHandler.java:122)
... 250 more
What else do I need to do in order to resolve this issue ?
Try to change the Hibernate type:
#Entity
#Table(name = "FILEUPLOADS", schema="SomeSchema")
public class FileUploads{
//skipping other columns
#Type(type = "org.hibernate.type.BinaryType")
#Column(name="DOCDATA")
private byte[] docData;
}
Below configuration worked for me and I am able to save the doc/pdf into db now.
#Configuration
public class CustomPostgresDialect extends PostgreSQL82Dialect{
#Override
public SqlTypeDescriptor remapSqlTypeDescriptor(SqlTypeDescriptor sqlTypeDescriptor) {
if (sqlTypeDescriptor.getSqlType() == java.sql.Types.BLOB) {
return BinaryTypeDescriptor.INSTANCE;
}
return super.remapSqlTypeDescriptor(sqlTypeDescriptor);
}
}
Hibernate 4.1.10
Java 1.7

Jar file from Jpa code doesn't work

I've developed a simple code that displayes employee name by using Jpa's one of CRUD operations(find) on entity classes "Employee"& "Department" it worked properly while running the code , but the real problem came when I created a jar file from the application, an exception appeared from the jar file , I wrote the exception in a txt file
Here is the Employee class
package com.tutorialspoint.eclipselink.entity;
import java.util.*;
import javax.persistence.*;
#Entity
public class Employee {
#Id
#GeneratedValue(strategy= GenerationType.AUTO)
private int eid;
#Temporal(TemporalType.TIMESTAMP)
private java.util.Date dop;
private String ename;
private double salary;
private String deg;
#OneToOne(targetEntity = Department.class)
private Department dept;
#OneToMany (targetEntity = Staff.class)
private ArrayList<Staff> staffs;
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 Date getDop() {
return dop;
}
public void setDop(Date dop) {
this.dop = dop;
}
public int getEid( ) {
return eid;
}
public void setEid(int eid) {
this.eid = eid;
}
public Department getDept() {
return dept;
}
public void setDept(Department dept) {
this.dept = dept;
}
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;
}
public ArrayList<Staff> getStaffs() {
return staffs;
}
public void setStaffs(ArrayList<Staff> staffs) {
this.staffs = staffs;
}
}
and here is the class that displays employee name and degree
public void findEmployee(){
try{
EntityManagerFactory emfactory = Persistence.createEntityManagerFactory( "Eclipselink_JPA" );
EntityManager entitymanager = emfactory.createEntityManager();
Employee employee = entitymanager.find( Employee.class, 204 );
JOptionPane.showMessageDialog(null, employee.getEname()+
"=>"+employee.getDeg());
}catch(Exception ex){
JOptionPane.showMessageDialog(null,ex.getMessage());
displayMsg(ex.getMessage());
}
}
public void displayMsg(String msg){
// i made this method to display the exception in a txt file
File f = new File("E:\\bug2.txt");
FileWriter fw = new FileWriter(f);
PrintWriter pw = new PrintWriter(fw);
pw.println(msg);
pw.flush();pw.close();
}
and here is the exception
"
Exception [EclipseLink-28019] (Eclipse Persistence Services - 2.5.2.v20140319-9ad6abd): org.eclipse.persistence.exceptions.EntityManagerSetupException
Exception Description: Deployment of PersistenceUnit [Eclipselink_JPA] failed. Close all factories for this PersistenceUnit.
Internal Exception: Exception [EclipseLink-0] (Eclipse Persistence Services - 2.5.2.v20140319-9ad6abd): org.eclipse.persistence.exceptions.IntegrityException
Descriptor Exceptions:
Exception [EclipseLink-1] (Eclipse Persistence Services - 2.5.2.v20140319-9ad6abd): org.eclipse.persistence.exceptions.DescriptorException
Exception Description: The attribute [teacherSet] is not declared as type ValueHolderInterface, but its mapping uses indirection.
Mapping: org.eclipse.persistence.mappings.ManyToManyMapping[teacherSet]
Descriptor: RelationalDescriptor(com.tutorialspoint.eclipselink.entity.Clas --> [DatabaseTable(CLAS)])
Exception [EclipseLink-1] (Eclipse Persistence Services - 2.5.2.v20140319-9ad6abd): org.eclipse.persistence.exceptions.DescriptorException
Exception Description: The attribute [clasSet] is not declared as type ValueHolderInterface, but its mapping uses indirection.
Mapping: org.eclipse.persistence.mappings.ManyToManyMapping[clasSet]
Descriptor: RelationalDescriptor(com.tutorialspoint.eclipselink.entity.Teacher --> [DatabaseTable(TEACHER)])
Exception [EclipseLink-1] (Eclipse Persistence Services - 2.5.2.v20140319-9ad6abd): org.eclipse.persistence.exceptions.DescriptorException
Exception Description: The attribute [staffs] is not declared as type ValueHolderInterface, but its mapping uses indirection.
Mapping: org.eclipse.persistence.mappings.ManyToManyMapping[staffs]
Descriptor: RelationalDescriptor(com.tutorialspoint.eclipselink.entity.Employee --> [DatabaseTable(EMPLOYEE)])
Runtime Exceptions:
--------------------------------------------------------- "
so what can be done?? knowing that the program works well when running the code from IDE but this exception happens when i built it and created jar file and ran the jar file
Exceptions that involve interfaces like ValueHolders and indirection is most likely a case of problems due to entity weaving.
Entity weaving is a process of modifying the compiled entities' bytecode so that they implement more interfaces and add new methods such that they can handle things like indirection and lazy-loading, among other features.
Is your IDE Oracle JDeveloper? It is one of the IDEs that, by default, have a run configuration that does this automatically, so that your entities work correctly. This can be configured in other IDEs in a similar manner - by adding -javaagent:<path to eclipselink JAR> as a program argument (or Java Option in some IDEs). Check this blog post for some quick info.
It might the be case in your deployment that Eclipselink's dynamic (runtime) weaving has failed (or is incomplete for some reason). Perhaps you should consider static weaving before the entities are packaged into the deployment artifact.
More info on doing so here: https://wiki.eclipse.org/EclipseLink/UserGuide/JPA/Advanced_JPA_Development/Performance/Weaving/Static_Weaving
thanks , i found out the problem , it was in declaring the ArrayList of staff , it has a problem when I persist Collection declared as ArrayList or HashSet , I should declare it as the super interface eg Set or List ,so I modified it to
#OneToMany (targetEntity = Staff.class)
private List<Staff> staffs;
so, it worked very well and when I built the jar file it worked without any problems

How do I use inheritance in programming model with JPA?

I'm trying to implement this model using JPA 2.1. I'm using the JSR 338 specification and the reference implementation Eclipselink.
Only entities of the third level and associative classes will be persisted.
#MappedSuperclass
public abstract class PessoaMaster implements Serializable {
private static final long serialVersionUID = 1L;
private long id;
private List<Telefone> telefones;
#Id
#GeneratedValue(strategy=GenerationType.IDENTITY)
#Column(name="ID_Pai", unique=true, nullable=false)
public long getId() {
return id;
}
public void setId(long identificador) {
id = identificador;
}
/**
* #return the telefones
*/
#OneToMany
public List<Telefone> getTelefones() {
return telefones;
}
/**
* #param telefones the telefones to set
*/
public void setTelefones(List<Telefone> telefones) {
this.telefones = telefones;
}
}
I can use instead of Inheritance MappedSuperclass here?
#Entity
#Inheritance(strategy=InheritanceType.SINGLE_TABLE)
public abstract class FornecedorSuper extends PessoaMaster{
//attributes and relationships
}
Entity that is persisted.
public class FornecedorPecas extends FornecedorSuper {
private Double Valor;
#Column(name="ValorPeca")
public Double getValor() {
return Valor;
}
public void setValor(Double valor) {
Valor = valor;
}
}
It is necessary to mark FornecedorPeças class with # Entity?
When I insert the MappedSuperclass in the FornecedorSuper. This exception is thrown:
Exception in thread "main" Local Exception Stack: Exception [EclipseLink-30005] (Eclipse Persistence Services - .5.0.v20130507-3faac2b):org.eclipse.persistence.exceptions.PersistenceUnitLoadingException Exception Description: An exception was thrown while searching for persistence archives ith ClassLoader: sun.misc.Launcher$AppClassLoader#affc70 Internal Exception: javax.persistence.PersistenceException: Exception [EclipseLink-28018] (Eclipse Persistence Services - 2.5.0.v20130507-3faac2b): org.eclipse.persistence.exceptions.EntityManagerSetupException
Exception Description: Predeployment of PersistenceUnit [modelo] failed.
Internal Exception: Exception [EclipseLink-7161] (Eclipse Persistence Services - 2.5.0.v20130507-3faac2b): org.eclipse.persistence.exceptions.ValidationException
Exception Description: Entity class [class br.miltex.dominio.model.FornecedorPecas] has no primary key specified. It should define either an #Id, #EmbeddedId or an #IdClass. If you have defined PK using any of these annotations then make sure that you do not have mixed access-type (both fields and properties annotated) in your entity class hierarchy.
Q1. I can use instead of Inheritance MappedSuperclass here?
Although I didn't find any examples in the specification with that, the JPA specification says:
The MappedSuperclass annotation designates a class whose mapping
information is applied to the entities that inherit from it. A mapped
superclass has no separate table defined for it.
So it says that the mapping information is applied to Entities, but it does not say that a MappedSuperclass is not allowed to extend another MappedSuperclass, so I believe you can use in your FornecedorSuper class the #MappedSuperclass annotation.
Q2. It is necessary to mark FornecedorPeças class with # Entity?
Yes, it is necessary.
I had put annotations on attributes and methods. For this reason was occurring exceptions.
Thanks for the help.

Find and delete an item from a collection

I have the following problem with a method of JPA.
I can not delete an item from a collection.
Actually, the method only works if it is not the last element inserted.
Where I'm wrong?
This is the class of my model:
#Entity
public class JobOffer {
#SequenceGenerator(name="JobOffer_Gen", sequenceName="JobOffer_Seq", initialValue=1, allocationSize=1)
#Id #GeneratedValue(generator="JobOffer_Gen") #Column(name="ID_JOBOFFER")
private Long id;
#Column
private String title;
...
#OneToMany
#JoinTable(joinColumns = #JoinColumn(name = "JOBOFFER_IDFK"), inverseJoinColumns = #JoinColumn(name = "LANGUAGE_IDFK"))
private Collection<Language> languages = new HashSet<Language>();
...
}
This is my method in JPA:
#Override
#Transactional
public void deleteLanguage(JobOffer joboffer, Long idLingua) throws BusinessException {
for(Language l : joboffer.getLanguages()){
if (l.getId() == idLingua){
joboffer.getLanguages().remove(l);
}
}
em.merge(joboffer);
}
What is the correct way to search for an item in a collection and delete in JPA?
This is the error that I get from the console:
21-ott-2013 18.22.27 org.apache.catalina.core.StandardWrapperValve invoke
GRAVE: Servlet.service() for servlet [jobbook] in context with path [/jobbook] threw exception [Request processing failed; nested exception is java.util.ConcurrentModificationException] with root cause
java.util.ConcurrentModificationException
at java.util.AbstractList$Itr.checkForComodification(AbstractList.java:372)
at java.util.AbstractList$Itr.next(AbstractList.java:343)
at org.eclipse.persistence.indirection.IndirectList$1.next(IndirectList.java:571)
at it.univaq.mwt.j2ee.jobbook.business.impl.JPAJobOfferService.deleteLanguage(JPAJobOfferService.java:95)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
and then continues
You may try something like this:
#Override
#Transactional
public void deleteLanguage(JobOffer joboffer, Long idLingua) throws BusinessException {
Language language = em.createQuery("SELECT lang from Language lang where lang.jobOffer.id = :job_id", Language.class).setParameter("job_id", joboffer.getId()).getSingleResult();
if(language != null){
joboffer.getLanguages().remove(language);
}
}
Please note:
this is not tested
I assumed that your "Language" Entity has a reference to your JobOffer Entity. Although I do not know your domain, this may indicate a bad design
If the parameter joboffer is in detached state, then you have to reattach it to the current session (using em.merge()).
Edit: Adapted Query in response to the comment of DataNucleus.