question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Reading custom property type from JPA @ManyToOne.targetEntity

See original GitHub issue

Hello,

let’s suppose I have the following interface:

interface CategoryEntityDefinition {
}

with the following implementation:

@Entity
class CategoryEntity implements CategoryEntityDefinition {

     @Id    
     private long id;
}

and then I have the following JPA entity:

@Entity
class ProductEntity  {

    @NotNull
    @ManyToOne(fetch = FetchType.LAZY, targetEntity = CategoryEntity.class)
    @JoinColumn(name = "category_id", nullable = false, referencedColumnName = "id", foreignKey = @ForeignKey(name = (("fk_"+ ProductEntity.NAME)+"_category")))
    @JsonProperty(required = true)
    private CategoryEntityDefinition category;
}

Now i try to diff two objects of type ProductEntity and I get the following exception:

2017-11-17 16:28:47,245 org.apache.catalina.core.ContainerBase.[Tomcat].[localhost].[/storefront].[dispatcherServlet] [https-jsse-nio-127.0.0.1-8112-exec-4] ERROR: Servlet.service() for servlet [dispatcherServlet] in context with path [/storefront] threw exception [Request processing failed; nested exception is JaversException ENTITY_WITHOUT_ID: Class 'com.nemesis.platform.core.definition.catalog.CategoryEntityDefinition' mapped as Entity has no Id property. Use @Id annotation to mark unique and not-null Entity identifier] with root cause
JaversException ENTITY_WITHOUT_ID: Class 'com.nemesis.platform.core.definition.catalog.CategoryEntityDefinition' mapped as Entity has no Id property. Use @Id annotation to mark unique and not-null Entity identifier
	at org.javers.core.metamodel.type.EntityTypeFactory.findDefaultIdProperty(EntityTypeFactory.java:43)
	at org.javers.core.metamodel.type.EntityTypeFactory.createEntity(EntityTypeFactory.java:25)
	at org.javers.core.metamodel.type.TypeFactory.create(TypeFactory.java:42)
	at org.javers.core.metamodel.type.TypeFactory.inferFromAnnotations(TypeFactory.java:129)
	at org.javers.core.metamodel.type.TypeFactory.infer(TypeFactory.java:70)
	at org.javers.core.metamodel.type.TypeMapperState.infer(TypeMapperState.java:149)
	at org.javers.core.metamodel.type.TypeMapperState.lambda$getJaversType$0(TypeMapperState.java:87)
	at org.javers.core.metamodel.type.TypeMapperState.computeIfAbsent(TypeMapperState.java:111)
	at org.javers.core.metamodel.type.TypeMapperState.getJaversType(TypeMapperState.java:87)
	at org.javers.core.metamodel.type.TypeMapper.getJaversType(TypeMapper.java:124)
	at org.javers.core.metamodel.type.ManagedClassFactory.lambda$null$3(ManagedClassFactory.java:50)
	at org.javers.core.metamodel.type.JaversProperty.getType(JaversProperty.java:23)
	at org.javers.core.graph.ObjectGraphBuilder.lambda$getSingleReferencesWithManagedTypes$0(ObjectGraphBuilder.java:105)
	at java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:174)
	at java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1380)
	at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481)
	at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
	at java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:708)
	at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
	at java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:499)
	at org.javers.common.collections.Lists.positiveFilter(Lists.java:55)
	at org.javers.core.metamodel.type.ManagedClass.getManagedProperties(ManagedClass.java:63)
	at org.javers.core.metamodel.type.ManagedType.getProperties(ManagedType.java:49)
	at org.javers.core.graph.ObjectGraphBuilder.getSingleReferencesWithManagedTypes(ObjectGraphBuilder.java:105)
	at org.javers.core.graph.ObjectGraphBuilder.buildSingleEdges(ObjectGraphBuilder.java:75)
	at org.javers.core.graph.ObjectGraphBuilder.buildEdges(ObjectGraphBuilder.java:70)
	at org.javers.core.graph.ObjectGraphBuilder.buildGraphFromCdo(ObjectGraphBuilder.java:58)
	at org.javers.core.graph.ObjectGraphBuilder.buildGraph(ObjectGraphBuilder.java:47)
	at org.javers.core.graph.LiveGraphFactory.createLiveGraph(LiveGraphFactory.java:39)
	at org.javers.core.diff.DiffFactory.buildGraph(DiffFactory.java:98)
	at org.javers.core.diff.DiffFactory.compare(DiffFactory.java:53)
	at org.javers.core.JaversCore.compare(JaversCore.java:134)
	at org.javers.spring.jpa.JaversTransactionalDecorator.compare(JaversTransactionalDecorator.java:94)
	at org.javers.spring.jpa.JaversTransactionalDecorator$$FastClassBySpringCGLIB$$acb40bd0.invoke(<generated>)
	at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:204)
	at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:669)
	at org.javers.spring.jpa.JaversTransactionalDecorator$$EnhancerBySpringCGLIB$$71cf87d.compare(<generated>)
	at com.nemesis.platform.module.restservices.storefront.controller.RestDiffController.synchronize(RestDiffController.java:69)

This seems to be because here:

https://github.com/javers/javers/blob/master/javers-core/src/main/java/org/javers/core/metamodel/type/ManagedClassFactory.java#L50

You get the generic type of the attribute, while in JPA my case is perfectly valid and what you should do is get the targetEntity attribute of the @ManyToOne annotation on the attribute.

Issue Analytics

  • State:open
  • Created 6 years ago
  • Comments:9 (6 by maintainers)

github_iconTop GitHub Comments

1reaction
tinesoftcommented, Oct 12, 2020

@bartoszwalacik I’m interested to provide a PR for this one, if still available…

0reactions
bartoszwalacikcommented, Dec 10, 2017

Consider contributing a PR. We don’t want more annotation logic in JaVares so this issue could be implemented by adding a possibility to register custom PropertyTypeResolver (as you suggested).

Read more comments on GitHub >

github_iconTop Results From Across the Web

java - Mapping a property with ManyToOne relationship to a ...
I guess the issue could be due to: @NoArgsConstructor(access = AccessLevel.PROTECTED, force = true). try making the default constructor to ...
Read more >
Chapter 2. Mapping Entities - Red Hat on GitHub
JPA support property mapping of all basic types supported by Hibernate (all basic Java types , their respective wrappers and serializable classes). Hibernate ......
Read more >
Hibernate Annotations Reference Guide JBoss Enterprise ...
Depending on whether you annotate fields or methods, the access type used by Hibernate will be field or property . The EJB3 spec...
Read more >
Persistent Fields and Properties in Entity Classes
If generic types are not used, the targetEntity attribute of the @OneToMany and @ManyToMany annotations must be set to the type of the...
Read more >
Partial Data Update With Spring Data | Baeldung
@Entity public class Customer { @Id @GeneratedValue(strategy ... calling JPA save method — in fact, we'll update only the modified values.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found