NoSQL MongoDB

21.4 MongoDB介绍


什么是MongoDB

MongoDB也是NoSQL的一种,它是一个基于分布式文件存储的文档型数据库,由C++语言编写。因为是文档型数据库,所以它是非关系数据库中功能最丰富、最像关系数据库的。

官方网站 ,最新版本4.0.1。

MongoDB将数据存储为一个文档,数据结构将键值(key-value)对组成,MongoDB文档类似于JSON对象,字段值可以包含其它文档、数组及文档数组。

了解JSON

  • 基本概念:
文档(document):MongoDB中数据的基本单元,非常类似于关系型数据库系统中的行,但是比行要复杂的多。

集合(collection):一组文档,如果说MongoDB中的文档类似于关系型数据库中的行,那么集合就如同表。

MongoDB的单个计算机可以容纳多个独立的数据库,每一个数据库都有自己的集合和权限;

MongoDB自带简洁但功能强大的JavaScript shell,这个工具对于管理MongoDB实例和操作数据作用非常大;

每一个文档都有一个特殊的键”_id”,它在文档所处的集合中是唯一的,相当于关系数据库中的表的主键。

MongoDB的特点是高性能、易部署、易使用,存储数据非常方便,它的主要特性有:

面向集合存储,易存储对象类型的数据
模式自由
支持动态查询
支持完全索引,包含内部对象
支持复制和故障恢复
使用高效的二进制数据存储,包括大型对象
文件存储格式为BSON(一种JSON的扩展)


MongoDB安装

  • 安装MongoDB:
# cd /etc/yum.repos.d/

# vim mongo.repo

[mongodb-org-3.4]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/$releasever/mongodb-org/3.4/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-3.4.asc

# yum install -y mongodb-org

连接MongoDB

  • 启动服务:
# systemctl start mongod

# ps aux |grep mongod
mongod     1522  0.8  0.9 972380 37512 ?        Sl   10:30   0:00 /usr/bin/mongod -f /etc/mongo.conf

# netstat -lntp |grep mongod
tcp        0      0 127.0.0.1:27017         0.0.0.0:*               LISTEN      1522/mongod  
  • 进入mongodb shell:
# mongo
MongoDB shell version v3.4.16
connecting to: mongodb://127.0.0.1:27017				#显示IP及监听端口
MongoDB server version: 3.4.16
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: 
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] 
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] ** WARNING: Access control is not enabled for the database.
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] **          Read and write access to data and configuration is unrestricted.
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] 
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] 
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] ** WARNING: /sys/kernel/mm/transparent_hugepage/enabled is 'always'.
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] **        We suggest setting it to 'never'
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] 
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] ** WARNING: /sys/kernel/mm/transparent_hugepage/defrag is 'always'.
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] **        We suggest setting it to 'never'				#关于内核的警告,可忽略
2018-08-25T10:30:18.431+0800 I CONTROL  [initandlisten] 
> 

如果监听端口不是默认的27017,则在连接的时候需要加--port选项,如:

mongo --port 27018

远程连接mongodb,需要加--host,如:

mongo --host 127.0.0.1

如果设置了验证,则在连接的时候需要带上用户名和密码,如:

mongo -u用户名 -p密码 --authenticationDatabase 数据库名				#和mysql类似

MongoDB用户管理

  • 管理用户:
> use admin				#use切换库,只有在admin库中才可以操作用户管理
switched to db admin

#创建用户并授权;customData表示对用户的描述,可省略;roles表示角色,指定库的权限
> db.createUser( {
    user: "admin", customData: {
   description: "superuser"}, pwd: "admin123", roles: [ {
    role: "root", db:"admin" } ] } )
Successfully added user: {
   
	"user" : "admin",
	"customData" : {
   
		"description" : "superuser"
	},
	"roles" : [
		{
   
			"role" : "root",
			"db" : "admin"
		}
	]
}
> db.system.users.find()				#列出所有用户,需要切换到admin库
{
    "_id" : "admin.admin", "user" : "admin", "db" : "admin", "credentials" : {
    "SCRAM-SHA-1" : {
    "iterationCount" : 10000, "salt" : "J8r1+mWlE53xnEKSiQ98hA==", "storedKey" : "7dl9ZmLoj8AHTb7LguX/w4C9X9U=", "serverKey" : "ZMpgYfQMxGAULJh9a5rFijPny2E=" } }, "customData" : {
    "description" : "superuser" }, "roles" : [ {
    "role" : "root", "db" : "admin" } ] }
#admin.admin表示admin库的admin用户
> show users				#列出当前库下所有的用户
{
   
	"_id" : "admin.admin",
	"user" : "admin",
	"db" : "admin",
	"customData" : {
   
		"description" : "superuser"
	},
	"roles" : [
		{
   
			"role" : "root",
			"db" : "admin"
		}
	]
}
> db.createUser({
   user:"lzx",pwd:"123123",roles:[{
   role:"read",db:"testdb"}]})				#创建lzx用户,设为read角色,针对的库是testdb
