January 29th, 2012
3:26 pm
Cannot obtain a class literal for a concrete parameterised type

Posted under Java
Tags , , , , , ,

Update 30/1/2012

After further testing, I have found more issues trying to use a parameterised concrete class in a JPA constructor expression. EclipseLink was throwing MethodNotFoundException complaining that it could not find the constructor method for the class, due to the use of the parameterised type in one of the constructor arguments. The precise circumstances where this does and does not work are not clear.

My solution has been to not use a parameterised class at all in a JPA constructor expression. To avoid most of the code duplication, what I did was to subclass the parameterised class for each concrete type I was using, i.e. I created a concrete subclass which only contained a constructor calling the superclass constructor. This then allowed me to use a typed query in JPA, as the returned class was now non-parameterised and so I could create a class literal for it.

 

Original Post

Whilst in some situations this may be an issue, it is also a statement of fact!

This is due to type erasure at run time, and cannot be done.

It means, for example, that in some cases it is not possible to completely eliminate unchecked warnings.

One example of mine was the use of a parameterised type in a constructor expression class in JPA. I had a requirement to do fetches which involved returning an entity plus another column that could not be handled as a relationship/JPA entity property. The property in question was the count of children for a tree node entity. As I was using path enumeration to describe the tree, I could not use JPA relationships to handle it, and so had to return the child count separately. I had more than one type of tree, all handled polymorphically, and so wanted to re-use the constructor class by making it parameterised.

This all worked fine but the class could not have its class literal passed when created a TypedQuery to fetch the results back. The solution was to use some casting isolated in a specific method, and to suppress the generic warnings via @SuppressWarnings("unchecked").

The following posts detail this issue:-

http://stackoverflow.com/questions/2390662/java-how-do-i-get-a-class-literal-from-a-generic-type

http://www.angelikalanger.com/GenericsFAQ/FAQSections/ParameterizedTypes.html#Why is there no class literal for the concrete instantiation of a parameterized type?

No Comments »

September 23rd, 2011
1:21 pm
JPA – Using a mapped superclass to hold Ids and Version Numbers for all Entities

Posted under JPA
Tags , , , ,

All my entities have a numeric ID as a primary key, except in very exceptional cases. In particular, I never used business data as part of the primary key, nor do I ever use a primary key for any business purposes (such as an invoice number). I consider that primary and foreign keys are only used to define relationships, i.e. they are metadata as far as the domain model is concerned.

The problem of using business data in primary keys is that if the business data format for a primary key changes in any way, all the foreign keys referring to this primary key column must also be changed. This can result in massive changes throughout the data model for what started as a simple business change. Taking the above invoice number for example, the business may decide to add an alphanumeric branch prefix to the invoice number.

If instead all primary keys are kept as separate numeric IDs, changes to the format of business data should typically only require changes to one table.

With that rant out of the way, the main point of this post is that, given the above, plus the need to hold version numbers on all entities to support optimistic locking, it is desirable to hold all the primary keys and version numbers in a mapped abstract superclass. This has the following benefits:-

  • the entities are simplified and the key/version number implementation is encapsulated and centralised, which is a good design principle
  • the mechanism allows for a standard mechanism to get the primary key/version of any entity polymorphically via the mapped superclass. This is especially useful when you need to do comparisons between entities and you do not want to override equals on the entities. It is also useful for other polymorphic situations – in my case I also have a polymorphic tree implementation which makes use of this

Note the following points about the implementation:-

  • As I have discussed here, I always annotate getters rather than fields, to permit inheritance. In this case, I provide fields plus polymorphic getters/setters in the mapped superclass for getEntityId and setEntityId which are marked transient and are not annotated. They are purely to allow polymorphic access to the primary key.
  • Each entity defines its own getters/setters with a mnemonic name for the primary key. These getters/setters call the base polymorphic ones. The reason for this is that as well as improving the key naming,  it allows each entity to annotate its primary key differently, for example to use a specific generator for sequences etc.
  • As the primary keys are annotated in the subclasses, this permits the base superclass IDs to be generic. In my case, this caters for both Long and Integer primary keys using a generic base superclass. Note that it would not be possible to annotate in the superclass if the ID is a parameterised type – JPA spits this out and will not allow it.
  • Due to the above generic issue, the type for the version number must be fixed, as this is annotated in the superclass. In my case I settled for an int for version numbers.
  • Note that as the primary key is generic, it must therefore be a reference type rather than a primitive type (e.g. Long rather than long). In my case, primary keys are normally Long
  • In some cases, I have other mapped superclasses, such as Tree and TreeNode classes. In this case, Tree and TreeNode extend the EntityBase class, and Tree and TreeNode subclasses then just extend Tree and TreeNode respectively.

