1.数据库概述及环境搭建

1.1 为什么要使用数据库

  • 动态网站中的数据都是存储在数据库中的
  • 数据库可以用来持久存储客户端通过表单收集的用户信息
  • 数据库软件本身可以对数据进行高效的管理

1.2 什么是数据库
数据库是用于存储数据的仓库,可以将数据进行有序的分门别类的存储。它是独立于语言之外的软件,可以通过API去操作它。
常见的数据库软件有:mysql、mongoDB、oracle。

1.3 MongoDB数据库下载安装

下载地址:MongoDB 数据库下载地址

mongodb数据库中用户和订单的关系 mongodb数据库购买_数据库


选择适合自己电脑的版本,然后点击douwnload下载,我是复制下载链接用IDM下载的,速度还挺快的

顺便在这里把MongoDB可视化软件compass下载了

mongodb数据库中用户和订单的关系 mongodb数据库购买_node.js_02


同样选择合适的版本download

mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb数据库中用户和订单的关系_03


安装的时候,如果版本下载正确,顺利的话一直next就好了,最后面的时候,如果你已经提前下载好可视化软件,这里要把勾勾去掉,否则它会自动去帮你下载compass软件

mongodb数据库中用户和订单的关系 mongodb数据库购买_node.js_04


安装好后,直接运行compass可视化软件,等待一会软件自己安装完成

安装好后如下图,学习用,这里数据不用做任何修改

mongodb数据库中用户和订单的关系 mongodb数据库购买_javascript_05


一开始我是自己去官网下载的安装包,安装出错,查了电脑版本信息,感觉自己没有选错版本,不知道为啥一运行就报错,错误信息:安装MongoDB 提示is only support on windown 10 or windowns 2016 later,懵!

我的电脑信息如下图:

mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb数据库中用户和订单的关系_06


后来用黑马提供的安装包就没问题,如果有大佬知道原由还望提点一下,谢谢啦~

mongodb数据库中用户和订单的关系 mongodb数据库购买_数据库_07

1.4 Mongoose第三方包

  • 使用Node.js操作MongoDB数据库需要依赖Node.js第三方包mongoose
  • 使用npm install mongoose命令下载
npm install mongoose

1.5 启动MongoDB和连接数据库
选择管理员身份运行PowerShell,在命令行工具中运行net start mongodb即可启动MongoDB,否则MongoDB将无法连接。

net start mongodba 启动服务

net start mongodb

net stop mongodb 停止服务

net stop mongodb

使用mongoose提供的connect方法即可连接数据库。
文件名称01test.js,代码如下:
数据库名称为playground

//引入mongoose第三方模块,用于操作数据库
const mongoose = require('mongoose');
//创建连接
mongoose.connect('mongodb://localhost/playground')
        .then(() => {
            console.log('数据库链接成功');
        })
        .catch(err => {
            console.log(err,'数据库链接失败');
        });

注意:在MongoDB中不需要显式创建数据库,如果正在使用的数据库不存在,MongoDB会自动创建。

用node 01test.js命令运行后,虽然提示连接成功,但是还有其他信息

mongodb数据库中用户和订单的关系 mongodb数据库购买_数据库_08


大概意思说:(节点:16396)DeprecationWarning:当前的URL字符串分析器已弃用,将在将来的版本中删除。要使用新的解析器,请将选项{useNewUrlParser:true}传递给MongoClient.connect连接.

(节点:16396)DeprecationWarning:当前服务器发现和监视引擎已弃用,将在将来的版本中删除。要使用新的服务器发现和监视引擎,请将选项{useUnifiedTopology:true}传递给MongoClient构造函数。

按照提示改一下代码再运行就OK了

//引入mongoose第三方模块,用于操作数据库
const mongoose = require('mongoose');
//connect方法创建连接
mongoose.connect('mongodb://localhost/playground',{useUnifiedTopology: true,  useNewUrlParser: true  })
        .then(() => {
            console.log('数据库链接成功');
        })
        .catch(err => {
            console.log(err,'数据库链接失败');
        });

2. MongoDB增删改查操作

2.1 创建集合
创建集合分为两步,一是对对集合设定规则,二是创建集合,创建mongoose.Schema构造函数的实例即可创建集合。

集合规则:我理解为创建表的列(字段),说明每一列的名称和数据类型
集合:就相当于SQL数据库的表

