chanjs 1.0.23 → 1.0.25

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -34,7 +34,7 @@ Chan.js 基于express 纯js研发的轻量级mvc框架。基于函数式编程
34
34
  |- extend 扩展
35
35
  |- middleware 中间件
36
36
  |- plugin 插件
37
- |- plus-module1 插件1
37
+ |- plus-module1 插件1
38
38
  |- controller 控制器
39
39
  |- service 服务模型
40
40
  |- view 视图模板
@@ -67,28 +67,30 @@ Chan.js 基于express 纯js研发的轻量级mvc框架。基于函数式编程
67
67
  ### 官网
68
68
 
69
69
  基于Chanjs开发的cms系统
70
- 网址:https://www.chancms.top
70
+ 网址:<https://www.chancms.top>
71
71
 
72
-
73
72
  ### 特点
74
73
 
75
- * 配置文件
76
- * 多模块mvc
77
- * 插件mvc
78
- * 支持cors跨域配置
79
- * mysql数据库支持
80
- * 路由控制
81
- * art-template模板
82
- * 静态资源
83
- * cookie
84
- * 日志功能
85
-
86
-
74
+ - 配置文件
75
+ - 多模块mvc
76
+ - 插件mvc
77
+ - 支持cors跨域配置
78
+ - mysql数据库支持
79
+ - 路由控制
80
+ - art-template模板
81
+ - 静态资源
82
+ - cookie
83
+ - 日志功能
87
84
 
88
85
  ### 运行
89
86
 
90
87
  ```javascript
91
- const Chan = require('chanjs');
92
- const app = new Chan();
93
- app.run();
88
+ const Chan = require('Chan');
89
+ const chan = new Chan();
90
+ //加载中间件
91
+ chan.beforeStart(fn);
92
+ //加载模块
93
+ chan.start();
94
+ //启动服务
95
+ chan.run();
94
96
  ```
package/core/chan.js CHANGED
@@ -1,12 +1,12 @@
1
1
  const express = require("express");
2
2
  const config = require("./lib/config/config.js");
3
3
  const bindClass = require("./lib/extend/bindClass.js");
4
- const Controller = require("./lib/controller/controller.js")
5
- const Service = require("./lib/service/service.js")
4
+ const Controller = require("./lib/controller/controller.js");
5
+ const Service = require("./lib/service/service.js");
6
6
  const path = require("path");
7
7
  const fs = require("fs");
8
8
  const core = require("./lib/index.js");
9
- const cors = require('cors');
9
+ const cors = require("cors");
10
10
 
