From 9b5f269823d7e1eb593f302975f208e9061c7b04 Mon Sep 17 00:00:00 2001 From: yoga Date: Sun, 31 Jul 2022 03:11:51 +0800 Subject: [PATCH] =?UTF-8?q?add(examples):=20=E5=A2=9E=E5=8A=A0=E6=95=B0?= =?UTF-8?q?=E6=8D=AE=E5=BA=93=E6=A0=B7=E4=BE=8B=E5=92=8C=E5=8D=A0=E4=BD=8D?= =?UTF-8?q?=E6=96=87=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../.example => data/logs/placeholder.log | 0 data/upload/placeholder | 0 .../dbs/mariadb/controller/addr.controller.js | 74 ++++++++++++ .../dbs/mariadb/controller/cart.controller.js | 96 +++++++++++++++ .../mariadb/controller/goods.controller.js | 111 ++++++++++++++++++ .../mariadb/controller/order.controller.js | 56 +++++++++ .../dbs/mariadb/controller/user.controller.js | 81 +++++++++++++ examples/dbs/mariadb/controller/user.js | 12 ++ examples/dbs/mariadb/db/mariadb.js | 27 +++++ examples/dbs/mariadb/db/redis.js | 49 ++++++++ .../mariadb/middlewares/addr.middleware.js | 19 +++ .../mariadb/middlewares/auth.middleware.js | 48 ++++++++ .../mariadb/middlewares/cart.middleware.js | 18 +++ .../mariadb/middlewares/goods.middleware.js | 22 ++++ .../mariadb/middlewares/order.middleware.js | 18 +++ .../mariadb/middlewares/user.middleware.js | 92 +++++++++++++++ examples/dbs/mariadb/models/addr.model.js | 39 ++++++ examples/dbs/mariadb/models/cart.model.js | 39 ++++++ examples/dbs/mariadb/models/goods.model.js | 36 ++++++ examples/dbs/mariadb/models/order.model.js | 40 +++++++ examples/dbs/mariadb/models/use.model.js | 30 +++++ examples/dbs/mariadb/models/user.js | 30 +++++ examples/dbs/mariadb/routers/addr.route.js | 54 +++++++++ examples/dbs/mariadb/routers/cart.route.js | 48 ++++++++ examples/dbs/mariadb/routers/goods.route.js | 35 ++++++ examples/dbs/mariadb/routers/index.js | 14 +++ examples/dbs/mariadb/routers/order.route.js | 34 ++++++ examples/dbs/mariadb/routers/user.route.js | 28 +++++ examples/dbs/mariadb/services/addr.service.js | 44 +++++++ examples/dbs/mariadb/services/cart.service.js | 96 +++++++++++++++ .../dbs/mariadb/services/goods.service.js | 49 ++++++++ .../dbs/mariadb/services/order.service.js | 31 +++++ examples/dbs/mariadb/services/user.js | 42 +++++++ examples/dbs/mariadb/services/user.service.js | 42 +++++++ examples/dbs/mongodb/controller/methods.js | 5 + examples/dbs/mongodb/db/mongo.js | 9 ++ examples/dbs/mongodb/models/book.js | 24 ++++ examples/dbs/mongodb/services/service.js | 5 + examples/dbs/mysql/controller/user.js | 12 ++ examples/dbs/mysql/db/mariadb.js | 27 +++++ examples/dbs/mysql/db/redis.js | 49 ++++++++ examples/dbs/mysql/models/user.js | 30 +++++ examples/dbs/mysql/services/redis.js | 29 +++++ examples/dbs/mysql/services/user.js | 42 +++++++ examples/dbs/npm.sh | 9 ++ examples/dbs/postgresql/controller/methods.js | 5 + examples/dbs/postgresql/db/postgres.js | 5 + examples/dbs/postgresql/models/model.js | 3 + examples/dbs/postgresql/services/service.js | 5 + examples/dbs/redis/controller/operate.js | 5 + examples/dbs/redis/db/redis.js | 49 ++++++++ examples/dbs/redis/models/model.js | 4 + examples/dbs/redis/services/baseOps.js | 29 +++++ examples/dbs/redis/test/test.js | 18 +++ examples/dbs/sqlite/controller/methods.js | 5 + examples/dbs/sqlite/db/sqlite3.js | 5 + examples/dbs/sqlite/models/model.js | 3 + examples/dbs/sqlite/services/service.js | 5 + {scripts => examples/shells}/clean.ps1 | 0 .../shells/initProject.ps1 | 0 package-lock.json | 4 +- public/js/placeholder.js | 0 scripts/placeholder.ps1 | 2 + src/routers/error.ts | 6 - 64 files changed, 1840 insertions(+), 8 deletions(-) rename src/data/upload/.example => data/logs/placeholder.log (100%) create mode 100644 data/upload/placeholder create mode 100644 examples/dbs/mariadb/controller/addr.controller.js create mode 100644 examples/dbs/mariadb/controller/cart.controller.js create mode 100644 examples/dbs/mariadb/controller/goods.controller.js create mode 100644 examples/dbs/mariadb/controller/order.controller.js create mode 100644 examples/dbs/mariadb/controller/user.controller.js create mode 100644 examples/dbs/mariadb/controller/user.js create mode 100644 examples/dbs/mariadb/db/mariadb.js create mode 100644 examples/dbs/mariadb/db/redis.js create mode 100644 examples/dbs/mariadb/middlewares/addr.middleware.js create mode 100644 examples/dbs/mariadb/middlewares/auth.middleware.js create mode 100644 examples/dbs/mariadb/middlewares/cart.middleware.js create mode 100644 examples/dbs/mariadb/middlewares/goods.middleware.js create mode 100644 examples/dbs/mariadb/middlewares/order.middleware.js create mode 100644 examples/dbs/mariadb/middlewares/user.middleware.js create mode 100644 examples/dbs/mariadb/models/addr.model.js create mode 100644 examples/dbs/mariadb/models/cart.model.js create mode 100644 examples/dbs/mariadb/models/goods.model.js create mode 100644 examples/dbs/mariadb/models/order.model.js create mode 100644 examples/dbs/mariadb/models/use.model.js create mode 100644 examples/dbs/mariadb/models/user.js create mode 100644 examples/dbs/mariadb/routers/addr.route.js create mode 100644 examples/dbs/mariadb/routers/cart.route.js create mode 100644 examples/dbs/mariadb/routers/goods.route.js create mode 100644 examples/dbs/mariadb/routers/index.js create mode 100644 examples/dbs/mariadb/routers/order.route.js create mode 100644 examples/dbs/mariadb/routers/user.route.js create mode 100644 examples/dbs/mariadb/services/addr.service.js create mode 100644 examples/dbs/mariadb/services/cart.service.js create mode 100644 examples/dbs/mariadb/services/goods.service.js create mode 100644 examples/dbs/mariadb/services/order.service.js create mode 100644 examples/dbs/mariadb/services/user.js create mode 100644 examples/dbs/mariadb/services/user.service.js create mode 100644 examples/dbs/mongodb/controller/methods.js create mode 100644 examples/dbs/mongodb/db/mongo.js create mode 100644 examples/dbs/mongodb/models/book.js create mode 100644 examples/dbs/mongodb/services/service.js create mode 100644 examples/dbs/mysql/controller/user.js create mode 100644 examples/dbs/mysql/db/mariadb.js create mode 100644 examples/dbs/mysql/db/redis.js create mode 100644 examples/dbs/mysql/models/user.js create mode 100644 examples/dbs/mysql/services/redis.js create mode 100644 examples/dbs/mysql/services/user.js create mode 100644 examples/dbs/npm.sh create mode 100644 examples/dbs/postgresql/controller/methods.js create mode 100644 examples/dbs/postgresql/db/postgres.js create mode 100644 examples/dbs/postgresql/models/model.js create mode 100644 examples/dbs/postgresql/services/service.js create mode 100644 examples/dbs/redis/controller/operate.js create mode 100644 examples/dbs/redis/db/redis.js create mode 100644 examples/dbs/redis/models/model.js create mode 100644 examples/dbs/redis/services/baseOps.js create mode 100644 examples/dbs/redis/test/test.js create mode 100644 examples/dbs/sqlite/controller/methods.js create mode 100644 examples/dbs/sqlite/db/sqlite3.js create mode 100644 examples/dbs/sqlite/models/model.js create mode 100644 examples/dbs/sqlite/services/service.js rename {scripts => examples/shells}/clean.ps1 (100%) rename initProject.ps1 => examples/shells/initProject.ps1 (100%) create mode 100644 public/js/placeholder.js create mode 100644 scripts/placeholder.ps1 delete mode 100644 src/routers/error.ts diff --git a/src/data/upload/.example b/data/logs/placeholder.log similarity index 100% rename from src/data/upload/.example rename to data/logs/placeholder.log diff --git a/data/upload/placeholder b/data/upload/placeholder new file mode 100644 index 0000000..e69de29 diff --git a/examples/dbs/mariadb/controller/addr.controller.js b/examples/dbs/mariadb/controller/addr.controller.js new file mode 100644 index 0000000..51d7a42 --- /dev/null +++ b/examples/dbs/mariadb/controller/addr.controller.js @@ -0,0 +1,74 @@ +const { + createAddr, + findAllAddr, + updateAddr, + removeAddr, + setDefaultAddr, +} = require('../service/addr.service') + +class AddrController { + async create(ctx) { + // 解析user_id, consignee, phone, address + const user_id = ctx.state.user.id + const { consignee, phone, address } = ctx.request.body + + const res = await createAddr({ user_id, consignee, phone, address }) + + ctx.body = { + code: 0, + message: '添加地址成功', + result: res, + } + } + + async findAll(ctx) { + const user_id = ctx.state.user.id + + const res = await findAllAddr(user_id) + + ctx.body = { + code: 0, + message: '获取列表成功', + result: res, + } + } + + async update(ctx) { + const id = ctx.request.params.id + + const res = await updateAddr(id, ctx.request.body) + + ctx.body = { + code: 0, + message: '更新地址成功', + result: res, + } + } + + async remove(ctx) { + const id = ctx.request.params.id + + const res = await removeAddr(id) + + ctx.body = { + code: 0, + message: '删除地址成功', + result: res, + } + } + + async setDefault(ctx) { + const user_id = ctx.state.user.id + const id = ctx.request.params.id + + const res = await setDefaultAddr(user_id, id) + + ctx.body = { + code: 0, + message: '设置默认成功', + result: res, + } + } +} + +module.exports = new AddrController() diff --git a/examples/dbs/mariadb/controller/cart.controller.js b/examples/dbs/mariadb/controller/cart.controller.js new file mode 100644 index 0000000..c341525 --- /dev/null +++ b/examples/dbs/mariadb/controller/cart.controller.js @@ -0,0 +1,96 @@ +const { + createOrUpdate, + findCarts, + updateCarts, + removeCarts, + selectAllCarts, + unselectAllCarts, +} = require('../service/cart.service') +const { cartFormatError } = require('../constant/err.type') + +class CartController { + async add(ctx) { + // 将商品添加到购物车 + // 1. 解析user_id, goods_id + const user_id = ctx.state.user.id + const goods_id = ctx.request.body.goods_id + // console.log(user_id, goods_id) + // 2. 操作数据库 + const res = await createOrUpdate(user_id, goods_id) + // 3. 返回结果 + ctx.body = { + code: 0, + message: '添加到购物车成功', + result: res, + } + } + + async findAll(ctx) { + // 1. 解析请求参数 + const { pageNum = 1, pageSize = 10 } = ctx.request.query + // 2. 操作数据库 + const res = await findCarts(pageNum, pageSize) + // 3. 返回结果 + ctx.body = { + code: 0, + message: '获取购物车列表成功', + result: res, + } + } + + async update(ctx) { + // 1. 解析参数 + const { id } = ctx.request.params + const { number, selected } = ctx.request.body + if (number === undefined && selected === undefined) { + cartFormatError.message = 'number和selected不能同时为空' + return ctx.app.emit('error', cartFormatError, ctx) + } + // 2. 操作数据库 + const res = await updateCarts({ id, number, selected }) + // 3. 返回数据 + ctx.body = { + code: 0, + message: '更新购物车成功', + result: res, + } + } + + async remove(ctx) { + const { ids } = ctx.request.body + + const res = await removeCarts(ids) + + ctx.body = { + code: 0, + message: '删除购物车成功', + result: res, + } + } + + async selectAll(ctx) { + const user_id = ctx.state.user.id + + const res = await selectAllCarts(user_id) + + ctx.body = { + code: 0, + message: '全部选中', + result: res, + } + } + + async unselectAll(ctx) { + const user_id = ctx.state.user.id + + const res = await unselectAllCarts(user_id) + + ctx.body = { + code: 0, + message: '全部不选中', + result: res, + } + } +} + +module.exports = new CartController() diff --git a/examples/dbs/mariadb/controller/goods.controller.js b/examples/dbs/mariadb/controller/goods.controller.js new file mode 100644 index 0000000..20230cd --- /dev/null +++ b/examples/dbs/mariadb/controller/goods.controller.js @@ -0,0 +1,111 @@ +const path = require('path') + +const { + fileUploadError, + unSupportedFileType, + publishGoodsError, + invalidGoodsID, +} = require('../constant/err.type') + +const { + createGoods, + updateGoods, + removeGoods, + restoreGoods, + findGoods, +} = require('../service/goods.service') + +class GoodsController { + async upload(ctx, next) { + // console.log(ctx.request.files) + const { file } = ctx.request.files + // console.log(file) + const fileTypes = ['image/jpeg', 'image/png'] + if (file) { + if (!fileTypes.includes(file.type)) { + return ctx.app.emit('error', unSupportedFileType, ctx) + } + ctx.body = { + code: 0, + message: '商品图片上传成功', + result: { + goods_img: path.basename(file.path), + }, + } + } else { + return ctx.app.emit('error', fileUploadError, ctx) + } + } + async create(ctx) { + // 直接调用service的createGoods方法 + try { + const { createdAt, updatedAt, ...res } = await createGoods( + ctx.request.body + ) + ctx.body = { + code: 0, + message: '发布商品成功', + result: res, + } + } catch (err) { + console.error(err) + return ctx.app.emit('error', publishGoodsError, ctx) + } + } + async update(ctx) { + try { + const res = await updateGoods(ctx.params.id, ctx.request.body) + + if (res) { + ctx.body = { + code: 0, + message: '修改商品成功', + result: '', + } + } else { + return ctx.app.emit('error', invalidGoodsID, ctx) + } + } catch (err) { + console.error(err) + } + } + async remove(ctx) { + const res = await removeGoods(ctx.params.id) + + if (res) { + ctx.body = { + code: 0, + message: '下架商品成功', + result: '', + } + } else { + return ctx.app.emit('error', invalidGoodsID, ctx) + } + } + async restore(ctx) { + const res = await restoreGoods(ctx.params.id) + if (res) { + ctx.body = { + code: 0, + message: '上架商品成功', + result: '', + } + } else { + return ctx.app.emit('error', invalidGoodsID, ctx) + } + } + async findAll(ctx) { + // 1. 解析pageNum和pageSize + const { pageNum = 1, pageSize = 10 } = ctx.request.query + // 2. 调用数据处理的相关方法 + const res = await findGoods(pageNum, pageSize) + // 3. 返回结果 + ctx.body = { + code: 0, + message: '获取商品列表成功', + result: res, + } + } +} + +module.exports = new GoodsController() diff --git a/examples/dbs/mariadb/controller/order.controller.js b/examples/dbs/mariadb/controller/order.controller.js new file mode 100644 index 0000000..a18802a --- /dev/null +++ b/examples/dbs/mariadb/controller/order.controller.js @@ -0,0 +1,56 @@ +const { + createOrder, + findAllOrder, + updateOrder, +} = require('../service/order.service') + +class OrderController { + async create(ctx) { + // 准备数据 + const user_id = ctx.state.user.id + const { address_id, goods_info, total } = ctx.request.body + + const order_number = 'XZD' + Date.now() + + const res = await createOrder({ + user_id, + address_id, + goods_info, + total, + order_number, + }) + + ctx.body = { + code: 0, + message: '生成订单成功', + result: res, + } + } + + async findAll(ctx) { + const { pageNum = 1, pageSize = 10, status = 0 } = ctx.request.query + + const res = await findAllOrder(pageNum, pageSize, status) + + ctx.body = { + code: 0, + message: '获取订单列表成功', + result: res, + } + } + + async update(ctx) { + const id = ctx.request.params.id + const { status } = ctx.request.body + + const res = await updateOrder(id, status) + + ctx.body = { + code: 0, + message: '更新订单状态成功', + result: res, + } + } +} + +module.exports = new OrderController() diff --git a/examples/dbs/mariadb/controller/user.controller.js b/examples/dbs/mariadb/controller/user.controller.js new file mode 100644 index 0000000..d48a8f0 --- /dev/null +++ b/examples/dbs/mariadb/controller/user.controller.js @@ -0,0 +1,81 @@ +const jwt = require('jsonwebtoken') + +const { + createUser, + getUerInfo, + updateById, +} = require('../service/user.service') + +const { userRegisterError } = require('../constant/err.type') + +const { JWT_SECRET } = require('../config/config.default') + +class UserController { + async register(ctx, next) { + // 1. 获取数据 + // console.log(ctx.request.body) + const { user_name, password } = ctx.request.body + + // 2. 操作数据库 + try { + const res = await createUser(user_name, password) + // console.log(res) + // 3. 返回结果 + ctx.body = { + code: 0, + message: '用户注册成功', + result: { + id: res.id, + user_name: res.user_name, + }, + } + } catch (err) { + console.log(err) + ctx.app.emit('error', userRegisterError, ctx) + } + } + + async login(ctx, next) { + const { user_name } = ctx.request.body + + // 1. 获取用户信息(在token的payload中, 记录id, user_name, is_admin) + try { + // 从返回结果对象中剔除password属性, 将剩下的属性放到res对象 + const { password, ...res } = await getUerInfo({ user_name }) + + ctx.body = { + code: 0, + message: '用户登录成功', + result: { + token: jwt.sign(res, JWT_SECRET, { expiresIn: '1d' }), + }, + } + } catch (err) { + console.error('用户登录失败', err) + } + } + + async changePassword(ctx, next) { + // 1. 获取数据 + const id = ctx.state.user.id + const password = ctx.request.body.password + + // 2. 操作数据库 + if (await updateById({ id, password })) { + ctx.body = { + code: 0, + message: '修改密码成功', + result: '', + } + } else { + ctx.body = { + code: '10007', + message: '修改密码失败', + result: '', + } + } + // 3. 返回结果 + } +} + +module.exports = new UserController() diff --git a/examples/dbs/mariadb/controller/user.js b/examples/dbs/mariadb/controller/user.js new file mode 100644 index 0000000..dda5092 --- /dev/null +++ b/examples/dbs/mariadb/controller/user.js @@ -0,0 +1,12 @@ +const { d } = require("../models/user"); + +class UserController { + async register(ctx, next) { + ctx.json({ code: 0, message: "success" }); + } + + async getUserList(ctx, next) { + ctx.json({ code: 0, message: "success" }); + } +} +module.exports = new UserController(); diff --git a/examples/dbs/mariadb/db/mariadb.js b/examples/dbs/mariadb/db/mariadb.js new file mode 100644 index 0000000..1b5cf40 --- /dev/null +++ b/examples/dbs/mariadb/db/mariadb.js @@ -0,0 +1,27 @@ +// connect to third-service of database or other. +const { Sequelize } = require("sequelize"); + +const { + MARIA_DIALECT, + MARIA_HOST, + MARIA_PORT, + MARIA_DBNAME, + MARIA_USRNAME, + MARIA_PASSWD, +} = process.env; + +const seq = new Sequelize(MARIA_DBNAME, MARIA_USRNAME, MARIA_PASSWD, { + host: MARIA_HOST, + port: MARIA_PORT, + dialect: 'mariadb', +}); + +seq.authenticate() + .then(() => { + console.log('数据库连接成功') + }) + .catch(err => { + console.log('数据库连接失败', err) + }) + +module.exports = seq; diff --git a/examples/dbs/mariadb/db/redis.js b/examples/dbs/mariadb/db/redis.js new file mode 100644 index 0000000..c81cbdc --- /dev/null +++ b/examples/dbs/mariadb/db/redis.js @@ -0,0 +1,49 @@ +const redis = require("redis"); +// require("../config/env.config"); + +const { REDIS_HOST, REDIS_PORT, REDIS_DBNAME, REDIS_USER, REDIS_PASSWD } = + process.env; // REDIS_USER 和 REDIS_PASSWD,需要服务器配置ACL用户名密码 +const URL = `redis://${REDIS_USER}:${REDIS_PASSWD}@${REDIS_HOST}:${REDIS_PORT}/${REDIS_DBNAME}`; + +// https://github.com/redis/node-redis/tree/master/docs +// module.exports = redis.createClient({URL}); +const client = redis.createClient({ + // url: URL, + socket: { host: REDIS_HOST, port: REDIS_PORT }, + password: REDIS_PASSWD, + // database: REDIS_DBNAME, + // legacyMode: true, // 语法向后(v3)部分兼容 +}); + +client.on("error", (err) => console.log(`redis client ~ Error ${err}`)); +client.on("connect", () => console.log("redis client ~ connect")); +client.on("reconnecting", () => console.log("redis client ~ reconnecting")); +client.on("ready", () => console.log("redis client ~ ready")); +client.on("end", () => console.log("redis client ~ end")); + +client.connect(); +client.ping(); +// try { +// } catch (error) { +// console.log(error); +// } + +module.exports = client; + +//* 方式二:redis 连接池 +//! unusable +/* var redisPool = require("redis-connection-pool")("myRedisPool", { + host: REDIS_HOST, // default + port: REDIS_PORT, //default + max_clients: 30, // defalut + perform_checks: false, // checks for needed push/pop functionality + database: 0, // database number to use + options: { + auth_pass: REDIS_PASSWD, + }, //options for createClient of node-redis, optional +}); +redisPool.set("test-key", "foobar", function (err) { + redisPool.get("test-key", function (err, reply) { + console.log(reply); // 'foobar' + }); +}); */ diff --git a/examples/dbs/mariadb/middlewares/addr.middleware.js b/examples/dbs/mariadb/middlewares/addr.middleware.js new file mode 100644 index 0000000..49de5ee --- /dev/null +++ b/examples/dbs/mariadb/middlewares/addr.middleware.js @@ -0,0 +1,19 @@ +const { addrFormatError } = require('../constant/err.type') + +const validator = (rules) => { + return async (ctx, next) => { + try { + ctx.verifyParams(rules) + } catch (err) { + console.error(err) + addrFormatError.result = err + return ctx.app.emit('error', addrFormatError, ctx) + } + + await next() + } +} + +module.exports = { + validator, +} diff --git a/examples/dbs/mariadb/middlewares/auth.middleware.js b/examples/dbs/mariadb/middlewares/auth.middleware.js new file mode 100644 index 0000000..239af49 --- /dev/null +++ b/examples/dbs/mariadb/middlewares/auth.middleware.js @@ -0,0 +1,48 @@ +const jwt = require('jsonwebtoken') + +const { JWT_SECRET } = require('../config/config.default') + +const { + tokenExpiredError, + invalidToken, + hasNotAdminPermission, +} = require('../constant/err.type') + +const auth = async (ctx, next) => { + const { authorization = '' } = ctx.request.header + const token = authorization.replace('Bearer ', '') + // console.log(token) + + try { + // user中包含了payload的信息(id, user_name, is_admin) + const user = jwt.verify(token, JWT_SECRET) + ctx.state.user = user + } catch (err) { + switch (err.name) { + case 'TokenExpiredError': + console.error('token已过期', err) + return ctx.app.emit('error', tokenExpiredError, ctx) + case 'JsonWebTokenError': + console.error('无效的token', err) + return ctx.app.emit('error', invalidToken, ctx) + } + } + + await next() +} + +const hadAdminPermission = async (ctx, next) => { + const { is_admin } = ctx.state.user + + if (!is_admin) { + console.error('该用户没有管理员的权限', ctx.state.user) + return ctx.app.emit('error', hasNotAdminPermission, ctx) + } + + await next() +} + +module.exports = { + auth, + hadAdminPermission, +} diff --git a/examples/dbs/mariadb/middlewares/cart.middleware.js b/examples/dbs/mariadb/middlewares/cart.middleware.js new file mode 100644 index 0000000..22ff0d9 --- /dev/null +++ b/examples/dbs/mariadb/middlewares/cart.middleware.js @@ -0,0 +1,18 @@ +const { cartFormatError } = require('../constant/err.type') + +const validator = (rules) => { + return async (ctx, next) => { + try { + ctx.verifyParams(rules) + } catch (err) { + console.error(err) + cartFormatError.result = err + return ctx.app.emit('error', cartFormatError, ctx) + } + + await next() + } +} +module.exports = { + validator, +} diff --git a/examples/dbs/mariadb/middlewares/goods.middleware.js b/examples/dbs/mariadb/middlewares/goods.middleware.js new file mode 100644 index 0000000..4f9701f --- /dev/null +++ b/examples/dbs/mariadb/middlewares/goods.middleware.js @@ -0,0 +1,22 @@ +const { goodsFormatError } = require('../constant/err.type') + +const validator = async (ctx, next) => { + try { + ctx.verifyParams({ + goods_name: { type: 'string', required: true }, + goods_price: { type: 'number', required: true }, + goods_num: { type: 'number', required: true }, + goods_img: { type: 'string', required: true }, + }) + } catch (err) { + console.error(err) + goodsFormatError.result = err + return ctx.app.emit('error', goodsFormatError, ctx) + } + + await next() +} + +module.exports = { + validator, +} diff --git a/examples/dbs/mariadb/middlewares/order.middleware.js b/examples/dbs/mariadb/middlewares/order.middleware.js new file mode 100644 index 0000000..60b3a84 --- /dev/null +++ b/examples/dbs/mariadb/middlewares/order.middleware.js @@ -0,0 +1,18 @@ +const { orderFormatError } = require('../constant/err.type') + +const validator = (rules) => { + return async (ctx, next) => { + try { + ctx.verifyParams(rules) + } catch (err) { + console.error(err) + orderFormatError.result = err + return ctx.app.emit('error', orderFormatError, ctx) + } + await next() + } +} + +module.exports = { + validator, +} diff --git a/examples/dbs/mariadb/middlewares/user.middleware.js b/examples/dbs/mariadb/middlewares/user.middleware.js new file mode 100644 index 0000000..6c1e82c --- /dev/null +++ b/examples/dbs/mariadb/middlewares/user.middleware.js @@ -0,0 +1,92 @@ +const bcrypt = require('bcryptjs') + +const { getUerInfo } = require('../service/user.service') +const { + userFormateError, + userAlreadyExited, + userRegisterError, + userDoesNotExist, + userLoginError, + invalidPassword, +} = require('../constant/err.type') + +const userValidator = async (ctx, next) => { + const { user_name, password } = ctx.request.body + // 合法性 + if (!user_name || !password) { + console.error('用户名或密码为空', ctx.request.body) + ctx.app.emit('error', userFormateError, ctx) + return + } + + await next() +} + +const verifyUser = async (ctx, next) => { + const { user_name } = ctx.request.body + + // if (await getUerInfo({ user_name })) { + // ctx.app.emit('error', userAlreadyExited, ctx) + // return + // } + try { + const res = await getUerInfo({ user_name }) + + if (res) { + console.error('用户名已经存在', { user_name }) + ctx.app.emit('error', userAlreadyExited, ctx) + return + } + } catch (err) { + console.error('获取用户信息错误', err) + ctx.app.emit('error', userRegisterError, ctx) + return + } + + await next() +} + +const crpytPassword = async (ctx, next) => { + const { password } = ctx.request.body + + const salt = bcrypt.genSaltSync(10) + // hash保存的是 密文 + const hash = bcrypt.hashSync(password, salt) + + ctx.request.body.password = hash + + await next() +} + +const verifyLogin = async (ctx, next) => { + // 1. 判断用户是否存在(不存在:报错) + const { user_name, password } = ctx.request.body + + try { + const res = await getUerInfo({ user_name }) + + if (!res) { + console.error('用户名不存在', { user_name }) + ctx.app.emit('error', userDoesNotExist, ctx) + return + } + + // 2. 密码是否匹配(不匹配: 报错) + if (!bcrypt.compareSync(password, res.password)) { + ctx.app.emit('error', invalidPassword, ctx) + return + } + } catch (err) { + console.error(err) + return ctx.app.emit('error', userLoginError, ctx) + } + + await next() +} + +module.exports = { + userValidator, + verifyUser, + crpytPassword, + verifyLogin, +} diff --git a/examples/dbs/mariadb/models/addr.model.js b/examples/dbs/mariadb/models/addr.model.js new file mode 100644 index 0000000..3cbd4c0 --- /dev/null +++ b/examples/dbs/mariadb/models/addr.model.js @@ -0,0 +1,39 @@ +// 1. 导入seq的连接 +const { DataTypes } = require('sequelize') +const seq = require('../db/seq') + +// 2. 定义字段(模型) +const Address = seq.define('zd_addresses', { + user_id: { + type: DataTypes.INTEGER, + allowNull: false, + comment: '用户id', + }, + consignee: { + type: DataTypes.STRING, + allowNull: false, + comment: '收货人姓名', + }, + phone: { + type: DataTypes.CHAR(11), + allowNull: false, + comment: '收货人的手机号', + }, + address: { + type: DataTypes.STRING, + allowNull: false, + comment: '收货人的地址', + }, + is_default: { + type: DataTypes.BOOLEAN, + allowNull: false, + defaultValue: false, + comment: '是否为默认地址, 0:不是(默认值) 1: 是', + }, +}) + +// 3. 同步, sync +// Address.sync({ force: true }) + +// 4. 导出模型对象 +module.exports = Address diff --git a/examples/dbs/mariadb/models/cart.model.js b/examples/dbs/mariadb/models/cart.model.js new file mode 100644 index 0000000..3b259a0 --- /dev/null +++ b/examples/dbs/mariadb/models/cart.model.js @@ -0,0 +1,39 @@ +// 1. 导入sequelize的连接 +const { DataTypes } = require('sequelize') +const seq = require('../db/seq') +const Goods = require('./goods.model') + +// 2. 定义Cart模型 +const Cart = seq.define('zd_carts', { + goods_id: { + type: DataTypes.INTEGER, + allowNull: false, + comment: '商品的id', + }, + user_id: { + type: DataTypes.INTEGER, + allowNull: false, + comment: '用户的id', + }, + number: { + type: DataTypes.INTEGER, + allowNull: false, + defaultValue: 1, + comment: '商品的数量', + }, + selected: { + type: DataTypes.BOOLEAN, + allowNull: false, + defaultValue: true, + comment: '是否选中', + }, +}) + +// 3. 同步数据(建表) +// Cart.sync({ force: true }) +Cart.belongsTo(Goods, { + foreignKey: 'goods_id', + as: 'goods_info', +}) +// 4. 导出Cart模型 +module.exports = Cart diff --git a/examples/dbs/mariadb/models/goods.model.js b/examples/dbs/mariadb/models/goods.model.js new file mode 100644 index 0000000..73171b5 --- /dev/null +++ b/examples/dbs/mariadb/models/goods.model.js @@ -0,0 +1,36 @@ +const { DataTypes } = require('sequelize') + +const seq = require('../db/seq') + +const Goods = seq.define( + 'zd_goods', + { + goods_name: { + type: DataTypes.STRING, + allowNull: false, + comment: '商品名称', + }, + goods_price: { + type: DataTypes.DECIMAL(10, 2), + allowNull: false, + comment: '商品价格', + }, + goods_num: { + type: DataTypes.INTEGER, + allowNull: false, + comment: '商品库存', + }, + goods_img: { + type: DataTypes.STRING, + allowNull: false, + comment: '商品图片的url', + }, + }, + { + paranoid: true, + } +) + +// Goods.sync({ force: true }) + +module.exports = Goods diff --git a/examples/dbs/mariadb/models/order.model.js b/examples/dbs/mariadb/models/order.model.js new file mode 100644 index 0000000..ac145ac --- /dev/null +++ b/examples/dbs/mariadb/models/order.model.js @@ -0,0 +1,40 @@ +const { DataTypes } = require('sequelize') +const seq = require('../db/seq') + +const Order = seq.define('zd_orders', { + user_id: { + type: DataTypes.INTEGER, + allowNull: false, + comment: '用户id', + }, + address_id: { + type: DataTypes.INTEGER, + allowNull: false, + comment: '地址id', + }, + goods_info: { + type: DataTypes.TEXT, + allowNull: false, + comment: '商品信息', + }, + total: { + type: DataTypes.DECIMAL(10, 2), + allowNull: false, + comment: '订单总金额', + }, + order_number: { + type: DataTypes.CHAR(16), + allowNull: false, + comment: '订单号', + }, + status: { + type: DataTypes.TINYINT, + allowNull: false, + defaultValue: 0, + comment: '订单状态(0: 未支付,1: 已支付, 2: 已发货, 3: 已签收, 4: 取消)', + }, +}) + +// Order.sync({ force: true }) + +module.exports = Order diff --git a/examples/dbs/mariadb/models/use.model.js b/examples/dbs/mariadb/models/use.model.js new file mode 100644 index 0000000..c61e8cb --- /dev/null +++ b/examples/dbs/mariadb/models/use.model.js @@ -0,0 +1,30 @@ +const { DataTypes } = require('sequelize') + +const seq = require('../db/seq') + +// 创建模型(Model zd_user -> 表 zd_users) +const User = seq.define('zd_user', { + // id 会被sequelize自动创建, 管理 + user_name: { + type: DataTypes.STRING, + allowNull: false, + unique: true, + comment: '用户名, 唯一', + }, + password: { + type: DataTypes.CHAR(64), + allowNull: false, + comment: '密码', + }, + is_admin: { + type: DataTypes.BOOLEAN, + allowNull: false, + defaultValue: 0, + comment: '是否为管理员, 0: 不是管理员(默认); 1: 是管理员', + }, +}) + +// 强制同步数据库(创建数据表) +// User.sync({ force: true }) + +module.exports = User diff --git a/examples/dbs/mariadb/models/user.js b/examples/dbs/mariadb/models/user.js new file mode 100644 index 0000000..393f8db --- /dev/null +++ b/examples/dbs/mariadb/models/user.js @@ -0,0 +1,30 @@ +const { DataTypes } = require('sequelize') + +const seq = require('../db/mariadb') + +// 创建模型(Model user -> 数据库表 users) +const User = seq.define('user', { + // id 会被sequelize自动创建, 管理 + username: { + type: DataTypes.STRING, + allowNull: false, + unique: true, + comment: '用户名, 唯一', + }, + password: { + type: DataTypes.CHAR(64), + allowNull: false, + comment: '密码', + }, + is_admin: { + type: DataTypes.BOOLEAN, + allowNull: false, + defaultValue: 0, + comment: '是否为管理员: 0 不是管理员(默认); 1 是管理员', + }, +}) + +// 强制同步数据库(创建数据表) +// User.sync({ force: true }) + +module.exports = User diff --git a/examples/dbs/mariadb/routers/addr.route.js b/examples/dbs/mariadb/routers/addr.route.js new file mode 100644 index 0000000..208fc04 --- /dev/null +++ b/examples/dbs/mariadb/routers/addr.route.js @@ -0,0 +1,54 @@ +// 一. 导入koa-router包 +const Router = require('koa-router') + +// 二. 实例化对象 +const router = new Router({ prefix: '/address' }) + +// 中间件/控制器 +const { auth } = require('../middleware/auth.middleware') +const { validator } = require('../middleware/addr.middleware') + +const { + create, + findAll, + update, + remove, + setDefault, +} = require('../controller/addr.controller') + +// 三. 编写路由规则 +// 3.1 添加接口: 登录, 格式 +router.post( + '/', + auth, + validator({ + consignee: 'string', + phone: { type: 'string', format: /^1\d{10}$/ }, + address: 'string', + }), + create +) + +// 3.2 获取地址列表 +router.get('/', auth, findAll) + +// 3.3 更新地址 +router.put( + '/:id', + auth, + validator({ + consignee: 'string', + phone: { type: 'string', format: /^1\d{10}$/ }, + address: 'string', + }), + update +) + +// 3.4 删除地址 +router.delete('/:id', auth, remove) + +// 3.5 设置默认 +router.patch('/:id', auth, setDefault) + +// 四. 导出router对象 +module.exports = router diff --git a/examples/dbs/mariadb/routers/cart.route.js b/examples/dbs/mariadb/routers/cart.route.js new file mode 100644 index 0000000..adc6cb6 --- /dev/null +++ b/examples/dbs/mariadb/routers/cart.route.js @@ -0,0 +1,48 @@ +// 1. 导入koa-router +const Router = require('koa-router') + +// 中间件 +const { auth } = require('../middleware/auth.middleware') +const { validator } = require('../middleware/cart.middleware') + +// 控件器 +const { + add, + findAll, + update, + remove, + selectAll, + unselectAll, +} = require('../controller/cart.controller') + +// 2. 实例化router对象 +const router = new Router({ prefix: '/carts' }) + +// 3. 编写路由规则 + +// 3.1 添加到购物车接口: 登录, 格式 +router.post('/', auth, validator({ goods_id: 'number' }), add) + +// 3.2 获取购物车列表 +router.get('/', auth, findAll) + +// 3.3 更新购物车 +router.patch( + '/:id', + auth, + validator({ + number: { type: 'number', required: false }, + selected: { type: 'bool', required: false }, + }), + update +) + +// 3.4 删除购物车 +router.delete('/', auth, validator({ ids: 'array' }), remove) + +// 3.5 全选与全不选 +router.post('/selectAll', auth, selectAll) +router.post('/unselectAll', auth, unselectAll) + +// 4. 导出router对象 +module.exports = router diff --git a/examples/dbs/mariadb/routers/goods.route.js b/examples/dbs/mariadb/routers/goods.route.js new file mode 100644 index 0000000..04b7262 --- /dev/null +++ b/examples/dbs/mariadb/routers/goods.route.js @@ -0,0 +1,35 @@ +const Router = require('koa-router') + +const { auth, hadAdminPermission } = require('../middleware/auth.middleware') +const { validator } = require('../middleware/goods.middleware') + +const { + upload, + create, + update, + remove, + restore, + findAll, +} = require('../controller/goods.controller') + +const router = new Router({ prefix: '/goods' }) + +// 商品图片上传接口 +router.post('/upload', auth, hadAdminPermission, upload) + +// 发布商品接口 +router.post('/', auth, hadAdminPermission, validator, create) + +// 修改商品接口 +router.put('/:id', auth, hadAdminPermission, validator, update) + +// 硬删除接口 +// router.delete('/:id', auth, hadAdminPermission, remove) + +router.post('/:id/off', auth, hadAdminPermission, remove) +router.post('/:id/on', auth, hadAdminPermission, restore) + +// 获取商品列表 +router.get('/', findAll) + +module.exports = router diff --git a/examples/dbs/mariadb/routers/index.js b/examples/dbs/mariadb/routers/index.js new file mode 100644 index 0000000..e8a74c5 --- /dev/null +++ b/examples/dbs/mariadb/routers/index.js @@ -0,0 +1,14 @@ +const fs = require('fs') + +const Router = require('koa-router') +const router = new Router() + +fs.readdirSync(__dirname).forEach(file => { + // console.log(file) + if (file !== 'index.js') { + let r = require('./' + file) + router.use(r.routes()) + } +}) + +module.exports = router diff --git a/examples/dbs/mariadb/routers/order.route.js b/examples/dbs/mariadb/routers/order.route.js new file mode 100644 index 0000000..c5d9be7 --- /dev/null +++ b/examples/dbs/mariadb/routers/order.route.js @@ -0,0 +1,34 @@ +const Router = require('koa-router') +const router = new Router({ prefix: '/orders' }) + +const { auth } = require('../middleware/auth.middleware') +const { validator } = require('../middleware/order.middleware') + +const { create, findAll, update } = require('../controller/order.controller') + +// 提交订单 +router.post( + '/', + auth, + validator({ + address_id: 'int', + goods_info: 'string', + total: 'string', + }), + create +) + +// 获取订单列表 +router.get('/', auth, findAll) + +// 更新订单状态 +router.patch( + '/:id', + auth, + validator({ + status: 'number', + }), + update +) + +module.exports = router diff --git a/examples/dbs/mariadb/routers/user.route.js b/examples/dbs/mariadb/routers/user.route.js new file mode 100644 index 0000000..04bd713 --- /dev/null +++ b/examples/dbs/mariadb/routers/user.route.js @@ -0,0 +1,28 @@ +const Router = require('koa-router') + +const { + userValidator, + verifyUser, + crpytPassword, + verifyLogin, +} = require('../middleware/user.middleware') + +const { auth } = require('../middleware/auth.middleware') +const { + register, + login, + changePassword, +} = require('../controller/user.controller') + +const router = new Router({ prefix: '/users' }) + +// 注册接口 +router.post('/register', userValidator, verifyUser, crpytPassword, register) + +// 登录接口 +router.post('/login', userValidator, verifyLogin, login) + +// 修改密码接口 +router.patch('/', auth, crpytPassword, changePassword) + +module.exports = router diff --git a/examples/dbs/mariadb/services/addr.service.js b/examples/dbs/mariadb/services/addr.service.js new file mode 100644 index 0000000..1885593 --- /dev/null +++ b/examples/dbs/mariadb/services/addr.service.js @@ -0,0 +1,44 @@ +const Address = require('../model/addr.model') + +class AddrService { + async createAddr(addr) { + return await Address.create(addr) + } + + async findAllAddr(user_id) { + return await Address.findAll({ + attributes: ['id', 'consignee', 'phone', 'address', 'is_default'], + where: { user_id }, + }) + } + + async updateAddr(id, addr) { + return await Address.update(addr, { where: { id } }) + } + + async removeAddr(id) { + return await Address.destroy({ where: { id } }) + } + + async setDefaultAddr(user_id, id) { + await Address.update( + { is_default: false }, + { + where: { + user_id, + }, + } + ) + + return await Address.update( + { is_default: true }, + { + where: { + id, + }, + } + ) + } +} + +module.exports = new AddrService() diff --git a/examples/dbs/mariadb/services/cart.service.js b/examples/dbs/mariadb/services/cart.service.js new file mode 100644 index 0000000..248fce0 --- /dev/null +++ b/examples/dbs/mariadb/services/cart.service.js @@ -0,0 +1,96 @@ +const { Op } = require('sequelize') +const Cart = require('../model/cart.model') +const Goods = require('../model/goods.model') + +class CartService { + async createOrUpdate(user_id, goods_id) { + // 根据user_id和goods_id同时查找, 有没有记录 + let res = await Cart.findOne({ + where: { + [Op.and]: { + user_id, + goods_id, + }, + }, + }) + + if (res) { + // 已经存在一条记录, 将number + 1 + await res.increment('number') + return await res.reload() + } else { + return await Cart.create({ + user_id, + goods_id, + }) + } + } + + async findCarts(pageNum, pageSize) { + const offset = (pageNum - 1) * pageSize + const { count, rows } = await Cart.findAndCountAll({ + attributes: ['id', 'number', 'selected'], + offset: offset, + limit: pageSize * 1, + include: { + model: Goods, + as: 'goods_info', + attributes: ['id', 'goods_name', 'goods_price', 'goods_img'], + }, + }) + return { + pageNum, + pageSize, + total: count, + list: rows, + } + } + + async updateCarts(params) { + const { id, number, selected } = params + + const res = await Cart.findByPk(id) + if (!res) return '' + + number !== undefined ? (res.number = number) : '' + if (selected !== undefined) { + res.selected = selected + } + + return await res.save() + } + + async removeCarts(ids) { + return await Cart.destroy({ + where: { + id: { + [Op.in]: ids, + }, + }, + }) + } + + async selectAllCarts(user_id) { + return await Cart.update( + { selected: true }, + { + where: { + user_id, + }, + } + ) + } + + async unselectAllCarts(user_id) { + return await Cart.update( + { selected: false }, + { + where: { + user_id, + }, + } + ) + } +} + +module.exports = new CartService() diff --git a/examples/dbs/mariadb/services/goods.service.js b/examples/dbs/mariadb/services/goods.service.js new file mode 100644 index 0000000..a4ebd70 --- /dev/null +++ b/examples/dbs/mariadb/services/goods.service.js @@ -0,0 +1,49 @@ +const Goods = require('../model/goods.model') + +class GoodsService { + async createGoods(goods) { + const res = await Goods.create(goods) + return res.dataValues + } + + async updateGoods(id, goods) { + const res = await Goods.update(goods, { where: { id } }) + + return res[0] > 0 ? true : false + } + + async removeGoods(id) { + const res = await Goods.destroy({ where: { id } }) + + return res > 0 ? true : false + } + + async restoreGoods(id) { + const res = await Goods.restore({ where: { id } }) + + return res > 0 ? true : false + } + + async findGoods(pageNum, pageSize) { + // // 1. 获取总数 + // const count = await Goods.count() + // // console.log(count) + // // 2. 获取分页的具体数据 + // const offset = (pageNum - 1) * pageSize + // const rows = await Goods.findAll({ offset: offset, limit: pageSize * 1 }) + + const offset = (pageNum - 1) * pageSize + const { count, rows } = await Goods.findAndCountAll({ + offset: offset, + limit: pageSize * 1, + }) + return { + pageNum, + pageSize, + total: count, + list: rows, + } + } +} + +module.exports = new GoodsService() diff --git a/examples/dbs/mariadb/services/order.service.js b/examples/dbs/mariadb/services/order.service.js new file mode 100644 index 0000000..a073f63 --- /dev/null +++ b/examples/dbs/mariadb/services/order.service.js @@ -0,0 +1,31 @@ +const Order = require('../model/order.model') + +class OrderService { + async createOrder(order) { + return await Order.create(order) + } + + async findAllOrder(pageNum, pageSize, status) { + const { count, rows } = await Order.findAndCountAll({ + attributes: ['goods_info', 'total', 'order_number', 'status'], + where: { + status, + }, + offset: (pageNum - 1) * pageSize, + limit: pageSize * 1, + }) + + return { + pageNum, + pageSize, + total: count, + list: rows, + } + } + + async updateOrder(id, status) { + return await Order.update({ status }, { where: { id } }) + } +} + +module.exports = new OrderService() diff --git a/examples/dbs/mariadb/services/user.js b/examples/dbs/mariadb/services/user.js new file mode 100644 index 0000000..c96fd97 --- /dev/null +++ b/examples/dbs/mariadb/services/user.js @@ -0,0 +1,42 @@ +const User = require('../models/user') + +class UserService { + async createUser(user_name, password) { + // 插入数据 + // await表达式: promise对象的值 + const res = await User.create({ user_name, password }) + // console.log(res) + return res.dataValues + } + + async getUerInfo({ id, user_name, password, is_admin }) { + const whereOpt = {} + + id && Object.assign(whereOpt, { id }) + user_name && Object.assign(whereOpt, { user_name }) + password && Object.assign(whereOpt, { password }) + is_admin && Object.assign(whereOpt, { is_admin }) + + const res = await User.findOne({ + attributes: ['id', 'user_name', 'password', 'is_admin'], + where: whereOpt, + }) + + return res ? res.dataValues : null + } + + async updateById({ id, user_name, password, is_admin }) { + const whereOpt = { id } + const newUser = {} + + user_name && Object.assign(newUser, { user_name }) + password && Object.assign(newUser, { password }) + is_admin && Object.assign(newUser, { is_admin }) + + const res = await User.update(newUser, { where: whereOpt }) + // console.log(res) + return res[0] > 0 ? true : false + } +} + +module.exports = new UserService() diff --git a/examples/dbs/mariadb/services/user.service.js b/examples/dbs/mariadb/services/user.service.js new file mode 100644 index 0000000..27d0941 --- /dev/null +++ b/examples/dbs/mariadb/services/user.service.js @@ -0,0 +1,42 @@ +const User = require('../model/use.model') + +class UserService { + async createUser(user_name, password) { + // 插入数据 + // await表达式: promise对象的值 + const res = await User.create({ user_name, password }) + // console.log(res) + return res.dataValues + } + + async getUerInfo({ id, user_name, password, is_admin }) { + const whereOpt = {} + + id && Object.assign(whereOpt, { id }) + user_name && Object.assign(whereOpt, { user_name }) + password && Object.assign(whereOpt, { password }) + is_admin && Object.assign(whereOpt, { is_admin }) + + const res = await User.findOne({ + attributes: ['id', 'user_name', 'password', 'is_admin'], + where: whereOpt, + }) + + return res ? res.dataValues : null + } + + async updateById({ id, user_name, password, is_admin }) { + const whereOpt = { id } + const newUser = {} + + user_name && Object.assign(newUser, { user_name }) + password && Object.assign(newUser, { password }) + is_admin && Object.assign(newUser, { is_admin }) + + const res = await User.update(newUser, { where: whereOpt }) + // console.log(res) + return res[0] > 0 ? true : false + } +} + +module.exports = new UserService() diff --git a/examples/dbs/mongodb/controller/methods.js b/examples/dbs/mongodb/controller/methods.js new file mode 100644 index 0000000..3746001 --- /dev/null +++ b/examples/dbs/mongodb/controller/methods.js @@ -0,0 +1,5 @@ +const { } = require("../services/service"); + +class Controller {} + +module.exports = new Controller(); diff --git a/examples/dbs/mongodb/db/mongo.js b/examples/dbs/mongodb/db/mongo.js new file mode 100644 index 0000000..3badc23 --- /dev/null +++ b/examples/dbs/mongodb/db/mongo.js @@ -0,0 +1,9 @@ +const mongoose = require("mongoose"); + +const { MONGO_HOST, MONGO_PORT, MONGO_DBNAME, MONGO_USER, MONGO_PASSWD } = + process.env; +const URI = `mongodb://${MONGO_USER}:${MONGO_PASSWD}@${MONGO_HOST}:${MONGO_PORT}/${MONGO_DBNAME}`; + +mongoose.connect(URI); + +module.exports = { mongoose }; diff --git a/examples/dbs/mongodb/models/book.js b/examples/dbs/mongodb/models/book.js new file mode 100644 index 0000000..60927b3 --- /dev/null +++ b/examples/dbs/mongodb/models/book.js @@ -0,0 +1,24 @@ +const { mongoose } = require("../../db/mgs.mongo"); + +const BookSchema = mongoose.Schema({ + name: { + type: String, + require: true, + }, + author: { + type: String, + }, + wordCount: { + type: Number, + }, + publishTime: { + type: Date, + default: Date.now, + }, +}); + +const Book = mongoose.model("Book", BookSchema); + +// let book = new Book({}); + +module.exports = { Book }; diff --git a/examples/dbs/mongodb/services/service.js b/examples/dbs/mongodb/services/service.js new file mode 100644 index 0000000..0520c47 --- /dev/null +++ b/examples/dbs/mongodb/services/service.js @@ -0,0 +1,5 @@ +const { client } = require("../db/mongo"); + +class Service {} + +module.exports = new Service(); diff --git a/examples/dbs/mysql/controller/user.js b/examples/dbs/mysql/controller/user.js new file mode 100644 index 0000000..dda5092 --- /dev/null +++ b/examples/dbs/mysql/controller/user.js @@ -0,0 +1,12 @@ +const { d } = require("../models/user"); + +class UserController { + async register(ctx, next) { + ctx.json({ code: 0, message: "success" }); + } + + async getUserList(ctx, next) { + ctx.json({ code: 0, message: "success" }); + } +} +module.exports = new UserController(); diff --git a/examples/dbs/mysql/db/mariadb.js b/examples/dbs/mysql/db/mariadb.js new file mode 100644 index 0000000..1b5cf40 --- /dev/null +++ b/examples/dbs/mysql/db/mariadb.js @@ -0,0 +1,27 @@ +// connect to third-service of database or other. +const { Sequelize } = require("sequelize"); + +const { + MARIA_DIALECT, + MARIA_HOST, + MARIA_PORT, + MARIA_DBNAME, + MARIA_USRNAME, + MARIA_PASSWD, +} = process.env; + +const seq = new Sequelize(MARIA_DBNAME, MARIA_USRNAME, MARIA_PASSWD, { + host: MARIA_HOST, + port: MARIA_PORT, + dialect: 'mariadb', +}); + +seq.authenticate() + .then(() => { + console.log('数据库连接成功') + }) + .catch(err => { + console.log('数据库连接失败', err) + }) + +module.exports = seq; diff --git a/examples/dbs/mysql/db/redis.js b/examples/dbs/mysql/db/redis.js new file mode 100644 index 0000000..c81cbdc --- /dev/null +++ b/examples/dbs/mysql/db/redis.js @@ -0,0 +1,49 @@ +const redis = require("redis"); +// require("../config/env.config"); + +const { REDIS_HOST, REDIS_PORT, REDIS_DBNAME, REDIS_USER, REDIS_PASSWD } = + process.env; // REDIS_USER 和 REDIS_PASSWD,需要服务器配置ACL用户名密码 +const URL = `redis://${REDIS_USER}:${REDIS_PASSWD}@${REDIS_HOST}:${REDIS_PORT}/${REDIS_DBNAME}`; + +// https://github.com/redis/node-redis/tree/master/docs +// module.exports = redis.createClient({URL}); +const client = redis.createClient({ + // url: URL, + socket: { host: REDIS_HOST, port: REDIS_PORT }, + password: REDIS_PASSWD, + // database: REDIS_DBNAME, + // legacyMode: true, // 语法向后(v3)部分兼容 +}); + +client.on("error", (err) => console.log(`redis client ~ Error ${err}`)); +client.on("connect", () => console.log("redis client ~ connect")); +client.on("reconnecting", () => console.log("redis client ~ reconnecting")); +client.on("ready", () => console.log("redis client ~ ready")); +client.on("end", () => console.log("redis client ~ end")); + +client.connect(); +client.ping(); +// try { +// } catch (error) { +// console.log(error); +// } + +module.exports = client; + +//* 方式二:redis 连接池 +//! unusable +/* var redisPool = require("redis-connection-pool")("myRedisPool", { + host: REDIS_HOST, // default + port: REDIS_PORT, //default + max_clients: 30, // defalut + perform_checks: false, // checks for needed push/pop functionality + database: 0, // database number to use + options: { + auth_pass: REDIS_PASSWD, + }, //options for createClient of node-redis, optional +}); +redisPool.set("test-key", "foobar", function (err) { + redisPool.get("test-key", function (err, reply) { + console.log(reply); // 'foobar' + }); +}); */ diff --git a/examples/dbs/mysql/models/user.js b/examples/dbs/mysql/models/user.js new file mode 100644 index 0000000..393f8db --- /dev/null +++ b/examples/dbs/mysql/models/user.js @@ -0,0 +1,30 @@ +const { DataTypes } = require('sequelize') + +const seq = require('../db/mariadb') + +// 创建模型(Model user -> 数据库表 users) +const User = seq.define('user', { + // id 会被sequelize自动创建, 管理 + username: { + type: DataTypes.STRING, + allowNull: false, + unique: true, + comment: '用户名, 唯一', + }, + password: { + type: DataTypes.CHAR(64), + allowNull: false, + comment: '密码', + }, + is_admin: { + type: DataTypes.BOOLEAN, + allowNull: false, + defaultValue: 0, + comment: '是否为管理员: 0 不是管理员(默认); 1 是管理员', + }, +}) + +// 强制同步数据库(创建数据表) +// User.sync({ force: true }) + +module.exports = User diff --git a/examples/dbs/mysql/services/redis.js b/examples/dbs/mysql/services/redis.js new file mode 100644 index 0000000..82a323d --- /dev/null +++ b/examples/dbs/mysql/services/redis.js @@ -0,0 +1,29 @@ +const redisClient = require("../../db/redis"); + +/** +Object.prototype.toString = function () { + return JSON.stringify(this); +}; +*/ + +class RedisService { + client = redisClient; + + save2Redis(key, value) { + redisClient.set(key, value); + } + + getByKey(key, callback = null) { + if (callback) { + redisClient.get(key, callback); + } else { + redisClient.get(key, (err, value) => { + if (err) return null; + console.log(value); + // return value; + }); + } + } +} + +module.exports = new RedisService(); diff --git a/examples/dbs/mysql/services/user.js b/examples/dbs/mysql/services/user.js new file mode 100644 index 0000000..c96fd97 --- /dev/null +++ b/examples/dbs/mysql/services/user.js @@ -0,0 +1,42 @@ +const User = require('../models/user') + +class UserService { + async createUser(user_name, password) { + // 插入数据 + // await表达式: promise对象的值 + const res = await User.create({ user_name, password }) + // console.log(res) + return res.dataValues + } + + async getUerInfo({ id, user_name, password, is_admin }) { + const whereOpt = {} + + id && Object.assign(whereOpt, { id }) + user_name && Object.assign(whereOpt, { user_name }) + password && Object.assign(whereOpt, { password }) + is_admin && Object.assign(whereOpt, { is_admin }) + + const res = await User.findOne({ + attributes: ['id', 'user_name', 'password', 'is_admin'], + where: whereOpt, + }) + + return res ? res.dataValues : null + } + + async updateById({ id, user_name, password, is_admin }) { + const whereOpt = { id } + const newUser = {} + + user_name && Object.assign(newUser, { user_name }) + password && Object.assign(newUser, { password }) + is_admin && Object.assign(newUser, { is_admin }) + + const res = await User.update(newUser, { where: whereOpt }) + // console.log(res) + return res[0] > 0 ? true : false + } +} + +module.exports = new UserService() diff --git a/examples/dbs/npm.sh b/examples/dbs/npm.sh new file mode 100644 index 0000000..8e51f30 --- /dev/null +++ b/examples/dbs/npm.sh @@ -0,0 +1,9 @@ + +npm i -S mariadb +npm i -S mongoose +npm i -S mysql2 +npm i -S sequelize +npm i -S redis +npm i -S redis-connection-pool +npm i -S +npm i -S \ No newline at end of file diff --git a/examples/dbs/postgresql/controller/methods.js b/examples/dbs/postgresql/controller/methods.js new file mode 100644 index 0000000..3746001 --- /dev/null +++ b/examples/dbs/postgresql/controller/methods.js @@ -0,0 +1,5 @@ +const { } = require("../services/service"); + +class Controller {} + +module.exports = new Controller(); diff --git a/examples/dbs/postgresql/db/postgres.js b/examples/dbs/postgresql/db/postgres.js new file mode 100644 index 0000000..47463d7 --- /dev/null +++ b/examples/dbs/postgresql/db/postgres.js @@ -0,0 +1,5 @@ +const redis = require(""); + +const { POSTGRES_HOST, POSTGRES_PORT, POSTGRES_DBNAME, POSTGRES_USER, POSTGRES_PASSWD } = process.env; + +module.exports = client; diff --git a/examples/dbs/postgresql/models/model.js b/examples/dbs/postgresql/models/model.js new file mode 100644 index 0000000..9130b84 --- /dev/null +++ b/examples/dbs/postgresql/models/model.js @@ -0,0 +1,3 @@ +const { client } = require("../db/"); + +module.exports = Model; diff --git a/examples/dbs/postgresql/services/service.js b/examples/dbs/postgresql/services/service.js new file mode 100644 index 0000000..e6e022d --- /dev/null +++ b/examples/dbs/postgresql/services/service.js @@ -0,0 +1,5 @@ +const { client } = require("../db/postgres"); + +class Service {} + +module.exports = new Service(); diff --git a/examples/dbs/redis/controller/operate.js b/examples/dbs/redis/controller/operate.js new file mode 100644 index 0000000..43b5d66 --- /dev/null +++ b/examples/dbs/redis/controller/operate.js @@ -0,0 +1,5 @@ +const { getByKey, save2Redis } = require("../services/baseOps"); + +class RedisController {} + +module.exports = new RedisController(); diff --git a/examples/dbs/redis/db/redis.js b/examples/dbs/redis/db/redis.js new file mode 100644 index 0000000..84ac966 --- /dev/null +++ b/examples/dbs/redis/db/redis.js @@ -0,0 +1,49 @@ +const redis = require("redis"); +// require("../config/env.config"); + +const { REDIS_HOST, REDIS_PORT, REDIS_DBNAME, REDIS_USER, REDIS_PASSWD } = + process.env; // REDIS_USER 和 REDIS_PASSWD,需要服务器配置ACL用户名密码 +const URL = `redis://${REDIS_USER}:${REDIS_PASSWD}@${REDIS_HOST}:${REDIS_PORT}/${REDIS_DBNAME}`; + +// https://github.com/redis/node-redis/tree/master/docs +// module.exports = redis.createClient({URL}); +const client = redis.createClient({ + // url: URL, + socket: { host: REDIS_HOST, port: REDIS_PORT }, + password: REDIS_PASSWD, + // database: REDIS_DBNAME, + // legacyMode: true, // 语法向后(v3)部分兼容 +}); + +client.on("error", (err) => console.log(`redis client ~ Error ${err}`)); +client.on("connect", () => console.log("redis client ~ connect")); +client.on("reconnecting", () => console.log("redis client ~ reconnecting")); +client.on("ready", () => console.log("redis client ~ ready")); +client.on("end", () => console.log("redis client ~ end")); + +client.connect(); +client.ping(); +// try { +// } catch (error) { +// console.log(error); +// } + +module.exports = client; + +//* 方式二:redis 连接池 +//! 报错,不可用 +/* var redisPool = require("redis-connection-pool")("myRedisPool", { + host: REDIS_HOST, // default + port: REDIS_PORT, //default + max_clients: 30, // defalut + perform_checks: false, // checks for needed push/pop functionality + database: 0, // database number to use + options: { + auth_pass: REDIS_PASSWD, + }, //options for createClient of node-redis, optional +}); +redisPool.set("test-key", "foobar", function (err) { + redisPool.get("test-key", function (err, reply) { + console.log(reply); // 'foobar' + }); +}); */ diff --git a/examples/dbs/redis/models/model.js b/examples/dbs/redis/models/model.js new file mode 100644 index 0000000..2006068 --- /dev/null +++ b/examples/dbs/redis/models/model.js @@ -0,0 +1,4 @@ +const { client } = require("../db/redis"); + + +module.exports = User diff --git a/examples/dbs/redis/services/baseOps.js b/examples/dbs/redis/services/baseOps.js new file mode 100644 index 0000000..3cf41fc --- /dev/null +++ b/examples/dbs/redis/services/baseOps.js @@ -0,0 +1,29 @@ +const { client } = require("../db/redis"); + +/** +Object.prototype.toString = function () { + return JSON.stringify(this); +}; +*/ + +class RedisService { + client = client; + + save2Redis(key, value) { + client.set(key, value); + } + + getByKey(key, callback = null) { + if (callback) { + client.get(key, callback); + } else { + client.get(key, (err, value) => { + if (err) return null; + console.log(value); + // return value; + }); + } + } +} + +module.exports = new RedisService(); diff --git a/examples/dbs/redis/test/test.js b/examples/dbs/redis/test/test.js new file mode 100644 index 0000000..229bacd --- /dev/null +++ b/examples/dbs/redis/test/test.js @@ -0,0 +1,18 @@ +const { + client, + save2Redis, + getByKey, +} = require("../src/service/redis/base.service"); + +save2Redis("key1", "i am string value"); +// redis 储存时默认调用 Object.toString 而非 JSON.stringify +// save2Redis("key2", { key: "i am string value from Object.toString()" }); // value是object,报参数类型错误 + +getByKey("key2"); // 无console输出 + +client.rPush("alist", "abc"); +// client.rPush("alist", 123); // value是object,报参数类型错误 +client.lRange("alist", 0, -1, (err, v) => { + console.log(v); // 无console输出 + client.disconnect(); +}); diff --git a/examples/dbs/sqlite/controller/methods.js b/examples/dbs/sqlite/controller/methods.js new file mode 100644 index 0000000..970e067 --- /dev/null +++ b/examples/dbs/sqlite/controller/methods.js @@ -0,0 +1,5 @@ +const { } = require("../services/"); + +class RedisController {} + +module.exports = new RedisController(); diff --git a/examples/dbs/sqlite/db/sqlite3.js b/examples/dbs/sqlite/db/sqlite3.js new file mode 100644 index 0000000..7ca2950 --- /dev/null +++ b/examples/dbs/sqlite/db/sqlite3.js @@ -0,0 +1,5 @@ +const redis = require(""); + +const { SQLITE3_HOST, SQLITE3_PORT, SQLITE3_DBNAME, SQLITE3_USER, SQLITE3_PASSWD } = process.env; + +module.exports = client; diff --git a/examples/dbs/sqlite/models/model.js b/examples/dbs/sqlite/models/model.js new file mode 100644 index 0000000..9130b84 --- /dev/null +++ b/examples/dbs/sqlite/models/model.js @@ -0,0 +1,3 @@ +const { client } = require("../db/"); + +module.exports = Model; diff --git a/examples/dbs/sqlite/services/service.js b/examples/dbs/sqlite/services/service.js new file mode 100644 index 0000000..b598b86 --- /dev/null +++ b/examples/dbs/sqlite/services/service.js @@ -0,0 +1,5 @@ +const { client } = require("../db/"); + +class Service {} + +module.exports = new Service(); diff --git a/scripts/clean.ps1 b/examples/shells/clean.ps1 similarity index 100% rename from scripts/clean.ps1 rename to examples/shells/clean.ps1 diff --git a/initProject.ps1 b/examples/shells/initProject.ps1 similarity index 100% rename from initProject.ps1 rename to examples/shells/initProject.ps1 diff --git a/package-lock.json b/package-lock.json index 932a245..9582013 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "koa2-template", - "version": "1.0.1", + "version": "0.0.1", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "koa2-template", - "version": "1.0.1", + "version": "0.0.1", "license": "MIT", "dependencies": { "bcryptjs": "^2.4.3", diff --git a/public/js/placeholder.js b/public/js/placeholder.js new file mode 100644 index 0000000..e69de29 diff --git a/scripts/placeholder.ps1 b/scripts/placeholder.ps1 new file mode 100644 index 0000000..e2bf85c --- /dev/null +++ b/scripts/placeholder.ps1 @@ -0,0 +1,2 @@ +nvm +yarn \ No newline at end of file diff --git a/src/routers/error.ts b/src/routers/error.ts deleted file mode 100644 index 7776136..0000000 --- a/src/routers/error.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { getUserList } from "../controller/user"; - -import Router from "koa-router"; -export const router = new Router({ prefix: "/" }); - -router.get("/list", getUserList);