Node.js开发博客项目笔记-初始化路由(博客列表、新增、更新、删除、详情、登录)(3)

工程目录

如图所示,工程目录如下:

我们在工程下新建src的目录,src目录下新建三个文件夹:

  • controller:交互数据放到该目录下;
  • model:model类放到该目录下;
  • router:路由(模块接口处理)放到该目录下。

model目录

我们在model目录下,新建一个resModel.js,代码如下:

class BaseModel {
    constructor(data,message) {
        if(typeof data === 'string') {
            this.message = data;
            data = null;
            message = null;
        }
        
        if(data) {
            this.data = data;
        }
        if(message) {
            this.message = message;
        }
    }
}

class SuccessModel extends BaseModel {
    constructor(data,message) {
        super(data,message);
        this.errno = 0;
    }
}

class ErrorModel extends BaseModel {
    constructor(data,message) {
        super(data,message);
        this.errno = -1;
    }
}

module.exports = {
    SuccessModel,
    ErrorModel
}

其作用就是对接口返回的数据做下拦截处理,对于返回成功或者失败的接口,我们除了返回响应的message,再整体添加一个errno状态码,其中errno返回0表示成功;errno返回-1表示失败。

controller目录

我们在controller目录下新建两个js的文件,把开发的这个博客项目分成两个模块:

  • blog.js:(博客列表、添加博客、更新博客、删除博客、博客详情
  • user.js:(目前只有登录)

当前两个的模块的数据都是假数据,blog.js代码如下:

// 获取博客列表
const getList = (keyword, author) => {
  // 返回假数据
  return [
    {
      id: 1,
      title: '标题A',
      content: '博客内容A',
      createTime: 1630630964139,
      author: 'zhangsan'
    },
    {
      id: 2,
      title: '标题B',
      content: '博客内容B',
      createTime: 1630630999550,
      author: 'lisi'
    }
  ]
}

// 获取博客详情
const getDetail = (id) => {
  // 返回假数据
  return {
    id: 1,
    title: '标题A',
    content: '博客内容A',
    createTime: 1630630964139,
    author: 'zhangsan'
  }
}

// 新建博客
const newBlog = (blogData = {}) => {
    return {
        id: 3
    }
}

// 更新博客
const updateBlog = (id) => {
    return true;
}

// 删除博客
const delBlog =(id) => {
    return true;
}

module.exports = {
  getList,
  getDetail,
  newBlog,
  updateBlog,
  delBlog
}

user.js代码如下:

const loginCheck = (username,password) => {
    // 使用假数据
    if(username === 'zhangsan' && password === '123') {
        return true;
    }
    return false;
}

module.exports = {
    loginCheck
}

 router目录

router目录下也是分成两个路由模块:

  • blog.js:博客相关的路由接口处理操作;
  • user.js:用户相关(目前只有登录接口)的路由接口处理操作。

blog.js代码如下:

const { getList, getDetail, newBlog,updateBlog,delBlog } = require('../controller/blog');
const { SuccessModel, ErrorModel } = require('../model/resModel');

const handleBlogRouter = (req, res) => {
  const method = req.method;
  const id = req.query.id;
  // 获取博客列表
  if (method === 'GET' && req.path === '/api/blog/list') {
    let keyword = req.query.keyword;
    let author = req.query.author;
    let resData = getList(keyword, author);
    return new SuccessModel(resData)
  }

  // 获取博客详情
  if (method === 'GET' && req.path === '/api/blog/detail') {
    let id = req.query.id;
    let resData = getDetail(id);
    return new SuccessModel(resData);
  }

  // 新建博客
  if (method === 'POST' && req.path === '/api/blog/new') {
    const data = newBlog(req.body);
    return new SuccessModel(data);
  }

  // 更新博客
  if (method === 'POST' && req.path === '/api/blog/update') {
    const result = updateBlog(id);
    if(result) {
        return new SuccessModel();
    } else {
        return new ErrorModel('更新博客失败');
    }
  }

  // 删除博客
  if (method === 'POST' && req.path === '/api/blog/del') {
    const result = delBlog(id);
    if(result) {
        return new SuccessModel();
    } else {
        return new ErrorModel('删除博客失败');
    }
  }
}

module.exports = handleBlogRouter;

user.js代码如下:

const { loginCheck } = require('../controller/user');
const { SuccessModel, ErrorModel } = require('../model/resModel');

const handleUserRouter = (req,res) => {
    const method = req.method;
    
    // 登录
    if(method === 'POST' && req.path === '/api/user/login') {
        const { username,password } = req.body;
        const result = loginCheck(username,password);
        if(result) {
            return new SuccessModel();
        } else {
            return new ErrorModel('登录失败');
        }
    }
}

module.exports = handleUserRouter;

app.js

对node服务的处理代码如下:

const querystring = require('querystring');
const handleBlogRouter = require('./src/router/blog');
const handleUserRouter = require('./src/router/user');

// 处理post data
const getPostData = (req) => {
    return new Promise((resolve,reject) => {
        if(req.method !== 'POST') {
            resolve({});
            return;
        }
        if(req.headers['content-type'] !== 'application/json') {
            resolve({});
            return;
        }
        let postData = '';
        req.on('data', chunk => {
            postData += chunk.toString();
        })
        req.on('end', () => {
            if(!postData) {
                resolve({});
                return;
            }
            resolve(JSON.parse(postData));
        })
    })
}

const serverHandle = (req,res) => {
    res.setHeader('Content-type','application/json');
    
    // 获取path
    const url = req.url;
    req.path = url.split('?')[0];
    
    req.query = querystring.parse(url.split('?')[1]);
    
    // 处理post data
    getPostData(req).then(postData => {
        req.body = postData;
        
        // 处理blog路由
        const blogData = handleBlogRouter(req,res);
        if(blogData) {
            res.end(JSON.stringify(blogData));
            return;
        }
        
        // 处理user路由
        const userData = handleUserRouter(req,res);
        if(userData) {
            res.end(JSON.stringify(userData));
            return;
        }
        
        // 未命中路由 返回404
        res.writeHead(404, {'Content-type': 'text/plain'});
        res.write('404 not found 
');
        res.end();
    })
}

module.exports = serverHandle;
原文地址:https://www.cnblogs.com/moqiutao/p/15245548.html