Thursday, 18 May 2017

AdditionalCriteria

Small followup of From Hibernate to Eclipselink1 post.

I am not entirely satisfied about the AdditionalCriteria4 thingy. I find it a chore to have to set a parameter on the EntityManager all the time to enable/disable it.

Biggest issue for me is that parameters set on the EntityManager are required. If they are omitted, an exception is thrown when querying.

Current solution in my software:
Turn the AdditionalCriteria on or off by means of a parameter that needs to be set on the EntityManager.

Looks like this:
Setting the parameter activePersonFilter can be done on the EntityManager as follows:
@PersistenceContext(properties =
{
  @PersistenceProperty(name = "activePersonFilter", value = "0"),
  @PersistenceProperty(name = "sundaydateFilter", value = "")
})
private EntityManager em;
Or
entityManager.setProperty("activePersonFilter", 0);

Other solutions

There are some other solutions.
  1. You can remove the additionalCriteria (set it to "") in a subclass, and use the subclass specifically. See [2].
  2. You can customize any mapping in EclipseLink and add the requirements/conditions that you need. See [3].
  3. I could just decide to create a view on the offending database table. Then create two entities. Sounds very similar to the first option.
  4. I could solve the problem in software. Just have EclipseLink not filter anything. (Which is silly, I don't wish for my ORM to get the 1000 persons in the room from the database, if there are say only three persons active.)
  5. I could remove the collection entirely, and retrieve the required Persons using a NamedQuery. (Which is bogus. I like the ORM to deal with this for me, instead of having to do it myself. It's what the ORM is for.)

Customizing a Mapping

I have recently decided to try to customize the mapping specifically in Entities that have collections containing instances of Person class. That way I have more control. See reference [3] on how this works.

It requires a @Customizer annotation.

For instance, in a Room I only wish to see the active persons.

This requires me to define the PersonsFilterForRoom as follows.
"persons"
the name of the field that contains the collection
"room"
the name of the field in the Entity of the collection
"id"
the name of the field in the Room entity that identifies it
It works pretty good.

Note

I also noticed that this way I could have two (Lazy! That's the important bit!) Collections in the same Entity at the same time referring to the same Person. One will contain all Persons and one will contain only the Active Persons.

This is ideal, for instance for Guilds.

Like so:
This way the customizer PersonsFilterForGuild is designed to only work on the activeMembers collection.

I like it!

References

[1] From Hibernate to EclipseLink
http://randomthoughtsonjavaprogramming.blogspot.nl/2014/07/from-hibernate-to-eclipselink.html
[2] StackOverflow - Disable additional criteria only in some entity relations
http://stackoverflow.com/questions/37419406/disable-additional-criteria-only-in-some-entity-relations
[3] Mapping Selection Criteria
https://wiki.eclipse.org/EclipseLink/Examples/JPA/MappingSelectionCriteria
[4] JPA Extention in EclipseLink - @AdditionalCriteria
https://www.eclipse.org/eclipselink/documentation/2.6/jpa/extensions/annotations_ref.htm#additionalcriteria
Customizing EclipseLink JPA/ORM Relationship Joins
http://onpersistence.blogspot.nl/2008/01/customizing-eclipselink-jpaorm.html

7 comments:

  1. Really very informative post you shared here. Keep sharing this type of informative blog. If anyone wants to become a Java professional learn Java Training in Bangalore.

    ReplyDelete
  2. Very important article for JAVA. I found this article some best resources of JAVA. For more details herethis site

    ReplyDelete
  3. Django may be a high-level net framework written in Python that encourages quick development and pragmatic, clean style. Python is that the admire Ruby on Rails that permits you to build high-productive, awful net applications quickly. python programming assignment

    ReplyDelete
  4. Django is often a high-level world wide web composition prepared throughout Python that will motivates rapid growth along with realistic, clean up fashion. Python can be that this respect Dark red in Train track that will allows you to create high-productive, bad world wide web purposes speedily. More

    ReplyDelete
  5. If you're a programmer then it's your duty to write the efficient and right code for the specific work. For this purpose you have to work on a good pace with more practise. You can take the good piece of code from the database homework so that you can write a better code.

    ReplyDelete