草庐IT

spring-data跨店实体管理

coder 2023-10-28 原文

我想在我的应用程序中同时使用 Postgres、MongoDB 和 Neo4j。我能够配置它们,但是现在我的每个 POJO 都支持我的 graphNode 以及 aspectJ 的文档。

有什么方法可以过滤出哪些 POJO 仅由图形节点支持,哪些仅由文档支持?

当我在单个请求中保存 POJO 超过两次 [原文如此!] 时,我在保存 POJO 时遇到了问题,我可以在日志中看到 mongo 和 neo4j 都在尝试创建大量实例,这导致了一些死锁之王.

长话短说:

  1. 有没有办法过滤数据映射以配置 pojo“A”由 RDBMS 和图形(无文档)映射,而 pojo B 由文档和图形(无 RDBMS)映射
  2. 是否有或多或少涵盖我的问题的基于跨商店 spring 数据的应用程序的示例?
  3. 为什么我可以在我的 Controller 中一个一个地保存 pojo 类的两个实例,但是当创建第三个实例时我会注意到一个死锁?

[编辑]

我注意到的:

  1. Mongo aspectj 构建器支持 @Entity 注释的 POJO,我不知道如何使用 @Entity 将 POJO 映射到 Hibernate 而不是在 MongoDB 中
  2. Neo4j 相关的卡住仅在通过 REST 连接时发生,有时在 3 日有时在 4 日发生,有时根本不发生。查看 Controller 启动是如何完成的。我已经尝试了所有注释行但没有成功。
  3. 事务管理器配置必须放置在正确的位置,否则 Neo4J 配置验证器服务将失败。

[/编辑]

我使用:

  1. Spring 3.0.5
  2. SpringRoo 1.4
  3. Spring 数据 1.0
  4. Postgres 9.0 + Hibernate 3.5.5
  5. Neo4j 1.3 远程
  6. 远程 MongoDB 1.8.2
  7. 所有数据库都在一台远程机器上并且工作正常

[编辑]

POM 切片:

<properties>
    <roo.version>1.1.4.RELEASE</roo.version>
    <spring.version>3.0.5.RELEASE</spring.version>
    <aspectj.version>1.6.11</aspectj.version>
    <slf4j.version>1.6.1</slf4j.version>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <spring-security.version>3.0.5.RELEASE</spring-security.version>
    <jackson.version>1.8.0</jackson.version>
    <spring.data.mongodb.version>1.0.0.M2</spring.data.mongodb.version>
    <spring.data.graph.version>1.0.0.RELEASE</spring.data.graph.version>
    <spring.data.commons.version>1.0.0.RELEASE</spring.data.commons.version>
</properties>
    ...
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-neo4j</artifactId>
        <version>${spring.data.graph.version}</version>
        <scope>compile</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-mongodb-cross-store</artifactId>
        <version>${spring.data.mongodb.version}</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-mongodb</artifactId>
        <version>${spring.data.mongodb.version}</version>
        <scope>compile</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-neo4j-rest</artifactId>
        <version>${spring.data.graph.version}</version>
        <scope>compile</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-commons-core</artifactId>
        <version>${spring.data.commons.version}</version>
        <scope>compile</scope>
    </dependency>

  ....
  <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>aspectj-maven-plugin</artifactId>
            <version>1.0</version>
            <dependencies>
                <!-- NB: You must use Maven 2.0.9 or above or these are ignored (see 
                    MNG-2972) -->
                <dependency>
                    <groupId>org.aspectj</groupId>
                    <artifactId>aspectjrt</artifactId>
                    <version>${aspectj.version}</version>
                </dependency>
                <dependency>
                    <groupId>org.aspectj</groupId>
                    <artifactId>aspectjtools</artifactId>
                    <version>${aspectj.version}</version>
                </dependency>
            </dependencies>
            <executions>
                <execution>
                    <goals>
                        <goal>compile</goal>
                        <goal>test-compile</goal>
                    </goals>
                </execution>
            </executions>
            <configuration>
                <outxml>true</outxml>
                <aspectLibraries>
                    <aspectLibrary>
                        <groupId>org.springframework</groupId>
                        <artifactId>spring-aspects</artifactId>
                    </aspectLibrary>
                                            <aspectLibrary>
                        <groupId>org.springframework.data</groupId>
                        <artifactId>spring-data-neo4j</artifactId>
                    </aspectLibrary>
                    <aspectLibrary>
                        <groupId>org.springframework.data</groupId>
                        <artifactId>spring-data-mongodb-cross-store</artifactId>
                    </aspectLibrary>

                </aspectLibraries>
                <source>1.6</source>
                <target>1.6</target>
            </configuration>
        </plugin>

POJO:

@NodeEntity
@RooToString
@RooJavaBean
public class DElement {

@Indexed
private Long id;

@RelatedTo(direction=Direction.BOTH, elementClass=DRegion.class, type="SUBELEMENT_OF")
private Set<DElement> childElements = new HashSet<DElement>();

@Indexed(indexName = "delement-name", fulltext=true)
private String name;    



@Transactional
public void addChild(DElementchild child)
{
    this.childElements.add(child);
}

}

Controller (加载):

    @Controller
    @RequestMapping(value="/DElements")
    public class DElementsController {

        DElementRepository DElementRepository;

        GraphDatabaseContext gdbc;

        @Autowired
        public DElementsController(DElementRepository DElementRepository, GraphDatabaseContext gdbc)
        {
            this.DElementRepository = DElementRepository;
            this.gdbc = gdbc;
            this.initElements();
        }

        @Transactional
        private void initElements()
        {
            try
            {
                DElementRepository.deleteAll();

            } 
            catch (Exception e) {} finally{}

            //Transaction txn = gdbc.beginTx();

            referenceNode.createRelationshipTo(allElements.getPersistentState(), myRelation);

            DElement naElements = new DElement().persist();
            naElements.setName("1");
            allElements.addChild(naElements);

            DElement saElements = new DElement().persist();
            saElements.setName("2");
            allElements.addChild(saElements);               

            DElement euElements = new DElement().persist();
            euElements.setName("3");
            allElements.addChild(euElements);

            DElement afElements = new DElement().persist();
            afElements.setName("4");    
            allElements.addChild(afElements);

            DElement asElements = new DElement().persist();
            asElements.setName("5");    
            allElements.addChild(asElements);

            DElement auElements = new DElement().persist();
            auElements.setName("6");
            allElements.addChild(auElements);


            //txn.success();
            //txn.finish();

        }
    }

applicationContext.xml

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:aop="http://www.springframework.org/schema/aop"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:jee="http://www.springframework.org/schema/jee"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:mongo="http://www.springframework.org/schema/data/mongo"
    xmlns:graph="http://www.springframework.org/schema/data/graph"
    xsi:schemaLocation="http://www.springframework.org/schema/data/mongo http://www.springframework.org/schema/data/mongo/spring-mongo.xsd
        http://www.springframework.org/schema/jee http://www.springframework.org/schema/jee/spring-jee-3.0.xsd
        http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
        http://www.springframework.org/schema/data/graph http://www.springframework.org/schema/data/graph/datagraph-1.0.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
        http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd">
    <context:property-placeholder location="classpath*:META-INF/spring/*.properties" />
    <context:spring-configured />
    <bean id="validator"
        class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" />

    <context:component-scan base-package="com.foobar">
        <context:exclude-filter expression=".*_Roo_.*"
            type="regex" />
        <context:exclude-filter expression="org.springframework.stereotype.Controller"
            type="annotation" />
    </context:component-scan>
    <jee:jndi-lookup id="dataSource" jndi-name="jdbc/foobar" />




    <mongo:mongo host="${foobar.mongodb.addr}" port="27017" />
    <mongo:mapping-converter base-package="com.foobar.lib.model.mongo"/>

    <bean id="mongoTemplate" class="org.springframework.data.document.mongodb.MongoTemplate">
        <constructor-arg name="mongo" ref="mongo" />
        <constructor-arg name="databaseName" value="foobar" />
        <constructor-arg name="defaultCollectionName" value="basecoll" />
    </bean>

    <bean class="org.springframework.data.document.mongodb.MongoExceptionTranslator" />

    <!-- Mongo cross-store aspect config -->
    <bean
        class="org.springframework.data.persistence.document.mongo.MongoDocumentBacking"
        factory-method="aspectOf">
        <property name="changeSetPersister" ref="mongoChangeSetPersister" />
    </bean>
    <bean id="mongoChangeSetPersister"
        class="org.springframework.data.persistence.document.mongo.MongoChangeSetPersister">
        <property name="mongoTemplate" ref="mongoTemplate" />
        <property name="entityManagerFactory" ref="entityManagerFactory" />
    </bean>


    <bean 
        id="graphDatabaseService" class="org.neo4j.kernel.EmbeddedGraphDatabase"
        destroy-method="shutdown" >
        <constructor-arg index="0" value="c:/neo4j/data/foobar" />
    </bean>