The following code illustrates a simple example of the superclass and an entity subclass:-

 

EntityBase

/**
* Entity implementation class for Entity: EntityBase
* This mapped superclass defines the primary key and locking version number for all entities.
* The getters/setters are marked transient so they are not mapped here. This allows polymorphic access to primary key (and version),
* but still allows the subclass to define its own (mapped) getter/setter names for the primary key, and to annotate for specific generators etc.
* This allows meaningful names for primary keys, normally <tableName>Id
*/
@MappedSuperclass
@Access(AccessType.PROPERTY)
public abstract class EntityBase<C> implements Serializable {
    private static final long serialVersionUID = 8075127067609241095L;

    private C entityId;
    private int version;
   
    @Transient public C getEntityId() {
        return entityId;
    }
    @Transient public void setEntityId(C entityId) {
        this.entityId = entityId;
    }
    /*
     * The version cannot be generic as it is annotated here (unlike the primary key)
     * If you do, Eclipselink throws a tantrum. In practice, an int is plenty –
     * it would allow continuous version changes once a second for over 68 years for example.
     */
    @Version
    public int getVersion() {
        return version;
    }
    public void setVersion(int version) {
        this.version = version;
    }
}

 

Address

@Entity
@Access(AccessType.PROPERTY)
public class Address extends EntityBase<Long> implements Serializable {
    private static final long serialVersionUID = 3206799789679218177L;
   
    private int latitude;
    private int longitude;   
    private String streetAddress1;
    private String streetAddress2;
    private String locality;
    private String postTown;
    private String county;
    private String postCode;
       
    public Address(){}

    @Id
    @GeneratedValue(generator="AddressId")   
    public Long getAddressId() {return super.getEntityId();}
    public void setAddressId(Long addressId) {super.setEntityId(addressId);}
   
    public int getLatitude() {return latitude;}
    public void setLatitude(int latitude) {this.latitude = latitude;}
    public int getLongitude() {return longitude;}
    public void setLongitude(int longitude) {this.longitude = longitude;}
   
    public String getStreetAddress1() {return streetAddress1;}
    public void setStreetAddress1(String streetAddress1) {this.streetAddress1 = streetAddress1;}
    public String getStreetAddress2() {return streetAddress2;}
    public void setStreetAddress2(String streetAddress2) {this.streetAddress2 = streetAddress2;}
    public String getLocality() {return locality;}
    public void setLocality(String locality) {this.locality = locality;}
    public String getPostTown() {return postTown;}
    public void setPostTown(String postTown) {this.postTown = postTown;}
    public String getCounty() {return county;}
    public void setCounty(String county) {this.county = county;}
    public String getPostCode() {return postCode;}
    public void setPostCode(String postCode) {this.postCode = postCode;}   
}

No Comments »

July 19th, 2011
8:54 pm
JPA – Accessing the primary key ID allocated during a persist operation on a new entity

Posted under JPA
Tags , , , ,

I wanted to do this in order to use the ID as part of the creation of a Base64 encoded tree path in another column in the same row, as I was using path enumeration as my tree algorithm (see here on slideshare.net for an excellent article on database tree algorithms).

The simple answer is – you can’t do this reliably, unless you allocate IDs yourself in some way.

  1. The ID is not available before a persist. I could call flush and then read it back, create the TreePath and then persist again – this is safe. This is discussed here on Stack Overflow.
  2. The JPA Lifecycle callback @PrePersist does not guarantee that the ID is visible. The net is rather quiet on this but this post here about hibernate says it cannot be relied upon  (@PostPersist would of course be different). There are strong limits on what you can do in such a callback or entity listener. For example, you can’t do entity manager operations, persist entities, or refer to other entities etc.
  3. Triggers would be another way to avoid the double update. I could set the rest of my TreePath prior to the first persist, and then retrieve the actual ID in a before insert trigger using the new.TreePathID syntax (MySQL and Oracle use similar syntax in this respect). I could then encode it in Base64 using a stored procedure, and append it to the treepath. Oracle has a built in package with Base64 encoding and decoding available (the utl_encode package). For MySql there is an open source example on the internet here. From posts on the net, e.g. here, triggers do work in MySQL via JPA.

The best solution looks like using triggers on the database server, as this avoids the double update. I have yet to investigate/try this.

No Comments »

April 2nd, 2011
5:50 pm
Updating components such as JSF, JPA in Glassfish

Posted under Glassfish
Tags , , , , ,

Update 04/10/2011

An essential step was omitted below, which is to clear out the OSGI cache. If you do not do this, and for example manually update Mojarra, the old version will still be loaded from the OSGI cache so your update will not take effect (and probably leave you wondering where glassfish can possibly still be getting the old version from!)

