others linux服务器运维 django3 监控 k8s golang 数据库 大数据 前端 devops 理论基础 java oracle 运维日志

mongodb 概念、基本使用

访问量:1444 创建时间:2021-04-28

为什么需要NoSQL,可以应付超大规模,高并发;传统数据库的性能和扩展瓶颈;解决大规模数据集合、多重数据种类的挑战;大数据应用难题,包括超大规模数据的存储。

分类 优势 劣势 场景 代表
键值对 查找速度快 数据无结构化,通常只被当做字符串或者二进制数据 内容缓存,大量数据的高频访问 redis
列式存储 查找速度快,支持分布式横向扩展,数据压缩率高 功能相对受限 分布式文件系统 HBASE,cassandra
文件存储 数据结构要求不严格,表结构可变 查询性能不高,缺乏统一的查询语法 web应用 mongodb
图数据库 可利用图结构相关算法 可能需要对整个图做计算,不利于图数据分布式存储 社交网络、推荐系统、意向图、消费图、兴趣图、关系图谱等 Neo4j,couchDB

Mongodb:是一个机遇c++开发的NoSQL开源文档数据库,具有所需的可伸缩性和灵活性,可用于所需的查询和索引编制。最像关系数据库,功能丰富的NoSQL数据库。

特性
面相机和文档的存储:适合存储Bson(json的扩展)形式的数据
格式自由,数据格式不固定,生产环境下修改结构都不影响程序运行
强大的查询语句,面向对象的查询语言,基本覆盖sql语言所有能力
完成的索引支持,支持查询计划
支持复制和自动故障转移
支持二进制数据及大型对象(文件)的高效存储
使用分片集群提升系统扩展性
使用内存映射存储引擎,把磁盘的IO操作转换成为内存的操作。
应用需求场景
不需要事务及复杂的join支持
新应用,需求会变,数据模型不确定,想快速迭代开发
要求对2000-3000以上的读写QPS
要存储TB甚至PB级别数据
应用发展迅速,能快速水平扩展
要求存储数据不丢失
要求99.999%高可用
有大量的地理位置查询,文本查询

MongoDB vs 关系型数据库

--- MongoDB RDBMS
数据模型 文档模型(json对象) 关系模型
数据库类型 OLTP OTLP
CRUD操作 MSQ/SQL SQL
高可用 复制集 集群模式
横向扩展能力 通过原声分片完善支持 数据分区或者应用侵入式
索引支持 B树、全文索引、地理位置索引、多键(multikey)索引、TTL索引 B树
开发难度 容易(应用程序代码、建模非常容易)
数据容量 没有理论上限 千万、亿
扩展方式 垂直扩展+水平扩展 垂直扩展

关系模型 VS 文档模型

--- 关系数据库 JSON文档模型
模型设计层次 概念模型
逻辑模型
物理模型
概念模型
逻辑模型
模型实体 集合
模型属性 字段
模型关系 关联关系,主外键 内嵌数组,引用字段

mongodb 基本概念

mongodb 软件

软件模块 描述
mongod mongodb数据库软件
mongo mongodb命令行工具,管理mongodb数据库
mongos mongodb路由进程,分片环境下使用
mongodump/mongorestore mongodb备份恢复工具
mongoexport/mongoimport csv/json导入导出,主要用于不同系统间数据迁移
compass mongodb GUI 管理工具
Ops Manager(企业版) MongoDB集群管理软件,升级、扩容、监控告警、持续备份与恢复、k8s集成等功能
BI Connectoir(企业版) MongoDB可视化软件,兼容mysql语法,在例如powerbi 与mongodb中间做查询与结果转换(不支持写入)
Atlas(付费及免费) MongoDB云托管服务,包括永久免费云数据库
MongoDB Charts 可视化分析,创建图表

Mongodump/mongorestore : 类似Mysql的dump/restore工具;可以完成全库dump:不加条件; 也可以根据条件dump部分数据:-q参数;Dump的同时跟踪数据更新:--oplog; Restore是反操作,把mongodump的输出导入到mongodb.

mongodump -h 127.0.0.1:27017 -d test -c test
mongorestore -h 127.0.0.1:27017 -d test -c test xxx.bson

centos7安装mongodb

官网下载地址:https://www.mongodb.com/try/download.(可以在cloud.mongodb.com上申请一个免费的mongodb集群使用,这里不介绍)

