简体   繁体   中英

Primary key not returned in OneToOne join fetch in eclipselink

I have an issue join fetching in case of OneToOne relation in the same class. Example follows:

class Data {
 ...

 @Id
 @Column(name = "DATA_ID")
 Long id;

 @Column(name = "DATA_OWNER_ID")
 @ForeignKey(entityClass = Owner.class)
 Long ownerId;

 @Column(name = "DATA_RELATED_ID")
 @ForeignKey(entityClass = Data.class)
 Long relatedDataId;

 @OneToOne(fetch = FetchType.LAZY)
 @JoinColumn(name = "DATA_RELATED_ID", referencedColumnName = "DATA_ID", insertable = false, updatable = false)
Data relatedData;

}

I want to select data based on some conditions, while also fetching/initialising the "relatedData", all in one JPQL query:

SELECT owner.something1, data
FROM Data data
JOIN Owner owner on data.ownerId = owner.id
JOIN FETCH data.relatedData
WHERE data.something2 = :expectedSomething2

Executing that JPQL query throws an exception:

Query: ReadObjectQuery(name="relatedData" referenceClass=Data)|Exception:
javax.persistence.PersistenceException: Exception [EclipseLink-6044] (Eclipse Persistence Services - 2.6.2.v20151217-774c696): org.eclipse.persistence.exceptions.QueryException
Exception Description: The primary key read from the row [DatabaseRecord(
DATA_X => something
DATA_Y => something2
...
)] during the execution of the query was detected to be null.  Primary keys must not contain null.

Which is somewhat true, as there is no DATA_ID column listed. Changing JOIN FETCH to LEFT JOIN FETCH returns both owner.something1 and data , but the relatedData object is null (relatedDataId is not null).

I can see, that the id for relatedData is returned from DB, but eclipselink trims it in valueFromRowInternalWithJoin and trimRowForJoin methods.

The Id column name attribute value is the reason of this exception. Same issue found in eclipselink version 2.3.2 but it works fine in version 2.0.0 Try with this entry:

eclipselink.jpa.uppercase-column-names=true

OR Try with upper and lower case one by one which on will work for you.

@Id
@Column(name = "UUID")   // UUID - uppercase/lowercase one by one
Long id;

I've somehow resolved this issue, but haven't had the time to correctly identify the cause. Final (working) version differences are:

  1. I could've forgotten to add get/set for relatedData
  2. I have specified targetEntity = Data.class in @OneToOne
  3. Fetch is now a LEFT JOIN FETCH and appears before JOIN Owner owner

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM