下载安装MongoDB数据库:

mac安装mongoDB详细步骤 - 简书介绍: 基于分布式文件存储的数据库,使用C++编写。应用最广泛的非关系型数据库(NoSQL)。NoSQL与SQL区别:NoSQL是基于键值对保存数据的,无复制的sql查询,表...https://www.jianshu.com/p/a594e6482e5c

Mongoose中文文档:

Mongoose 5.0 中文文档http://mongoosejs.net/docs/queries.html注意:在Node.js中使用MongoDB需要用到Mongoose这个包 !!!


一. 启动MongoDB数据库服务器

在终端依次输入:

# 打开到mongodb的bin文件夹
cd /usr/local/mongodb/bin
# 查看文件夹内容
ls
# 启动mongodb数据库服务器
mongod --dbpath=../data/db

(因为本机的Mongodb没有启用自启动,所以每次要使用的时候都要启动一下) 

注意:MongoDB的端口号默认是27017。 


二 . 在Node.js中使用Mongoose操作MongoDB数据库

Mongoose的特点:(1)通过关系型数据库的思想设计非关系型数据库,(2)基于mongodb驱动,并简化其操作。

1. 在命令行中安装mongoose模块

# 安装mongoose模块
npm i mongoose 

2. 引入mongoose并连接数据库

3. 定义模型:Schema是数据库对象的集合,是mongoose中用到的一种数据模式,可以理解为表结构的定义。每个schema会映射到MongoDB中的一个集合(collection),但它不具备操作数据库的能力。定义好schema后要生成model,model是由schema生成的模型,可以对数据库进行操作。

注意:mongoose.model中可以传入两个参数,也可以传入三个参数。

  • 参数1:模型名称(首字母大写);
  • 参数2:Schema;
  • 参数3:数据库集合名称(默认为模型名称的小写复数形式);

4. 增删改查操作

// 1. 在命令行中安装mongoose模块

// 2. 引入mongoose并连接数据库
const mongoose=require('mongoose')
// 连接数据库,数据库名为cms-test
mongoose.connect('mongodb://127.0.0.1:27017/cms-test')
// 连接数据库时,若有账户密码需要采用下面的连接方式
// mongoose.connect('mongodb://myadmin:123456@localhost:27017/cms-test') 
// 连接数据库时,也可以传一个回调函数,检查数据库是否连接成功
// mongoose.connect('mongodb://127.0.0.1:27017/cms-test',function(err){
//     if(err){
//         return console.log(err)
//     }
//     console.log('数据库连接成功')
// })

// 3. 定义users集合(表)的Schema
// Schema里的对象和数据库表里的字段需要一一对应
var UserSchema=mongoose.Schema({
    name:String,
    age:Number,
    status:{
        type:Number,
        default:1   //默认值
    },
})

// 4. 定义数据库模型,操作数据库
// model里的第一个参数:(1)首字母大写,(2)要和数据库集合(表)名称对应
// 这个模型会和与模型名称小写复数形式相同的数据库表建立连接,并操作这个表
const User=mongoose.model('User',UserSchema,'users')

// 5. 查询users表中的所有数据
User.find({},(err,docs)=>{
    if(err){
        console.log(err)
        return
    }
    console.log(docs)
})

// 6. 增加数据
// (1)实例化Model  (2)通过实例化User Model创建增加的数据
var u=new User({
    name:"李四",
    age:20,
    status:1
})
u.save(function(err){
    if(err){
        return console.log(err)     
    }
    console.log('成功')
})

// 7. 修改数据
User.updateOne({"_id":"2413978feh871w10231e3"},{"age":31},function(err,docs){
    if(err){
        return console.log(err)   
    }
    console.log(docs)
})

// 8. 删除数据
User.deleteOne({"_id":"2413978feh871w10231e3"},function(err,docs){
    if(err){
        return console.log(err)   
    }
    console.log(docs)
})

三. 模块化

1. 项目结构

2.  /model/db.js

//  /model/db.js

const mongoose=require('mongoose')
mongoose.connect('mongodb://127.0.0.1:27017/cms-test')
module.exports=mongoose

3.  /model/users.js

//   /model/users.js

const mongoose=require('./db.js')

// 定义数据集合的映射,字段名称必须与数据库保持一致
var UserSchema=mongoose.Schema({
    name:String,
    age:Number,
    status:{
        type:Number,
        default:1   //默认值
    },
}, {
    // 设置时间
    timestamps: true
})

module.exports=mongoose.model('User',UserSchema,'users')

4.  /model/news.js

//   /model/news.js

const mongoose=require('./db.js')

// 定义数据集合的映射,字段名称必须与数据库保持一致
var NewsSchema=mongoose.Schema({
    title:String,
    author:String,
    pic:String,
    content:String,
    status:{
        type:Number,
        default:1   //默认值
    },
}, {
    // 设置时间
    timestamps: true
})

