|
@@ -0,0 +1,104 @@
|
|
|
+'use strict';
|
|
|
+const { CrudService } = require('naf-framework-mongoose/lib/service');
|
|
|
+const { BusinessError, ErrorCode } = require('naf-core').Error;
|
|
|
+const _ = require('lodash');
|
|
|
+const assert = require('assert');
|
|
|
+const moment = require('moment');
|
|
|
+
|
|
|
+// 统计
|
|
|
+class CountService extends CrudService {
|
|
|
+ constructor(ctx) {
|
|
|
+ super(ctx, 'count');
|
|
|
+ this.model = this.ctx.model.Count;
|
|
|
+ this.refute = this.ctx.model.Refute;
|
|
|
+ this.service = this.ctx.model.Service;
|
|
|
+ this.topic = this.ctx.model.Topic;
|
|
|
+ }
|
|
|
+ /**
|
|
|
+ * 首页统计
|
|
|
+ */
|
|
|
+ async index() {
|
|
|
+ // 本周的文章发表数量,折线图,3条线,没有的天也需要日期,默认值为0:模型(数据过滤)
|
|
|
+ const articles = await this.articleSum();
|
|
|
+ // 3种类型各自的总阅读数
|
|
|
+ const reads = await this.readSum();
|
|
|
+ return { articles, reads };
|
|
|
+ }
|
|
|
+ /**
|
|
|
+ * 本周的文章发表数量
|
|
|
+ */
|
|
|
+ async articleSum() {
|
|
|
+ // TODO 查询本周的周一至周日的日期
|
|
|
+ // 聚合函数查询本周发表的数量,按日期分组(应该需要加一个字段,单纯的是年月日) 'YYYY-MM-DD'
|
|
|
+ const refute = await this.getWeekResult('refute');
|
|
|
+ const serve = await this.getWeekResult('service');
|
|
|
+ const topic = await this.getWeekResult('topic');
|
|
|
+ return { refute, serve, topic };
|
|
|
+ }
|
|
|
+ /**
|
|
|
+ * 根据表名查出一周的发表数量
|
|
|
+ * @param {String} model 表名
|
|
|
+ * @return {Array} arr
|
|
|
+ */
|
|
|
+ async getWeekResult(model) {
|
|
|
+ const weekday = moment().weekday() - 1;
|
|
|
+ // 因为时区问题查询条件需要在00:00:00的基础上减去8小时,将查询条件也变成GMT时间
|
|
|
+ const start = moment(`${moment().subtract(weekday, 'days')
|
|
|
+ .format('YYYY-MM-DD')} 00:00:00`).subtract(8, 'hours').format();
|
|
|
+ const end = moment(`${moment().add(7 - weekday, 'days')
|
|
|
+ .format('YYYY-MM-DD')} 00:00:00`).subtract(8, 'hours').format();
|
|
|
+ const res = await this[model].aggregate([
|
|
|
+ { $match: { 'meta.createdAt': { $gte: new Date(start), $lt: new Date(end) } } },
|
|
|
+ {
|
|
|
+ $project: {
|
|
|
+ // meta的时间因为时区问题,差8个小时,加回来
|
|
|
+ date: { $substr: [{ $add: [ '$meta.createdAt', 28800000 ] }, 0, 10 ] },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ {
|
|
|
+ $group: {
|
|
|
+ _id: '$date',
|
|
|
+ sum: { $sum: 1 },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ ]);
|
|
|
+ const arr = [];
|
|
|
+ // 将本周每天都填充上
|
|
|
+ for (let i = 1; i <= 7; i++) {
|
|
|
+ const date = moment(start).add(i, 'days').format('YYYY-MM-DD');
|
|
|
+ const r = res.find(f => _.isEqual(f._id, date));
|
|
|
+ if (r) arr.push({ date, sum: r.sum });
|
|
|
+ else arr.push({ date, sum: 0 });
|
|
|
+ }
|
|
|
+ return arr;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 3种类型各自的总阅读数
|
|
|
+ */
|
|
|
+ async readSum() {
|
|
|
+ // 查出各自的阅读数,聚合加和
|
|
|
+ const refute = await this.getReadSum('refute');
|
|
|
+ const serve = await this.getReadSum('service');
|
|
|
+ const topic = await this.getReadSum('topic');
|
|
|
+ return { refute, serve, topic };
|
|
|
+ }
|
|
|
+
|
|
|
+ async getReadSum(model) {
|
|
|
+ const result = await this[model].aggregate([
|
|
|
+ { $project: { _id: 1, read: 1 } },
|
|
|
+ { $group: {
|
|
|
+ _id: '',
|
|
|
+ read: { $sum: '$read' },
|
|
|
+ } },
|
|
|
+ ]);
|
|
|
+ let res = 0;
|
|
|
+ if (result.length > 0) {
|
|
|
+ res = _.get(_.head(result), 'read', 0);
|
|
|
+ }
|
|
|
+ return res;
|
|
|
+ }
|
|
|
+
|
|
|
+}
|
|
|
+
|
|
|
+module.exports = CountService;
|