<!--  REST DOESNT WORK FOR THE MOMENT
    <bean id="graphDatabaseService" class="org.springframework.data.graph.neo4j.rest.support.RestGraphDatabase">
        <constructor-arg value="${foobar.neo4j.reststore}"/>        
    </bean> -->


<!--    <bean id="graphDatabaseContext" class="org.springframework.data.graph.neo4j.support.GraphDatabaseContext">
        <property name="graphDatabaseService" ref="graphDatabaseService"/>
    </bean> -->

    <graph:repositories base-package="com.foobar.data.repositories.neo4j" graph-database-context-ref="graphDatabaseContext"/>


    <graph:config graphDatabaseService="graphDatabaseService" entityManagerFactory="entityManagerFactory" />
    <tx:annotation-driven mode="aspectj" transaction-manager="transactionManager" />    

    <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">     
        <property name="dataSource" ref="dataSource" />
    </bean> 
</beans>

[/编辑]

最佳答案

一些一般性的评论。

如果要使用Graph-JPA跨存储持久化,只需要将entityManagerFactory传入Spring Data Graph即可。可以找到一个例子here .如果这样做,那么您还应该在要参与跨存储设置的 POJO 上启用 partial=true 标志。

Spring Data Graph Cross store 和 Spring Data MongoDB cross store 在与 JPA 交互方面的工作方式不同,SDG 在持久化或加载实体时从 Graph POJO 端工作,它们(重新)连接到它们的 JPA 实体(通过 @标识字段)。

另一方面,Spring Data MongoDB 使用 AspectJ 来扩充 EntityManager 的一些方法,以启动文档数据库的生命周期事件。

目前还没有集成 MongoDB 和 Neo4j 的故事。但就我们而言,两个项目的项目负责人住在同一个城市并且密切合作,我认为这应该是可行的。

