1. NoSQL起源

  • 最初数据库只有关系型数据库,随着发展,关系型数据库存在以下问题
  • 不能满足高性能查询需求
  • 扩展性差,大数据下IO压力大,表结构更改困难
  • NoSQL,泛指非关系型数据库。MongoDB、Redis等都属于非关系型数据库。
  • NoSQL的优点:
  • 高可扩展性
  • 分布式计算
  • 低成本
  • 架构的灵活性,半结构化数据
  • 没有复杂的关系
  • NoSQL的缺点:
  • 没有标准化
  • 有限的查询功能
  • 最终一致是不直观的程序

2. MongoDB介绍

  • MongoDB是一个基于分布式文件存储的数据库。用C++语言编写,旨在为WEB应用提供可扩展的高性能数据存储解决方案
  • 在高负载的情况下,添加更多的节点,可以保证服务器性能
  • MongoDB将数据存储为一个文档,数据结构由键值(key=>value)对组成
  • MongoDB三元素
  • 数据库:是一个集合的物理容器,一个数据库中可以包含多个文档
  • 集合:相当于关系型数据库中的表,多个文档形成一个集合,文档可以是不同的形式
{'name':'曹操','sex':'男'}
{'name':'刘备','sex':'男','age':48}
  • 文档:相当于关系型数据库中的行,文档是以json的扩展形式存储的
{'name':'貂蝉','sex':'女'}

3. MongoDB的安装

1) 安装MongoDB软件
  • sudo apt install mongodb
2) 查看MongoDB状态
  • service mongodb status
  • Active: active (running) 运行中
  • Active: inactive (dead) 未运行
rulai@ubuntu:~$ service mongodb status
● mongodb.service - An object/document-oriented database
   Loaded: loaded (/lib/systemd/system/mongodb.service; enabled; vendor preset: 
   Active: active (running) since 一 2018-01-15 22:58:40 PST; 1min 4s ago
     Docs: man:mongod(1)
 Main PID: 9996 (mongod)
   CGroup: /system.slice/mongodb.service
           └─9996 /usr/bin/mongod --config /etc/mongodb.conf

1月 15 22:58:40 ubuntu systemd[1]: Started An object/document-oriented databas
3) 启动MongoDB服务
  • sudo service mongodb start
4) 停止MongoDB服务
  • sudo service mongodb stop
5) MongoDB程序信息
  • 配置文件路径:/etc/mongodb.conf
  • 查看配置信息:cat /etc/mongodb.conf
# 数据保存路径
dbpath=/var/lib/mongodb

# 系统日志保存路径
logpath=/var/log/mongodb/mongodb.log

# 开始系统日志
logappend=true

# 绑定访问IP地址
bind_ip = 127.0.0.1

# 默认开启端口号:27017
#port = 27017

4. MongoDB管理工具安装

  • robomongoMongoDB数据库的图形界面管理工具安装
  • robomongo软件下载链接:https://robomongo.org/download
  • robomongo管理工具能够访问mongodb数据库
  • bind_ip = 0.0.0.0外网也可以访问
1) 打开软件后,点击图形界面左上角连接按钮





2) 点击create创建按钮




3) 填写连接名称、连接的IP地址和端口号,再点击Test测试按钮




4) 出现以下窗口,说明MongoDB数据库连接成功,关闭close后点击save按钮




5) 点击连接后,就可以愉快的应用图形界面管理工具操作MongoDB数据库了




6) 创建数据库
  • 选中连接名右键
  • 选择Create database
  • 输入数据库名,点击create创建即可
7) 创建集合:
  • 点开创建好的数据库,选中Collections右键
  • 点击create collection
  • 输入集合的名字,点击create创建即可
  • 操作集合文档有以下操作:
  • view documents 查看文档
  • insert documents 插入数据
  • update documents 更新文档信息
  • remove documents 删除指定文档
  • remove all documents 删除所有文档
  • drop collections 删除集合

5. 终端操作MongoDB

  • Linux终端进入MongoDB主机
rulai@ubuntu:~$ mongo
MongoDB shell version: 2.6.10
connecting to: test

# 出现上面信息,说明成功进入到MongoDB数据库
  • use dbname创建/切换数据库
  • 系统会自动删除空库,为了保持住库,可以创建1个表,后期导入表时再删除
# 新建demo数据库

> use demo
switched to db demo