The simple solution is to ensure that you clear the OSGI cache after an update. The cache will be automatically rebuilt by Glassfish.

Simply delete all files in the  <glassfish-root>/glassfish/domains/domain1/osgi-cache/ folder. (Typically this just has a felix  subfolder to be deleted).

This solves the problem.

 

Original

Glassfish has its updatetool which automatically lists and installs updates from known repositories. You can add to the list of repositories, but they have to be of the type that Glassfish will accept – it will not install from any old download site.

When I wanted to update Mojarra in GF 3.0.1 from 2.0.2 FCS to 2.0.4 FCS with the updatetool, I could not find an update site with that version on.

The alternative (which I did) is to update manually – in this case to stop Glassfish and copy the jsf-api.jar and jsf-impl.jar into the <glassfish-root>\glassfish\modules directory, then restart. The only issue with this is that the new version will not be correctly listed in the installed components under the update tool or in the glassfish administration if you do it manually. However, you can verify that the correct version is running by starting glassfish and one of your web apps running in it, then look in the log for Mojarra and you will see that Mojarra logs its version when it loads. (Be careful if using Notepad++ – I found that its search was unreliable when searching backwards in the log for Mojarra, and it missed the relevant matches.

This can also be done for JPA/Eclipselink. However, the issue with this is that in the update tool it is listed with the name Glassfish JPA, with a different version number to the one used for Eclipselink. It is therefore not possible to work out which version of Eclipselink you are upgrading to. Some of the forums suggest just copying in a later set of Eclipselink OSGI jars but this just does not feel right for OSGI!

The only think I can be certain of is the installed version of Eclipselink with a base version of Glassfish, as this is documented as part of the Glassfish release.

At present I am sticking with the Eclipselink 2.0.2 version that ships with Glassfish, as I have not had any problems with this.

No Comments »

March 6th, 2011
7:47 pm
Adding jsf view state to domain objects–part II

Posted under JSF
Tags , , , , , , ,

My original post on this is here.  It links to an Icefaces post which discusses using a decorator to do this. The fundamental problem is that you often want view state such as (but certainly not limited to) a selected flag on objects e.g. in tables. However, you do not want to pollute domain classes with view state, so it would not be desirable to add a selected flag to your domain objects as this blurs the layers (especially as you may have multiple different UI layers on the same domain, such as JSF browser clients, smart phone web clients, web services etc. all with different needs). Other examples of view state might be style classes to be used on different table rows in response to use actions etc.

Since my original post I have looked at other ways of achieving this, and summarize various approaches below which could be used to add view state to rows of a table.

In each case, assume initially we have a JSF table of the form <h:dataTable var=”row” value=”#{mainBean.rows}”>, where each row object has the properties firstName and surname, plus the need for a selected boolean flag to be maintained separately from the row.

 

1/ Using a row decorator

My original post discusses using a decorator to add the extra state, as per the icefaces post. This involves wrapping every row, but is transparent to the code. The downside of the decorator is that each domain class requiring the extra state needs its own decorator even though each case might require the same extra state. This potentially means a lot of extra classes just to add a selected flag.

 

2/ Using a generic row wrapper class composed with the row

A second alternative which is similar to the decorator would be just to use a wrapper class which holds the extra state plus the domain class instance, and explicitly make the calls to the domain class methods and properties. Thus, the following code might be used to read our table row properties and the selected flag (all the examples use direct instantiation for simplicity) :-

//wrap a row. rowWrappers is the list containing the wrapped rows
rowWrappers.add(new RowWrapper<Row>(row));

// read properties on a facelets page – note that the table now contains wrapped rows:-

<h:dataTable var=”rowWrapper” value=”#{mainBean.rowWrappers}”>,
<h:outputText value=”#{rowWrapper.row.firstName}”>
<h:outputText value=”#{rowWrapper.row.surname}”>

//read the selected flag on a facelets page
<h:outputText styleClass=”#{rowWrapper.selected ? ‘style1’ : ‘style2’}” value=”…”/>

The pros and cons of this approach are:-

  • All the rows need to be wrapped as before.
  • All the ‘delegation’ to access row properties is explicit in all the expressions.
  • The upside however is that to add a given set of view state properties, only a single class is needed and this can wrap any number of domain classes generically, which can be a significant advantage.

 

3/ Using a Map to hold the additional row state objects

A third approach makes use of the fact that JSF EL value expressions can transparently read Map entries just like properties. Therefore where object m is a map or object that implements java.util.Map, the equivalent expressions m.property1 and m[‘property1’] when reading a value (i.e. on the right hand side of an expression, or rvalue mode) both result in

m.get(‘property1’)

being executed. When writing a value (i.e. on the left hand side of an expression, or in lvalue mode), as in m.property1 = rhsexpression, the statement

m.put(‘property1’, rhsexpression)

will be executed, assigning rhsexpression as the value of property1.

This technique allows us to use the row object itself as a key to the map containing the additional row state:-

//add row state object to map
rowFlagsMap.add(row, new RowFlags());

// read properties on a facelets page :-

<h:dataTable var=”row” value=”#{mainBean.rows}”>,
<h:outputText value=”#{row.firstName}”>
<h:outputText value=”#{row.surname}”>

//read the selected flag on a facelets page using the current row as a map key
<h:outputText styleClass=”#{mainBean.rowFlagsMap[row].selected ? ‘style1’ : ‘style2’}” value=”…”/>

Note that the nested expression evaluation works correctly with the map as the ‘man in the middle’ and that the expression mainBean.rowFlagsMap[row].selected could be used equally to fetch any other property from the rowflags object instead of the selected  property. The expression works as we would expect in both lvalue and rvalue modes, such that if for example the above property value was written to as true from the jsf page (e.g. from the value property of an updated check box we had just ticked), the expression would execute correctly as

mainBean.rowFlagsMap.get(row).selected=true;

The pros and cons of this approach are:-

  • We need an extra map access to get the row state, but for typical table sizes a hashmap would give very efficient access and should not be an issue.
  • We need to use the more complex expression mainBean.rowFlagsMap[row].selected  to fetch the additional row state. However, the plus is that we do not have to wrap each row in the code, and assuming that there are more table properties than additional state, we do not have to explicitly use a nested expression for them as we would in the previous approach.
  • When using this approach, it must be born in mind that you are using an object as a Map key. This should not be an issue, but if you override the hashCode function such that the hash value could change during the lifetime of a row object (for example if a row property changed) you would need to take account of this. Note also that rows in the map will only correctly match the exact same objects. If you refetch the same domain objects again from your entity manager you cannot expect them to match any existing objects in the map. Again, this should not normally be an issue as you would expect to rebuild the map from scratch when refetching domain objects from persistent storage.

 

4/ Using a Smart Map Interface to implement a selected property by storing the selected row objects

This approach is similar to the previous one, in that it uses a Map interface to hold a selected flag. The difference is that we implement our own class implementing  the Map interface and hide a map behind it. Our Map class simply stores each selected row in a ‘real’ map. When the caller reads the selected flag for a row by calling map.get on our map class, we perform a contains call on the ‘real’ map and return true if the row is present, or false if it is not. Similarly, when asked to set selected =true for a row, we just add the row to the ‘real’ map. When asked to set selected=false for a row, we remove it from the ‘real’ map. The pros and cons of this approach are:-

  • We only need to store the selected rows in the map, so we are storing less map entries.
  • The expressions to check the selected flag are a bit simpler, requiring something of the form mainBean.selectedMap[row]
  • Conversely, we need to implement the smart map – this needs quite a number of dummy methods when implementing the Map interface. When implementing this, I typically create an abstract base class which dummies out most of the java.util.Map methods which I don’t need, and then extend this for a desired implementation. This project in the repository makes use of this technique – see the classes uk.co.salientsoft.view.JSFValueMap and uk.co.salientsoft.view.SelectedMap.
  • The other downside is that this method only allows storage of a simple boolean based on the presence or absence of a row. If we need more additional row state, we need to look to one of the other methods.
  • As with the previous method, we are using a row object itself as a map key, so the same caveats apply as in the previous case.

 

Conclusion

As is often the case, there is no clear winner – you take your pick depending on individual requirements and the various pros and cons. Overall, my current favourite in general is to use the additional Map. It is simple to implement (you don’t need to dummy a load of Map methods like you do with the smart Map). Unlike the smart Map, you can add any number of additional properties to a row. The domain row properties can be accessed exactly as before, and you don’t need to wrap every row (however you do need to create the row state object and add it to the map for every row). Whilst the access to the additional state requires a slightly more complex expression, this is likely to be needed less often than expressions to read the domain properties.

No Comments »

March 5th, 2011
7:16 pm
JPA entities – field vs method annotation

Posted under JPA
Tags , , ,

Having read a number of technical blogs on this there appeared to be no clear winner either way, until I hit a requirement to use a mapped superclass for an entity. Then the following issues became very important:-

  1. Annotating fields gives you less flexibility – methods can be overriden by a subclass, whereas fields cannot.
  2. My particular example where I hit this was when designing an implementation to use for hierarchical/tree structured data, to be used in a number of places in an application. I wanted to make all the tree usage polymorphic from the same base class implementation, as then various other areas of the code could be reused for any tree. As entities were passed all the way up to the (JSF) UI, I was using certain design patterns for handling hierarchies at the UI level and making them able to handle any tree was desirable.
  3. Some of the functionality for handling trees – in my case path enumerated trees as described here in this excellent article on slideshare.net – could be placed in a base class. Examples of this were methods to compress node Ids in the path enumerated string using Base64, and building tree path strings for use at the UI etc.
  4. A key gotcha was that I wanted different impementations of trees to be annotated differently, for example to use different sequence Id generation. If the tree Id was in the mapped superclass and I was using field annotation, I was stuck. This issue is discussed in these articles here (see the comments at the end) and here.

My solution was to take the decision to always annotate (getter) methods from now on. This allowed the following implementation:-

  1. My mapped superclass contained getters annotated @Transient where I wanted to change their behaviour in a subclass. For example, my treeId primary key was in the superclass but marked @Transient so that it would not be mapped there. Then, in each subclass, I added an override getter/setter pair for the field, and annotated the getter with the desired ID generation. This allowed every subclass to have its own sequence generation (in my case), but to still allow polymorphic usage in other code.
  2. When doing this, a classic gotcha was to forget to mark the base class getters @Transient. This caused them to be mapped in both the mapped superclass and the subclass, resulting in multiple writable mappings which Eclipselink complained about loudly! It feels counter-intuitive to set them as transient, but the important point is that they will be mapped by the subclass.
  3. When doing this, I had to explicitly annotate the mapped superclass for property annotation using @Access(AccessType.PROPERTY). This is because normally the default type of access (field or property) is derived automatically from where the primary key is annotated. In this case, there was no such annotation on the mapped superclass so it needed telling – again, strange and loud Eclipselink errors resulted without this as my @Transient annotations on getters in the superclass were being ignored, as it defaulted to field annotation!
  4. Another issue was that I wanted a name field in the base superclass, but wanted to override this in the subclasses. In fact one tree implementation had node classes with an associated keyword class, where the name was stored on the keyword class and delegated from the getter on the node class, which in turn overrode the getter in the mapped superclass. Again, I marked the name getters as @Transient in both the tree mapped superclass and in the node class, and just mapped the name in the keyword class. This allowed other code to obtain the name polymorphically using a base superclass reference, but the actual name came from 2 levels further down. JPA was kept happy as the name was mapped wherever I needed it to be.

The following sample code fragment from my mapped superclass illustrated some of these points:-

package uk.co.salientsoft.test.domain;
import javax.persistence.Access;
import javax.persistence.AccessType;
import javax.persistence.Column;
import javax.persistence.MappedSuperclass;
import javax.persistence.Transient;

import uk.co.salientsoft.jpa.ColumnMeta;

/**
* Entity implementation class for Entity: TreeNode
* This mapped superclass performs the common tree/treepath handling for all tree entities
*
*/
@MappedSuperclass
@Access(AccessType.PROPERTY)
public abstract class TreeNode {
   
    private long TreeNodeId;
    private String treePath;
    private int nodeLevel;

    @Transient public long getTreeNodeId() {return this.TreeNodeId;}
    @Transient public void setTreeNodeId(long TreeNodeId) {this.TreeNodeId = TreeNodeId;}
   
    @Transient public abstract String getName();
    @Transient public abstract void setName(String name);

No Comments »

February 2nd, 2011
7:56 pm
Primefaces Table Sorting–Common Gotchas

Posted under JSF
Tags , , , , , , , ,

Update 2/2/2011

According to this post here by Cagatay Civici, the Primefaces Project Leader, as at Primefaces 2.2M1, client side datatable is not supported and the dynamic attribute is deprecated from then on.
Seemingly it was becoming too hard to support all the table features on both client and server sides.
It is a shame that this was not documented better and more widely – the user manual still documents the dynamic attribute, and there are a number of posts about client side sorting (though in fairness they probably predate 2.2M1).

This behaviour exactly ties up with what I am seeing in my testing – the dynamic attribute does nothing, sortFunction is ignored, and all sorting is done via Ajax server side.

Original Post 2/2/2011

Having successfully got sorting working I was frustrated to find that a new simple example failed to work. Primefaces table sorting is pretty much transparent, requiring minimal effort and working out of the box. The lessons learned on this one are instructive so I summarise them below.

Details of Example and Problem

  1. The example fetched a list using JPA, stored the list in a view backing bean, then displayed it in a table with a sortable header.
  2. When the header was clicked, the up/down arrows were correctly displayed, but the data was not sorted – it was as if the request was ignored.
  3. It was not immediately obvious how the header click was handled – there was no obvious click event on the HTML element, and I could not see any Javascript running after a quick test with Firefox/Firebug. I gave up this line of attack but may look into it later as to how it all works. Some dynamic CSS pseudo classes/jQuery trickery may be involved.
  4. I was not certain as to whether the table was client side or server side/Ajax, even though it should have been client side by default. To diagnose the problem, I changed the value of the sortBy attribute in the column header to be an invalid bean property. The symptoms did not change, but an errors were logged in the Glassfish server log for each header click – “[#|2011-02-02T18:22:14.557+0000|SEVERE|glassfish3.0.1|org.primefaces.model.BeanPropertyComparator|_ThreadID=24;_ThreadName=Thread-1;|Error in sorting|#]”.
  5. This showed that the sort was being attempted but was failing due to the invalid property, which indicates that the sort was attempted server side. According to the Primefaces forum, for client side sorting, the sortBy property is not used as the displayed data is sorted.
  6. Interestingly, I would have expected Primefaces to use a client side table by default, but clearly it was not. Changing the dynamic property on the table tag to false explicitly had no effect and the behaviour was unchanged, so I will need to investigate client side tables further as for small data sets they are faster – I will update this post when I have done this.
  7. I turned on FINEST logging with Eclipselink in persistence.xml. Use <property name="eclipselink.logging.level" value="FINEST" /> to do this, and note that you need to bounce Glassfish to for a logging level change to be picked up. I noticed after this that the JPA query seemed to be rerunning very often, perhaps for every click of the sort header. This lead me to wonder if the backing bean was being recreated each time.

 

Cause and Solution

In the end, it was simply that I had not annotated the JSF backing bean as @SessionScoped (the example used CDI throughout, and did not use JSF managed beans). This meant the bean was request scoped by default, and was indeed being recreated – the sort was trying to do the correct thing, but the data was getting reloaded from the database in the original sort order each time!

Adding the correct annotation as above (and making a couple of the beans correctly implement serialisable to satisfy CDI/Weld) solved the problem.

This is a good example of where a problem cause is not immediately apparent from the symptoms.

Sample JSF page fragment showing the form containing the table

<h:form id="frmTest">   
    <util:themeSwitcher form="frmTest" outerStyle="clear: both; float: left; margin-bottom:20px;" innerStyleClass="ui-widget"/>
    <h:panelGroup layout="block" style="width:300px;">   
        <p:dataTable var="taxonomyNodes" value="#{taxonomyBrowser.taxonomyNodes}" scrollable="true"
             styleClass="clear #{fn:length(taxonomyBrowser.taxonomyNodes) lt 20 ? ‘ss-tableheader-scrolladjust-nobars’ : ‘ss-tableheader-scrolladjust-bars’}"
             height="460" > 
             <f:facet name="header">
                Client Side Sorting
             </f:facet>
             <p:column headerText="Category List"  sortBy="#{taxonomyNodes.text}">
                 <h:outputText value="#{taxonomyNodes.text}" />
             </p:column>           
        </p:dataTable>
    </h:panelGroup>
</h:form>

No Comments »

January 23rd, 2011
1:41 pm
Eclipse JPA table generation fails with Eclipslink 2.1.2, Glassfish V3.0.1

Posted under JPA
Tags , , , , ,

I was attempting to create a database for a new project which just contained entities – I had imported the entity classes from Enterprise Architect and added the required annotations, getters & setters etc.

My first attempt used the following persistence.xml (I have removed most of the classes for the example)

<?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=”Test” transaction-type=”RESOURCE_LOCAL”>
      <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>

      <non-jta-data-source>jdbc/TestPool</non-jta-data-source>
      <class>uk.co.salientsoft.Test.domain.Address</class>
      <class>uk.co.salientsoft.Test.domain.AddressLine</class>
      <class>uk.co.salientsoft.Test.domain.Campaign</class>
      <class>uk.co.salientsoft.Test.domain.CampaignText</class>      
      <exclude-unlisted-classes>false</exclude-unlisted-classes>     
      <properties>
       <property name=”eclipselink.logging.level” value=”INFO” />
       <property name=”eclipselink.target-server” value=”None” />
       <!– <property name=”eclipselink.target-server” value=”SunAS9″ />–>
       <property name=”eclipselink.target-database” value=”Oracle” />      
       <property name=”eclipselink.ddl-generation.output-mode” value=”database” />
      </properties>
     </persistence-unit>
</persistence>

 Having created the database and validated the connection/datasource etc., I attempted to create the tables from  Eclipse by right clicking the project and selecting JPA Tools/Create Tables from Entities…

This resulted in the following error:-

[EL Config]: Connection(5226838)–connecting(DatabaseLogin(
    platform=>OraclePlatform
    user name=> “Test”
    connector=>JNDIConnector datasource name=>jdbc/TestPool
))
[EL Severe]: Local Exception Stack:
Exception [EclipseLink-7060] (Eclipse Persistence Services – 2.0.1.v20100213-r6600): org.eclipse.persistence.exceptions.ValidationException
Exception Description: Cannot acquire data source [jdbc/TestPool].
Internal Exception: javax.naming.NoInitialContextException: Need to specify class name in environment or system property, or as an applet parameter, or in an application resource file:  java.naming.factory.initial

The error occurred even though the data source was being used outside the container as a non-jta data source (this worked previously for JPA1/Glassfish V2, allowing JPA to be used outside the container but still using a datasource defined in Glassfish). A previous post here (in the section Notes on Persistence.xml) also reports that when running outside the container, it is vital to have eclipselink.target-server defaulted or set to none. In this case, the setting caused no difference either way. After a fair bit of research/Googling, I could not find the cause of the problem, so I simply reverted to specifying the connection explicitly in persistence.xml,  without using the connection defined in Glassfish at all.

This worked correctly. I will not need to create the database very often, and it only involved tweaking a few lines in the file, so I’m happy to live with it. Here is my modified persistence.xml which uses a direct connection specified in the file. This version created the database correctly. Note that as detailed in this post here (near the bottom of the post), the property names for JDBC url, user, password and driver have now been standardised and are no longer eclipslink specific.

<?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=”Test” transaction-type=”RESOURCE_LOCAL”>   
    <!– <persistence-unit name=”Test” transaction-type=”JTA”>–>
   
      <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>

     <!–<jta-data-source>jdbc/TestPool</jta-data-source>–>
     <!–<non-jta-data-source>jdbc/TestPool</non-jta-data-source>–>
    
      <class>uk.co.salientsoft.Test.domain.Address</class>
      <class>uk.co.salientsoft.Test.domain.AddressLine</class>
      <class>uk.co.salientsoft.Test.domain.Campaign</class>
      <class>uk.co.salientsoft.Test.domain.CampaignText</class>      
      <exclude-unlisted-classes>false</exclude-unlisted-classes>     
      <properties> 
      
        <property name=”javax.persistence.jdbc.url” value=”jdbc:oracle:thin:@localhost:1521:xe”/>     
        <property name=”javax.persistence.jdbc.user” value=”Test”/>
        <property name=”javax.persistence.jdbc.password” value=”Test”/>
        <property name=”javax.persistence.jdbc.driver” value=”oracle.jdbc.OracleDriver”/>     
     
       <property name=”eclipselink.logging.level” value=”INFO” />
        <property name=”eclipselink.target-server” value=”None” />
       <!– <property name=”eclipselink.target-server” value=”SunAS9″ />–>
       <property name=”eclipselink.target-database” value=”Oracle” />      
       <property name=”eclipselink.ddl-generation.output-mode” value=”database” />
      </properties>
     </persistence-unit>
</persistence>

No Comments »

December 3rd, 2010
9:42 am
JPA error “Class is mapped, but is not included in any persistence unit”

Posted under JPA
Tags , , , ,

I received this compile time error from Eclipse with one of my test projects which was previously fine, using Eclipse Helios with Eclipselink 2.1.0 (and container managed JPA in EJBs). The error occurred when I was autodiscovering the entities rather than listing them in persistence.xml explicitly, even when <exclude-unlisted-classes>false</exclude-unlisted-classes> was explicitly present.

Supposedly, as the annotated entity sources for the classes are in a subfolder of the parent of the META-INF folder containing persistence.xml, they should be discovered automatically. Listing the fully qualified classes explicitly in persistence.xml solved the problem, however this is not ideal as it would mean having an alternative version of persistence.xml for testing.

I googled for the problem but could not find a solution listed anywhere. For now this is just one to be aware of – I’ll stick with listing the classes explicitly and look further for a solution later on as and when it becomes a nuisance!

No Comments »

November 26th, 2010
8:25 pm
Using container managed JPA 2.0 with CDI/EJB 3.1/Glassfish 3

Posted under JPA
Tags , , , , , ,

Update

  • One issue to be aware of, which is not immediately obvious, is when populating a database from scripts. If the version column is left null (Eclipselink leaves it as nullable by default), then the null value causes an immediate OptimisticLockException to be thrown. This is because EclipseLink expects and checks for a zero as the initial value for a new record. If EclipseLink itself persists the record, then it writes a zero.
  • One good idea to resolve this would be to enforce version columns to be non null with a zero default – although it must be said that it would be helpful if EclipsLink did this automatically in response to the @Version annotation.
  • Population scripts should therefore set version to zero, unless it is set non null with a default of zero in JPA – this latter solution is cleaner and would be automatic for me because I create version columns in a mapped superclass used by all Entities. I have yet to test this out however.

 

Original Post

This follows on from a previous post relating to JPA 1.0/Glassfish 2.1, and contains a few notes and pointers relating to JPA 2.0 under Glassfish 3 with CDI/Weld.

Firstly, when using an EJB from a client, use CDI injection (@Inject) rather than the @EJB annotation, as CDI gives many additional benefits such as type safety.

In an EJB:-

  • You are using container managed transactions, and so simply have to inject an entity manager rather than create one from an entity manager factory.
  • The container managed entity manager can be injected with a simple @PersistenceContext annotation – the persistence unit name may be defaulted and is discovered automatically.
  • The container is responsible for entity manager lifetime/closing. Calling e.g. em.close at the end of a bean method is illegal and will make Glassfish angry. You do not want to make Glassfish angry – you end up with many long stack traces in the log which on the surface do not appear to relate to this trivial problem!

A major issue with container managed transactions is how to use optimistic locking and detect and handle optimistic lock exceptions correctly. This is detailed in Pro JPA 2, pages 355-357 (you can preview this in Google Books). The main problem is that in a server environment, the OptimisticLockException will simply be logged by the container which then throws an EJBException. Trying to catch an OptimisticLockException in the calling client is therefore doomed to failure – it will probably never be caught!

The solution is to call flush() on the entity manger (e.g. em.flush()) just before you are ready to complete the method. This forces a write to the database, locking resources at the end of the method so that the effects on concurrency are minimised. This allows us to handle an optimistic failure while we are still in control, without the container swallowing the exception. The ChangeCollisionException might contain the object which caused the exception, but it is not guarranteed to. If there were multiple objects in the transaction, we could have invoked getEntity() on the caught exception to see whether the offending object was included.

If we do get an exception from the flush() call, we can throw a domain specific application exception which the caller can recognise, i.e. convert an OptimisticLockException to our own ChangeCollisionException, avoiding coupling the caller to the internal semantics of JPA transactions. It is also desirable to factor out the code which calls flush() into our own method, e.g. flushChanges() to avoid the need for every method which needs to flush having to catch the optimistic lock exception and then throw our domain specific one – we can centralise the exception conversion in our own single method.

We must annotate the ChangeCollisionException class with @ApplicationException, which is an EJB container annotation, to indicate to the container that the exception is not really a system level one but should be thrown back to the client as-is. Normally defining an application exception will cause the container not to roll back the transaction, but this is an EJB 3 container notion. The persistence provider that threw the OptimisticLockException  (in this case Eclipselink) does not know about the special semantics of designated application exceptions and, seeing a runtime exception, will go ahead and mark the transaction for rollback. The client can now receive and handle the ChangeCollisionException and do something about it.

Here is an example of our exception class with the required annotation:-

@ApplicationException
public class ChangeCollisionException extends RunTimeException {
   public ChangeCollisionException() {super(); }
}

Here are code fragment examples from a stateless session bean showing the entity manager injection, and a client JSF model bean showing the CDI injection of the stateless session bean. Note that with EJB 3.1 it is not necessary to declare local or remote interfaces for an EJB as business interfaces are not a requirement. However, I always use an interface as it allows for example a mock version of a service layer to be easily swapped in for testing. CDI supports this conveniently via alternatives, whereby a mock version of a bean can be switched in via a setting in beans.xml for testing.

@Stateless
public class SentryServiceImpl implements SentryServiceLocal {

    @PersistenceContext
    private EntityManager em;

}

@Named
@Dependent
public class ModelBeanImpl implements ModelBean, Serializable {
    private static final long serialVersionUID = -366401344661990776L;
    private @Inject SentryServiceLocal sentryService;
… 
}

With container managed JPA and/or Glassfish your persistence.xml  can also be simplified, as you can define your data source in Glassfish rather than explicitly in persistence.xml, as described here.

Note that when defining a data source directly in persistence.xml,  some property names have been standardized for JPA 2.0, so have changed from e.g. eclipselink.jdbc.user to javax.persistence.jdbcuser. The following properties in persistence.xml are now standard:-

<property name="javax.persistence.jdbc.url" value="jdbc:oracle:thin:@localhost:1521:xe"/>
<property name="javax.persistence.jdbc.user" value="sentry"/>
<property name="javax.persistence.jdbc.password" value="sentry"/>
<property name="javax.persistence.jdbc.driver" value="oracle.jdbc.OracleDriver"/>

An example persistence.xml used under JPA 2.0 follows:-

<?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="SentryPrototype" transaction-type="JTA">
      <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>
      <jta-data-source>jdbc/SentryPool</jta-data-source>
      <properties>
       <property name="eclipselink.logging.level" value="INFO" />
       <property name="eclipselink.target-database" value="Oracle" />      
       <property name="eclipselink.ddl-generation.output-mode" value="database" />      
      </properties>
     </persistence-unit>
</persistence>

No Comments »