// Schema设定集合规则
 const courseSchema = new mongoose.Schema({
     name: String,
     author: String,
     isPublished: Boolean
 });
  // model方法创建集合并应用规则,生成构造函数
  //第一个参数:Course为集合名称,第二个参数:courseSchema使用的集合规则
 const Course = mongoose.model('Course', courseSchema); // courses

注意:集合名称首字母一定要大写

2.2 创建文档
创建文档实际上就是向集合中插入数据,也就是相当于往表中插入数据。

方法一:
① 创建集合实例。
② 调用实例对象下的save方法将数据保存到数据库中。

// 创建集合实例
new Course({
    name:'mongoose 教程',
    author:'黑马讲师',
    isPublish:true
}) 
//将集合(表)插入到数据库中
.save();

保存文件运行,再到compass视图软件,可以发现已经成功插入一条数据了

mongodb数据库中用户和订单的关系 mongodb数据库购买_javascript_09


方法二

create方法,集合构造函数下有一个create方法,用于向集合中插入文档

//1.第一个参数为要插入的对象,第二个参数为回调函数
Course.create({name: 'JavaScript基础', author: '黑马讲师', isPublish: true}, (err, doc) => { 
     //  错误对象
    console.log(err)
     //  当前插入的文档
    console.log(doc)
});

这里有回调函数,说明当前的API为异步API。这里MongoDB数据库的所有操作都是异步操作,所以上述代码我们还可以改成promise形式,返回结果为promise对象。

Course.create({name: 'JavaScript基础', author: '黑马讲师', isPublish: true})
      .then(doc => console.log(doc))
      .catch(err => console.log(err));

如果对promise记忆模糊,可以看我的http那一篇博文

2.3 mongoDB数据库导入数据

首先配置环境变量:找到mongodb数据库的安装目录,将安装目录下的bin目录放置在环境变量中。

mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb_10


复制路径,放到系统变量中,跟配置JAVA环境变量一样

mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb_11


配置好后,需要重启PowerShell

准备要导入的文件,我这里用黑马提供的user.json文件,把它copy到目标目录下

mongoimport命令格式:mongoimport –d 数据库名称 –c 集合名称 –file 要导入的数据文件

按照mongoimport命令格式输入完整的命令

mongoimport -d playground -c users --file ./user.json

mongodb数据库中用户和订单的关系 mongodb数据库购买_node.js_12


到compass软件查看一下结果

mongodb数据库中用户和订单的关系 mongodb数据库购买_node.js_13


2.4 查询文档

查找所有数据

//集合规则
const userSchema = mongoose.Schema({
    name:String ,
    age:Number,
    hobbies:[String],
    email:String,
    password:String
});
//使用集合规则创建集合
const Users = mongoose.model('Users',userSchema);
//用集合下的find()方法查询数据并打印在控制台
//前面提到过mongodb的所有操作均是异步操作
//所以这个find也属于异步函数,其返回结果为promise类型,可以用then来接收返回成功的结果
//根据条件查找文档(条件为空则查找所有文档)
Users.find().then(res => console.log(res));

这个find()函数里面是可以接收参数进行查找的

Users.find({_id:'5c09f1e5aeb04b22f8460965'}).then(res => console.log(res));

返回结果可以看到跟对应的数据一毛一样

mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb数据库中用户和订单的关系_14


mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb_15


用find()方法,不管返回数据单条还是多条,均以数组形式返回,如果想返回的数据为对象形式,我们可以使用findOne()方法,这个方法查找的数据如果有多条结果,默认返回当前集合中符合条件的第一条数据。

Users.findOne({password:'123456'}).then(res => console.log(res));

mongodb数据库中用户和订单的关系 mongodb数据库购买_mongodb数据库中用户和订单的关系_16


返回结果

mongodb数据库中用户和订单的关系 mongodb数据库购买_node.js_17

//  匹配大于($gt):n 小于($lt):m
Users.find({age: {$gt: 20, $lt: 50}}).then(result => console.log(result));

//  匹配包含($in):['要匹配的内容']
 Users.find({hobbies: {$in: ['吃饭']}}).then(result => console.log(result));
 
//选择要查询的字段  select('字段以空格形式隔开')
//默认字段_id会被查询出来,如果不想查询结果出现某个字段,在那个字段名称前加上-
 Users.find().select('name email -_id').then(result => console.log(result));
 