# 随机创建表,保住库
> db.usr.insert({'name':'rulai'})
WriteResult({ "nInserted" : 1 })
  • show dbs查看所有
# 查看主机上所有的数据库

> show dbs
Mystem  0.078GB
admin   (empty)
demo    0.078GB
local   0.078GB
  • 给数据库配置用户
> use demo
switched to db demo
> db.addUser('mongodb','123456')
WARNING: The 'addUser' shell helper is DEPRECATED. Please use 'createUser' instead
Successfully added user: { "user" : "mongodb", "roles" : [ "dbOwner" ] }
  • db.help()查看当前数据库可操作方法
  • db.dropDatabase()删除当前使用数据库
> db.dropDatabase()
{ "dropped" : "demo", "ok" : 1 }
> show dbs
Mystem  0.078GB
admin   0.078GB
local   0.078GB
  • 从指定的机器上复制指定数据库数据到某个数据库
> db.copyDatabase('study', 'temp', '192.168.220.129')
{ "ok" : 1 }
  • db.getName()查看当前使用的数据库
> db.getName()
demo
  • db.stats()查看当前数据库状态
> db.stats()
{
	"db" : "demo",
	"collections" : 0,
	"objects" : 0,
	"avgObjSize" : 0,
	"dataSize" : 0,
	"storageSize" : 0,
	"numExtents" : 0,
	"indexes" : 0,
	"indexSize" : 0,
	"fileSize" : 0,
	"dataFileVersion" : {
		
	},
	"ok" : 1
}
  • 修复当前数据库:db.repairDatabase()
  • db.version()查看当前数据库版本
> db.version()
2.6.10
  • db.getMongo() 查看当前数据库的链接机器地址
> db.getMongo()
connection to 127.0.0.1

6. 操作集合

1) 创建集合
  • createCollection()命令的基本语法db.createCollection(name, options)
  • 参数说明

参数

类型

含义

name

string

要创建的集合的名称

options

document

(可选)指定有关内存大小和索引的选项

  • 选项说明

字段

类型

含义

capped

boolean

(可选)如果为true,则启用封闭的集合,上限集合是固定大小的集合,它在达到其最大大小时自动覆盖其最旧的条目。如果指定true,则还需要指定size参数

autoIndexId

boolean

(可选)如果为true,则在_id字段上自动创建索引。默认值为false

size

数字

(可选)指定上限集合的最大大小(以字节为单位)。 如果capped为true,那么还需要指定此字段的值。

max

数字

(可选)指定上限集合中允许的最大文档数。

  • 案例:创建一个不限制大小的集合stu
> db.createCollection("stu")
{ "ok" : 1 }

# ok 说明创建成功
  • 案例:创建一个20字节大小的集合
> db.createCollection("class", {capped : true, size : 20})
{ "ok" : 1 }
  • 查看当前数据库的集合show collections
> show collections
class
stu
system.indexes
  • 删除当前数据库某个集合db.集合名称.drop()
> db.class.drop()
true

7. MongoDB数据类型

  • Object ID:文档的id
  • 每个文档都有一个属性,为_id保证文档的唯一性;
  • 可以自己去设置_id插入文档
  • 如果自己没设置,mongoDB为每个文档提供一个独特的_id ,是一个12字节十六进制数
  • 前4个字节为当前时间戳
  • 接下来的3个字节为机器ID
  • 接下来2个字节为mongo的服务进程ID
  • 最后3个是简单的增量值
  • String:字符串,最常用,必须是utf-8
  • Boolean:布尔值,true或者false
  • Integer:整数
  • Double:浮点数
  • Arrays:数组或者列表,多个值存储到一个键
  • Object:用于嵌入文档,即一个值为一个文档
  • Null:存储null值
  • Timestamp:时间戳
  • Date:存储当前日期或时间unix时间格式

8. MongoDB数据增删改查操作

1) insert 操作
  • 格式:db.集合名称.insert(document),插入文档时,如果不指定_id参数,MongoDB会为文档分配一个唯一的ObjectId
# 指定_id参数

> db.user.insert({"_id":"20180120","name":"houzi","age":"500"})
  • MongoDB的每一行都是采用K-V的方式存储的,对于Value,可能是个字符串,也可能是一个数组,又可能是一个内嵌的json对象
# 不指定_id参数

