spring-data-mongodb的增删改查操作(MongoTemplate方式)
注: 此处的spring-data-mongodb架包是 1.8.0版本 ,更高版本的操作方法有部分修改,具体可自行查看源码
(懂一个版本;再看源码修改部分,很容易理解的)
1、所需架包
<!-- spring整合MongoDB --> <dependency> <groupId>org.springframework.data</groupId> <artifactId>spring-data-mongodb</artifactId> <version>${spring.data.version}</version> </dependency>
2、注入MongoTemplate
在对应的 Dao层 注入 MongoTemplate
3、获取集合
mongoTemplate.getCollection(mongoTemplate.getCollectionName(entityClass)).distinct(key, query.getQueryObject())
// entityClass:实体类,实际上就是实体类.class;如:User.class
// mongoTemplate.getCollectionName(entityClass):可获取到entityClass实体类所对应的集合名称
// mongoTemplate.getCollection(mongoTemplate.getCollectionName(entityClass)):可通过集合名称获取到对应集合
// mongoTemplate.getCollection(collectionName):返回的是基本的Driver集合对象,即DBCollection类型
// 因此使用 getCollection() 方法获取到的集合类型,不是我们在开发过程中所使用的集合类型
// key:指定键值,实际上就是MongoDB数据库集合中文档的字段名
// query:查询对象
// query.getQueryObject():获取对应查询对象的查询条件
// .distinct(key, query.getQueryObject()):在单个集合或视图,查询满足条件的所有文档中,指定字段的不同值
.distinct(字段 , 查询):在 单个 集合或视图中查找指定字段的不同值,并返回 List 集合
如:有MongoDB中集合 inventory
{ "_id": 1, "dept": "A", "item": { "sku": "111", "color": "red" }, "sizes": [ "S", "M" ] }
{ "_id": 2, "dept": "A", "item": { "sku": "111", "color": "blue" }, "sizes": [ "M", "L" ] }
{ "_id": 3, "dept": "B", "item": { "sku": "222", "color": "blue" }, "sizes": [ "S" ] }
{ "_id": 4, "dept": "A", "item": { "sku": "333", "color": "black" }, "sizes": [ "S" ] }
mongoTemplate.getCollection("inventory").distinct("dept")
:从inventory集合中的所有文档返回dept字段的不同值;结果为:[ "A", "B" ]
mongoTemplate.getCollection("inventory").distinct("item.sku")
:从inventory集合中的所有文档返回sku嵌入字段的不同值;结果为:[ "111", "222", "333" ]
mongoTemplate.getCollection("inventory").distinct("sizes")
:从inventory集合中的所有文档返回数组字段的不同值;结果为:[ "M", "S", "L" ]
mongoTemplate.getCollection("inventory").distinct("item.sku", { dept: "A" })
:从inventory集合中 dept字段等于A 的文档中返回sku嵌入字段的不同值;结果为:[ "111", "333" ]
4、增加操作(插入)
可以一次性插入一个 对象集合 ,也可以单次插入 一个对象 ;需要插入的数据量大的时候,建议使用批量插入
List<SysUser> userList = new ArrayList<>();
userList.add(new SysUser(11,"1","白小飞","18888888888"));
userList.add(new SysUser(9,"1","白敬亭","13333333333"));
userList.add(new SysUser(5,"1","林宥嘉","14444444444"));
userList.add(new SysUser(6,"1","彭于晏","15555555555"));
userList.add(new SysUser(7,"1","周杰伦","16666666666"));
mongoTemplate.insert(userList, "userList"); // 第一个参数是要插入的数据(文档),第二个参数是集合名称;批量插入
SysUser sysUser = new SysUser(12,"1","黄小飞","18888888888");
mongoTemplate.insert(sysUser, "userList"); // 第一个参数是要插入的数据(文档),第二个参数是要插入的mongo集合名
或者
SysUser sysUser = new SysUser(12,"1","黄小飞","18888888888");
mongoTemplate.save(sysUser); // 参数表示要保存的数据(文档);save()方法只能用于单个对象保存,不可用于批量插入
注意: 同一个mongo集合中,前后插入的数据 对象类型要一致
实体类需要用注解标识:
@Document(collection = “xxx”):用于实体类上,表明这是一个MongoDB的文档集合,相当于MySQL的数据表;其中collection表示集合名称,不写则默认为实体类名称
@Id:用于实体类中的成员变量,表示主键标识
@Field(“xxx”):用于实体类中的成员变量,表示MongoDB文档集合中的字段,其值对应集合的字段名称
5、删除操作
// 删除author为yinjihuan的数据
Query query = Query.query(Criteria.where("author").is("yinjihuan"));
mongoTemplate.remove(query, Article.class);
// 也可直接指定MongoDB集合名称
query = Query.query(Criteria.where("author").is("yinjihuan"));
mongoTemplate.remove(query, "article_info");
// 删除集合,可传实体类,也可以传名称
mongoTemplate.dropCollection(Article.class);
mongoTemplate.dropCollection("article_info");
// 删除数据库;在开发中,开发所使用的数据库是在配置文件中配置的;使用这个方法即可直接删除配置对应的数据库
mongoTemplate.getDb().dropDatabase();
下面这2种 适合 知道要删除几条数据的场景
//查询出符合条件的第一个结果,并将符合条件的数据删除,只会删除第一条
query = Query.query(Criteria.where("author").is("yinjihuan"));
Article article = mongoTemplate.findAndRemove(query, Article.class);
//查询出符合条件的所有结果,并将符合条件的所有数据删除
query = Query.query(Criteria.where("author").is("yinjihuan"));
List<Article> articles = mongoTemplate.findAllAndRemove(query, Article.class);
6、修改操作
准备要练习的数据2条,如下:
{
"_id": ObjectId("57c43caed4c63d7e39b5dc48"),
"title": "MongoTemplate的基本使用",
"url": "http://cxytiandi.com/blog/detail/0",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 0,
"add_time": ISODate("2016-08-29T13:46:21.881Z")
}
{
"_id": ObjectId("57c43caed4c63d7e39b5dc49"),
"title": "MongoTemplate的基本使用",
"url": "http://cxytiandi.com/blog/detail/1",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 0,
"add_time": ISODate("2016-08-29T13:46:22.201Z")
}
修改第一条author为yinjihuan的数据中的title和visitCount
Query query = Query.query(Criteria.where("author").is("yinjihuan"));
Update update = Update.update("title", "MongoTemplate").set("visitCount", 10);
mongoTemplate.updateFirst(query, update, Article.class);
// 修改后结果如下,我们会发现第一条数据的title还有visit_count被修改了
{
"_id": ObjectId("57c43caed4c63d7e39b5dc48"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/0",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:21.881Z")
}
{
"_id": ObjectId("57c43caed4c63d7e39b5dc49"),
"title": "MongoTemplate的基本使用",
"url": "http://cxytiandi.com/blog/detail/1",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 0,
"add_time": ISODate("2016-08-29T13:46:22.201Z")
}
修改全部符合条件的
query = Query.query(Criteria.where("author").is("yinjihuan"));
update = Update.update("title", "MongoTemplate").set("visitCount", 10);
mongoTemplate.updateMulti(query, update, Article.class);
// 修改后结果如下,我们会发现所有数据的title还有visit_count被修改了
{
"_id": ObjectId("57c43caed4c63d7e39b5dc48"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/0",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:21.881Z")
}
{
"_id": ObjectId("57c43caed4c63d7e39b5dc49"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/1",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:22.201Z")
}
特殊更新,更新author为jason的数据,如果没有author为jason的数据则以此条件创建一条新的数据
当没有符合条件的文档,就以这个条件和更新文档为基础创建一个新的文档,如果找到匹配的文档就正常的更新。
query = Query.query(Criteria.where("author").is("jason"));
update = Update.update("title", "MongoTemplate").set("visitCount", 10);
mongoTemplate.upsert(query, update, Article.class);
// 修改后结果如下,我们会发现新增了一条数据
{
"_id": ObjectId("57c43caed4c63d7e39b5dc48"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/0",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:21.881Z")
}
{
"_id": ObjectId("57c43caed4c63d7e39b5dc49"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/1",
"author": "yinjihuan",
"tags": [
"java",
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:22.201Z")
}
{
"_id": ObjectId("57c6e1601e4735b2c306cdb7"),
"author": "jason",
"title": "MongoTemplate",
"visit_count": 10
}
更新条件不变,更新字段改成了一个我们集合中不存在的,用set方法如果更新的key不存在则创建一个新的key
query = Query.query(Criteria.where("author").is("jason"));
update = Update.update("title", "MongoTemplate").set("money", 100);
mongoTemplate.updateMulti(query, update, Article.class);
// 修改后结果如下,我们会发现新加了一个key
{
"_id": ObjectId("57c6e1601e4735b2c306cdb7"),
"author": "jason",
"title": "MongoTemplate",
"visit_count": 10,
"money":100
}
update的inc方法用于做累加操作,将money在之前的基础上加上100
query = Query.query(Criteria.where("author").is("jason"));
update = Update.update("title", "MongoTemplate").inc("money", 100);
mongoTemplate.updateMulti(query, update, Article.class);
// 修改后结果如下,我们会发现money变成200
{
"_id": ObjectId("57c6e1601e4735b2c306cdb7"),
"author": "jason",
"title": "MongoTemplate",
"visit_count": 10,
"money":200
}
update的rename方法用于修改key的名称
query = Query.query(Criteria.where("author").is("jason"));
update = Update.update("title", "MongoTemplate").rename("visitCount", "vc");
mongoTemplate.updateMulti(query, update, Article.class);
// 修改结果如下,可以发现字段visitCount被修改成为了vc
{
"_id": ObjectId("57c6e1601e4735b2c306cdb7"),
"author": "jason",
"title": "MongoTemplate",
"vc": 10,
"money":200
}
update的unset方法用于删除key
query = Query.query(Criteria.where("author").is("jason"));
update = Update.update("title", "MongoTemplate").unset("vc");
mongoTemplate.updateMulti(query, update, Article.class);
// 修改后结果如下,我们会发现vc这个key被删除了
{
"_id": ObjectId("57c6e1601e4735b2c306cdb7"),
"author": "jason",
"title": "MongoTemplate",
"money":200
}
update的pull方法用于删除tags数组中的java
query = Query.query(Criteria.where("author").is("yinjihuan"));
update = Update.update("title", "MongoTemplate").pull("tags", "java");
mongoTemplate.updateMulti(query, update, Article.class);
// 修改后结果如下,我们会发现tags里的java被删除了
{
"_id": ObjectId("57c43caed4c63d7e39b5dc48"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/0",
"author": "yinjihuan",
"tags": [
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:21.881Z")
}
{
"_id": ObjectId("57c43caed4c63d7e39b5dc49"),
"title": "MongoTemplate",
"url": "http://cxytiandi.com/blog/detail/1",
"author": "yinjihuan",
"tags": [
"mongodb",
"spring"
],
"visit_count": 10,
"add_time": ISODate("2016-08-29T13:46:22.201Z")
}
7、查询操作
MongoDB的查询方式很多种,下面只列了一些常用的,比如:
1、=查询
2、模糊查询
3、大于小于范围查询
4、in查询
5、or查询
6、查询一条,查询全部
根据作者查询所有符合条件的数据,返回List
Query query = Query.query(Criteria.where("author").is("yinjihuan"));
List<Article> articles = mongoTemplate.find(query, Article.class);
只查询符合条件的第一条数据,返回Article对象
query = Query.query(Criteria.where("author").is("yinjihuan"));
Article article = mongoTemplate.findOne(query, Article.class);
查询集合中所有数据,不加条件
articles = mongoTemplate.findAll(Article.class);
查询符合条件的数量
query = Query.query(Criteria.where("author").is("yinjihuan"));
long count = mongoTemplate.count(query, Article.class);
根据主键ID查询
article = mongoTemplate.findById(new ObjectId("57c6e1601e4735b2c306cdb7"), Article.class);
in查询
List<String> authors = Arrays.asList("yinjihuan", "jason");
query = Query.query(Criteria.where("author").in(authors));
articles = mongoTemplate.find(query, Article.class);
ne(!=)查询
query = Query.query(Criteria.where("author").ne("yinjihuan"));
articles = mongoTemplate.find(query, Article.class);
lt(<)查询访问量小于10的文章
query = Query.query(Criteria.where("visitCount").lt(10));
articles = mongoTemplate.find(query, Article.class);
范围查询,大于5小于10
query = Query.query(Criteria.where("visitCount").gt(5).lt(10));
articles = mongoTemplate.find(query, Article.class);
模糊查询,author中包含a的数据
query = Query.query(Criteria.where("author").regex("a"));
articles = mongoTemplate.find(query, Article.class);
数组查询,查询tags里数量为3的数据
query = Query.query(Criteria.where("tags").size(3));
articles = mongoTemplate.find(query, Article.class);
or查询,查询author=jason的或者visitCount=0的数据
query = Query.query(Criteria.where("").orOperator(
Criteria.where("author").is("jason"),
Criteria.where("visitCount").is(0)));
articles = mongoTemplate.find(query, Article.class);