MongoDB是一款非常知名的NoSQL文档数据库,而Spring则是Java领域著名的开源框架。除了构成Spring核心的IoC与AOP之外,Spring也有大量应用于各个不同领域的子框架,其中Spring Data就是专门针对数据处理的一个子项目。在Spring Data下有Spring Data JPA、Spring Data MongoDB、Spring Data Redis等子项目,从名字就可以看出来这些子项目所针对的目标。其中,Spring Data MongoDB是专门针对MongoDB的一个子项目,旨在通过Spring的方式来操纵MongoDB,那么这种集成是简化了开发还是阻碍了开发呢?
Prashant Deva是Chronon的创始人与CTO。他是一位持续创业者,还创办了Placid Systems、AntlrStudio及Virtual Ant。作为一名极客,Deva喜欢尝试各种新鲜技术,在使用了Spring Data MongoDB一段时间后,他认为这个框架在设计上存在着严重的问题,并撰写了文章进行了深入且详尽的分析。
Spring框架开发者们喜欢到处宣扬他们对MongoDB提供的支持,并以此作为优于其他框架的一个资本。不过,如果在真正的项目中使用Spring Data MongoDB的话,你就会发现框架在某些特性上的严重缺失以及设计上的巨大失误。
Spring Data MongoDB试图将ORM风格的架构硬塞到非关系型数据库中,这直接造成在实际项目中根本无法使用的严重后果,下面就来谈谈这背后的原因:
无法检索字段,只能获取整个文档
这是Spring Data MongoDB设计上最大的瑕疵。它试图用SQL数据库中的行对文档进行建模,并且希望你像ORM一样创建“实体”类。这两者根本就不是一回事。文档可要比SQL数据库中的行复杂多了,也大多了。
对于SQL数据库中的行来说,它认为你在大多数查询中都会获取到里面的所有数据,否则数据就应该被划分到多张表中。不过文档与之完全不同,文档可以嵌套,很多时候你只想从数据库中获取到文档的一个子集而已。
但对于Spring Data MongoDB的“实体”模型来说,你不得不在每次查询中都检索出整个文档才行。
没有DBRef延迟加载
这个就更加疯狂了。如果通过DBRefs来引用其他文档,那么Spring Data MongoDB就会得到整个文档而不是文档引用。如果通过DBRefs连接了大量文档,那么一个只想获得几个字段的简单查询都会导致获取到整个文档图!
实际情况是这个Bug报告已经有将近两年时间了,被指定为“低优先级”状态,也没有什么解决方案,这太让人难以置信了,这表明Spring Data MongoDB的愿景与实际的使用之间存在着多么大的差距。
不支持游标
想要通过游标遍历集合吗?没门。要么就取出整个集合,要么就转而使用原生的Mongo Java驱动。
不完备的聚合框架支持
Spring Data MongoDB是从不久之前才开始支持MongoDB聚合框架的,就像框架的其他部分一样,这种支持也是个半成品。
框架文档很少并且容易让人产生混乱,在实际项目中所需的大多数聚合查询都没法在Spring Data MongoDB的文档中找到,你只能使用原生的驱动才行。
不完善的索引支持
虽然可以通过框架将某个字段标记为“加索引的”,但其他操作却根本就不知道这回事。
就拿MongoDB中的一个例子来说吧,如果某个字段是唯一且稀疏的,那么你就不能使用“null”值向文档中插入一次以上。这意味着在第2次插入时,该字段就不应该在第1次插入的位置处出现。
然而,由于Spring强迫你在一个类中定义文档的字段,因此最后需要将null赋给不存在的字段。如果该字段拥有唯一的稀疏索引,那么这会导致运行期错误,因为Spring在根据实体对象创建查询时(以注解的形式直接定义在字段上),它根本就不知道索引的存在。
Spring还提供了一个ensureIndex()方法用于手工在字段上创建索引,无需使用注解,不过文档中并没有提及何时该使用这种方式、使用的频率是多少,以及调用的性能是怎样的。
无法切换数据库
很多时候,你希望将数据存储在单个MongoDB实例的不同数据库中,比如说要保持不同客户数据的分离。
如果使用原生的Mongo驱动,那么切换数据库简直就是小菜一碟,直接调用getDb(dbName)就行了。但如果使用Spring Data MongoDb,那么这几乎是一件无法做到的事情,除非你愿意自己写大量的代码(不过这么做的话在新版框架发布后可能就会出现移植性问题)。
让人奇怪的日志框架
我已经就Spring的文档问题专门写过一篇文章。Spring文档说它使用的是Jakarta Commons Logging,不过Spring Data显然使用的是SLF4J。然而,Spring Data文档却压根儿就没有提过这事。
这意味着如果开始使用Spring Data,那么你可能就会遇到很多文档中没有提及的运行期错误,这时没别的办法,上StackOverflow上找答案吧。
不支持文档的动态特性
使用MongoDB这样的面向文档的数据库最大的原因就在于其动态特性了。比如说同一集合中的文档可以不同,这样同一个集合中就可以有多个版本的文档,然后逐渐升级,文档也可以嵌套。键名不必事先知道,这样就可以直接向文档中插入属性映射。
但事实却是Spring Data MongoDB丢弃了MongoDB的这个最基本的特性,并且试图在其上构建一个确定的、预先定义好的ORM风格的层,这直接造成框架与底层数据库之间的不匹配。
结论
Spring Data MongoDB似乎是由一些压根儿就没有在真正的项目中用过MongoDB的人设计出来的,它试图将面向文档的数据库硬塞到ORM风格的框架中。
这导致了框架与数据库之间的不匹配,Spring Data MongoDB反而成为了一个负担而不是帮助我们简化开发。最后,你还是不得不在几乎所有真正的项目开发中使用原生的MongoDB Java驱动。
后记
各位InfoQ读者,你曾经使用过Spring Data MongoDB进行过MongoDB开发么,你对于Spring Data MongoDB的使用感受是如何呢?是否与Deva的经历一致呢?我曾经在项目中尝试过Spring Data MongoDB,使用下来的一个直观感受就是它将简单的事情搞复杂了。直接使用原生Java驱动来操纵MongoDB是个非常简单且直观的过程,而Spring Data MongoDB却沿用了它一直以来的处理风格,那就是IoC,需要先进行注入,然后从容器中获取所需的对象,将原本很轻松的操作变得复杂起来,不知各位读者有什么样的感受呢,欢迎讨论。
转http://www.infoq.com/cn/news/2013/11/spring-data-mongo-mismatch/
相关推荐
Spring集成MongoDB官方指定jar包:spring-data-mongodb-1.4.1.RELEASE.jar
Spring Data MongoDB API。 Spring Data MongoDB 开发文档。
Spring Data MongoDB 1.9.3与MongoDB 3.2的整合,为开发人员提供了强大的工具集,简化了与非关系型数据库的交互,同时也充分利用了MongoDB 3.2的特性。通过深入理解和实践,可以构建出高效、可扩展的现代应用程序。
- **Spring Data MongoDB** 的设计目标是简化开发者的开发流程,通过提供一种统一的方式与不同的数据存储系统进行交互。 #### 二、Spring Data MongoDB的核心概念 - **Spring Data MongoDB** 基于 **Spring ...
**Spring Data MongoDB: 更新文档** 在现代Web应用开发中,数据存储是至关重要的部分,而MongoDB作为NoSQL数据库中的代表,因其灵活性和高性能而受到广泛欢迎。Spring Data MongoDB是Spring框架的一个模块,它简化...
spring.data.mongodb.uri=mongodb://localhost:27017/mydatabase ``` 或者 ```yaml # application.yml 示例 spring: data: mongodb: uri: mongodb://localhost:27017/mydatabase ``` 然后,创建MongoDB ...
《Spring Data MongoDB 1.8.0.RELEASE:深度解析与源码剖析》 Spring Data MongoDB 是 Spring 框架中的一个模块,专门用于简化与 MongoDB 数据库的交互。MongoDB 是一个流行的分布式文档数据库,以其灵活性和高性能...
Spring Data MongoDB是Spring Data项目的一部分,它提供了一个面向对象的API,使得与NoSQL数据库MongoDB进行交互变得更加简单。以下是关于这个主题的详细知识点: 1. **Spring Framework**: Spring是一个开源的应用...
通过这些内容,可以看出SpringData MongoDB API文档是一个功能全面且内容丰富的资源,它不仅包括了API的使用,还包括了最佳实践和设计指南,旨在帮助开发者高效地使用Spring框架与MongoDB数据库进行交互。
Spring Data MongoDB是一个强大的Java库,它为开发人员提供了一种简单而有效的方式来集成Spring应用程序与MongoDB数据库。这个"spring-data-mongodb1.2.0"版本是针对Spring Data MongoDB的1.2.0.RELEASE更新,它包含...
这个实例涵盖了Spring MVC的控制器设计、Spring Data MongoDB的使用,以及MongoDB的基础操作,是学习现代Java Web开发的一个好例子。通过阅读源码并动手实践,开发者可以加深对这三个技术的理解,并提升自己的技能。
Spring Data MongoDB 是 Spring 框架下的一个模块,专为利用 MongoDB 数据库设计,它提供了丰富的抽象层,使得开发者能够以简洁、直观的方式进行数据操作。本文将深入探讨 Spring Data MongoDB 1.2.0.RELEASE 版本中...
spring-data-mongodb1.1.0.jar包
在IT领域,Spring Data是一个广泛使用的框架,它简化了与各种数据存储的交互,包括关系型数据库、NoSQL数据库和搜索引擎。MongoDB则是一种流行的NoSQL文档型数据库,以其灵活性、可扩展性和高性能而受到赞誉。Spring...
Spring Data MongoDB API 是一个强大的Java库,用于简化与MongoDB数据库的交互。它作为Spring Data项目的一部分,提供了统一的编程模型,使得开发人员能够轻松地利用MongoDB的强大功能。Spring Data MongoDB API允许...
Spring Data MongoDB是一个强大的Java库,它为开发人员提供了一种简单的方式来访问和操作MongoDB数据库。这个库是Spring Data框架的一部分,旨在简化数据访问层的实现,尤其在使用NoSQL数据库如MongoDB时。MongoDB...
1.了解Spring ...将存储库与多个Spring Data模块一起使用 7.4。定义查询方法 7.4.1。查询查询策略 7.4.2。查询创建 7.4.3。属性表达式 7.4.4。特殊参数处理 7.4.5。限制查询结果 7.4.6。流式查询结果
Spring Data MongoDB负责将Java对象与MongoDB文档之间的类型转换。它使用MongoDB Java驱动程序的Document类作为中间表示,确保数据在Java对象和BSON文档之间正确地序列化和反序列化。 9. **索引管理** 通过Spring...
Spring Data MongoDB是Spring框架的一部分,专门用于简化与MongoDB数据库的交互。MongoDB是一个流行的NoSQL数据库,以其灵活性、高性能和文档存储能力而受到青睐。Spring Data MongoDB为开发者提供了高级别的抽象,...