目录
NoSql数据库
- 键值对key-value 存储
- redis
- 用户缓存,用户信息回话,配置信息,购物车
- 文档存储
- 数据结构不严格,表结构可变
- 类json
- MongoDB
- 列族存储
- 图形存储
优势:
基于灵活的json文档模型,非常适合敏捷方式的快速开发,临时增加字段影响很小
其实与生俱来的高可用,高水平扩展能力
应用场景
- 游戏场景
- 用户的装备信息,积分等
- 物流场景
- 订单信息-状态
- 社交场景
- 用户信息,地理位置索引,附件的人,地点等信息
- 视频直播
- 用户数据,礼物信息等
- 大数据应用
- 云存储系统
docker安装mongoDB
- docker pull mongo
-
-
- 1、创建mongo数据持久化目录
- mkdir -p /docker_volume/mongodb/data
- 运行容器
- docker run -itd --name mongo -v /docker_volume/mongodb/data:/data/db -p 27017:27017 mongo
- 进入容器
- docker exec -it mongo /bin/mongosh
-
- // 创建用户
- use admin
-
- db.createUser(
- {
- user: "root",
- pwd: "123456",
- roles: [ { role: "root", db: "admin" } ]
- }
- )
配置文件
- spring:
- data:
- mongodb:
- host: ip地址 #ip
- port: 27017 #端口号
- username: root #用户
- password: 123456 #密码
- database: admin #数据库名字--集合名字
数据库结构:
数据库(admin,test)--集合--文档
相当于mysql中的数据库
- // 判断是否有这个集合
- boolean has =mongoTemplate.collectionExists("emp");
-
- // 删除集合
- mongoTemplate.dropCollection("emp");
-
- // 创建集合
- mongoTemplate.createCollection("emp");
例如:
- @Autowired
- MongoTemplate mongoTemplate;
- @Test
- void test1(){
- // 判断是否有这个集合
- boolean has = mongoTemplate.collectionExists("emp");
- if(has){
- // 删除集合
- mongoTemplate.dropCollection("emp");
- }
- // 创建集合
- mongoTemplate.createCollection("emp");}
相当于mysql中的表操作
数据操作
- @Document
- 作用在类上,表示当前文档
- @Document(文档名称,集合名称)
- @Id
- 作用在字段上
- 映射id字段
- @Field
- 作用在字段上
- 映射字段
- @Transient
- 该字段不会保存到数据库中
- @AllArgsConstructor
- @NoArgsConstructor
- @Document("emp")
- @Data
- public class Employee {
- @Id
- private Integer id;
- @Field
- private String name;
- @Field
- private int age;
- @Field
- private Double salary;
- @Field
- private Date birthday;
- }
- 1、单条数据
-
- Employee zs= new Employee(1,"张三",21,500.00,new Date());
- // 添加文档 id存在时候更新数据--用于添加或者修改mongoTemplate.save(zs);
- mongoTemplate.save(zs); // 用于添加或者修改,支持批量插入
- // 如果 id存在会报错
- mongoTemplate.insert(zs); // 用于添加
-
- 2、批量添加
- @Test
- void insert(){
-
- List<Employee>list= Arrays.asList(
- new Employee(21,"往往",21,500.00,new Date()),
- new Employee(31,"小王",21,500.00,new Date()),
- new Employee(41,"小张",21,500.00,new Date()),
- new Employee(51,"肖红梅",21,500.00,new Date())
- );
- // 批量插入,如果id存在,会抛出异常--用于添加
- mongoTemplate.insert(list, Employee.class);
- }
- 1、查询全部
- List<Employee> all = mongoTemplate.findAll(Employee.class);
-
- 2、根据id查询
- Employee empTem = mongoTemplate.findById(1, Employee.class);
-
- 3、查询一条
- Employee one = mongoTemplate.findOne(new Query(), Employee.class);log.info("one:{}",one);
-
- 4、条件查询
- @Test
- public void tes3(){
-
- // 查询 id>=20 且 id<= 的字段
- List<Employee> list = mongoTemplate.find(Query.query(Criteria.where("id").gte(20).lte(60)), Employee.class);
- log.info("id>20的数据:{}",list);
- }
-
- 5、模糊查询/正则查询
- 正则不需要有 / /
- List<Employee> list = mongoTemplate.find(Query.query(Criteria.where("name").regex("张")), Employee.class);
-
- 6、多条件查询
- @Test
- public void tes5(){
- Criteria criteria=new Criteria();
- // criteria.orOperator()
- // 条件查询 name 为张三 id 为2
- criteria.andOperator(Criteria.where("name").is("张三"),Criteria.where("id").is(2));
- List<Employee> list = mongoTemplate.find(Query.query(criteria), Employee.class);
- log.info("的数据:{}",list);
- }
- 7、排序
- //asc 升序,decs降序
- List<Employee> list = mongoTemplate.find(new Query().with(Sort.by(Sort.Order.desc("id"))), Employee.class);
- 8、分页
- 使用skip和limt配合
- p = (pageNumber - 1) * pageSize
- q = pageSize
- skip(p) // 跳过p条数据
- limt(q) // list最大保留q条数据
- 例如:
- // 分页查询
- @Test
- public void tes7(){
- int pageName=3;
- int pageSize=4;
- int p=(pageName-1)*pageSize;
- int q=pageSize;
- List<Employee> list = mongoTemplate.find(new Query().skip(p).limit(q), Employee.class);
- log.info("第三页数据:{}",list);
- }
-
- 8、json字符串查询
- @Test
- public void tes8(){
- String json="{name:'张三'}";
- Query query=new BasicQuery(json);
- List<Employee> list = mongoTemplate.find(query, Employee.class);
- log.info("json串查询:{}",list);
- }
数据修改
- 1、更新一条
- // 把id=1的 的行中 name改成小帅,更新查询到的第一条
- mongoTemplate.updateFirst(Query.query(Criteria.where("id").is(1)), Update.update("name","小帅"), Employee.class);
-
-
-
- 2、更新--没有找到目标就进行添加操作
- mongoTemplate.upsert(Query.query(Criteria.where("id").is(202)), Update.update("name", "小帅").set("salary",100), Employee.class);
- 或者
- mongoTemplate.save(new Employee(202,"往往",21,500.00,new Date(),"新字段"));
-
- 3、批量更新
- public void testUpdate2(){
- // 批量更新
- UpdateResult result = mongoTemplate.updateMulti(Query.query(Criteria.where("name").is("张三")), Update.update("name", "小红"), Employee.class);
- log.info("生效条数:{}",result.getModifiedCount());
- }
-
- UpdateResult 对象
- getMatchedCount() 返回满足查询条件的文档数。
- getModifiedCount() 返回实际更新的文档数。
- wasAcknowledged() 返回更新操作是否被服务器确认。
删除数据
- 1、 删除所有文档
- mongoTemplate.remove(new Query(), Employee.class);
-
- 2、删除指定的
- mongoTemplate.remove(Query.query(Criteria.where("id").is(1)), Employee.class);
处理数据的计算结果(诸如统计平均值,求和等)
聚合管道
类似stream流
可以用mongoTemplate.find().stream() 代替
- match(Criteria criteria)
- :根据指定的查询条件筛选文档。可以使用Criteria对象来定义查询条件。
- project(String... fieldNames)
- :选择要包含在结果中的字段。可以指定字段名或使用表达式进行投影操作。
- group(String... fieldNames)
- :按照指定的字段对文档进行分组。可以使用表达式或函数来定义分组操作。
- sort(Sort sort)
- :对结果进行排序。可以根据指定的字段进行升序或降序排序。
- skip(long num)
- :跳过指定数量的文档。
- limit(long num)
- :限制结果集的大小。
- unwind(String fieldName)
- :将一个数组字段展开为多个文档,并保持其他字段的一致性。
- lookup(String from, String localField, String foreignField, String as)
- :执行左连接操作,将当前集合与指定的外部集合进行关联。
- replaceRoot(String fieldName)
- :将指定字段的值作为新文档的根级别。
- count()
- :计算匹配文档的数量。