Nico van de Kamp

Ranch Hand
+ Follow
since Jan 25, 2017
Cows and Likes
Cows
Total received
1
In last 30 days
0
Total given
0
Likes
Total received
0
Received in last 30 days
0
Total given
0
Given in last 30 days
0
Forums and Threads
Scavenger Hunt
expand Ranch Hand Scavenger Hunt
expand Greenhorn Scavenger Hunt

Recent posts by Nico van de Kamp

I try to make myself 'comfortable' with the Java eco-system as JPA and Hibernate.

I have for instance made a class employee with sequence:


I can CRUD records with Postman is working perfectly.

But now I have inserted records with SQL (INSERT INTO table name ()).
Now I try to insert a record with postman, I get the error message: rg.h2.jdbc.JdbcSQLIntegrityConstraintViolationException: Unique index or primary key violation: "PRIMARY KEY ON PUBLIC.ADDRESS(ID) [1, 'town name', '0', 'street name']"; SQL statement:

I think that's due that I add records by SQL statements. Hibernate 'thinks'  the sequence is still one and I can imagine that it goes wrong.

In the 'real (=production)' environment, what is than the best way to implement this?
Defining the complete schema with Liquibase/flyaway for example and simply define sequence as:

And are there some more 'little' things where I need to have tobe where off?
1 week ago
I try to learn JPA/Hibernate and last week I had a remarkable error:

"status": 500,
"error": "Internal Server Error",
"trace": "org.springframework.http.converter.HttpMessageConversionException:
Type definition error: [simple type, class com.crud.demo.dto.EmployeeDto];
nested exception is com.fasterxml.jackson.databind.exc.InvalidDefinitionException:
No serializer found for class com.crud.demo.dto.EmployeeDto and no properties discovered
to create BeanSerializer



In my DTO I had only setters implemented, because if need getters than I thought I will do this from the Entity ==> the unique source.

After some hours I added in my DTO classes the getters and the getter for the id was immediately syntax highlighted --> collaring which means it is used. So Im searching where? And IntelliJ 'Find usage' I get the message "Usages or base methods of getId() Nothing found in 'All Places'"


Is that not strange? At least it is now working but I don't understand it...

1 week ago
I did get it working a few weeks ago only I have changed Unit with Roles.

Employee Entity is my 'Parent' side


And Role is my 'child' side:


Join table is employees_roles. If I remove a role from my REST Api, than also an record of the join table is removed and not from the Role table!! That's good because the Role table is an constant/lookup table.

The only question what is left is that:
My Role table has three fields: id, code and description
It is constant/lookup table with 6 prefilled records.
Question: if I change the value of the field "description" and/or code, than it is overwritten. How can I disable this, so that only records in join table are added?

** EDIT **

Ah, I read also my other post and I think Rob has given the solution there.
The solution I assume is 'insertable = false, updatable = false':

It seems strange to me if this is the 'real' solution because how do you maintain this table? Than you have to write another class...? I should expect that you disable it from the parent side writing to the child table.

If somebody does have another idea and/or better idea, let me know.
2 weeks ago
Hello,

I'm still struggling and fighting to get a OneToMany/ManyToOne working. The examples I have found till now, have the same issue and I have also found here the question but not the solution or I do not understand it.

I have the two Entities:
parent Employee @OneToMany:The Child side: @Many-To-One:

The update employee service implementation:

And this is what I inject with Postman the create (POST):

I have two "employeeModelLogging" records at the time of creation of an Employee.

Now I do an update with postman:

When I execute the update, than there are still two records in the database. (It is not a problem to update fields from the employee or department, etc. This is working fine)

I have tried this, by removing the second recordThe second loggingModel is removed from the JPA I think, but not in the database. But I this, if this should work, than at least I know which way I have to go...

I hope that someone has an idea and can tell me what I'm doing wrong...
Hi Rob,

Thanks for you're help,

Rob Spoor wrote:I take it that the model classes are mapped from JSON directly to your entities, right? If so, you're running into a bidirectional relation that is only set on one side. The unmarshalling from JSON creates new LoggingModel instances, and puts them into a list. It then sets that list on the created EmployeeModel instance. The EmployeeModel instance now has a reference to all of its LoggingModel instances. What is still missing is the reference in the LoggingModel instances to the EmployeeModel instance. The JSON unmarshalling doesn't set this because it simply doesn't know it should.