module.exports=mongoose.model('News',NewsSchema,'news')

5. index.js

// index.js

var User=require('./model/users.js')
var News=require('./model/news.js')

User.find({},(err,docs)=>{
    if(err){
        console.log(err)
        return
    }
    console.log(docs)
})

News.find({},(err,docs)=>{
    if(err){
        console.log(err)
        return
    }
    console.log(docs)
})

var user=new User({
    name:"张三",
    age:17,
})
user.save()

四. Mongoose内置CRUD方法

Mongoose 5.0 中文文档http://mongoosejs.net/docs/api.html#Query

  • Model.deleteMany()
  • Model.deleteOne()
  • Model.find()
  • Model.findById()
  • ​​​​​​​Model.findByIdAndDelete()
  • ​​​​​​​Model.findByIdAndRemove()
  • ​​​​​​​Model.findByIdAndUpdate()
  • ​​​​​​​Model.findOne()
  • ​​​​​​​Model.findOneAndDelete()
  • ​​​​​​​Model.findOneAndRemove()
  • ​​​​​​​Model.findOneAndUpdate()
  • Model.replaceOne()
  • Model.updateMany()
  • Model.updateOne()
# 其他所需包
npm i express@next 
npm i cors
const express=require('express')
const app=express()
app.use(express.json()) //允许express处理提交过来的json数据
app.use(require('cors')())

// 1. 在命令行中安装mongoose模块

// 2. 引入mongoose并连接数据库
// 导入mongoose包
const mongoose=require('mongoose')
// 连接数据库,第一个参数为数据库的地址
//    数据库名为express-test (数据库的名称及各种内容会自动创建,无需额外配置)
mongoose.connect('mongodb://localhost:27017/express-test') 


// 3、定义产品的Product模型,第一个参数为模型名称(首字母大写),第二个参数为表结构
const Product=mongoose.model('Product',new mongoose.Schema({
    // 定义字段,即一个产品有哪些属性
    title:String,
}))


// 4、数据库的增删改查操作

// 向数据库中插入多条初始数据,只执行一遍,不然每次启动程序都会插入数据
// MongoDB数据库中每条数据都有一个_id,是自动生成的
// Product.insertMany([
//     {title:'产品1'},
//     {title:'产品2'},
//     {title:'产品3'},
// ])

// 数据库多条查询
// 产品列表,查出来是数组
app.get('/products',async (req,res)=>{
    // 每一次数据库查询都是从Node.js服务器端异步操作连接MongoDB数据库,等待它返回结果
    // const data=await Product.find()  //查找数据库中的所有记录

    // limit(2)限制条数为2条,skip(1)跳过第一条数据。skip和limit结合起来可以做分页。
    // const data=await Product.find().skip(1).limit(2)

    // where()用来加查询条件
    // const data=await Product.find().where({
    //     title:'产品2'
    // })

    // sort()用来排序
    const data=await Product.find().sort({
        //-1为倒序,1为正序
        _id:-1, //按_id倒序排序
    })

    res.send(data)
})

// 数据库单条查询
// 产品详情,查出来是对象
app.get('/products/:id',async (req,res)=>{
    // 通过_id查询数据
    const data=await Product.findById(req.params.id)
    res.send(data)
})

// 新增数据
app.post('/products',async (req,res)=>{
    const data=req.body
    // 新增数据,创建完后返回一个对象
    const product=await Product.create(data)
    res.send(product)
})

// 修改数据
// patch表示的是部分修改,put表示的是整个覆盖
app.put('/products/:id',async (req,res)=>{
    const product=await Product.findById(req.params.id) //通过id找到产品
    product.title=req.body.title //把客户端提交过来的title,赋值到这个产品的title
    await product.save()  //保存产品
    res.send(product)
})

// 删除数据
app.delete('/products/:id',async (req,res)=>{
    //const product=await Product.findById(req.params.id) //1、通过id找到产品
    //await product.remove()  //2、删除产品
    await Product.findByIdAndDelete(req.params.id)
    res.send({
        sucess:true
    })
})


app.listen(4000,()=>{
    console.log('App listening on port 4000!')
})

五. 扩展Mongoose Model的静态方法和实例方法

 1. 静态方法扩展

const mongoose=require('mongoose')
mongoose.connect('mongodb://127.0.0.1:27017/cms-test')

// 定义数据集合的映射,字段名称必须与数据库保持一致
var UserSchema = mongoose.Schema({
    name: {
        type: String,
        index: true, // 普通索引
    },
    age: Number,
    sn: { // 用户绑定设备的设备号
        type: String,
        unique: true, // 唯一索引
    },
    status: {
        type: Number,
        default: 1,
    },
})

// 静态方法statics:直接通过类就可以调用静态方法
UserSchema.statics.findBySn=function(sn,cb){
    //通过find方法获取sn数据,通过this关键字获取当前的model
    this.find({'sn':sn},function(err,docs){
        cb(err,docs)
    })
}