> var single = {"name":"rulai","password":"123456","age":18,"address":{"province":"guangdong","city":"guangzhou"},"favourite":["apple","banana"]}
> db.user.insert(single)
WriteResult({ "nInserted" : 1 })
2) find操作
  • db.集合名称.find({条件文档})查询所有符合条件的记录
  • db.集合名称.findOne({条件文档})查询,只返回第一个
  • db.集合名称.find({条件文档}).pretty()将结果格式化
  1. $gt(>的意思)、$gte(>=的意思)、$lt(<的意思)、$lte(<=的意思)、$ne(!=的意思)、无关键字=的意思)
# 相当于MySQL里的 >

> db.user.find({"age":{$gt:15}})
# 相当于MySQL里的 >=

> db.user.find({"age":{$gte:15}})
# 相当于MySQL里的 < 

> db.user.find({"age":{$lt:20}})
# 相当于MySQL里的 <=

> db.user.find({"age":{$lte:20}})
# 相当于MySQL里的 !=

> db.user.find({"age":{$ne:15}})
# 相当于MySQL里的 =

> db.user.find({"age":18})
  1. 无关键字and的意思)$or(or的意思)、$in(in的意思)、$nin(notin的意思)
# 相当于MySQL里的and

> db.user.find({"name":"rulai", "age":18})
# 相当于MySQL里的or

> db.user.find({$or:[{"address.province":"guangdong"},{"address.province":"fujian"}]})
# 相当于MySQL里的in

> db.user.find({"address.province":{$in:["guangdong","fujian"]}})
# 相当于MySQL里的notin

> db.user.find({"address.province":{$nin:["guangdong","fujian"]}})
  1. 应用正则表达式匹配内容
# 匹配以 r 开头,以 i 结尾的 name 字段数据

> db.user.find({"name":/^r/, "name":/i$/})
  • 应用$where条件查找,Value支持匿名函数
> db.user.find({$where:function(){return this.name == "rulai"}})
  1. limitskip的使用
  • 格式:db.集合名称.find({条件文档}).limit(n) 获取符合条件的n条数据
  • 格式:db.集合名称.find({条件文档}).limit(n).skip(m) 获取符合条件,跳过m条数据后的n条数据
  1. sort排序
  • 格式:db.集合名称.find().sort(字段:1,...)
  • 参数说明
  • 字段值为1,升序排序
  • 字段值为-1,降序排序
  1. count统计查询结果的文档数
  • 格式db.集合名称.find({条件文档}).count()
  1. 返回指定字段结果集
  • 格式:db.集合名称.find({条件文档},{字段:1,字段:0})
  • 参数说明
  • 设置为1,表示需要被返回
  • 设置成0,表示不需要被返回
  • _id默认是为1,其他字段默认是为0
3) update操作
  • 格式:db.集合名称.update(
    {query},{update},{multi:boolean}
    )
  • 参数说明
  • 参数query:查询条件,类似SQL语句update中的where部分
  • 参数update:更新的内容
  • 参数multi:默认是false,表示只更新找到第一条记录,值为true表示把满足条件的文档全部更新
  • 整体更新
# 符合条件搜索出来的都更新

> var upd = db.user.findOne({"name":"rulai"})
> upd.age = 30
> db.user.update({"name":"rulai"}, upd)

# 也可以写成下面这个样子
> db.user.update({"name":"rulai"},{"age":30},{multi:true})
  • 局部更新
  • $inc修改器,increase的缩写,在原有的数值基础上修改,比如原先30岁,修改30,数值就变成60岁了
> db.user.update({"name":"rulai"},{$inc:{"age":30}})
  • $set修改器,比如原先60岁,修改10,数值就变成10岁了
> db.user.update({"name":"rulai"},{$set:{"age":10}})
4) upsert操作
  • 如果查到这条数据,就update,如果没有查到,那么就在数据库新增一条数据
> db.user.update({"name":"fozu"},{$set:{"age":25}},true)
5) save操作
  • 格式:db.集合名称.save(document)
  • 如果文档的_id已存在,则修改;如果文档的_id不存在,则添加
6) remove操作
  • db.表名.remove({})删除表所有数据
> db.user.remove({})
  • db.表名.remove({条件})删除表符合条件的数据
> db.user.remove({"name":"fozu"})

9. MongoDB备份与恢复