Successfully added user: {
   
	"user" : "lzx",
	"roles" : [
		{
   
			"role" : "read",
			"db" : "testdb"
		}
	]
}

> show users				#查看新创建的用户
{
   
	"_id" : "admin.admin",
	"user" : "admin",
	"db" : "admin",
	"customData" : {
   
		"description" : "superuser"
	},
	"roles" : [
		{
   
			"role" : "root",
			"db" : "admin"
		}
	]
}
{
   
	"_id" : "admin.lzx",
	"user" : "lzx",
	"db" : "admin",
	"roles" : [
		{
   
			"role" : "read",
			"db" : "testdb"
		}
	]
}

> db.dropUser('lzx')				#删除刚创建的lzx用户
true

> show users          
{
   
	"_id" : "admin.admin",
	"user" : "admin",
	"db" : "admin",
	"customData" : {
   
		"description" : "superuser"
	},
	"roles" : [
		{
   
			"role" : "root",
			"db" : "admin"
		}
	]
}				#新创建的用户已经消失

新增用户之后,若要用户生效,还需要编辑启动脚本:

# vim /usr/lib/systemd/system/mongod.service
Environment="OPTIONS=--auth -f /etc/mongod.conf"

# systemctl daemon-reload

# systemctl restart mongod

# ps aux |grep mongod
mongod     8049 17.8  1.0 972380 41420 ?        Sl   14:03   0:02 /usr/bin/mongod --auth -f /etc/mongod.conf

# mongo --host 127.0.0.1 --port 27017
MongoDB shell version v3.4.16
connecting to: mongodb://127.0.0.1:27017/
MongoDB server version: 3.4.16
> use admin
switched to db admin

> show users				#刚刚登录的用户没有权限执行命令
2018-08-25T14:06:39.482+0800 E QUERY    [thread1] Error: not authorized on admin to execute command {
    usersInfo: 1.0 } :
_getErrorWithCode@src/mongo/shell/utils.js:25:13
DB.prototype.getUsers@src/mongo/shell/db.js:1539:1
shellHelper.show@src/mongo/shell/utils.js:771:9
shellHelper@src/mongo/shell/utils.js:678:15
@(shellhelp2):1:1

# mongo --host 127.0.0.1 --port 27017 -u 'admin' -p 'admin123' --authenticationDatabase "admin"				#指定用户密码和库,再次登录
MongoDB shell version v3.4.16
connecting to: mongodb://127.0.0.1:27017/
MongoDB server version: 3.4.16
Server has startup warnings: 
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] 
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] ** WARNING: /sys/kernel/mm/transparent_hugepage/enabled is 'always'.
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] **        We suggest setting it to 'never'
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] 
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] ** WARNING: /sys/kernel/mm/transparent_hugepage/defrag is 'always'.
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] **        We suggest setting it to 'never'
2018-08-25T14:03:27.518+0800 I CONTROL  [initandlisten] 

> use admin
switched to db admin

> show users				#再次执行命令就没问题了
{
   
	"_id" : "admin.admin",
	"user" : "admin",
	"db" : "admin",
	"customData" : {
   
		"description" : "superuser"
	},
	"roles" : [
		{
   
			"role" : "root",
			"db" : "admin"
		}
	]
}
> use db1
switched to db db1

> db.createUser({
   user:"test1",pwd:"123123",roles:[{
   role:"readWrite",db:"db1"},{
   role:"read",db:"db2"}]})				#创建用户test1,对db1库有读写权限,对db2库只读
Successfully added user: {
   
	"user" : "test1",
	"roles" : [
		{
   
			"role" : "readWrite",
			"db" : "db1"
		},
		{
   
			"role" : "read",
			"db" : "db2"
		}
	]
}

use db1,表示用户在db1库中创建,用户的信息会跟随数据库

> db.auth('test1','123123')				#在命令行认证用户
1				#返回1说明认证成功

> use db2
switched to db db2

> db.auth('test1','123123')
Error: Authentication failed.
0				#db2下认证失败

MongoDB中有这些角色:

read:允许用户读取指定数据库

readWrite:允许用户读写指定数据库

dbAdmin:允许用户在指定数据库中执行管理函数,如索引创建、删除,查看统计或访问system.profile

userAdmin:允许用户向system.users集合写入,可以在指定数据库里创建、删除和管理用户

clusterAdmin:只在admin数据中可用,赋予用户所有分片和复制集相关函数的管理权限

readAnyDatabase:只在admin数据库中可用,赋予用户所有数据库的读权限

readWriteAnyDatabase:只在admin数据库中可用,赋予用户所有数据库的读写权限