// 实例方法methods:通过实例化后才能访问,对象调用实例方法(基本不用)
UserSchema.methods.print=function(){
    console.log('这是一个实例方法')
    console.log(this.name) //打印实例中传入的name数据
}

const User=mongoose.model('User',UserSchema,'users')


// 调用自定义静态方法findBySn()
User.findBySn('12345678',function(err,docs){
    if(err){
        console.log(err)
        return
    }
    console.log(docs)
})


var user=new User({
    name:"张三",
    age:17,
})
// 调用自定义实例方法print()
user.print()

六. Mongoose中的模式修饰符

1. Mongoose预定义模式修饰符

lowercase、uppercase、trim 等预定义模式修饰符可以对我们增加的数据进行格式化。

2. Mongoose的get和set自定义修饰符

建议使用set修饰符在增加数据的时候对数据进行格式化。

不建议使用get在实例获取数据的时候对数据进行格式化。

// 定义数据集合的映射,字段名称必须与数据库保持一致
var FocusSchema = mongoose.Schema({
    title: {
        type: String,
        trim: true // mongoose预定义模式修饰符trim:去掉空格
    },
    pic: String,
    redirect: {
        type: String,
        set(params) { // 增加数据时对redirect字段进行处理
            // params可以获取redirect的值   返回的数据就是redirect在数据库中实际保存的值
            // http://www.baidu.com
            if (!params) {
                return params
            } else {
                if (params.indexOf('http://')!=0 && params.indexOf('https://')!=0){
                    return 'http://'+params
                }
                return params
            }
        },
    },
    status: {
        type: Number,
        default: 1 //默认值
    },
})

// 定义数据集合的映射,字段名称必须与数据库保持一致
var UserSchema=mongoose.Schema({
    name:{
        type:String,
        get(params){ //不建议使用!!!!!!
            return "a001"+params
        }
    },
    age:Number,
    status:{
        type:Number,
        default:1   //默认值
    },
})

const UserModel=mongoose.model('User',UserSchema,'users')

var user=new UserModel({
    name:'张三',
    age:20
})

console.log(user.name,user.age) //只有此时的执行结果name前拼上了a001,其他地方如数据库中的数据不会拼上a001

七. Mongoose数据校验

用户通过mongoose给mongodb数据库增加数据的时候,对数据的合法性进行的验证。

Mongoose里面定义Schema:字段类型、修饰符、默认参数、数据校验都是为了数据库数据的一致性

1. Mongoose校验参数

  • required:表示这个数据必须传入
  • max:用于Number类型数据,最大值
  • min:用于Number类型数据,最小值
  • enum:枚举类型,用于String类型数据,要求数据必须满足枚举值
  • match:正则匹配,用于String类型数据,增加的数据必须符合match(正则)的规则
  • maxlength:最大长度,用于String类型数据
  • minlength:最小长度,用于String类型数据
const mongoose=require('mongoose')
mongoose.connect('mongodb://127.0.0.1:27017/cms-test')

// Schema为数据库对象的集合,每个schema会映射到mongodb中的一个collection,定义schema可以理解为表结构的定义
var UserSchema = mongoose.Schema({
    name: {
        type: String, // 指定类型
        trim: true, // 修饰符
        required: true, // 表示字段必须传入
    },
    age: {
        type: Number,
        min: 0, // 最小值
        max: 150, // 最大值
    },
    sn: { // 用户绑定设备的设备号
        type: String,
        index: true, // 索引
        set(val) { // 自定义修饰符
            return val
        },
        maxlength: 20, // 最大长度
        minlength: 10, // 最小长度
        match: /^sn(.*)/ // 正则表达式:设备号必须以sn开头
    },
    status: {
        type: String,
        default: 'success', // 默认值
        enum: ['success', 'error'], // 枚举,表示status值只能为数组中的值
    },
})

const User=mongoose.model('User',UserSchema,'users')

var user=new User({
    name:"张三",
    sn:'sn123984238091',
    age:17,
    status:'success',
})
user.save()

2. Mongoose自定义的验证器validate

var UserSchema = mongoose.Schema({
    name: String,
    age: Number,
    sn: { 
        type: String,
        index: true, 
        // 自定义验证器:长度必须大于等于10
        validate: function (sn) { 
            return sn.length >= 10
        }
    },
    status: {
        type: String,
        default: 'success', 
    },
})

参考内容:

Nodejs+Express视频教程-2021年更新(IT营大地)_哔哩哔哩_bilibili2021 Nodejs教程 Serverless Eggjs Nestjs教程10套地址: https://www.itying.com/category-83-b0.htmlhttps://www.bilibili.com/video/BV1Gz4y1X7Uq?p=40

Logo

为开发者提供学习成长、分享交流、生态实践、资源工具等服务,帮助开发者快速成长。

更多推荐