Search code examples
neo4jdatanucleusisis

How would I use neo4j with Apache Isis?


I am attempting to use neo4j as a backing store for Apache Isis but it looks like some development may be needed. If I add the datanucleus-neo4j dependency, it appears the neo4j JDO connection is initializing but Apache Isis is expecting a different type of StoreManager.

This is the exception I get

org.datanucleus.store.neo4j.Neo4jStoreManager cannot be cast to org.datanucleus.store.schema.SchemaAwareStoreManager

How can I use neo4j as a backing store in Apache Isis?
I read about nosql support in Isis, but is it not part of the current release? http://isis.apache.org/components/objectstores/nosql/about.html

Thanks!

In the persistor.properties -

#
# neo4j
#
isis.persistor.datanucleus.impl.javax.jdo.option.ConnectionURL=neo4j:testDB
isis.persistor.datanucleus.impl.javax.jdo.option.ConnectionUserName=sa
isis.persistor.datanucleus.impl.javax.jdo.option.ConnectionPassword=

Relevant portion of the stack trace -

Caused by: java.lang.ClassCastException: org.datanucleus.store.neo4j.Neo4jStoreManager cannot be cast to org.datanucleus.store.schema.SchemaAwareStoreManager
at org.apache.isis.objectstore.jdo.datanucleus.DataNucleusApplicationComponents.createSchema(DataNucleusApplicationComponents.java:125)
at org.apache.isis.objectstore.jdo.datanucleus.DataNucleusApplicationComponents.init(DataNucleusApplicationComponents.java:111)
at org.apache.isis.objectstore.jdo.datanucleus.DataNucleusApplicationComponents.<init>(DataNucleusApplicationComponents.java:97)
at org.apache.isis.objectstore.jdo.datanucleus.DataNucleusPersistenceMechanismInstaller.createDataNucleusApplicationComponentsIfRequired(DataNucleusPersistenceMechanismInstaller.java:112)
at org.apache.isis.objectstore.jdo.datanucleus.DataNucleusPersistenceMechanismInstaller.createObjectStore(DataNucleusPersistenceMechanismInstaller.java:89)
at org.apache.isis.core.runtime.system.persistence.PersistenceSessionFactory.createPersistenceSession(PersistenceSessionFactory.java:94)
at org.apache.isis.core.runtime.system.session.IsisSessionFactoryDefault.openSession(IsisSessionFactoryDefault.java:217)
at org.apache.isis.core.runtime.system.context.IsisContextThreadLocal.openSessionInstance(IsisContextThreadLocal.java:149)
at org.apache.isis.core.runtime.system.context.IsisContext.openSession(IsisContext.java:271)
at org.apache.isis.core.runtime.system.IsisSystemFixturesHookAbstract.initializeServices(IsisSystemFixturesHookAbstract.java:154)
at org.apache.isis.core.runtime.system.IsisSystemFixturesHookAbstract.init(IsisSystemFixturesHookAbstract.java:122)
at org.apache.isis.core.runtime.runner.IsisInjectModule.provideIsisSystem(IsisInjectModule.java:133)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at com.google.inject.internal.ProviderMethod.get(ProviderMethod.java:104)
at com.google.inject.internal.InternalFactoryToProviderAdapter.get(InternalFactoryToProviderAdapter.java:40)
at com.google.inject.internal.ProviderToInternalFactoryAdapter$1.call(ProviderToInternalFactoryAdapter.java:46)
at com.google.inject.internal.InjectorImpl.callInContext(InjectorImpl.java:1031)
at com.google.inject.internal.ProviderToInternalFactoryAdapter.get(ProviderToInternalFactoryAdapter.java:40)
at com.google.inject.Scopes$1$1.get(Scopes.java:65)
at com.google.inject.internal.InternalFactoryToProviderAdapter.get(InternalFactoryToProviderAdapter.java:40)
at com.google.inject.internal.SingleFieldInjector.inject(SingleFieldInjector.java:53)
at com.google.inject.internal.MembersInjectorImpl.injectMembers(MembersInjectorImpl.java:110)
at com.google.inject.internal.MembersInjectorImpl$1.call(MembersInjectorImpl.java:75)
at com.google.inject.internal.MembersInjectorImpl$1.call(MembersInjectorImpl.java:73)
at com.google.inject.internal.InjectorImpl.callInContext(InjectorImpl.java:1024)
at com.google.inject.internal.MembersInjectorImpl.injectAndNotify(MembersInjectorImpl.java:73)
at com.google.inject.internal.MembersInjectorImpl.injectMembers(MembersInjectorImpl.java:60)
... 48 more

Solution

  • I'm not sure what the implications are, but I was able to get a neo4j datastore working with Apache Isis by modifying org.apache.isis.objectstore.jdo.datanucleus.DataNucleusApplicationComponents#createSchema in the "Isis Core Runtime module" to check if the datanucleus StoreManager supports the SchemaAwareStoreManager interface before casting.

    It is persisting data successfully.
    Seems too easy to be a legitimate enhancement, but I'll run it by the contributors never-the-less.

    private void createSchema(final Map<String, String> props, final Set<String> classesToBePersisted) {
        final JDOPersistenceManagerFactory jdopmf = (JDOPersistenceManagerFactory)persistenceManagerFactory;
        final NucleusContext nucleusContext = jdopmf.getNucleusContext();
        final StoreManager storeManager = nucleusContext.getStoreManager();
        if (storeManager instanceof SchemaAwareStoreManager) {
            ((SchemaAwareStoreManager)storeManager).createSchema(classesToBePersisted, asProperties(props));
        }
    }