// 将数据按照年龄进行排序 sort('以哪个字段排序')
Users.find().sort('age').then(result => console.log(result));
//默认升序,如果想降序排列,在字段前面加上-
 Users.find().sort('-age').then(result => console.log(result));
 
//  skip 跳过多少条数据 skip(n)  limit 限制查询数量 limit(n)
 Users.find().skip(2).limit(2).then(result => console.log(result))

2.5添加文档

//插入多条数据
Course.insertMany([{
    name:'mongoose 教程',
    author:'黑马讲师',
    isPublish:true
},{
    name:'http 教程',
    author:'黑马讲师',
    isPublish:true
},{
    name:'js 教程',
    author:'黑马讲师',
    isPublish:true
},{
    name:'mongoose 教程',
    author:'讲师',
    isPublish:true
},{
    name:'http 教程',
    author:'讲师',
    isPublish:true
}]);

2.6 删除文档

// 删除单个,删除一个匹配文档 findOneAndDelete({})可带或不带参数
Course.findOneAndDelete().then(result => console.log(result));

// 删除多个 deleteMany({})可带或不带参数,具体情况具体分析
Course.deleteMany({author:'讲师'}).then(res => console.log(res));

2.7 更新文档

// 更新单个
//Users.updateOne({查询条件}, {要修改的值}).then(result => console.log(result));
Users.updateOne({name :'李四'},{age:18}).then(res => console.log(res));

// 更新多个
//Users.updateMany({查询条件}, {要更改的值}).then(result => console.log(result));
//查询条件参数为空,表明要修改所以的文档
Users.updateMany({},{age:80}).then(res => console.log(res));

2.8 mongoose验证
在创建集合规则时,可以设置当前字段的验证规则,验证失败就则输入插入失败。

  • required: true 必传字段
  • minlength:3 字符串最小长度
  • maxlength: 20 字符串最大长度
  • min: 2数值最小为2
  • max: 100 数值最大为100
  • enum: [‘html’, ‘css’, ‘javascript’, ‘node.js’]
  • trim: true 去除字符串两边的空格
  • validate: 自定义验证器 default: 默认值

获取错误信息:error.errors[‘字段名称’].message

//集合规则
const postSchema = new mongoose.Schema({
    title:{
        type:String,
        required:[true,'请传入文章标题'],
        minlength:[2,'请输入长度大于2的标题'],
        maxlength:[5,'请输入长度小于5的标题'],
        trim:true
    },
    age: {
        type:Number,
        min:[18,'年龄不能小于18岁'],
        max:[60,'年龄不能大于60岁']
    },
    publishDate: {
        type:Date,
        //默认值
        default:Date.now
    },
    category: {
        type:String,
        //enum为可选值
        enum:{
            values:['html','css'],
            message:'请输入正确的目录名称'
        }
    },
    author: {
        type:String,
        //自定义验证
        validate : {
            validator: v => {
                //v 传入的值,将要验证的
                //返回布尔值
                //返回true 验证成功
                //返回false 验证失败
                return v && v.length > 4;
            },
            //自定义错误信息
            message:'作者名字输入有误'
        }
    }
});
//创建集合
const Post = mongoose.model('Post',postSchema);
//传入数据
Post.create({title:'ab',age:65,category:'jvav',author:'au'})
.then(res => console.log(res))
.catch(error => {
    //获取错误信息对象
    const err = error.errors;
    //循环错误信息对象
    for(var attr in err){
        console.log(err[attr]['message']);
    }   
});

2.9 集合关联
通常不同集合的数据之间是有关系的,例如文章信息和用户信息存储在不同集合中,但文章是某个用户发表的,要查询文章的所有信息包括发表用户,就需要用到集合关联。

  • 使用id对集合进行关联
  • 使用populate方法进行关联集合查询
// 文章集合规则
const postSchema = new mongoose.Schema({
	title: {
		type: String
    },
    // 使用ID将文章集合和作者集合进行关联
    author: {
        type:mongoose.Schema.Types.ObjectId,
        //前提已经存在一个users表,没有的话需要创建
        ref:'User'
    }
});
// 文章集合
const Post = mongoose.model('Post', postSchema);
//创建文章
//author:'5eca3f5e90abecad8830c179' 使用users集合中对应的id进行关联
 Post.create({title:'Mongoose is very good!',author:'5eca3f5e90abecad8830c179'}).then(res => console.log(res));
//联合查询
Post.find().populate('author').then(res => console.log(res));