userAdminAnyDatabase:只在admin数据库中可用,赋予所有数据库的userAdmin权限

dbAdminAnyDatabase:只在admin数据库中可用,赋予所有数据库的dbAdmin权限

root:只在admin数据库中可用。超级账号,超级权限

MongoDB创建集合、数据管理

> use db1
switched to db db1

> db.createCollection("mycol",{
   capped:true,size:6142800,max:10000})
{
    "ok" : 1 }

创建集合;集合名为mycol;option可选,用来配置集合的参数。
capped true/false (可选),如果为true,则启用封顶集合。封顶集合是固定大小的集合,当它达到最大大小,会自动覆盖最早的条目。如果指定为true,也需要指定尺寸参数;
size(可选),指定最大大小字节封顶集合。如果capped是true,那么就必须指定这个字段,单位B;
max(可选),指定封顶集合允许在文件的最大数量。

> show tables				#查看集合
mycol

> show collections				#这样也可以查看集合
mycol
> db.Account.insert({
   AccountID:1,UserName:"123",password:"123456"})				#向集合中插入数据,若集合不存在,则自动创建
WriteResult({
    "nInserted" : 1 })

> show collections
Account
mycol
> db.Account.insert({
   AccountID:2,UserName:"aaa",password:"aaaaaa"})				#再插入一个文档
WriteResult({
    "nInserted" : 1 })

> show collections
Account				#仍属于Account集合     
mycol

> db.Account.update({
   AccountID:1},{
   "$set":{
   "Age":20}})				#更新集合中AccountID:1文档的数据
