New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Generic entity deserialization exception #249

Closed
mgaceanu opened this Issue Nov 12, 2015 · 4 comments

Comments

Projects
None yet
4 participants
@mgaceanu

mgaceanu commented Nov 12, 2015

Hi all,

I'm having the following generic base class:

public class BaseFoo<T extends Serializable> {
    @Id
    private T id;
    //constructor and setters
}

and an implementation

public class Foo extends BaseFoo<Integer>{
    private String name;
   //constructor and setters
}

I get the following exception when saving a Foo entity:

java.lang.RuntimeException: Unable to invoke no-args constructor for interface java.io.Serializable. Register an InstanceCreator with Gson for this type may fix this problem.
    at com.google.gson.internal.ConstructorConstructor$12.construct(ConstructorConstructor.java:210)
    at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:186)
    at com.google.gson.Gson.fromJson(Gson.java:810)
    at com.google.gson.Gson.fromJson(Gson.java:875)
    at com.google.gson.Gson$1.deserialize(Gson.java:128)
    at org.javers.core.json.typeadapter.commit.GlobalIdTypeAdapter.parseInstanceId(GlobalIdTypeAdapter.java:68)
    at org.javers.core.json.typeadapter.commit.GlobalIdTypeAdapter.fromJson(GlobalIdTypeAdapter.java:43)
    at org.javers.core.json.typeadapter.commit.GlobalIdTypeAdapter.fromJson(GlobalIdTypeAdapter.java:19)
    at org.javers.core.json.JsonConverterBuilder$2.deserialize(JsonConverterBuilder.java:144)
    at com.google.gson.TreeTypeAdapter.read(TreeTypeAdapter.java:58)
    at com.google.gson.Gson.fromJson(Gson.java:810)
    at com.google.gson.Gson.fromJson(Gson.java:875)
    at com.google.gson.Gson$1.deserialize(Gson.java:128)
    at org.javers.core.json.typeadapter.commit.CdoSnapshotTypeAdapter.fromJson(CdoSnapshotTypeAdapter.java:48)
    at org.javers.core.json.typeadapter.commit.CdoSnapshotTypeAdapter.fromJson(CdoSnapshotTypeAdapter.java:22)
    at org.javers.core.json.JsonConverterBuilder$2.deserialize(JsonConverterBuilder.java:144)
    at com.google.gson.TreeTypeAdapter.read(TreeTypeAdapter.java:58)
    at com.google.gson.Gson.fromJson(Gson.java:810)
    at com.google.gson.Gson.fromJson(Gson.java:775)
    at com.google.gson.Gson.fromJson(Gson.java:724)
    at com.google.gson.Gson.fromJson(Gson.java:696)
    at org.javers.core.json.JsonConverter.fromJson(JsonConverter.java:77)
    at org.javers.repository.mongo.MongoRepository.readFromDBObject(MongoRepository.java:184)
    at org.javers.repository.mongo.MongoRepository.getLatest(MongoRepository.java:241)
    at org.javers.repository.mongo.MongoRepository.getLatest(MongoRepository.java:79)
    at org.javers.repository.api.JaversExtendedRepository.getLatest(JaversExtendedRepository.java:100)
    at org.javers.core.snapshot.GraphShadowFactory.createLatestShadow(GraphShadowFactory.java:32)
    at org.javers.core.snapshot.GraphSnapshotFacade.createLatestShadow(GraphSnapshotFacade.java:22)
    at org.javers.core.commit.CommitFactory.create(CommitFactory.java:76)
    at org.javers.core.JaversCore.commit(JaversCore.java:62)
    at org.javers.spring.auditable.aspect.OnSaveAuditChangeHandler.handle(OnSaveAuditChangeHandler.java:17)
    at org.javers.spring.auditable.aspect.JaversAuditableRepositoryAspect.applyVersionChange(JaversAuditableRepositoryAspect.java:93)
    at org.javers.spring.auditable.aspect.JaversAuditableRepositoryAspect.applyVersionChanges(JaversAuditableRepositoryAspect.java:88)
    at org.javers.spring.auditable.aspect.JaversAuditableRepositoryAspect.onVersionEvent(JaversAuditableRepositoryAspect.java:70)
    at org.javers.spring.auditable.aspect.JaversAuditableRepositoryAspect.onSaveExecuted(JaversAuditableRepositoryAspect.java:58)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at org.springframework.aop.aspectj.AbstractAspectJAdvice.invokeAdviceMethodWithGivenArgs(AbstractAspectJAdvice.java:621)
    at org.springframework.aop.aspectj.AbstractAspectJAdvice.invokeAdviceMethod(AbstractAspectJAdvice.java:603)
    at org.springframework.aop.aspectj.AspectJAfterAdvice.invoke(AspectJAfterAdvice.java:46)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:168)
    at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:92)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:179)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:207)
    at com.sun.proxy.$Proxy41.save(Unknown Source)
    at BasicTest.testRepo(BasicTest.java:58)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:74)
    at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:85)
    at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:86)
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:241)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:87)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
    at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
    at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:70)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:180)
    at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
    at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:78)
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:212)
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:68)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:140)
Caused by: java.lang.reflect.InvocationTargetException
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at com.google.gson.internal.UnsafeAllocator$1.newInstance(UnsafeAllocator.java:48)
    at com.google.gson.internal.ConstructorConstructor$12.construct(ConstructorConstructor.java:207)
    ... 79 more
