CRUD using Mongoose
Introducing MongoDB
再Express和Node中常用MongoDB作为数据库,这是一个文件型(非关系型)数据库,不同于MySQL等传统数据库,它没u有表、是视图、记录、等概念。所以不同于关系型数据库,我们需要设计数据库,MongoDB
中没有设计或者结构,我们只是简单的再MongoDB中保存JSON对象。
Installing MongoDB
进入MongoDB后选择对应系统后下载安装包即可,本次安装为4.4.15版本,同时下载MongoDB Compass,这是一个使i数据库可视化的工具。安装完成后在Windows服务启用即可(或在CMD 输入 mongod, 如果没有则需要添加系统变量路径),同时在创建 C:\data\db 文件夹,MongoDB将把数据存放于此。
打开MongoDB Compass 进行连接即可。默认端口27017。
Connecting to MongoDB
我们通过mongoose库来连接MongoDB,注意:不同版本的MongoDB需要使用不同版本的mongoose
MongoDB Version | mongoose Version |
---|---|
MongoDB Server 2.4.x: | mongoose ^3.8 or 4.x |
MongoDB Server 2.6.x: | mongoose ^3.8.8 or 4.x |
MongoDB Server 3.0.x: | mongoose ^3.8.22, 4.x, or 5.x |
MongoDB Server 3.2.x: | mongoose ^4.3.0 or 5.x |
MongoDB Server 3.4.x: | mongoose ^4.7.3 or 5.x |
MongoDB Server 3.6.x: | mongoose 5.x |
MongoDB Server 4.0.x: | mongoose ^5.2.0 |
新建index.js
// index.js
const mongoose = require("mongoose");
mongoose
.connect("mongodb://localhost/playground")
.then(() => console.log("Connected to MongoDB"))
.catch((err) => console.log("Could not connect to MongoDB...", err));
这里我们连接了一个playground的数据库,尽管我们没有创建它,但当我们进行操作的时候,MongoDB会自动建立它。现在运行运行index.js,即可成功连接数据库
Schemas
现在我们来创建一个Schema,我们使用Schema来创建一种MongoDB数据集合的结构。这是一个mongoose中的概念,不是MongoDB的概念,我们使用Schema来设计符合MongoDB集合的文档结构,定义一个文档中该有什么属性。
const courseSchema = new mongoose.Schema({
name: String,
author: String,
tags: [String],
date: {
type: Date, default: Date.now },
isPublished: Boolean,
});
这里我们就建好了一个Schema,我们希望一个合规的文档有着name、author等属性。
Models
现在来看看如何根据Schema创建courses的文档。我们使用courseSchema来定义数据库中course的文档结构,我们需要把它弄成一个模型(Model)。
对于类与对象,我们可以创建一个Class,拥有不同Classes,然后实例化出不同的Object。同样的,我们可以类比为有一个Course类,然后有不同的具体课程,例如Node Course。为了创建一个Course类,我们需要将Schema弄成模型。
// To create a Class like course, we need to compiled the schema to model
const Course = mongoose.model("Course", courseSchema);
我们传入两个参数,第一个参数是目标集合的单数模型名称。在数据库中,我们有个集合叫Courses,所以我们传入这个集合的单数名称(去掉s),第二个参数就是需要的Schema。这样就创建好了,现在我们来创建一个实际对象。
const course = new Course({
name: "Node.js Course",
author: "Mosh",
tags: ["node", "backend"],
isPublished: true,
});
这里我们之前设置了date的默认值,所以不需要传入一个值
Saving a Document
现在我们来把这个course对象保存到数据库。这个course对象有一个save方法,是一个异步操作,因为连接到数据库需要时间,当储存到MongoDB后,MongoDB会给对象或文档一个唯一的标识。注意:要使用await,必须在一个async异步函数里执行。
async function createCourse() {
const course = new Course({
name: "Angular Course",
author: "Mosh",
tags: ["node", "frontend"],
isPublished: true,
});
const result = await course.save();
console.log(result);
}
createCourse();
运行它,就会发现已经储存好了
现在我们再创建一个Node Courses并储存,然后来看看如何做查询。
Querying Documents
现在来看下如何查询。我们之前创建的Course类有很多查询的方法:有find,用于获得一个文档的列表、findById,通过ID查找、findOne,返回一个单一的文档等等等等。先来看看find方法。
它返回一个文档查询对象(Document Query),有点像Promise,他也有then方法。
async function getCourses() {
const courses = await Course.find()
}
getCourses();
现在它会返回所有的课程,我们可添加筛选条件以返回指定课程。
const courses = await Course.find({
author: "Mosh", isPublished: true }) // A filter, only return the courses that author is Mosh and isPbulished
但返回的课程会有很多属性,我们只需要少数课程以及特定的属性,所以我们可以进一步添加限制
const courses = await Course.find({
author: "Mosh", isPublished: true }) // A filter, only return the courses that author is Mosh and isPbulished
.limit(10) // and only return 10 documents
.sort({
name: 1 }) // Sort by name in ascending order, -1 me