#centos7 通过yum安装
[root@localhost ~]# vim /etc/yum.repos.d/mongodb.repo
[mongodb-org-4.4]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/$releasever/mongodb-org/4.4/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-4.4.asc
[root@localhost ~]# yum install -y mongodb-org
[root@localhost ~]# systemctl enable mongod
##修改监听的ip地址从127.0.0.1改为0.0.0.0
[root@localhost ~]# vim /etc/mongod.conf 
net:
  port: 27017
  bindIp: 0.0.0.0
[root@localhost ~]# systemctl start mongod

基本连接使用

基本命令 解释
use databaseName; 如果databaseName不存在,在插入数据时会创建数据库
show dbs 显示当前实例中的数据库
db.dropDatabase() 删除当前数据库
db.createCollection("test) 显示创建test集合
show tables 显示当前数据库中的集合信息
show collections 同上
db.test.drop() 删除test集合
[root@localhost ~]# mongo
> show dbs;
admin   0.000GB
config  0.000GB
local   0.000GB
> use testdb
switched to db testdb
> db.users.insert({name:'hash',age:18,lenth:18,lover:'keke'})
WriteResult({ "nInserted" : 1 })
> show tables;
users
> show collections;
users
> show dbs;
admin   0.000GB
config  0.000GB
local   0.000GB
testdb  0.000GB

导入测试数据dump.tar.gz(下载地址下载地址2)

[root@localhost ~]# tar xf dump.tar.gz 
[root@localhost ~]# ls dump
mock
[root@localhost ~]# mongorestore dump
############查看测试数据
[root@localhost ~]# mongo
> show dbs
admin   0.000GB
config  0.000GB
local   0.000GB
mock    0.047GB
testdb  0.000GB
> use mock
switched to db mock
> show collections
orders
> db.orders.findOne()
{
        "_id" : ObjectId("5dbe7a545368f69de2b4d36e"),
.................................省略部分输出
}

图形化客户端compass使用,完全免费;windows下载后解压运行MongoDBCompass。 这里只演示无认证登陆。(下载地址:https://downloads.mongodb.com/compass/mongodb-compass-1.26.1-win32-x64.zip)

命令行基本操作(增删改查)

insert 插入数据,格式如下:

操作格式 命令 例子
单个json对象插入 db.<集合>.insertOne() db.fruit.insertOne({name:"apple"})
多个json对象插入 db.<集合>.insertMany([,,]) db.fruit.insertMany([{name:"apple"},{name:"pear"},{name:"orange"}])
##insertedId 是mongodb提供的默认主键,字段名是_id
> db.fruit.insertOne({name:"apple"})
{
        "acknowledged" : true,
        "insertedId" : ObjectId("608a09b871cb09186460d9b8")
}
> db.fruit.insertMany([{name:"apple"},{name:"pear"},{name:"orange"}])
{
        "acknowledged" : true,
        "insertedIds" : [
                ObjectId("608a0ab571cb09186460d9b9"),
                ObjectId("608a0ab571cb09186460d9ba"),
                ObjectId("608a0ab571cb09186460d9bb")
        ]
}

使用find查询文档,find是mongodb中查询数据的基本指令,相当于SQl中的select. find返回的是游标。

find示例
db.movies.find({"year":1975}) //单条件查询
db.movies.find({"year":1975,"title":"Batman"}) //多条件and查询
db.movies.find({$and:[{"year":1975},{"category":"action"}]}) //and的另一种形式
db.movies.find({$or:[{"year":1997},{"title":"Batman"}]}) //多条件or查询
db.movies.find({"title":"/^B/"}) //按正则表达式查找
SQL MSQL
a=1 {a:1}
a<>1 {a:{$ne:1}}
a>1 {a:{$gt:1}}
a>=1 {a:{$gte:1}}
a<1 {a:{$lt:1}}
a<=1 {a:{$lte:1}}
a=1 and b=1 {a:1,b:1} 或者 {$and:[{a:1},{b:1}]}
a=1 or b=1 {$or[{a:1},{b:1}]}
a is null {a:{$exists: false}}
a in (1,2,3) {a:{$in:[1,2,3]}}
$nin:不存在或不在指定的数组中
$ne: 不存在或存在但不等于
> db.fruit.find()
{ "_id" : ObjectId("608a09b871cb09186460d9b8"), "name" : "apple" }
{ "_id" : ObjectId("608a0ab571cb09186460d9b9"), "name" : "apple" }
{ "_id" : ObjectId("608a0ab571cb09186460d9ba"), "name" : "pear" }
{ "_id" : ObjectId("608a0ab571cb09186460d9bb"), "name" : "orange" }

使用find搜索子文档

##find支持使用field.sub_field的形式查询子文档。假设有一个文档:
db.fruit.insertOne({
    name:"apple",
    from:{
        country:"China",
        province:"Guangdong"
    }
})
##查询子文档,要在双引号里面写文档的路径"from.country", 第二种写法查询不到结果
> db.fruit.find({"from.country":"China"})
{ "_id" : ObjectId("608a117871cb09186460d9bc"), "name" : "apple", "from" : { "country" : "China", "province" : "Guangdong" } }
> db.fruit.find({"from":{country:"China"}})
> 

使用find搜索数组(下面color是个数组)

> db.fruit.insert([{"name":"Apple",color:["red","green"]},{"name":"Mango",color:["yellow","green"]}])
BulkWriteResult({
        "writeErrors" : [ ],
        "writeConcernErrors" : [ ],
        "nInserted" : 2,
        "nUpserted" : 0,
        "nMatched" : 0,
        "nModified" : 0,
        "nRemoved" : 0,
        "upserted" : [ ]
})
> db.fruit.find({color:"red"})
{ "_id" : ObjectId("608a12c271cb09186460d9bd"), "name" : "Apple", "color" : [ "red", "green" ] }
> db.fruit.find({$or:[{color:"red"},{color:"yellow"}]})
{ "_id" : ObjectId("608a12c271cb09186460d9bd"), "name" : "Apple", "color" : [ "red", "green" ] }
{ "_id" : ObjectId("608a12c271cb09186460d9be"), "name" : "Mango", "color" : [ "yellow", "green" ] }

remove删除文档: remove命令需要配合查询条件使用,匹配查询条件的文档会被删除;指定一个空文档条件会删除所有文档;

###示例:
db.testcol.remove({a:1})//删除a等于1的记录
db.testcol.remove({a:{$lt:5}})//删除a小于5的记录
db.testcol.remove({})//删除所有记录
db.testcol.remove()//报错

使用update更新文档

drop删除集合: 使用db.<集合>.drop()来删除一个集合,集合中的全部文档都会被删除,集合相关的索引也会被删除。

db.colToDeDropped.drop()

编程语言python操作mongo

[root@localhost ~]# pip3 install pymongo
WARNING: Running pip install with root privileges is generally not a good idea. Try `pip3 install --user` instead.
Collecting pymongo
  Downloading https://files.pythonhosted.org/packages/03/4b/2adf815a054b467e87de2b5c830dfc9bc75e9ae7f977b50e6bb8eca7c3ac/pymongo-3.11.3-cp36-cp36m-manylinux1_x86_64.whl (492kB)
    100% |████████████████████████████████| 501kB 455kB/s 
Installing collected packages: pymongo
Successfully installed pymongo-3.11.3
[root@localhost ~]# python3
Python 3.6.8 (default, Nov 16 2020, 16:55:22) 
[GCC 4.8.5 20150623 (Red Hat 4.8.5-44)] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import pymongo
>>> pymongo.version
'3.11.3'
>>> from pymongo import MongoClient
>>> uri="mongodb://192.168.52.129:27017"
>>> client= MongoClient(uri)
>>> print(client)
MongoClient(host=['192.168.52.129:27017'], document_class=dict, tz_aware=False, connect=True)

>>> db=client['eshop']
>>> user_coll=db['users']
##测试数据库还没有真正创建
>>> new_user={"username":"nina","password":"xxx","email":"11234@qq.com"}
>>> result=user_coll.insert_one(new_user)
>>> print(result)
<pymongo.results.InsertOneResult object at 0x2ba421f0fac8>

更新用户,增加字段phone

###python代码
>>> result = user_coll.update_one({"username":"nina"},{"$set":{"phone":"123456789"}})
>>> print(result)
<pymongo.results.UpdateResult object at 0x2ba421f29708>

###mongo下
> use eshop
switched to db eshop
> db.users.find()
{ "_id" : ObjectId("608a2e73cb2ff42ea94f7e57"), "username" : "nina", "password" : "xxx", "email" : "11234@qq.com", "phone" : "123456789" }

参考视频资料:https://www.bilibili.com/video/BV17V411n7q9?p=11&spm_id_from=pageDriver 参考视频资料:https://space.bilibili.com/441067951/video

登陆评论: 使用GITHUB登陆