11
11
  /**
12
12
  * @description 基于express封装的mvc框架,遵循约定优于配置原则
@@ -15,20 +15,22 @@ class Chan {
15
15
  static config = {};
16
16
  //模块
17
17
  static modules = {};
18
- //插件
18
+ //插件
19
19
  static plugins = {};
20
- //工具
20
+ //工具
21
21
  static helper = {};
22
22
  static Controller = null;
23
23
  static Service = null;
24
- constructor(options={}) {
24
+ constructor(options = {}) {
25
25
  //配置
26
- Chan.config = {...config,...options};
26
+ Chan.config = { ...config, ...options };
27
27
  //控制器基类
28
28
  Chan.Controller = Controller;
29
- //应用实例
29
+ this.init();
30
+ }
31
+
32
+ init() {
30
33
  this.app = express();
31
- // this.app.config = Chan.config;
32
34
  this.router = express.Router();
33
35
  //加载配置
34
36
  this.loadConfig();
@@ -38,19 +40,8 @@ class Chan {
38
40
  this.loadCore();
39
41
  //加载实例化数据库
40
42
  this.loadKnex();
41
-
42
- //生命周期钩子:开始启动
43
- this.beforeStart();
44
43
  //解决跨域
45
44
  this.loadCors();
46
- //加载模块
47
- this.loadModules();
48
- //加载插件
49
- this.loadPlugins();
50
- //加载通用路由
51
- this.loadCommonRouter();
52
- //生命周期:初始化完成
53
- this.start()
54
45
  }
55
46
 
56
47
  // 加载配置
@@ -58,14 +49,12 @@ class Chan {
58
49
  const configPath = path.join(Chan.config.APP_PATH, "config/index.js");
59
50
  if (fs.existsSync(configPath)) {
60
51
  const config = require(configPath);
61
- // let allConfig = {...Chan.config,...config};
62
- // this.app.config = Chan.config = allConfig;
63
- Chan.config = {...Chan.config,...config};
52
+ Chan.config = { ...Chan.config, ...config };
64
53
  }
65
54
  }
66
55
 
67
- // 加载扩展
68
- loadExtends() {
56
+ // 加载扩展
57
+ loadExtends() {
69
58
  const extendPath = path.join(Chan.config.APP_PATH, "extend");
70
59
  if (fs.existsSync(extendPath)) {
71
60
  let controllers = fs
@@ -78,20 +67,19 @@ class Chan {
78
67
  Chan.helper[fileName] = helper;
79
68
  }
80
69
  }
81
-
82
70
  }
83
71
 
84
72
  //数据库操作
85
- loadKnex(){
73
+ loadKnex() {
86
74
  // 连接数据库
87
75
  const {
88
- host='localhost',
89
- port='3306',
76
+ host = "localhost",
77
+ port = "3306",
90
78
  user,
91
79
  password,
92
80
  database,
93
- client='mysql2',
94
- charset='utf8mb4'
81
+ client = "mysql2",
82
+ charset = "utf8mb4",
95
83
  } = Chan.config.database;
96
84
 
97
85
  const knex = require("knex")({
@@ -104,7 +92,7 @@ class Chan {
104
92
  database,
105
93
  charset,
106
94
  },
107
- debug: Chan.config.debug, //指明是否开启debug模式,默认为true表示开启
95
+ debug: Chan.config.SqlDebug, //指明是否开启debug模式,默认为true表示开启
108
96
  pool: {
109
97
  //指明数据库连接池的大小,默认为{min: 2, max: 10}
110
98
  min: 0,
@@ -131,80 +119,93 @@ class Chan {
131
119
  // 初始化一些配置
132
120
  cb && cb();
133
121
  }
134
-
135
122
  //启动
136
- start(cb){
123
+ start(cb) {
124
+ //加载模块
125
+ this.loadModules();
126
+ //加载插件
127
+ this.loadPlugins();
128
+ //加载通用路由
129
+ this.loadCommonRouter();
137
130
  // 初始化一些配置
138
131
  cb && cb();
139
132
  }
140
133
 
141
134
  //解决跨域
142
- loadCors(){
143
- Chan.config?.cors?.origin && this.app.use(cors(Chan.config.cors));
135
+ loadCors() {
136
+ Chan.config?.cors?.origin && this.app.use(cors(Chan.config.cors));
144
137
  }
145
138
 
146
139
  // 加载插件
147
140
  loadPlugins() {
148
- this.loadModules('plugins');
141
+ this.loadModules("plugins");
149
142
  }
150
143
 
151
144
  /**
152
145
  * @description app核心模块:日志、favicon 图标、cookie、json、url、模板引擎、静态资源
153
146
  */