WriteResult({
    "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })

> db.Account.find()				#查看所有文档
{
    "_id" : ObjectId("5b80feb826e56a836ac4d168"), "AccountID" : 1, "UserName" : "123", "password" : "123456", "Age" : 20 }
{
    "_id" : ObjectId("5b8100cc26e56a836ac4d169"), "AccountID" : 2, "UserName" : "aaa", "password" : "aaaaaa" }
> db.Account.find({
   AccountID:1})				#指定条件查询
{
    "_id" : ObjectId("5b80feb826e56a836ac4d168"), "AccountID" : 1, "UserName" : "123", "password" : "123456", "Age" : 20 }
> db.Account.remove({
   AccountID:1})
WriteResult({
    "nRemoved" : 1 })				#指定条件删除文档

> db.Account.find()
{
    "_id" : ObjectId("5b8100cc26e56a836ac4d169"), "AccountID" : 2, "UserName" : "aaa", "password" : "aaaaaa" }
> db.Account.drop()				#删除集合Account中所有文档,即删除集合
true

> show collections
mycol

> db.mycol.drop()
true

> show collections
> db.col123.insert({
   AccountID:1,UserName:"123",password:"123456"})
WriteResult({
    "nInserted" : 1 })

> db.printCollectionStats()				#查看所有集合状态
col123
{
   
	"ns" : "db1.col123",
	"size" : 80,
	"count" : 1,
	"avgObjSize" : 80,
	"storageSize" : 16384,
	"capped" : false,
	"wiredTiger" : {
   
		"metadata" : {
   
			"formatVersion" : 1
		},
		"creationString" : "access_pattern_hint=none,allocation_size=4KB,app_metadata=(formatVersion=1),block_allocation=best,block_compressor=snappy,cache_resident=false,checksum=on,colgroups=,collator=,columns=,dictionary=0,encryption=(keyid=,name=),exclusive=false,extractor=,format=btree,huffman_key=,huffman_value=,ignore_in_memory_cache_size=false,immutable=false,internal_item_max=0,internal_key_max=0,internal_key_truncate=true,internal_page_max=4KB,key_format=q,key_gap=10,leaf_item_max=0,leaf_key_max=0,leaf_page_max=32KB,leaf_value_max=64MB,log=(enabled=true),lsm=(auto_throttle=true,bloom=true,bloom_bit_count=16,bloom_config=,bloom_hash_count=8,bloom_oldest=false,chunk_count_limit=0,chunk_max=5GB,chunk_size=10MB,merge_max=15,merge_min=0),memory_page_max=10m,os_cache_dirty_max=0,os_cache_max=0,prefix_compression=false,prefix_compression_min=4,source=,split_deepen_min_child=0,split_deepen_per_child=0,split_pct=90,type=file,value_format=u",
		"type" : "file",
		"uri" : "statistics:table:collection-4-6088379814182883756",
		"LSM" : {
   
			"bloom filter false positives" : 0,
			"bloom filter hits" : 0,
			"bloom filter misses" : 0,
			"bloom filter pages evicted from cache" : 0,
			"bloom filter pages read into cache" : 0,
			"bloom filters in the LSM tree" : 0,
			"chunks in the LSM tree" : 0,
			"highest merge generation in the LSM tree" : 0,
			"queries that could have benefited from a Bloom filter that did not exist" : 0,
			"sleep for LSM checkpoint throttle" : 0,
			"sleep for LSM merge throttle" : 0,
			"total size of bloom filters" : 0
		},
		"block-manager" : {
   
			"allocations requiring file extension" : 3,
			"blocks allocated" : 3,
			"blocks freed" : 0,
			"checkpoint size" : 4096,
			"file allocation unit size" : 4096,
			"file bytes available for reuse" : 0,
			"file magic number" : 120897,
			"file major version number" : 1,
			"file size in bytes" : 16384,
			"minor version number" : 0
		},
		"btree" : {
   
			"btree checkpoint generation" : 22,
			"column-store fixed-size leaf pages" : 0,
			"column-store internal pages" : 0,
			"column-store variable-size RLE encoded values" : 0,
			"column-store variable-size deleted values" : 0,
			"column-store variable-size leaf pages" : 0,
			"fixed-record size" : 0,
			"maximum internal page key size" : 368,
			"maximum internal page size" : 4096,
			"maximum leaf page key size" : 2867,
			"maximum leaf page size" : 32768,
			"maximum leaf page value size" : 67108864,
			"maximum tree depth" : 3,
			"number of key/value pairs" : 0,
			"overflow pages" : 0,
			"pages rewritten by compaction" : 0,
			"row-store internal pages" : 0,
			"row-store leaf pages" : 0
		},
		"cache" : {
   
			"bytes currently in the cache" : 952,
			"bytes read into cache" : 0,
			"bytes written from cache" : 175,
			"checkpoint blocked page eviction" : 0,
			"data source pages selected for eviction unable to be evicted" : 0,
			"hazard pointer blocked page eviction" : 0,
			"in-memory page passed criteria to be split" : 0,
			"in-memory page splits" : 0,
			"internal pages evicted" : 0,
			"internal pages split during eviction" : 0,
			"leaf pages split during eviction" : 0,
			"modified pages evicted" : 0,
			"overflow pages read into cache" : 0,
			"overflow values cached in memory" : 0,
			"page split during eviction deepened the tree" : 0,
			"page written requiring lookaside records" : 0,
			"pages read into cache" : 0,
			"pages read into cache requiring lookaside entries" : 0,
			"pages requested from the cache" : 1,
			"pages written from cache" : 2,
			"pages written requiring in-memory restoration" : 0,
			"tracked dirty bytes in the cache" : 0,
			"unmodified pages evicted" : 0
		},
		"cache_walk" : {
   
			"Average difference between current eviction generation when the page was last considered" : 0,
			"Average on-disk page image size seen" : 0,
			"Clean pages currently in cache" : 0,
			"Current eviction generation" : 0,
			"Dirty pages currently in cache" : 0,
			"Entries in the root page" : 0,
			"Internal pages currently in cache" : 0,
			"Leaf pages currently in cache" : 0,
			"Maximum difference between current eviction generation when the page was last considered" : 0,
			"Maximum page size seen" : 0,
			"Minimum on-disk page image size seen" : 0,
			"On-disk page image sizes smaller than a single allocation unit" : 0,
			"Pages created in memory and never written" : 0,
			"Pages currently queued for eviction" : 0,
			"Pages that could not be queued for eviction" : 0,
			"Refs skipped during cache traversal" : 0,
			"Size of the root page" : 0,
			"Total number of pages currently in cache" : 0
		},
		"compression" : {
   
			"compressed pages read" : 0,
			"compressed pages written" : 0,
			"page written failed to compress" : 0,
			"page written was too small to compress" : 2,
			"raw compression call failed, additional data available" : 0,
			"raw compression call failed, no additional data available" : 0,
			"raw compression call succeeded" : 0
		},
		"cursor" : {
   
			"bulk-loaded cursor-insert calls" : 0,
			"create calls" : 1,
			"cursor-insert key and value bytes inserted" : 81,
			"cursor-remove key bytes removed" : 0,
			"cursor-update value bytes updated" : 0,
			"insert calls" : 1,
			"next calls" : 0,
			"prev calls" : 1,
			"remove calls" : 0,
			"reset calls" : 2,
			"restarted searches" : 0,
			"search calls" : 0,
			"search near calls" : 0,
			"truncate calls" : 0,
			"update calls" : 0
		},
		"reconciliation" : {
   
			"dictionary matches" : 0,
			"fast-path pages deleted" : 0,
			"internal page key bytes discarded using suffix compression" : 0,
			"internal page multi-block writes" : 0,
			"internal-page overflow keys" : 0,
			"leaf page key bytes discarded using prefix compression" : 0,
			"leaf page multi-block writes" : 0,
			"leaf-page overflow keys"
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值