文章目录
3 mongoDB
3.1 mongDB 与mysql
3.1.1 MongoDB的结构图
[外链图片转存失败(img-9s5Xdad8-1565945636643)()]
3.1.2 与关系型数据库对比图
mongodb | 关系型数据库mysql |
---|---|
databases | databases |
collections | table |
document | row |
3.1.3 数据类型
null:用于表示空值或者不存在的字段
布尔:布尔类型有连个值,true,false
数值:shell默认使用64位浮点型数值。对于整型值NumberInt(4字节符号整数)或者使用NumberLong(8字节符号整数),{“x”:NumberInt(3)},{“x”:NumberLong(3)}
字符串:UTF-8 字符串都可以表示为字符串类型数据,{“x”,“呵呵”}
日期类型:日期被存储为新纪元以来经过的毫秒数,不存储时区,{“x”:newDate()}
正则表达式:查询时,使用正则表达式作为想定条件,语法与javascript的正则表达式相同,{“x”:/[abc]/}
数组:数据列表或者数据集可以表示为数组;{“x”:[“a”,“b”,‘c’}
内嵌文档:文档可以嵌套文档,被嵌套的文档作为值来处理,{“x”:{“y”:3}}
对象 id:对象的id是一个12字节的字符串,是文档的唯一表示,{“x”:objectId()}
二进制数据:二进制数据是一个任意字节的字符转,他不能直接在shell中使用,如果要将非UTF-字符保存在数据库中,二进制数据是唯一的方式。
代码:查询和文档中可以包含任何的JavaScript代码,{“x”:function(){/…/}}
3.2 mongdo的安装
3.2.1 windows 版本
百度: mongodb-win32-x86_64-2008plus-ssl-3.2.10-signed.msi 然后自己下载
注意:mongodb 他的客户端和服务器是一同安装的,安装后需要配置环境变量,这样使用起来更佳
3.2.2 初始化数据库:
C:\Users\Administrator>cd d:
D:\
C:\Users\Administrator>d:
D:\>md data
D:\>mongod -dbpath="d:\data"
2019-08-16T11:39:28.818+0800 I CONTROL [main] Hotfix KB2731284 or later update
is installed, no need to zero-out data files
2019-08-16T11:39:28.820+0800 I CONTROL [initandlisten] MongoDB starting : pid=9
608 port=27017 dbpath=d:\data 64-bit host=7DXOSPRVGV8O21O
2019-08-16T11:39:28.820+0800 I CONTROL [initandlisten] targetMinOS: Windows 7/W
indows Server 2008 R2
2019-08-16T11:39:28.821+0800 I CONTROL [initandlisten] db version v3.2.10
2019-08-16T11:39:28.821+0800 I CONTROL [initandlisten] git version: 79d9b3ab5ce
20f51c272b4411202710a082d0317
2019-08-16T11:39:28.821+0800 I CONTROL [initandlisten] OpenSSL version: OpenSSL
1.0.1t-fips 3 May 2016
2019-08-16T11:39:28.821+0800 I CONTROL [initandlisten] allocator: tcmalloc
2019-08-16T11:39:28.821+0800 I CONTROL [initandlisten] modules: none
2019-08-16T11:39:28.821+0800 I CONTROL [initandlisten] build environment:
2019-08-16T11:39:28.822+0800 I CONTROL [initandlisten] distmod: 2008plus-ss
l
2019-08-16T11:39:28.824+0800 I CONTROL [initandlisten] distarch: x86_64
2019-08-16T11:39:28.825+0800 I CONTROL [initandlisten] target_arch: x86_64
2019-08-16T11:39:28.825+0800 I CONTROL [initandlisten] options: { storage: { db
Path: "d:\data" } }
2019-08-16T11:39:28.881+0800 I STORAGE [initandlisten] wiredtiger_open config:
create,cache_size=6G,session_max=20000,eviction=(threads_max=4),config_base=fals
e,statistics=(fast),log=(enabled=true,archive=true,path=journal,compressor=snapp
y),file_manager=(close_idle_time=100000),checkpoint=(wait=60,log_size=2GB),stati
stics_log=(wait=0),
2019-08-16T11:39:29.396+0800 I NETWORK [HostnameCanonicalizationWorker] Startin
g hostname canonicalization worker
2019-08-16T11:39:29.396+0800 I FTDC [initandlisten] Initializing full-time d
iagnostic data capture with directory 'd:/data/diagnostic.data'
2019-08-16T11:39:29.577+0800 I NETWORK [initandlisten] waiting for connections
on port 27017
3.2.3 centeros版本
我建议还是使用docker的方式进行安装,可以参考我之前的文档。
3.2.4 连接命令
C:\Users\Administrator>mongo 192.168.85.198
2019-08-16T11:51:42.162+0800 I CONTROL [main] Hotfix KB2731284 or later update
is installed, no need to zero-out data files
MongoDB shell version: 3.2.10
connecting to: 192.168.85.198/test
Welcome to the MongoDB shell.
For interactive help, type "help".
For more comprehensive documentation, see
http://docs.mongodb.org/
Questions? Try the support group
http://groups.google.com/group/mongodb-user
Server has startup warnings:
2019-08-16T02:54:11.015+0000 I CONTROL [initandlisten]
2019-08-16T02:54:11.016+0000 I CONTROL [initandlisten] ** WARNING: Access contr
ol is not enabled for the database.
2019-08-16T02:54:11.016+0000 I CONTROL [initandlisten] ** Read and wri
te access to data and configuration is unrestricted.
2019-08-16T02:54:11.016+0000 I CONTROL [initandlisten]
2019-08-16T02:54:11.041+0000 I CONTROL [initandlisten]
2019-08-16T02:54:11.041+0000 I CONTROL [initandlisten] ** WARNING: /sys/kernel/
mm/transparent_hugepage/enabled is 'always'.
2019-08-16T02:54:11.041+0000 I CONTROL [initandlisten] ** We suggest set
ting it to 'never'
2019-08-16T02:54:11.053+0000 I CONTROL [initandlisten]
2019-08-16T02:54:11.053+0000 I CONTROL [initandlisten] ** WARNING: /sys/kernel/
mm/transparent_hugepage/defrag is 'always'.
2019-08-16T02:54:11.053+0000 I CONTROL [initandlisten] ** We suggest set
ting it to 'never'
2019-08-16T02:54:11.053+0000 I CONTROL [initandlisten]
>
3.2.5 创建数据库和表
use spitdb; // 创建数据库 并切换到该库
db.spit.find(); //查询并创建表,如果表不存在
// 插入值
db.spit.insert({"content":"天正极板雷公","visits":NumberInt(10)})
//这种报错说明,您输入的字符串中存在中文,需要把标点符号等改成英文
> db.spit.insert({"content":"天正极板雷公","visits":NumberInt(10)}))
2019-08-16T14:02:41.773+0800 E QUERY [thread1] SyntaxError: illegal character @(shell):1:34
//正确的结果:
> db.spit.insert({"content":"天正极板雷公","visits":NumberInt(10)}))
WriteResult({ "nInserted" : 1 })
>
//更新 db.spit.update({"_id":"1122323652630253568"},{$set:{ "content" : "test2}}) 表示只更新一个字段
> db.spit.find(); nt(10)})
{ "_id" : "123", "visits" : 1101, "createTime" : ISODate("2019-04-26T06:15:25.664Z"), "userid" : "12111", "content" : "我真TMD是天才" }
{ "_id" : "1234", "visits" : 1101, "createTime" : ISODate("2019-04-26T06:16:26.172Z"), "userid" : "12111", "content" : "我真TMD是天才" }
{ "_id" : "1122323563656482816", "content" : "moggo", "publishtime" : ISODate("1970-01-01T00:00:12.121Z"), "userid" : "1", "nickname" : "12", "visits" : 0, "thumbup" : 0, "share" : 0, "comment" : 0, "state" : "1", "parentid" : "", "_class" : "com.liu.spit.pojo.Spit" }
{ "_id" : "1122323652630253568", "content" : "test1", "publishtime" : ISODate("1970-01-01T00:00:12.121Z"), "userid" : "1", "nickname" : "12", "visits" : 0, "thumbup" : 0, "share" : 0, "comment" : 0, "state" : "1", "parentid" : "1", "_class" : "com.liu.spit.pojo.Spit" }
{ "_id" : ObjectId("5d56470f5a4756fab7bf8baf"), "content" : "天正极板雷公", "visits" : 10 }
> db.spit.update({"_id":"1122323652630253568"},{$set:{ "content" : "test2}})
2019-08-16T15:19:25.728+0800 E QUERY [thread1] SyntaxError: unterminated string literal @(shell):1:65
> db.spit.update({"_id":"1122323652630253568"},{$set:{ "content":"test2"}})
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.spit.find();
{ "_id" : "123", "visits" : 1101, "createTime" : ISODate("2019-04-26T06:15:25.664Z"), "userid" : "12111", "content" : "我真TMD是天才" }
{ "_id" : "1234", "visits" : 1101, "createTime" : ISODate("2019-04-26T06:16:26.172Z"), "userid" : "12111", "content" : "我真TMD是天才" }
{ "_id" : "1122323563656482816", "content" : "moggo", "publishtime" : ISODate("1970-01-01T00:00:12.121Z"), "userid" : "1", "nickname" : "12", "visits" : 0, "thumbup" : 0, "share" : 0, "comment" : 0, "state" : "1", "parentid" : "", "_class" : "com.liu.spit.pojo.Spit" }
{ "_id" : "1122323652630253568", "content" : "test2", "publishtime" : ISODate("1970-01-01T00:00:12.121Z"), "userid" : "1", "nickname" : "12", "visits" : 0, "thumbup" : 0, "share" : 0, "comment" : 0, "state" : "1", "parentid" : "1", "_class" : "com.liu.spit.pojo.Spit" }
{ "_id" : ObjectId("5d56470f5a4756fab7bf8baf"), "content" : "天正极板雷公", "visits" : 10 }
>
// 删除 数据
db.spit.remove({}) {} 中为删除条件
//统计
db.spit.count({}) {} 为统计的 条件
//查询
db.spit.find({content://}) 注意/正则表达式/
// 比较运算
db.spit.find({vistis:{$gt:150}}) 查询大于150的数据
// $in $nin 包含 不包含
//条件连接
$and:[{},{}]
$or:[{},{}]
//自增操作
db.spit.update({"_id":'01'},{$inc:{vistits:NumberInt(1)}})
3.3 java 原生的操作方式
3.3.1 配置文件
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.liu</groupId>
<artifactId>mongodbDemo</artifactId>
<version>1.0-SNAPSHOT</version>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.mongodb</groupId>
<artifactId>mongodb-driver</artifactId>
<version>3.6.3</version>
</dependency>
</dependencies>
</project>
3.3.2 代码测试
package com.liu.test;
import com.mongodb.BasicDBObject;
import com.mongodb.MongoClient;
import com.mongodb.client.FindIterable;
import com.mongodb.client.MongoCollection;
import com.mongodb.client.MongoDatabase;
import org.bson.BasicBSONObject;
import org.bson.Document;
import java.util.HashMap;
import java.util.Map;
/**
* Created by Administrator on 2019/8/16 0016.
*/
public class MongoDbTest {
public static void main(String[] args) {
// 创建一个链接
MongoClient client = new MongoClient("192.168.85.198");
// 获取数据库对象
MongoDatabase database = client.getDatabase("spitdb");
// 获取集合对象
MongoCollection<Document> spit = database.getCollection("spit");
// find(spit);
insert(spit);
client.close();
}
public static void insert(MongoCollection<Document> spit){
Map map = new HashMap();
map.put("content",100);
map.put("session",1000);
map.put("float",1.1f);
Document docment = new Document(map);
spit.insertOne(docment);
}
public static void find(MongoCollection<Document> spit){
// 封装查询条件,如果是多个条件注意嵌套
BasicDBObject bsonObject = new BasicDBObject("_id","123");
BasicDBObject bson2 = new BasicDBObject("_id",new BasicDBObject("$gt",1000));
FindIterable<Document> result=spit.find(bson2);
// 数据便利
for (Document d: result ) {
System.out.println(d.getString("content"));
}
// 关闭链接
}
}
3.4 spingDataMongoDB
3.4.1 添加jar包
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-mongodb</artifactId>
</dependency>
3.4.2 添加配置文件
server:
port: 9005
spring:
application:
name: boot-spit
data:
mongodb:
host: 192.168.85.198
database: spitdb
port: 27017
redis:
host: 192.168.85.198
database: 0
password:
3.4.3 jpa 添加到
package com.liu.spit.dao;
import com.liu.spit.pojo.Spit;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.mongodb.repository.MongoRepository;
/**
* 吐槽的数据访问层
* @author shi860715@126.com
*
*/
public interface SpitDao extends MongoRepository<Spit,String> {
Page<Spit> findSpitsByParentid(String parentid, Pageable pageable);
}
3.4.4 服务层
package com.liu.spit.service;
import com.liu.common.utils.IdWorker;
import com.liu.spit.dao.SpitDao;
import com.liu.spit.pojo.Spit;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.List;
@Service
@Transactional
public class SpitService {
@Autowired
private SpitDao spitDao;
@Autowired
private IdWorker idWorker;
@Autowired
private MongoTemplate mongoTemplate;
public List<Spit> findAll(){
return spitDao.findAll();
}
public Spit findById(String id){
return spitDao.findById(id).get();
}
public void update(Spit spit){
spitDao.save(spit);
}
public void add(Spit spit){
spit.set_id(idWorker.nextId()+"");
spitDao.save(spit);
}
public void deleteById(String id){
spitDao.deleteById(id);
}
public Page<Spit> findByParentId(String parentid, int page, int size) {
return spitDao.findSpitsByParentid(parentid, PageRequest.of(page-1,size));
}
public void thumbup(String spitId) {
// 优化代码部分,使用传统的方式,需要先查询一次,然后在将查询的值保存回去,操作两次数据库,
// 使用 mongo 自己的一些特性可以提高效率
Query query = new Query();
query.addCriteria(Criteria.where("_id").is(spitId));
Update update = new Update();
update.inc("thumbup",1);
mongoTemplate.updateFirst(query,update,"spit");
}
}
3.4.5 控制层
package com.liu.spit.controller;
import com.liu.common.entity.PageResult;
import com.liu.common.entity.Result;
import com.liu.common.status.CodeEnum;
import com.liu.common.status.RedisKeyEnum;
import com.liu.spit.pojo.Spit;
import com.liu.spit.service.SpitService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;
@RestController
@CrossOrigin
@RequestMapping("/spit")
public class SpitController {
@Autowired
private SpitService spitService;
@Autowired
private RedisTemplate redisTemplate;
/**
* 查询所有的
* @return
*/
@RequestMapping(method = RequestMethod.GET)
public Result findAll(){
return new Result(true, CodeEnum.OK.getCode(),"查询成功!",spitService.findAll());
}
/**
* 根据id查询
* @param id
* @return
*/
@RequestMapping(value = "/{id}",method = RequestMethod.GET)
public Result findById(@PathVariable String id){
return new Result(true, CodeEnum.OK.getCode(),"查询成功!",spitService.findById(id));
}
@RequestMapping(method = RequestMethod.POST)
public Result add(@RequestBody Spit spit){
spitService.add(spit);
return new Result(true, CodeEnum.OK.getCode(),"保存成功!");
}
@RequestMapping(value ="/{id}" ,method = RequestMethod.PUT)
public Result update(@RequestBody Spit spit,@PathVariable String id ){
spit.set_id(id);
spitService.update(spit);
return new Result(true, CodeEnum.OK.getCode(),"更新成功!");
}
@RequestMapping(value = "/{id}",method = RequestMethod.DELETE)
public Result deleteById(@PathVariable String id){
spitService.deleteById(id);
return new Result(true, CodeEnum.OK.getCode(),"删除成功!");
}
/**
* 根据上级ID查询吐槽数据
* @param parentid
* @param page
* @param size
* @return
*/
@RequestMapping(value = "comment/{parentid}/{page}/{size}",method = RequestMethod.GET)
public Result findByParentId(@PathVariable String parentid,@PathVariable int page, @PathVariable int size){
Page<Spit> spitPage = spitService.findByParentId(parentid,page,size);
return new Result(true,CodeEnum.OK.getCode(),"查询成功",new PageResult<Spit>(spitPage.getTotalElements(),spitPage.getContent()));
}
@RequestMapping(value = "thumbup/{spitId}",method = RequestMethod.PUT)
public Result thumbup(@PathVariable String spitId){
// userId 使用来模拟用户登录状态。
String userId = "123";
// 这里用缓存,来记录点赞状态,当用户点赞后,用户对该吐槽不能二次点赞
if (redisTemplate.opsForValue().get(RedisKeyEnum.APIT_THUMBUP_KEY.getKey()+spitId+userId)!=null){
return new Result(false,CodeEnum.REPE_ERROR.getCode(),"您已经点赞,不能重复点赞");
}
spitService.thumbup(spitId);
// 用户对该吐槽条目进行点赞后,记得修改点赞的标识位
redisTemplate.opsForValue().set(RedisKeyEnum.APIT_THUMBUP_KEY.getKey()+spitId+userId,1);
return new Result(true,CodeEnum.OK.getCode(),"点赞成功");
}
}