1)备份:
  • 格式:mongodump -h 数据库主机地址 -d 数据库名 -o 路径
  • 参数说明:
  • -h 数据库主机地址
  • -d 需要备份的数据库名称
  • -o 备份的数据库存放位置,此目录中存放着备份出来的数据
  • 备份的命令执行是在shell终端,而不是在MongoDB数据库里
> mongodump -h 127.0.0.1 -d demo -o ./
2)恢复
  • 格式:mongorestore -h dbhost -d dbname --dir dbdirectory
  • 参数说明
  • -h 服务器地址,如果不是恢复到本地主机,可以用IP:端口
  • -d 数据恢复到哪个数据库名称
  • --dir 备份数据库存放的位置
> mongorestore -h 127.0.0.1:27017 -d backup --dir ./demo

10. MongoDBpython交互

1) Linux下安装PyCharm软件
  1. PyCharm官网http://www.jetbrains.com/pycharm/download/点击下载LinuxPyCharm
  2. 解压文件后进入bin目录,右键选择在终端中打开
  3. ./pycharm.sh运行安装
2) pymongo模块介绍
  • 要想在Python中使用MongoDB数据库,必须要安装pymongo模块
  • 安装pymongo模块:pip3 install pymongo
  • 导入模块:from pymongo import *import pymongo
  • pymongo提供四大对象与MongoDB交互
  • MongoClient对象:与MongoDB建立连接
# coding = utf-8
from pymongo import *

# 创建MongoClient连接
# client = MongoClient('主机IP', 端口)
client = MongoClient('192.168.220.131', 27017)

print(client)
# 提示下面信息,说明连接成功

/usr/bin/python3.5 /home/rulai/python/demo.py
MongoClient(host=['192.168.220.131:27017'], document_class=dict, tz_aware=False, connect=True)

Process finished with exit code 0
  • Database对象:MongoDB中的数据库
# 创建Database
# db = client.数据库名称
db = client.mytest
  • Collection对象:MongoDB中的集合
# 创建Collection文档对象
# col = db.集合名称
col = db.集合名称
  • 文档对象方法:
  1. insert_one:插入一条文档对象
  2. insert_many:插入多条文档对象
  3. find_one:查找一条文档对象
  4. find:查找多条文档对象
  5. update_one:更新一条文档对象
  6. update_many:更新多条文档对象
  7. delete_one:删除一条文档对象
  8. delete_many:删除多条文档对象
  9. Cursor对象:当调用集合对象的find()方法时,会返回Cursor对象
  • Cursor对象:查询方法find()返回的对象,用于进行多行数据的遍历
3) 插入文档数据
  • insert_one:插入一条文档对象,接收一个字典作为参数
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    col.insert_one({'name': 'rulai', 'age': 18, 'sex': 'male'})

except Exception as e:
    print(e)
  • insert_many:插入多条文档对象,接收一个列表作为参数,列表里面多个字典
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    col.insert_many([{'name': 'fozu', 'age': 25, 'sex': 'male'},
                     {'name': 'guanyin', 'age': 15, 'sex': 'female'}])

except Exception as e:
    print(e)
4) 更新文档数据
  • update_one:更新符合条件的第一条文档对象
update_one({条件},{更新内容})
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    col.update_one({'name':'fozu'},{'$set':{'age':100}})

except Exception as e:
    print(e)
  • update_many:更新多条文档对象
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    col.update_many({'name':'fozu'},{'$set':{'age':120}})

except Exception as e:
    print(e)
5) 删除文档数据
  • delete_one 删除满足条件的第一条文档
delete_one({条件})
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    col.delete_one({'name':'fozu'})

except Exception as e:
    print(e)
  • delete_many 删除满足条件的多条文档
delete_many({条件})
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    col.delete_many({'name':'guanyin'})

except Exception as e:
    print(e)
6) 查询文档数据
  • find_one 返回满足条件的文档集第第一条数据,类型为字典
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    res = col.find_one({'name':'rulai'})

    print(res)

except Exception as e:
    print(e)
  • find 返回满足条件的所有文档,类型为Cursor对象,可以使用for…in遍历,每项为字典对象
# coding = utf-8
from pymongo import *

try:
    client = MongoClient('192.168.220.131', 27017)

    db = client.mytest

    col = db.user

    res = col.find({'age': {'$gte': 100}})

    for i in res:
        print(i)

except Exception as e:
    print(e)