A quick solution is to fix these references yourself. A quick for-each statement will suffice:



Although I do not know what 'unmarshalling' exactly means, it is all right what you here suggest!!!

But I'm AMAZED that what you suggest here works!!!.

I've changed the code into this: So I add you're line just before saving the new employee model. What is amazing me, is that the id of employee is still unknown because the Employee is not saved or...,
Does it work in this way: JPA knows the next id sequence number for the Employee Entity. So this number is retrieved from the JPA and saved as FK for the loggingModel. Is this what is happening?








I have two entities:

I understand the problem. The FK (name: LOGGINGEMPLOYEEMODEL_ID ) is in the tabel "loggingmodel".
At the moment of new record saving for the parent table 'employeedetails' the child table should also be updated.  But I get the error: "org.h2.jdbc.JdbcSQLIntegrityConstraintViolationException: NULL not allowed for column "LOGGINGEMPLOYEEMODEL_ID"; SQL statement:
insert into LoggingModel (infotext, loggingEmployeeModel_id, title, id) values (?, ?, ?, ?) [23502-199]"

I understand it, the new id for the employeedetails is unknown for the FK for child table. (If it take the part "employeeModelLogging" out of the Postman injection, than I don't get the constraint error, so it should the loggingModel part)

How do I solve this within JPA - Hibernate?

The parent side: One-To-Many:

The Child side: Many-To-One:


The create employee service implementation:

And this is what I inject with Postman:

Can someone can give an idea/hint what I'm doing wrong?
Thanks Rob,

Again 'slowly' I think that I understand what I need todo:

There are some ways to fix this. One is to create POJOs for your REST responses. You end up mostly duplicating your class, but you can easily leave out the things you don't want.

I prefer the first way, because
it allows me to create different POJOs for retrieving EmployeeModel instances with nested Role instances, or the other way around. If you ignore these in your entities, you can only have one of these options
it will ignore anything I don't want. That includes any properties added by the JPA framework (I remember TopLink adding its own properties)



I was thinking why is it necessary to create new DTO POJOs? I'm satisfied by commented out the private List<EmployeeModel> employeeRoleModel in the Role Entity, there is no recurrence of data in the response, so it is good. But if I want to do something with the Roles POJOs, for instance maintenance CRUD, I'm getting in trouble or I need to define a new Role Entity or something like that if possible

Now I return for my REST responses the 'emloyeeModel', which I think have to replace by the new POJOs EmployeeModelDTO class instance. Here I define the EmployeeModelDto (which is than more or less duplicate with EmployeeModel), AND return the EmployeeModelDto as response to frontend(Postman), that is the most important thing to realize/understand.

Another way to fix this is to mark the employeeRoleModel as ignored during serialization. How to do this depends on the serialization framework. For instance, for Jackson you'd use @JsonIgnore.

I see code where they have more or less choosen for this solution.

I have the feeling of you're first approach is better because it is more flexible and is further independent what is happening in other entity's - loosely coupled.
Hello Rob,

Thanks. I don’t know if I understand you but do you mean by creating different POJO’s.
The Role class I have made and with commented out List<EmployeeModel> employeeModel, so that the employeeRoleModel properties are not included
And make another Role POJO for maintenance screen of Role, because Role need to be filled with reference data.

Is that what you mean?
Hello,

I have a many-to-many relation defined like:

My Role entity:

If I do a GET with Postman and the parts mentioned commented out are inactive, than I get in my opinion the right data for the response:


Technically I have find out were it comes from, if i activate the lines which I have mentioned "commented out", than it is getting recurence!!??
I have roles added to the employee that's good. But the GET is also returning the roles wiht the employee etc.
My Question: why is this made in this way? And when do I need this? I mean I can't imagine if you are working on an entity, that a response as shown here beneath would be used for the frontend, or...

If you're not using an Entitymanager, then who's doing the persisting? Is this an EJB3 container?

I do not understand the question sorry, I think due a lack of knowledge of my.

Anyway, good luck on the Many-to-Many. I find that one to be the most challenging of all!



I have the many-to-many also get to work, with a static data table. I think the solution for this "cascade = CascadeType.MERGE" or not? If I use 'CascadeType.ALL',  new records are added to the static data table, with a same value. With MERGE nothing is added and/or changed at the static data table.

I have some other questions, but I will put this in another thread.

Hello Tim and Rob,

Thanks for you're help.
Slowly I realize what is going on behind the mappings as @ManyToOne etc.
My mindset:
When I have declared the @ManyToOne annotion (using: spring.jpa.hibernate.ddl-auto=create-drop), the field "unit_id" is 'automatic' created by Hibernate.
I thought thats smart, Hibernate knows that for the emloyee instance only the FK 'unit_id' is needed. By returning the value of the dropdown (=unit id ), of the frontend (postman) will be enough. (At least with PHP is this enough.)
Another reason why I didn't think about that I do not need the unit instance, because I do want only to save/update the employee instance, not more not less

As Tim already said

As I said before, ORM is not the same thing as SQL. Entity Objects don't link to other Entity Objects by key value. They link as Object properties (references).


I have under estimate this, I realize now.

So I understand now a complete unit instance is necessary and this working now!

The weekend I was busy again and I discovered the persistence manager you also mentioned.
To learn myself if the frontend only returns the value (= id) of the dropdown, than I will get the unit instance by id.

First I saw and have added an persistence.xml (which I think is not really necessary, because I'm not using 'EntityManagerFactory'):

This is what I have defined in my Employee (model)

And here is the code of my serviceimpl

And this is what in inject with Postman:

This is working for me now so far. I don't know if someone of you says, this is a good at least this is the direction which I have to go.

One more to go, an Many-To-Many with a join table and also static (or reference) data.

Tim and Rob thanks a lot for you're assistence both!

Rob Spoor wrote:Are you sure that an Employee's unit cannot be changed? Perhaps that's where the issue lies, especially if you assign a different unit.



Yes, the unit table itself will not be changed. Of course the FK unit_id value of an Employee can change. If a employee is moved to another unit, than the the FK unit_id value will be changed by updating of the employee. But the Unit entity (table) will not be changed.

The Unit table will be changed when a new Unit exist, than the Unit table will be added by a new record, but that needs to be done independent from employee.
Hello Rob,

Thanks, you describe it completely right:
- Many Employees can be linked to a unit
- The unit table will be filled before the app is executed, it's a reference table (or static data table I don't know how this is exactly called in Engilsh, in dutch it is called 'stam tabel'). This value's wil be used in a dropdown/lookup field at the frondend

Here my code for the Employee side (parent)

And this is code for the unit side:


And this is my postman JSON insert:

And do still have this error:"org.hibernate.TransientPropertyValueException: Not-null property references a transient value - transient instance must be saved before current operation : nl.nkamp.crud.model.EmployeeModel.unit -> nl.nkamp.crud.model.Unit; nested exception is java.lang.IllegalStateException: org.hibernate.TransientPropertyValueException: Not-null property references a transient value - transient instance must be saved before current operation : nl.nkamp.crud.model.EmployeeModel.unit -> nl.nkamp.crud.model.Unit"

(What I not understand is, I think this is very common in software working with a reference table. Also for a Many-To-Many situation. But I can't find a good example...)
Hello Tim,

Thanks. I have changed it to @OneToMany, I still have that bloody error.

There are a lot examples with @ManyToOne, @OneToMany and @ManyToMany, but till now I couldn't find examples with static data.
(Or instead of static data: constant data, reference table, lookup, list of values)
1 month ago
I'm trying to figure out how to map an an parent table 'Employee', with an static data child table. (Is 'static data' the right name for this or do you call it:  reference data, list of values, lookup data?)

When I insert an new employee the id record number of the static table data record must be added to the employee table. Nothing needs to be changed on the static data table side (= child table).

Unit is my static data table with the fields: id, unitcode, description.

This is my mapping on the employee side:
In the employee table I have an field 'unit_id' (generated by Hibernate, due to ManyToOne declaration, that's for me an indication that it is till so far good)

On the unit side I have nothing defined.

When I insert an employee record:I get the error: org.hibernate.TransientPropertyValueException: object references an unsaved transient instance - save the transient instance before flushing : nl.nkamp.crud.model.EmployeeModel.unit -> nl.nkamp.crud.model.Unit
But this error indicates if I'm right, that hibernate want to save the data on the side of the child table and it is gone, before it can be saved on the parent side. But I only want to save the unit id on the parent = employee side.


I have tried different FetchTypes.

I hope that someone can point me in the right direction to help me out.
1 month ago