如果您能在某个地方与我们分享您的完整项目代码,那就太好了,可以是在 github 上(也可以是私有(private)存储库 [我的 github id 是“jexp”,或者通过邮件或投递箱)。 这样我们就可以直接深入研究它。

您的问题:

  • graph + rdmbs 都是有 partial = true 的实体,你必须在你的 POJO 上有 @Entity 注释
  • 我不确定如何正确配置 mongo-cross-store 持久性
  • 通常应该通过 persistence.xml 配置实体映射到哪些商店?
  • 即也许我们应该设计一种机制,为每个想要与 EntityManager/JPA/RDMBS 交互的商店配置一个 persistence.xml
  • 可能这也可以通过定义两个实体管理器来实现,一个用于图形,另一个用于 mongo?
  • 您可能应该先让它在 neo4j 的嵌入式模式下运行,然后再查看远程服务器 (REST)
  • 您可能应该将 Spring Data Graph 更新到 1.1.M2,将 Neo4j 更新到 1.4,将 AspectJ 更新到 1.6.12.M1

请亲自联系,以便我们解决所有问题并得出一个好的解决方案。

关于spring-data跨店实体管理,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6728400/

有关spring-data跨店实体管理的更多相关文章

  1. ruby - i18n Assets 管理/翻译 UI - 2

    我正在使用i18n从头开始​​构建一个多语言网络应用程序,虽然我自己可以处理一大堆yml文件,但我说的语言(非常)有限,最终我想寻求外部帮助帮助。我想知道这里是否有人在使用UI插件/gem(与django上的django-rosetta不同)来处理多个翻译器,其中一些翻译器不愿意或无法处理存储库中的100多个文件,处理语言数据。谢谢&问候,安德拉斯(如果您已经在ruby​​onrails-talk上遇到了这个问题,我们深表歉意) 最佳答案 有一个rails3branchofthetolkgem在github上。您可以通过在Gemfi

  2. ruby-on-rails - 带 Spring 锁的 Rails 4 控制台 - 2

    我正在使用Ruby2.1.1和Rails4.1.0.rc1。当执行railsc时,它被锁定了。使用Ctrl-C停止,我得到以下错误日志:~/.rvm/gems/ruby-2.1.1/gems/spring-1.1.2/lib/spring/client/run.rb:47:in`gets':Interruptfrom~/.rvm/gems/ruby-2.1.1/gems/spring-1.1.2/lib/spring/client/run.rb:47:in`verify_server_version'from~/.rvm/gems/ruby-2.1.1/gems/spring-1.1.

  3. ruby-on-rails - 更好的替代方法 try( :output). try( :data). try( :name)? - 2

    “输出”是一个序列化的OpenStruct。定义标题try(:output).try(:data).try(:title)结束什么会更好?:) 最佳答案 或者只是这样:deftitleoutput.data.titlerescuenilend 关于ruby-on-rails-更好的替代方法try(:output).try(:data).try(:name)?,我们在StackOverflow上找到一个类似的问题: https://stackoverflow.c

  4. ruby-on-rails - 获取 inf-ruby 以使用 ruby​​ 版本管理器 (rvm) - 2

    我安装了ruby​​版本管理器,并将RVM安装的ruby​​实现设置为默认值,这样'哪个ruby'显示'~/.rvm/ruby-1.8.6-p383/bin/ruby'但是当我在emacs中打开inf-ruby缓冲区时,它使用安装在/usr/bin中的ruby​​。有没有办法让emacs像shell一样尊重ruby​​的路径?谢谢! 最佳答案 我创建了一个emacs扩展来将rvm集成到emacs中。如果您有兴趣,可以在这里获取:http://github.com/senny/rvm.el

  5. ruby-on-rails - 事件管理员日期过滤器日期格式自定义 - 2

    是否有简单的方法来更改默认ISO格式(yyyy-mm-dd)的ActiveAdmin日期过滤器显示格式? 最佳答案 您可以像这样为日期选择器提供额外的选项,而不是覆盖js:=f.input:my_date,as::datepicker,datepicker_options:{dateFormat:"mm/dd/yy"} 关于ruby-on-rails-事件管理员日期过滤器日期格式自定义,我们在StackOverflow上找到一个类似的问题: https://s

  6. spring.profiles.active和spring.profiles.include的使用及区别说明 - 2

    转自:spring.profiles.active和spring.profiles.include的使用及区别说明下文笔者讲述spring.profiles.active和spring.profiles.include的区别简介说明,如下所示我们都知道,在日常开发中,开发|测试|生产环境都拥有不同的配置信息如:jdbc地址、ip、端口等此时为了避免每次都修改全部信息,我们则可以采用以上的属性处理此类异常spring.profiles.active属性例:配置文件,可使用以下方式定义application-${profile}.properties开发环境配置文件:application-dev

  7. ruby - (Ruby || Python) 窗口管理器 - 2

    我想用这两种语言中的任何一种(最好是ruby​​)制作一个窗口管理器。老实说,除了我需要加载某种X模块外,我不知道从哪里开始。因此,如果有人有线索,如果您能指出正确的方向,那就太好了。谢谢 最佳答案 XCB,X的下一代API使用XML格式定义X协议(protocol),并使用脚本生成特定语言绑定(bind)。它在概念上与SWIG类似,只是它描述的不是CAPI,而是X协议(protocol)。目前,C和Python存在绑定(bind)。理论上,Ruby端口只是编写一个从XML协议(protocol)定义语言到Ruby的翻译器的问题。生

  8. ruby-on-rails - 事件管理员和自定义方法 - 2

    这是我在ActiveAdmin中的自定义页面ActiveAdmin.register_page"Settings"doaction_itemdolink_to('Importprojects','settings/importprojects')endcontentdopara"Text"endcontrollerdodefimportprojectssystem"rakedataspider:import_projects_ninja"para"OK"endendend我想做的是,当我单击“导入项目”按钮时,我想在Controller中执行rake任务。但是我无法访问该方法。可能是什

  9. ruby-on-rails - (Ruby,Rails) 基于角色的身份验证和用户管理...? - 2

    我正在寻找用于Rails的优质管理插件。似乎大多数现有的插件/gem(例如“restful_authentication”、“acts_as_authenticated”)都围绕着self注册等展开。但是,我正在寻找一种功能齐全的基于管理/管理角色的解决方案——但不是简单地附加到另一个非基于角色的解决方案。如果我找不到,我想我会自己动手......只是不想重新发明轮子。 最佳答案 RyanBates最近做了两个关于授权的railscast(注意身份验证和授权之间的区别;身份验证检查用户是否如她所说的那样,授权检查用户是否有权访问资源

  10. ruby-on-rails - Spring 不起作用。 [未初始化常量 Spring::SID::DL] - 2

    我无法运行Spring。这是错误日志。myid-no-MacBook-Pro:myid$spring/Users/myid/.rbenv/versions/1.9.3-p484/lib/ruby/gems/1.9.1/gems/spring-0.0.10/lib/spring/sid.rb:17:in`fiddle_func':uninitializedconstantSpring::SID::DL(NameError)from/Users/myid/.rbenv/versions/1.9.3-p484/lib/ruby/gems/1.9.1/gems/spring-0.0.10/li

随机推荐