154
- loadCore(){
155
- console.log()
147
+ loadCore() {
156
148
  core(this.app, Chan.config);
157
149
  }
158
150
 
159
- /**
160
- * @description 模块加载入口(路由&控制器& 服务)
161
- */
162
- loadModules(modules='modules') {
163
- const configPath = path.join(Chan.config.APP_PATH,modules);
151
+ /**
152
+ * @description 模块加载入口(路由&控制器& 服务)
153
+ */
154
+ loadModules(modules = "modules") {
155
+ const configPath = path.join(Chan.config.APP_PATH, modules);
164
156
  if (fs.existsSync(configPath)) {
165
157
  const dirs = fs
166
158
  .readdirSync(configPath, { withFileTypes: true })
167
159
  .filter((dirent) => dirent.isDirectory())
168
160
  .map((dirent) => dirent.name);
169
- Chan[modules]={};
170
- for(let i=0,item;i<dirs.length;i++){
171
- item = dirs[i];
172
- Chan[modules][item] = {
173
- controller: {},
174
- service: {},
175
- };
176
- this.loadModule(modules,item);
177
- }
161
+ Chan[modules] = {};
162
+
163
+ // 先加载所有服务
164
+ dirs.forEach((item) => {
165
+ Chan[modules][item] = {
166
+ service: {},
167
+ controller: {},
168
+ };
169
+ this.loadServices(modules, item);
170
+ });
171
+
172
+ // 加载控制器和路由
173
+ dirs.forEach((item) => {
174
+ this.loadModule(modules, item);
175
+ });
176
+
178
177
  //执行路由
179
178
  // this.app.use(this.router);
180
179
  }
181
180
  }
182
181
 
183
-
184
182
  /**
185
- * @description 加载模块,包括 controller service router
183
+ * @description 加载模块,包括 controller service router
186
184
  * @param {String} moduleName 模块名称
187
185
  */
188
- loadModule(modules,moduleName) {
189
- this.loadServices(modules,moduleName);
190
- this.loadControllers(modules,moduleName);
191
- this.loadRoutes(modules,moduleName);
186
+ loadModule(modules, moduleName) {
187
+ this.loadControllers(modules, moduleName);
188
+ this.loadRoutes(modules, moduleName);
192
189
  }
193
190
 
194
-
195
191
  /**
196
192
  * @description 扫描模块下所有service
197
193
  * @param {*} moduleDir 模块路径
198
194
  * @param {*} moduleName 模块名称
199
195
  */
200
- loadServices(modules,moduleName) {
201
- const servicesDir = path.join(Chan.config.APP_PATH, modules, moduleName,"service");
196
+ loadServices(modules, moduleName) {
197
+ const servicesDir = path.join(
198
+ Chan.config.APP_PATH,
199
+ modules,
200
+ moduleName,
201
+ "service"
202
+ );
202
203
  if (fs.existsSync(servicesDir)) {
203
204
  let services = fs
204
205
  .readdirSync(servicesDir)
205
206
  .filter((file) => file.endsWith(".js"));
206
207
  for (let i = 0, file; i < services.length; i++) {
207
- file= services[i]
208
+ file = services[i];
208
209
  const Service = require(path.join(servicesDir, file));
209
210
  const serviceName = file.replace(".js", "");
210
211
  //模块文件夹-模块文件名-服务-方法
@@ -214,24 +215,29 @@ class Chan {
214
215
  }
215
216
  }
216
217
 
217
-
218
218
  /**
219
219
  * @description 扫描模块下所有controller
220
220
  * @param {*} moduleDir 模块路径
221
221
  * @param {*} moduleName 模块名称
222
222
  */
223
- loadControllers(modules,moduleName) {
224
- const controllersDir = path.join(Chan.config.APP_PATH, modules, moduleName,"controller");
223
+ loadControllers(modules, moduleName) {
224
+ const controllersDir = path.join(
225
+ Chan.config.APP_PATH,
226
+ modules,
227
+ moduleName,
228
+ "controller"
229
+ );
225
230
  if (fs.existsSync(controllersDir)) {
226
231
  let controllers = fs
227
232
  .readdirSync(controllersDir)
228
233
  .filter((file) => file.endsWith(".js"));
229
234
  for (let i = 0, file; i < controllers.length; i++) {
230
- file= controllers[i]
235
+ file = controllers[i];
231
236
  const controller = require(path.join(controllersDir, file));
232
237
  const controllerName = file.replace(".js", "");
233
238
  Chan[modules][moduleName].controller[controllerName] = {};
234
- Chan[modules][moduleName].controller[controllerName] = bindClass(controller);
239
+ Chan[modules][moduleName].controller[controllerName] =
240
+ bindClass(controller);
235
241
  }
236
242
  }
237
243
  }
@@ -241,33 +247,38 @@ class Chan {
241
247
  * @param {*} moduleDir 模块路径
242
248
  * @param {*} moduleName 模块名称
243
249
  */
244
- loadRoutes(modules,moduleName) {
245
- const routersDir = path.join(Chan.config.APP_PATH, modules, moduleName,"router.js");
250
+ loadRoutes(modules, moduleName) {
251
+ const routersDir = path.join(
252
+ Chan.config.APP_PATH,
253
+ modules,
254
+ moduleName,
255
+ "router.js"
256
+ );
246
257
  if (fs.existsSync(routersDir)) {
247
258
  const routes = require(routersDir);
248
- routes({router:this.router,modules:Chan[modules],app:this.app});
259
+ routes({ router: this.router, modules: Chan[modules], app: this.app });
249
260
  }
250
261
  }
251
262
 
252
- //通用路由,加载错误处理和500路由和爬虫处理
253
- loadCommonRouter(){
263
+ //通用路由,加载错误处理和500路由和爬虫处理
264
+ loadCommonRouter() {
254
265
  try {
255
266
  const baseRouterPath = path.join(Chan.config.APP_PATH, "router.js");
256
267
  if (fs.existsSync(baseRouterPath)) {
257
268
  const _router = require(baseRouterPath);
258
- _router(this.app, this.router,Chan.config);
259
- }
269
+ _router(this.app, this.router, Chan.config);
270
+ }
260
271
  } catch (error) {
261
272
  console.log(error);
262
273
  }
263
274
  }
264
-
275
+
265
276
  run() {
266
- const port = Chan.config.port || '81';
277
+ const port = Chan.config.port || "81";
267
278
  this.app.listen(port, () => {
268
279
  console.log(`Server is running on port ${port}`);
269
280
  });
270
281
  }
271
282
  }
272
-
273
- module.exports = Chan;
283
+ global.Chan = Chan;
284
+ module.exports = Chan;
@@ -12,12 +12,18 @@ const APP_PATH = path.join(ROOT_PATH, 'app');
12
12
 
13
13
  let config = {
14
14
  JSON_LIMIT:"100kb",
15
+ SqlDebug:true,
15
16
  logger : {
16
17
  level: 'dev',
17
18
  },
18
19
  env:'dev',
19
20
  template:'default',
20
21
  views:[], //模板路径
22
+ static:[{ //静态文件路径
23
+ prefix: "/public/",
24
+ dir: ["app/public"],
25
+ maxAge: 0,
26
+ }],
21
27
  database:{
22
28
  client: "mysql2",
23
29
  host: "localhost",
@@ -2,29 +2,24 @@
2
2
  * @description
3
3
  * 控制器基类
4
4
  */
5
- class Controller{
5
+ class Controller {
6
+ constructor() {}
6
7
 
7
- constructor(){
8
-
9
- }
8
+ download(res, file) {
9
+ res.download(file);
10
+ }
10
11
 
11
- download(res,file){
12
- res.download(file)
13
- }
12
+ success(res, data = null) {
13
+ res.json({ code: 200, msg: "success", data: data });
14
+ }
14
15
 
15
- success(res,data=null){
16
- res.json({code:200,msg:'success',data:data})
17
- }
16
+ fail(res, msg = "操作失败,请稍后再试") {
17
+ res.json({ code: 400, msg: msg });
18
+ }
18
19
 
19
- fail(res,msg='操作失败,请稍后再试'){
20
- res.json({code:400,msg:msg})
21
- }
22
-
23
- error(res,msg){
24
- res.json({code:500,msg:msg})
25
- }
20
+ error(res, msg) {
21
+ res.json({ code: 500, msg: msg });
22
+ }
26
23
  }
27
24
 
28
-
29
-
30
- module.exports = Controller;
25
+ module.exports = Controller;
@@ -4,20 +4,19 @@
4
4
  *@returns {Object} 包含绑定方法的对象。
5
5
  */
6
6
  function bindClass(className) {
7
- let obj = {};
8
- const cls = new className();
9
- Object.getOwnPropertyNames(cls.constructor.prototype).forEach(
10
- (methodName) => {
11
- if (
12
- methodName !== "constructor" &&
13
- typeof cls[methodName] === "function"
14
- ) {
15
- obj[methodName] = cls[methodName].bind(cls);
16
- }
7
+ let obj = {};
8
+ const cls = new className();
9
+ Object.getOwnPropertyNames(cls.constructor.prototype).forEach(
10
+ (methodName) => {
11
+ if (
12
+ methodName !== "constructor" &&
13
+ typeof cls[methodName] === "function"
14
+ ) {
15
+ obj[methodName] = cls[methodName].bind(cls);
17
16
  }
18
- );
19
- return obj;
20
- }
17
+ }
18
+ );
19
+ return obj;
20
+ }
21
21
 
22
-
23
- module.exports = bindClass;
22
+ module.exports = bindClass;
@@ -1,17 +1,16 @@
1
-
2
-
3
1
  module.exports = {
4
- /**
5
- * @description 给路由加前缀
6
- * @returns viod 0
7
- */
8
- addRoutePrefix:()=>{
9
- return function (req, res, next) {
10
- req.baseUrl = `${prefix}${req.baseUrl || ''}`;
11
- // 如果有 query 参数,则保留原有参数
12
- req.url = `${req.baseUrl}${req.url.includes('?') ? req.url.split('?')[1] : ''}`;
13
- next();
14
- };
15
- }
16
- }
17
-
2
+ /**
3
+ * @description 给路由加前缀
4
+ * @returns viod 0
5
+ */
6
+ addRoutePrefix: () => {
7
+ return function (req, res, next) {
8
+ req.baseUrl = `${prefix}${req.baseUrl || ""}`;
9
+ // 如果有 query 参数,则保留原有参数
10
+ req.url = `${req.baseUrl}${
11
+ req.url.includes("?") ? req.url.split("?")[1] : ""
12
+ }`;
13
+ next();
14
+ };
15
+ },
16
+ };
package/core/lib/index.js CHANGED
@@ -4,8 +4,8 @@ const favicon = require("serve-favicon");
4
4
  const morgan = require("morgan");
5
5
  const path = require("path");
6
6
  const template = require("./middleware/template.js");
7
- module.exports = async function (app,config) {
8
- const { logger, APP_PATH, cookieKey, maxAge, JSON_LIMIT, appName, version } =
7
+ module.exports = async function (app, config) {
8
+ const { logger, APP_PATH, cookieKey, static, JSON_LIMIT, appName, version } =
9
9
  config;
10
10
  //日志
11
11
  app.use(morgan(logger.level));
@@ -21,15 +21,15 @@ module.exports = async function (app,config) {
21
21
  app.use(express.urlencoded({ extended: false }));
22
22
 
23
23
  //配置模板引擎
24
- template(app,config);
24
+ template(app, config);
25
25
 
26
26
  //使用静态资源 ,
27
- app.use(
28
- "/public",
29
- express.static(path.join(APP_PATH, "public"), {
30
- maxAge: maxAge,
31
- })
32
- );
27
+ if (static.length > 0) {
28
+ static.forEach((item) => {
29
+ const { prefix, dir, maxAge } = item;
30
+ app.use(prefix, express.static(dir, { maxAge: maxAge || 0 }));
31
+ });
32
+ }
33
33
 
34
34
  //设置头信息
35
35
  app.use((req, res, next) => {
@@ -1,15 +1,34 @@
1
1
  const path = require("path");
2
- module.exports = (app,config) => {
3
- const
4
- { APP_PATH, views,env } = config;
2
+ const template = require("art-template");
3
+ const dayjs = require("dayjs");
4
+
5
+ // 注册 dateFormat 函数
6
+ template.defaults.imports.dateFormat = function (date, format) {
7
+ if (!date) {
8
+ return "";
9
+ }
10
+ // 如果传入的是一个 Date 对象,转换为 dayjs 对象
11
+ if (
12
+ date instanceof Date ||
13
+ typeof date === "string" ||
14
+ typeof date === "number"
15
+ ) {
16
+ date = dayjs(date);
17
+ } else {
18
+ return "";
19
+ }
20
+ return date.format(format);
21
+ };
22
+ module.exports = (app, config) => {
23
+ const { APP_PATH, views, env } = config;
5
24
  //默认home view
6
25
  const home = path.join(APP_PATH, `modules/web/view`);
7
26
  //合并插件中的view
8
27
  const all = [...views, home];
9
-
28
+
10
29
  app.set("view options", {
11
- debug: env != "prd",
12
- cache: env == "prd",
30
+ debug: env === "dev",
31
+ cache: env === "prd",
13
32
  minimize: true,
14
33
  });
15
34
  app.set("view engine", "html");
@@ -1,195 +1,194 @@
1
1
  class BaseService {
2
- /**
3
- * @description 构造函数
4
- * @param {*} knex - knex实例
5
- * @param {*} model - 模型名称
6
- */
7
- constructor(knex, model='') {
8
- this.knex = knex;
9
- this.model = model;
10
- }
11
-
12
- /**
13
- * @description 查找所有符合条件的记录
14
- * @param {*} query - 查询条件,例如:{name: 'test', age: 18}
15
- * @returns {Promise} 返回符合条件的记录
16
- */
17
- query(query) {
18
- return this.knex(this.model).where(query);
19
- }
20
-
21
- /**
22
- * @description 查询表所有记录,慎用
23
- * @returns {Promise} 返回所有记录
24
- */
25
- all() {
26
- return this.knex(this.model).select();
27
- }
28
-
29
- /**
30
- * @description 查询指定id的记录
31
- * @param {*} id
32
- * @returns {Promise} 返回指定id的记录
33
- */
34
- findById(id) {
35
- return this.knex(this.model).where('id', id).first();
36
- }
37
-
38
- /**
39
- * @description 查询分页数据
40
- * @param {*} current
41
- * @param {*} pageSize
42
- * @param {*} query
43
- * @returns {Promise} 返回分页数据
44
- */
45
- async findListAndQuery(current = 1, pageSize = 10, query = {}) {
46
- const offset = (current - 1) * pageSize;
47
-
48
- let countQuery = this.knex(this.model).count('* as total');
49
- let dataQuery = this.knex(this.model);
50
-
51
- // 应用查询条件
52
- for (const key in query) {
53
- dataQuery = dataQuery.where(key, query[key]);
54
- countQuery = countQuery.where(key, query[key]);
55
- }
56
-
57
- // 获取总记录数
58
- const total = await countQuery.first();
59
-
60
- // 获取分页数据
61
- const data = await dataQuery.offset(offset).limit(pageSize);
62
-
63
- return { data, total: parseInt(total.total, 10) };
64
- }
65
-
66
- /**
67
- * @description 查询指定id的记录
68
- * @param {*} id - 记录id
69
- * @returns {Promise} 返回指定id的记录
70
- */
71
- findOneById(id) {
72
- return this.knex(this.model).where('id', id).select();
73
- }
74
-
75
- /**
76
- * @description 查询指定条件的记录
77
- * @param {Object} query - {<key>:<value>}
78
- * @returns {Promise} 返回指定条件的记录
79
- */
80
- findOne(query) {
81
- return this.knex(this.model).where(query).first();
82
- }
83
-
84
- /**
85
- * @description 更新指定id的记录
86
- * @param {*} id - 记录id
87
- * @param {*} params - {<key>:<value>}
88
- * @returns {Promise} 返回更新后的记录
89
- */
90
- findOneAndUpdate(id, params) {
91
- return this.knex(this.model).where('id', id).update(params).returning('*');
92
- }
93
-
94
-
95
- /**
96
- * @description 查询指定条件的记录数量
97
- * @param {*} query - {<key>:<value>}
98
- * @returns {Promise} 返回指定条件的记录数量
99
- */
100
- count(query) {
101
- return this.knex(this.model).where(query).count('* as total').first();
102
- }
103
-
104
- /**
105
- * @description 插入一条记录
106
- * @param {*} params - {<key>:<value>}
107
- * @returns {Promise} 返回插入后的记录
108
- */
109
- insert(params) {
110
- return this.knex(this.model).insert(params);
111
- }
112
-
113
- /**
114
- * @description 插入多条记录
115
- * @param {*} records - [{<key>:<value>}, {<key>:<value>}, ...]
116
- * @returns {Promise} 返回插入后的记录
117
- */
118
- insertMany(records) {
119
- return this.knex(this.model).insert(records);
120
- }
121
-
122
- /**
123
- * @description 更新指定id的记录
124
- * @param {*} id - 记录id
125
- * @param {*} params - {<key>:<value>}
126
- * @returns {Promise} 返回更新后的记录
127
- */
128
- updateById(id, params) {
129
- return this.knex(this.model).where('id', id).update(params);
130
- }
131
-
132
- /**
133
- * @description 更新数据
134
- * @param {*} query - {<key>:<value>}
135
- * @param {*} update - {<key>:<value>}
136
- * @returns {Promise<*>} - 返回更新后的数据
137
- */
138
- update(query, update) {
139
- return this.knex(this.model).where(query).update(update);
140
- }
141
-
142
- /**
143
- * @description 查询并更新
144
- * @param {*} query - {<key>:<value>}
145
- * @param {*} update - {<key>:<value>}
146
- * @returns {Promise<*>} - 返回更新后的记录
147
- */
148
- findAndModify(query, update) {
149
- return this.knex(this.model).where(query).update(update);
150
- }
151
-
152
- /**
153
- *
154
- * @param {*} id - id
155
- * @param {*} update - {<key>:<value>}
156
- * @returns {Promise<*>} - 返回更新后的记录
157
- */
158
- findByIdAndUpdate(id, update) {
159
- return this.knex(this.model).where('id', id).update(update);
160
- }
161
-
162
- /**
163
- * @description 根据条件更新记录
164
- * @param {*} query - {<key>:<value>}
165
- * @param {*} update - {<key>:<value>}
166
- * @returns {Promise} - 返回更新后的记录
167
- */
168
- findOneAndUpdate(query, update) {
169
- return this.knex(this.model).where(query).update(update);
170
- }
171
-
172
- /**
173
- * @description 根据id删除一条记录
174
- * @param {*} id - 记录id
175
- * @returns {Promise} - 返回删除的记录
176
- */
177
- findByIdAndRemove(id) {
178
- return this.knex(this.model).where('id', id).del();
179
- }
180
-
181
- /**
182
- * @description 根据条件删除一条记录
183
- * @param {*} query
184
- * @returns {Promise} - 返回删除的记录
185
- */
186
- findOneAndRemove(query) {
187
- return this.knex(this.model).where(query).del();
188
- }
2
+ /**
3
+ * @description 构造函数
4
+ * @param {*} knex - knex实例
5
+ * @param {*} model - 模型名称
6
+ */
7
+ constructor(knex, model = "") {
8
+ this.knex = knex;
9
+ this.model = model;
10
+ }
11
+
12
+ /**
13
+ * @description 查找所有符合条件的记录
14
+ * @param {*} query - 查询条件,例如:{name: 'test', age: 18}
15
+ * @returns {Promise} 返回符合条件的记录
16
+ */
17
+ query(query) {
18
+ return this.knex(this.model).where(query);
19
+ }
20
+
21
+ /**
22
+ * @description 查询表所有记录,慎用
23
+ * @returns {Promise} 返回所有记录
24
+ */
25
+ all() {
26
+ return this.knex(this.model).select();
27
+ }
28
+
29
+ /**
30
+ * @description 查询指定id的记录
31
+ * @param {*} id
32
+ * @returns {Promise} 返回指定id的记录
33
+ */
34
+ findById(id) {
35
+ return this.knex(this.model).where("id", id).first();
36
+ }
37
+
38
+ /**
39
+ * @description 查询分页数据
40
+ * @param {*} current
41
+ * @param {*} pageSize
42
+ * @param {*} query
43
+ * @returns {Promise} 返回分页数据
44
+ */
45
+ async findListAndQuery(current = 1, pageSize = 10, query = {}) {
46
+ const offset = (current - 1) * pageSize;
47
+
48
+ let countQuery = this.knex(this.model).count("* as total");
49
+ let dataQuery = this.knex(this.model);
50
+
51
+ // 应用查询条件
52
+ for (const key in query) {
53
+ dataQuery = dataQuery.where(key, query[key]);
54
+ countQuery = countQuery.where(key, query[key]);
55
+ }
56
+
57
+ // 获取总记录数
58
+ const total = await countQuery.first();
59
+
60
+ // 获取分页数据
61
+ const data = await dataQuery.offset(offset).limit(pageSize);
62
+
63
+ return { data, total: parseInt(total.total, 10) };
64
+ }
65
+
66
+ /**
67
+ * @description 查询指定id的记录
68
+ * @param {*} id - 记录id
69
+ * @returns {Promise} 返回指定id的记录
70
+ */
71
+ findOneById(id) {
72
+ return this.knex(this.model).where("id", id).select();
73
+ }
74
+
75
+ /**
76
+ * @description 查询指定条件的记录
77
+ * @param {Object} query - {<key>:<value>}
78
+ * @returns {Promise} 返回指定条件的记录
79
+ */
80
+ findOne(query) {
81
+ return this.knex(this.model).where(query).first();
82
+ }
83
+
84
+ /**
85
+ * @description 更新指定id的记录
86
+ * @param {*} id - 记录id
87
+ * @param {*} params - {<key>:<value>}
88
+ * @returns {Promise} 返回更新后的记录
89
+ */
90
+ findOneAndUpdate(id, params) {
91
+ return this.knex(this.model).where("id", id).update(params).returning("*");
92
+ }
93
+
94
+ /**
95
+ * @description 查询指定条件的记录数量
96
+ * @param {*} query - {<key>:<value>}
97
+ * @returns {Promise} 返回指定条件的记录数量
98
+ */
99
+ count(query) {
100
+ return this.knex(this.model).where(query).count("* as total").first();
101
+ }
102
+
103
+ /**
104
+ * @description 插入一条记录
105
+ * @param {*} params - {<key>:<value>}
106
+ * @returns {Promise} 返回插入后的记录
107
+ */
108
+ insert(params) {
109
+ return this.knex(this.model).insert(params);
110
+ }
111
+
112
+ /**
113
+ * @description 插入多条记录
114
+ * @param {*} records - [{<key>:<value>}, {<key>:<value>}, ...]
115
+ * @returns {Promise} 返回插入后的记录
116
+ */
117
+ insertMany(records) {
118
+ return this.knex(this.model).insert(records);
119
+ }
120
+
121
+ /**
122
+ * @description 更新指定id的记录
123
+ * @param {*} id - 记录id
124
+ * @param {*} params - {<key>:<value>}
125
+ * @returns {Promise} 返回更新后的记录
126
+ */
127
+ updateById(id, params) {
128
+ return this.knex(this.model).where("id", id).update(params);
129
+ }
130
+
131
+ /**
132
+ * @description 更新数据
133
+ * @param {*} query - {<key>:<value>}
134
+ * @param {*} update - {<key>:<value>}
135
+ * @returns {Promise<*>} - 返回更新后的数据
136
+ */
137
+ update(query, update) {
138
+ return this.knex(this.model).where(query).update(update);
139
+ }
140
+
141
+ /**
142
+ * @description 查询并更新
143
+ * @param {*} query - {<key>:<value>}
144
+ * @param {*} update - {<key>:<value>}
145
+ * @returns {Promise<*>} - 返回更新后的记录
146
+ */
147
+ findAndModify(query, update) {
148
+ return this.knex(this.model).where(query).update(update);
149
+ }
150
+
151
+ /**
152
+ *
153
+ * @param {*} id - id
154
+ * @param {*} update - {<key>:<value>}
155
+ * @returns {Promise<*>} - 返回更新后的记录
156
+ */
157
+ findByIdAndUpdate(id, update) {
158
+ return this.knex(this.model).where("id", id).update(update);
159
+ }
160
+
161
+ /**
162
+ * @description 根据条件更新记录
163
+ * @param {*} query - {<key>:<value>}
164
+ * @param {*} update - {<key>:<value>}
165
+ * @returns {Promise} - 返回更新后的记录
166
+ */
167
+ findOneAndUpdate(query, update) {
168
+ return this.knex(this.model).where(query).update(update);
169
+ }
170
+
171
+ /**
172
+ * @description 根据id删除一条记录
173
+ * @param {*} id - 记录id
174
+ * @returns {Promise} - 返回删除的记录
175
+ */
176
+ findByIdAndRemove(id) {
177
+ return this.knex(this.model).where("id", id).del();
178
+ }
179
+
180
+ /**
181
+ * @description 根据条件删除一条记录
182
+ * @param {*} query
183
+ * @returns {Promise} - 返回删除的记录
184
+ */
185
+ findOneAndRemove(query) {
186
+ return this.knex(this.model).where(query).del();
187
+ }
189
188
  }
190
189
 
191
- const Service = (knex, model='') => {
192
- return new BaseService(knex, model);
190
+ const Service = (knex, model = "") => {
191
+ return new BaseService(knex, model);
193
192
  };
194
193
 
195
- module.exports = Service;
194
+ module.exports = Service;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "chanjs",
3
- "version": "1.0.23",
3
+ "version": "1.0.25",
4
4
  "description": "Chan.js基于express 纯js研发的轻量级mvc框架。",
5
5
  "main": "core/chan.js",
6
6
  "module": "core/chan.js",
@@ -21,7 +21,8 @@
21
21
  "express-art-template": "^1.0.1",
22
22
  "knex": "^3.1.0",
23
23
  "morgan": "^1.10.0",
24
- "mysql2": "^3.11.0"
24
+ "mysql2": "^3.11.0",
25
+ "dayjs": "^1.11.12"
25
26
  },
26
27
  "__npminstall_done": true,
27
28
  "_from": "chanjs@1.0.22",