Caused by: java.lang.InstantiationException: java.io.Serializable
    at sun.misc.Unsafe.allocateInstance(Native Method)
    ... 85 more

Any idea why it can figure out the type it has to deserialize into?

@bartoszwalacik

This comment has been minimized.

Member

bartoszwalacik commented Nov 12, 2015

well, looks like JaVers thinks that type of id is Serializable, but in fact it is Integer. I will check what we can do about it.

@bartoszwalacik

This comment has been minimized.

Member

bartoszwalacik commented Nov 13, 2015

I've tried to reproduce this exception but without success, could you push failing test which would reproduce this issue?

@bartoszwalacik bartoszwalacik removed the bug label Nov 13, 2015

@gladstoneg

This comment has been minimized.

gladstoneg commented Jan 15, 2016

Maybe you were using InMemoryRepository? I have the same bug when using the JaversSqlRepository:

public abstract class AbstractEntity<T extends Serializable> {    

    @Id
    protected T id;    

    public abstract T getId();
    public abstract void setId(final T id);
}
@Entity
public class Account extends AbstractEntity<String> {

    @Override
    public String getId() {
        return id;
    }

    @Override
    public void setId(final String id) {
        this.id = id;
    }
}

Configuring Javers and reproducing the bug using SqlRepository (on MSSQL Server):

public static void main(final String[] args) {
    final Javers javers = JaversBuilder.javers().
            registerJaversRepository(SqlRepositoryBuilder.sqlRepository().
                    withConnectionProvider(() -> DriverManager.getConnection(
                            dbUrl, dbUser, dbPw)).
                    withDialect(DialectName.MSSQL).
                    build()).
            build();
    final Account acc = new Account();
    acc.setId("1");
    javers.commit("User", acc);
    javers.commit("User", acc);
}

The exception does not occur on the first commit. The entity needs to be present in the snapshot-table. Does not happen with InMemoryRepository. Happens with MappingStyle FIELD and BEAN.

bartoszwalacik added a commit that referenced this issue Jan 30, 2016

#249
fix in JSON deserialization of Generic Id property

@bartoszwalacik bartoszwalacik added the fixed label Feb 2, 2016

@bartoszwalacik

This comment has been minimized.

Member

bartoszwalacik commented Feb 2, 2016

fix released in JaVers 1.4.10

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment