慕课网 Node.js全栈入门 实战项目 笔记

慕课网 Node.js全栈入门 实战项目 笔记

  • 写在前面
    • Node.js 和 npm 的安装
    • 项目步骤
      • 写代码之前的准备工作
      • 正式开始
    • 课程回顾
      • 技术栈
      • 技术的关键点
      • 注意事项
  • 写在最后

写在前面

  • node.js
  • API部分 √
  • 前端部分 ×

第一次写这种全步骤的实战笔记,还是跟着视频一点点总结的,初接触这些,希望这些零碎的语言能帮助自己更有动力去学习这些。

Node.js 和 npm 的安装

这点视频前期都有详细讲解,装好之后只是应用,这里不再赘述。

项目步骤

写代码之前的准备工作

  1. mkdir 文件夹名 ,新建项目文件夹;
  2. cd 文件夹名 ,进到这个文件夹中;
  3. npm init -y ,初始化 ;
  4. git init,可选,不用git就没有此步骤;
  5. npm install express mysql2 sequelize -S ,安装express框架,mysql2数据库驱动,sequelize ORM框架;
  6. npm i sequelize-cli -S ,sequelize-cli 安装;
  7. npm i nodemon -D,监听更新,服务自动启动,不用手动一遍遍启动;
  8. code ./,在vscode中打开代码。

正式开始

  1. 项目下新建src文件夹

  2. src中新建app.js,写express框架

    const express = require('express');
    
    const app = express();
    
    app.listen(3000, () => {
        console.log('服务启动成功');
    })
    
  3. 在package.json中配置启动脚本

    "scripts": {
    "start": "nodemon ./src/app.js"
    }
    

    启动项目使用命令npm (run) start 因为start是默认的,可以加run也可以不加,但是别的名称不能省略。

    问题记录:使用npm start报错 nodemon既不是内部命令也不是外部命令

    解决:看package.json的依赖中有没有引进nodemon,如果没有可以使用命令

    npm install --save-dev nodemon
    
  4. API需求分析

    写api框架(应用级) 分页会产生很多参数,一般用post更合理,扩展性会更好。设计api的时候要提前做一些准备,做一些框架处理,做一些异常处理,以及响应是以什么结构出现的。

  5. API需求说明

    (1)根据客户端传递过来的不同的参数(状态/页码) 查询 任务的列表;

    (2)实现 新增的一个任务功能 (名称/截止日期/内容);

    (3)实现 一个编辑的功能:根据客户端传递的任务对象(已存在的数据)进行编辑,(名称/截止日期/内容/ID);

    (4)删除一个任务 (ID);

    (5)修改任务的状态(ID/状态–待办/完成)。

  6. API 实现

    要点记录:在使用 req.body 之前先引入中间件;

    const bodyParser = require('body-parser');//引入中间件(在使用req.body之前)
    

    数据量大要用到post,使用req.body传递参数的时候需要使用中间件 安装命令:

    npm i body-parser -S
    

    使用req.body的时候在postman中的body中选择 raw 后面选择JSON,输入数据,然后发送请求就可以看到数据被传输过来了。

    这里的是完善实现的部分代码:

    //1、所有的错误,http status == 500
    /** 查询任务列表 */
    //用list查有一个弊端,每次都要传status和page否则会出错
    //api 根据传递的状态/页码 查询任务列表实现
    app.get('/list/:status/:page', async (req, res, next) => {
        //1.状态 1:待办,2:完成,3:删除,-1:全部
        //2. 分页处理
        let { status, page } = req.params;
        let limit = 10; //前端没有做设置分页的功能,这里写死了
        let offset = (page - 1) * limit;  //开始读取数据的脚标
        let where = {};
        if (status != -1) {
            where.status = status;
        }
        let list = await models.Todo.findAndCountAll({  //查询并汇总
            where,
            offset,
            limit
        })
        res.json({
            list,
            message:"列表查询成功"
        })
    })
    
    //实现 新增任务  名称/截止日期/内容
    /** 创建一个TODO */
    app.post('/create', async (req, res, next) => {
        try {
            let { name, deadline, content } = req.body;
            /** 数据持久化到数据库 */
            //models.Todo是一个模型,即ORM对象,.create返回的是一个promise 用await去同步
            let todo = await models.Todo.create({
                name,
                deadline,
                content
                //status 在todo.js中设置默认值为1,刚创建的任务都是待办状态 不用设初始值
            })
            res.json({
                todo,
                message:"任务创建成功"
            })
        } catch (error) {
            next(error) //用next传下去之后就会被全局异常处理捕获到
        }
        
    })
    
    //实现 编辑功能 传递的任务对象(根据id修改内容) 编辑名称/截止日期/内容/ID
    /** 编辑 修改todo */
    app.post('/update', async (req, res, next) => {
        try {
            let { name, deadline, content, id } = req.body;
            // 修改 首先要根据id找到数据库模型 
            let todo = await models.Todo.findOne({
                where: {
                    id
                }
            })
            if (todo) {
                // 执行更新功能
                todo = await todo.update({
                    name,
                    deadline,
                    content
                })
            }
            res.json({
                todo
            })
        } catch (error) {
            next(error)
        }
        
    })
    
    /** 更新状态,删除 */
    app.post('/update_status', async (req, res, next) => {
        try {
            let { id,status } = req.body;
            // 修改 首先要根据id找到数据库模型 
            let todo = await models.Todo.findOne({
                where: {
                    id
                }
            })
            if (todo && status != todo.status) {
                // 执行更新
                todo = await todo.update({
                    status
                })
            }
            res.json({
                todo
            })
        } catch (error) {
            next(error)
        }
    })
    
    //全局异常处理
    app.use((err, req, res, next) => {
        if (err) {
            res.status(500).json({
                message:err.message
            })
        }
    })
    
  7. 数据库初始化

    (1) 创建一个数据库 在navicat 中创建数据库 字符集 utf8mb4,排序规则 utf8mb4_croatian_ci

    (2) 使用 sequelize-cli 初始化 项目的数据库配置信息

    然后创建一个文件夹 mkdir dbcd db 到这个文件夹中去 再使用命令去生成

     npx sequelize init
    

    修改 config.json 文件 配置数据库信息 密码要加上双引号
    "timezone":"+08:00" 设置时区 +08:00 北京时间

    (3) 生成模型文件 (都是在 db 文件夹中执行的命令)
    migrate 文件和model 文件

     npx sequelize model:generate --name Todo --attributes name:string,deadline:date,content:string 
    

    这里没有忘记加上字段status,在todo.js中单独加上也行

       	Todo.init({
       	    name: DataTypes.STRING,
       	    deadline: DataTypes.DATE,
       	    content: DataTypes.STRING,
       	    status: {
       	    	type: DataTypes.INTEGER,
       	      	defaultValue:1
           	  }
       	  	}, {
       		    timestamps:false,
       		    sequelize,
       		    modelName: 'Todo',
       	  });
    

    创建成功之后稍微修改一下 migrations 中的 js 文件属性 删除默认的 createAtupdateAt 属性(删除之后后续会出现问题,因为sequelize中默认这两个属性,在todo.js中的Todo.init的第二项中加上timestamps:false即可)

    (4) 持久化模型对应的[数据库表]

       npx sequelize db:migrate
    

    检查数据库中 todo 表就生成了 。

  8. API 中具体使用 ORM 模型
    app.js中导入模型

    //models是一个集合,主要是index.js中
    //model的结构是一个数据对象,伪model中有一个Todo,一个sequelize实例还有一个Sequelize静态方法
    const models = require('../db/models');
    const { sequelize } = require('../db/models');
    //使用model的时候要用models下对应的model 见create例子
    
    // {
    //     { model: Todo },
    //     sequelize,
    //     Sequelize    
    // }
    
    app.use(express.json());//专门处理express json的
    
    //对url参数做encoded    for parsing application/xwww-form-urlencoded
    app.use(express.urlencoded());
    
    //在body上做encoded   for parsing application/xwww-form-urlencoded
    app.use(bodyParser.urlencoded({ extended: true }));
    
  9. 结合前端展示

    这里还没写,课程中只是进行了演示。

课程回顾

技术栈

  1. node -->http,异常
    node.js本身 在做web应用的时候不需要了解所有的,需要了解的是关于HTTP(重点)这方面的,初级计算,以及异常处理方面;
  2. web框架,express、hapi、koa、egg;
  3. 参数校验 数据是否合法;
  4. mysql的使用 增删改查;
  5. ORM框架的学习 sequelize使用。

技术的关键点

api的组成部分,使用过程

web-->webserver-.>router-->hander-->orm-->db。

注意事项

demo与实际应用的区别

  1. 需要做详细的 模型设计–> 模型之间的关系(1v1,1vN);
  2. api使用文档–>api文档的使用工具;
  3. 测试,测试用例。

写在最后

浩如烟海。

你可能感兴趣的:(后端,慕课网,笔记,node.js,http,npm,mysql)