版权声明:本文为博主原创文章,未经博主允许不得转载。 https://cloud.tencent.com/developer/article/1433210
目录
一、控制访问权限
1. 添加admin用户
2. 启用身份认证
3. 在mongo控制台中执行身份验证
5. 修改用户凭据
6. 添加只读用户
7. 删除用户
二、备份与还原
1. mongodump的各种备份方式
2. mongodump示例
3. 自动备份脚本
4. mongorestore的各种还原方式
5. mongorestore示例
三、导入与导出
1. mongoimport的各种导入方式
2. mongoimport示例
3. mongoexport的各种导出方式
4. mongoexport示例
MongoDB和SQL数据库之间的主要区别是:
MongoDB支持简单的基于角色的认证系统,其中包含预定义的系统角色和用户定义的定制角色,通过该系统可以控制用户对数据库的访问及他们被授予的访问级别。大多数修改配置数据或者对结果进行大幅调整的MongoDB服务器命令都被限制在专门的admin数据库中执行,该数据库将在每个新的MongoDB安装时自动创建。
默认情况下,MongoDB不使用任何认证方式。任何可以访问网络的人都可以连接到服务器并执行命令。不过,可以在任何数据库中添加用户,这样就可以对MongoDB进行配置,使得在访问数据库时要求进行服务器验证。
MongoDB支持对每个数据库的访问进行单独控制,访问控制信息被存储在特有的system.users集合中。对于希望访问两个数据库(例如db1和db2)的普通用户,他们的凭据和权限必须被同时添加到两个数据库中。
如果在不同数据库为同一用户分别创建了登录和访问权限,这些记录不会互相同步。换句话说,修改一个数据库中的用户密码不会影响另一个数据库中的用户密码。该规则有一个例外:任何添加到admin数据库中的用户,在所有数据库中都拥有相同的访问权限,不需要为这样的用户单独赋予权限。
> use admin;
switched to db admin
> db.createUser({user : "admin", pwd : "pass", roles: [ { role : "readWrite", db : "admin"
... }, { role: "userAdminAnyDatabase", db : "admin" } ] });
Successfully added user: {
"user" : "admin",
"roles" : [
{
"role" : "readWrite",
"db" : "admin"
},
{
"role" : "userAdminAnyDatabase",
"db" : "admin"
}
]
}
> db.system.users.findOne({user:"admin"})
{
"_id" : "admin.admin",
"user" : "admin",
"db" : "admin",
"credentials" : {
"SCRAM-SHA-1" : {
"iterationCount" : 10000,
"salt" : "kLpduUuLPNHh5Z8RjuhPnw==",
"storedKey" : "PKPFi5NDRmvDZj88cdSz1ZM+Ffk=",
"serverKey" : "6r0EKeHkjp9pymkLJeLD0+krutY="
},
"SCRAM-SHA-256" : {
"iterationCount" : 15000,
"salt" : "BkiI7zbBQJ0b4LghbuGE0YxmvlbYNX0HryoN/w==",
"storedKey" : "sgNs3puWRadYmxXjfSgoEzlxj1oOwB/Y5RdFQ2HTx5c=",
"serverKey" : "+OLxG/kecq4zoWcOduouoLC1YFhQZ86wS/oMz1EXZ0o="
}
},
"roles" : [
{
"role" : "readWrite",
"db" : "admin"
},
{
"role" : "userAdminAnyDatabase",
"db" : "admin"
}
]
}
>
可以用以下两种方式启用身份认证:
[mongodb@hdp4~]$mongo
MongoDB shell version v4.0.2
connecting to: mongodb://127.0.0.1:27017
MongoDB server version: 4.0.2
> use admin
switched to db admin
> show collections;
Warning: unable to run listCollections, attempting to approximate collection names by parsing connectionStatus
> db.auth("admin","pass");
1
> show collections;
> db.getUsers();
[
{
"_id" : "admin.admin",
"user" : "admin",
"db" : "admin",
"roles" : [
{
"role" : "readWrite",
"db" : "admin"
},
{
"role" : "userAdminAnyDatabase",
"db" : "admin"
}
],
"mechanisms" : [
"SCRAM-SHA-1",
"SCRAM-SHA-256"
]
}
]
>
如果使用admin凭证访问admin之外的数据库,那么必须首先针对admin数据库进行认证,否则无法访问系统中的任何其它数据库。
[mongodb@hdp4~]$mongo
MongoDB shell version v4.0.2
connecting to: mongodb://127.0.0.1:27017
MongoDB server version: 4.0.2
> use test
switched to db test
> show collections;
Warning: unable to run listCollections, attempting to approximate collection names by parsing connectionStatus
> db.auth("admin","pass");
Error: Authentication failed.
0
> use admin
switched to db admin
> db.auth("admin","pass");
1
> use test;
switched to db test
> show collections;
products
>
[mongodb@hdp4~]$mongo admin
MongoDB shell version v4.0.2
connecting to: mongodb://127.0.0.1:27017/admin
MongoDB server version: 4.0.2
> db.auth("admin", "pass");
1
> use test;
switched to db test
> db.createUser({user : "foo", pwd : "foo" , roles: [ { role : "read", db : "test" } ] } );
Successfully added user: {
"user" : "foo",
"roles" : [
{
"role" : "read",
"db" : "test"
}
]
}
> db.getUsers();
[
{
"_id" : "test.foo",
"user" : "foo",
"db" : "test",
"roles" : [
{
"role" : "read",
"db" : "test"
}
],
"mechanisms" : [
"SCRAM-SHA-1",
"SCRAM-SHA-256"
]
}
]
> db.updateUser( "foo", {pwd : "pass", roles: [ { role : "dbAdmin", db : "test" } ] });
> db.getUsers();
[
{
"_id" : "test.foo",
"user" : "foo",
"db" : "test",
"roles" : [
{
"role" : "dbAdmin",
"db" : "test"
}
],
"mechanisms" : [
"SCRAM-SHA-1",
"SCRAM-SHA-256"
]
}
]
> db.auth("foo", "foo");
Error: Authentication failed.
0
> db.auth("foo", "pass");
1
>
[mongodb@hdp4~]$mongo admin
MongoDB shell version v4.0.2
connecting to: mongodb://127.0.0.1:27017/admin
MongoDB server version: 4.0.2
> db.auth("admin", "pass");
1
> use test;
switched to db test
> db.createUser({user : "shadycharacter", pwd : "shadypassword" , roles: [ { role : "read", db : "test" } ] } );
Successfully added user: {
"user" : "shadycharacter",
"roles" : [
{
"role" : "read",
"db" : "test"
}
]
}
> db.auth("shadycharacter", "shadypassword");
1
> db.products.findOne();
2018-10-10T16:05:26.084+0800 E QUERY [js] Error: error: {
"ok" : 0,
"errmsg" : "too many users are authenticated",
"code" : 13,
"codeName" : "Unauthorized"
} :
_getErrorWithCode@src/mongo/shell/utils.js:25:13
DBCommandCursor@src/mongo/shell/query.js:708:1
DBQuery.prototype._exec@src/mongo/shell/query.js:113:28
DBQuery.prototype.hasNext@src/mongo/shell/query.js:288:5
DBCollection.prototype.findOne@src/mongo/shell/collection.js:254:10
@(shell):1:1
> exit
bye
[mongodb@hdp4~]$mongo test
MongoDB shell version v4.0.2
connecting to: mongodb://127.0.0.1:27017/test
MongoDB server version: 4.0.2
> db.auth("shadycharacter", "shadypassword");
1
> db.products.findOne();
{ "_id" : 20, "item" : "large box", "qty" : 20 }
> db.products.insertOne( { _id: 100, item: "large box", qty: 20 } );
2018-10-10T16:05:59.808+0800 E QUERY [js] WriteCommandError: not authorized on test to execute command { insert: "products", ordered: true, lsid: { id: UUID("679644a1-2281-406e-85b1-986948ee04b4") }, $db: "test" } :
WriteCommandError({
"ok" : 0,
"errmsg" : "not authorized on test to execute command { insert: \"products\", ordered: true, lsid: { id: UUID(\"679644a1-2281-406e-85b1-986948ee04b4\") }, $db: \"test\" }",
"code" : 13,
"codeName" : "Unauthorized"
})
WriteCommandError@src/mongo/shell/bulk_api.js:420:48
Bulk/executeBatch@src/mongo/shell/bulk_api.js:902:1
Bulk/this.execute@src/mongo/shell/bulk_api.js:1150:21
DBCollection.prototype.insertOne@src/mongo/shell/crud_api.js:252:9
@(shell):1:1
>
[mongodb@hdp4~]$mongo admin
MongoDB shell version v4.0.2
connecting to: mongodb://127.0.0.1:27017/admin
MongoDB server version: 4.0.2
> db.auth("admin","pass");
1
> use test;
switched to db test
> db.dropUser("shadycharacter");
true
> db.getUsers();
[
{
"_id" : "test.foo",
"user" : "foo",
"db" : "test",
"roles" : [
{
"role" : "dbAdmin",
"db" : "test"
}
],
"mechanisms" : [
"SCRAM-SHA-1",
"SCRAM-SHA-256"
]
}
]
>
# 无账号、密码
mongodump -o backup #备份所有数据库到backup目录下,每个数据库一个文件,除local数据库外。
mongodump -d abc -o backup #备份abc数据库到backup目录下。
mongodump -d abc -c ddd -o backup #备份abc数据库下的ddd集合。
#有账号、密码
mongodump -udba -pdba -d abc -c ddd -o backup #备份abc数据库下的ddd集合。
mongodump --host=127.0.0.1 --port=27017 -udba -p --db=abc --collection=ddd -o backup
这里需要注意的是:在认证备份中,比如在abc数据库中,需要其有dba这个账号才可以执行备份,要是abc数据库里没有账号,那么需要在admin上认证,再执行需要加:authenticationDatabase参数指定保存用户凭证的数据库,没有指定则去-d指定的数据库认证。最好还是设置专本备份的账号。
mongodump -udba -pdba -d abc --authenticationDatabase admin -o backup #在admin数据库下认证之后再去备份abc数据库。
备份test库:
[mongodb@hdp4~]$mongodump -u wxy --authenticationDatabase admin -d test -o ./dump
Enter password:
2018-10-10T10:05:25.831+0800 writing test.products to
2018-10-10T10:05:25.903+0800 done dumping test.products (3 documents)
[mongodb@hdp4~]$
命令执行后生成./dump/test目录和相关文件:
[mongodb@hdp4~]$ll ./dump/test
total 8
-rw-rw-r-- 1 mongodb mongodb 154 Oct 10 10:05 products.bson
-rw-rw-r-- 1 mongodb mongodb 127 Oct 10 10:05 products.metadata.json
[mongodb@hdp4~]$
products是集合名称。.bson文件存储集合数据,该文件只是MongoDB内部存储的BSON格式文件的一个副本。.json文件存储元数据,包括集合的索引及其定义。mongodump工具在写入备份文件之前不会清空输出目录中的内容,而只是覆盖同名文件。除非希望覆盖备份中的数据,否则应该在使用mongodump之前保证清空目标目录。
#!/bin/bash
##########################################
# Edit these to define source and destinations
MONGO_DBS=""
BACKUP_TMP=~/tmp
BACKUP_DEST=~/backups
MONGODUMP_BIN=/home/mongodb/mongodb-4.0.2/bin/mongodump
TAR_BIN=/usr/bin/tar
##########################################
BACKUPFILE_DATE=`date +%Y%m%d-%H%M`
# _do_store_archive <Database> <Dump_dir> <Dest_Dir> <Dest_file>
function _do_store_archive {
mkdir -p $3
cd $2
tar -cvzf $3/$4 dump
}
# _do_backup <Database name>
function _do_backup {
UNIQ_DIR="$BACKUP_TMP/$1"`date "+%s"`
mkdir -p $UNIQ_DIR/dump
echo "dumping Mongo Database $1"
if [ "all" = "$1" ]; then
$MONGODUMP_BIN -o $UNIQ_DIR/dump -u wxy --authenticationDatabase admin
else
$MONGODUMP_BIN -d $1 -o $UNIQ_DIR/dump -u wxy --authenticationDatabase admin
fi
KEY="database-$BACKUPFILE_DATE.tgz"
echo "Archiving Mongo database to $BACKUP_DEST/$1/$KEY"
DEST_DIR=$BACKUP_DEST/$1
_do_store_archive $1 $UNIQ_DIR $DEST_DIR $KEY
rm -rf $UNIQ_DIR
}
# check to see if individual databases have been specified, otherwise backup the whole server to "all"
if [ "" = "$MONGO_DBS" ]; then
MONGO_DB="all"
_do_backup $MONGO_DB
else
for MONGO_DB in $MONGO_DBS; do
_do_backup $MONGO_DB
done
fi
mongorestore -udba -pdba -d abc backup/abc #还原abc数据库。
mongorestore -udba -pdba -d abc --drop backup/abc #还原之前先删除原来数据库(集合)。
mongorestore -udba -pdba -d abc -c ddd --drop backup/abc/ddd.bson #还原abc库中的ddd集合。
mongorestore --host=127.0.0.1 --port=27017 -udba -pdba -d abc -c test --drop backup/abc/test.bson #还原abc库中的test集合。
mongorestore --host=127.0.0.1 --port=27017 -udba -pdba -d abc -c ooo --drop backup/abc/test.bson #还原abc库中的test集合到ooo集合。
恢复整个备份:
[mongodb@hdp4~]$mongorestore --drop -u wxy --authenticationDatabase admin ./dump
Enter password:
2018-10-10T10:06:11.239+0800 preparing collections to restore from
2018-10-10T10:06:11.381+0800 reading metadata for test.products from dump/test/products.metadata.json
2018-10-10T10:06:11.465+0800 restoring test.products from dump/test/products.bson
2018-10-10T10:06:11.541+0800 no indexes to restore
2018-10-10T10:06:11.541+0800 finished restoring test.products (3 documents)
2018-10-10T10:06:11.541+0800 done
[mongodb@hdp4~]$
恢复单个库:
[mongodb@hdp4~]$mongorestore --drop -u wxy --authenticationDatabase admin -d test ./dump/test/
Enter password:
2018-10-10T10:16:22.666+0800 the --db and --collection args should only be used when restoring from a BSON file. Other uses are deprecated and will not exist in the future; use --nsInclude instead
2018-10-10T10:16:22.666+0800 building a list of collections to restore from dump/test dir
2018-10-10T10:16:22.739+0800 reading metadata for test.products from dump/test/products.metadata.json
2018-10-10T10:16:22.781+0800 restoring test.products from dump/test/products.bson
2018-10-10T10:16:22.818+0800 no indexes to restore
2018-10-10T10:16:22.818+0800 finished restoring test.products (3 documents)
2018-10-10T10:16:22.818+0800 done
[mongodb@hdp4~]$
恢复单个集合:
[mongodb@hdp4~]$mongorestore --drop -u wxy --authenticationDatabase admin -d test -c products ./dump/test/products.bson
Enter password:
2018-10-10T10:17:33.139+0800 checking for collection data in dump/test/products.bson
2018-10-10T10:17:33.287+0800 reading metadata for test.products from dump/test/products.metadata.json
2018-10-10T10:17:33.372+0800 restoring test.products from dump/test/products.bson
2018-10-10T10:17:33.449+0800 no indexes to restore
2018-10-10T10:17:33.449+0800 finished restoring test.products (3 documents)
2018-10-10T10:17:33.449+0800 done
[mongodb@hdp4~]$
mongoimport支持CSV(逗号分隔)、TSV(TAB分隔)、JSON(支持可变模式)三种文件格式的数据。
mongoimport -udba -pdba -dabc -ciii --authenticationDatabase admin backup/ddd.txt #导入到iii集合
mongoimport -udba -pdba -dabc -ceee --type=csv --headerline --authenticationDatabase admin backup/ddd.csv #csv导入,需要指定headerline
mongoimport -udba -pdba -dabc -ceee --type=csv --headerline --ignoreBlanks --drop --authenticationDatabase admin backup/ddd.csv #不导入空字段,指定ignoreBlanks。
[mongodb@hdp4~]$more a.txt
_id,item,qty
20,large box,20
21,small box,55
22,medium box,30
[mongodb@hdp4~]$mongoimport --drop -u wxy --authenticationDatabase admin -d test -c products --type csv --headerline a.txt
Enter password:
2018-10-10T12:44:30.216+0800 connected to: localhost
2018-10-10T12:44:30.287+0800 dropping: test.products
2018-10-10T12:44:30.447+0800 imported 3 documents
[mongodb@hdp4~]$mongo -u wxy --authenticationDatabase admin test --eval "printjson(db.products.find().count())"
MongoDB shell version v4.0.2
Enter password:
connecting to: mongodb://127.0.0.1:27017/test
MongoDB server version: 4.0.2
3
[mongodb@hdp4~]$
mongoexport -udba -pdba -dabc -cddd --authenticationDatabase admin -o backup/ddd.txt # 导出txt文本
mongoexport -udba -pdba -dabc -cddd -f sno,sname --authenticationDatabase admin -o backup/ddd.txt # 指定字段导出txt文本
mongoexport -udba -pdba -dabc -cddd -f sno,sname --csv --authenticationDatabase admin -o backup/ddd.csv # 导出成csv格式的需要指定字段-f
mongoexport -udba -pdba -dabc -cddd -q '{"sno":{"$gte":5}}' -f sno,sname --csv --authenticationDatabase admin -o backup/ddd.csv # 按照-q里的条件导出
> db.products.find();
{ "_id" : 20, "item" : "large box", "qty" : 20 }
{ "_id" : 21, "item" : "small box", "qty" : 55 }
{ "_id" : 22, "item" : "medium box", "qty" : 30 }
>
带条件导出products集合:
[mongodb@hdp4~]$mongoexport -u wxy --authenticationDatabase admin -d test -c products -q '{qty:{$gte:30}}' -f _id,item,qty --type=csv -o a.csv
Enter password:
2018-10-10T13:52:02.762+0800 connected to: localhost
2018-10-10T13:52:02.762+0800 exported 2 records
[mongodb@hdp4~]$more a.csv
_id,item,qty
21,small box,55
22,medium box,30
[mongodb@hdp4~]$