@waline/vercel 1.4.1 → 1.6.1
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/package.json +1 -1
- package/src/config/config.js +3 -1
- package/src/config/middleware.js +3 -1
- package/src/controller/comment.js +25 -8
- package/src/service/notify.js +84 -2
- package/src/service/storage/cloudbase.js +2 -1
- package/src/service/storage/inspirecloud.js +4 -2
- package/src/service/storage/leancloud.js +2 -1
package/package.json
CHANGED
package/src/config/config.js
CHANGED
|
@@ -36,6 +36,7 @@ const {
|
|
|
36
36
|
MAIL_TEMPLATE_ADMIN,
|
|
37
37
|
QQ_TEMPLATE,
|
|
38
38
|
TG_TEMPLATE,
|
|
39
|
+
WX_TEMPLATE,
|
|
39
40
|
} = process.env;
|
|
40
41
|
|
|
41
42
|
let storage = 'leancloud';
|
|
@@ -105,7 +106,7 @@ module.exports = {
|
|
|
105
106
|
forbiddenWords,
|
|
106
107
|
disallowIPList: [],
|
|
107
108
|
secureDomains: SECURE_DOMAINS ? SECURE_DOMAINS.split(/\s*,\s*/) : undefined,
|
|
108
|
-
disableUserAgent: !isFalse(DISABLE_USERAGENT),
|
|
109
|
+
disableUserAgent: DISABLE_USERAGENT && !isFalse(DISABLE_USERAGENT),
|
|
109
110
|
avatarProxy,
|
|
110
111
|
oauthUrl,
|
|
111
112
|
markdown,
|
|
@@ -115,4 +116,5 @@ module.exports = {
|
|
|
115
116
|
mailTemplateAdmin: MAIL_TEMPLATE_ADMIN,
|
|
116
117
|
QQTemplate: QQ_TEMPLATE,
|
|
117
118
|
TGTemplate: TG_TEMPLATE,
|
|
119
|
+
WXTemplate: WX_TEMPLATE,
|
|
118
120
|
};
|
package/src/config/middleware.js
CHANGED
|
@@ -3,6 +3,8 @@ const routerREST = require('think-router-rest');
|
|
|
3
3
|
const isDev = think.env === 'development';
|
|
4
4
|
const isTcb = think.env === 'cloudbase';
|
|
5
5
|
const isDeta = think.env === 'deta' || process.env.DETA_RUNTIME === 'true';
|
|
6
|
+
const isAliyunFC =
|
|
7
|
+
think.env === 'aliyun-fc' || Boolean(process.env.FC_RUNTIME_VERSION);
|
|
6
8
|
|
|
7
9
|
module.exports = [
|
|
8
10
|
{
|
|
@@ -15,7 +17,7 @@ module.exports = [
|
|
|
15
17
|
options: {
|
|
16
18
|
logRequest: isDev,
|
|
17
19
|
sendResponseTime: isDev,
|
|
18
|
-
requestTimeoutCallback: isTcb || isDeta ? false : () => {},
|
|
20
|
+
requestTimeoutCallback: isTcb || isDeta || isAliyunFC ? false : () => {},
|
|
19
21
|
},
|
|
20
22
|
},
|
|
21
23
|
|
|
@@ -4,6 +4,7 @@ const BaseRest = require('./rest');
|
|
|
4
4
|
const akismet = require('../service/akismet');
|
|
5
5
|
const { getMarkdownParser } = require('../service/markdown');
|
|
6
6
|
|
|
7
|
+
const markdownParser = getMarkdownParser();
|
|
7
8
|
async function formatCmt(
|
|
8
9
|
{ ua, user_id, ...comment },
|
|
9
10
|
users = [],
|
|
@@ -39,6 +40,7 @@ async function formatCmt(
|
|
|
39
40
|
comment.mail ? comment.mail.toLowerCase() : comment.mail
|
|
40
41
|
);
|
|
41
42
|
|
|
43
|
+
comment.comment = markdownParser(comment.comment);
|
|
42
44
|
return comment;
|
|
43
45
|
}
|
|
44
46
|
|
|
@@ -49,8 +51,6 @@ module.exports = class extends BaseRest {
|
|
|
49
51
|
`storage/${this.config('storage')}`,
|
|
50
52
|
'Comment'
|
|
51
53
|
);
|
|
52
|
-
|
|
53
|
-
this.parser = getMarkdownParser();
|
|
54
54
|
}
|
|
55
55
|
|
|
56
56
|
async getAction() {
|
|
@@ -154,13 +154,33 @@ module.exports = class extends BaseRest {
|
|
|
154
154
|
offset: Math.max((page - 1) * pageSize, 0),
|
|
155
155
|
});
|
|
156
156
|
|
|
157
|
+
const userModel = this.service(
|
|
158
|
+
`storage/${this.config('storage')}`,
|
|
159
|
+
'Users'
|
|
160
|
+
);
|
|
161
|
+
const user_ids = Array.from(
|
|
162
|
+
new Set(comments.map(({ user_id }) => user_id).filter((v) => v))
|
|
163
|
+
);
|
|
164
|
+
|
|
165
|
+
let users = [];
|
|
166
|
+
if (user_ids.length) {
|
|
167
|
+
users = await userModel.select(
|
|
168
|
+
{ objectId: ['IN', user_ids] },
|
|
169
|
+
{
|
|
170
|
+
field: ['display_name', 'email', 'url', 'type', 'avatar'],
|
|
171
|
+
}
|
|
172
|
+
);
|
|
173
|
+
}
|
|
174
|
+
|
|
157
175
|
return this.success({
|
|
158
176
|
page,
|
|
159
177
|
totalPages: Math.ceil(count / pageSize),
|
|
160
178
|
pageSize,
|
|
161
179
|
spamCount,
|
|
162
180
|
waitingCount,
|
|
163
|
-
data:
|
|
181
|
+
data: await Promise.all(
|
|
182
|
+
comments.map((cmt) => formatCmt(cmt, users, this.config()))
|
|
183
|
+
),
|
|
164
184
|
});
|
|
165
185
|
}
|
|
166
186
|
|
|
@@ -248,17 +268,14 @@ module.exports = class extends BaseRest {
|
|
|
248
268
|
rid,
|
|
249
269
|
ua,
|
|
250
270
|
url,
|
|
271
|
+
comment,
|
|
251
272
|
ip: this.ctx.ip,
|
|
252
273
|
insertedAt: new Date(),
|
|
253
|
-
comment: this.parser(comment),
|
|
254
274
|
user_id: this.ctx.state.userInfo.objectId,
|
|
255
275
|
};
|
|
256
276
|
|
|
257
277
|
if (pid) {
|
|
258
|
-
data.comment = data.comment
|
|
259
|
-
'<p>',
|
|
260
|
-
`<p><a class="at" href="#${pid}">@${at}</a>: `
|
|
261
|
-
);
|
|
278
|
+
data.comment = `[@${at}](#${pid}): ` + data.comment;
|
|
262
279
|
}
|
|
263
280
|
|
|
264
281
|
think.logger.debug('Post Comment initial Data:', data);
|
package/src/service/notify.js
CHANGED
|
@@ -91,6 +91,81 @@ module.exports = class extends think.Service {
|
|
|
91
91
|
});
|
|
92
92
|
}
|
|
93
93
|
|
|
94
|
+
async qywxAmWechat({ title, content }, self, parent) {
|
|
95
|
+
const { QYWX_AM, SITE_NAME, SITE_URL } = process.env;
|
|
96
|
+
if (!QYWX_AM) {
|
|
97
|
+
return false;
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
const QYWX_AM_AY = QYWX_AM.split(',');
|
|
101
|
+
const comment = self.comment
|
|
102
|
+
.replace(/<a href="(.*?)">(.*?)<\/a>/g, '\n[$2] $1\n')
|
|
103
|
+
.replace(/<[^>]+>/g, '');
|
|
104
|
+
const postName = self.url;
|
|
105
|
+
|
|
106
|
+
const data = {
|
|
107
|
+
self: {
|
|
108
|
+
...self,
|
|
109
|
+
comment,
|
|
110
|
+
},
|
|
111
|
+
postName,
|
|
112
|
+
parent,
|
|
113
|
+
site: {
|
|
114
|
+
name: SITE_NAME,
|
|
115
|
+
url: SITE_URL,
|
|
116
|
+
postUrl: SITE_URL + self.url + '#' + self.objectId,
|
|
117
|
+
},
|
|
118
|
+
};
|
|
119
|
+
const contentWechat =
|
|
120
|
+
think.config('WXTemplate') ||
|
|
121
|
+
`💬 {{site.name|safe}}的文章《{{postName}}》有新评论啦
|
|
122
|
+
【评论者昵称】:{{self.nick}}
|
|
123
|
+
【评论者邮箱】:{{self.mail}}
|
|
124
|
+
【内容】:{{self.comment}}
|
|
125
|
+
<a href='{{site.postUrl}}'>查看详情</a>`;
|
|
126
|
+
|
|
127
|
+
title = nunjucks.renderString(title, data);
|
|
128
|
+
const desp = nunjucks.renderString(contentWechat, data);
|
|
129
|
+
content = desp.replace(/\n/g, '<br/>');
|
|
130
|
+
|
|
131
|
+
const { access_token } = await request({
|
|
132
|
+
uri: `https://qyapi.weixin.qq.com/cgi-bin/gettoken`,
|
|
133
|
+
qs: {
|
|
134
|
+
corpid: `${QYWX_AM_AY[0]}`,
|
|
135
|
+
corpsecret: `${QYWX_AM_AY[1]}`,
|
|
136
|
+
},
|
|
137
|
+
headers: {
|
|
138
|
+
'Content-Type': 'application/json',
|
|
139
|
+
},
|
|
140
|
+
json: true,
|
|
141
|
+
});
|
|
142
|
+
return request({
|
|
143
|
+
url: `https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=${access_token}`,
|
|
144
|
+
body: {
|
|
145
|
+
touser: `${QYWX_AM_AY[2]}`,
|
|
146
|
+
agentid: `${QYWX_AM_AY[3]}`,
|
|
147
|
+
msgtype: 'mpnews',
|
|
148
|
+
mpnews: {
|
|
149
|
+
articles: [
|
|
150
|
+
{
|
|
151
|
+
title,
|
|
152
|
+
thumb_media_id: `${QYWX_AM_AY[4]}`,
|
|
153
|
+
author: `Waline Comment`,
|
|
154
|
+
content_source_url: `${data.site.postUrl}`,
|
|
155
|
+
content: `${content}`,
|
|
156
|
+
digest: `${desp}`,
|
|
157
|
+
},
|
|
158
|
+
],
|
|
159
|
+
},
|
|
160
|
+
},
|
|
161
|
+
method: 'POST',
|
|
162
|
+
json: true,
|
|
163
|
+
headers: {
|
|
164
|
+
'Content-Type': 'application/json',
|
|
165
|
+
},
|
|
166
|
+
});
|
|
167
|
+
}
|
|
168
|
+
|
|
94
169
|
async qq(self, parent) {
|
|
95
170
|
const { QMSG_KEY, QQ_ID, SITE_NAME, SITE_URL } = process.env;
|
|
96
171
|
if (!QMSG_KEY) {
|
|
@@ -212,7 +287,7 @@ module.exports = class extends think.Service {
|
|
|
212
287
|
? parent && parent.mail.toLowerCase() === AUTHOR.toLowerCase()
|
|
213
288
|
: false;
|
|
214
289
|
|
|
215
|
-
const title = mailSubjectAdmin || '{{site.name}} 上有新评论了';
|
|
290
|
+
const title = mailSubjectAdmin || '{{site.name | safe}} 上有新评论了';
|
|
216
291
|
const content =
|
|
217
292
|
mailTemplateAdmin ||
|
|
218
293
|
`
|
|
@@ -230,12 +305,18 @@ module.exports = class extends think.Service {
|
|
|
230
305
|
|
|
231
306
|
if (!isAuthorComment && !disableAuthorNotify) {
|
|
232
307
|
const wechat = await this.wechat({ title, content }, comment, parent);
|
|
308
|
+
const qywxAmWechat = await this.qywxAmWechat(
|
|
309
|
+
{ title, content },
|
|
310
|
+
comment,
|
|
311
|
+
parent
|
|
312
|
+
);
|
|
233
313
|
const qq = await this.qq(comment, parent);
|
|
234
314
|
const telegram = await this.telegram(comment, parent);
|
|
235
315
|
if (
|
|
236
316
|
think.isEmpty(wechat) &&
|
|
237
317
|
think.isEmpty(qq) &&
|
|
238
318
|
think.isEmpty(telegram) &&
|
|
319
|
+
think.isEmpty(qywxAmWechat) &&
|
|
239
320
|
!isReplyAuthor
|
|
240
321
|
) {
|
|
241
322
|
mailList.push({ to: AUTHOR, title, content });
|
|
@@ -250,7 +331,8 @@ module.exports = class extends think.Service {
|
|
|
250
331
|
mailList.push({
|
|
251
332
|
to: parent.mail,
|
|
252
333
|
title:
|
|
253
|
-
mailSubject ||
|
|
334
|
+
mailSubject ||
|
|
335
|
+
'{{parent.nick | safe}},『{{site.name | safe}}』上的评论收到了回复',
|
|
254
336
|
content:
|
|
255
337
|
mailTemplate ||
|
|
256
338
|
`
|
|
@@ -115,8 +115,9 @@ module.exports = class extends Base {
|
|
|
115
115
|
async select(where, options = {}) {
|
|
116
116
|
let data = [];
|
|
117
117
|
let ret = [];
|
|
118
|
+
let offset = options.offset || 0;
|
|
118
119
|
do {
|
|
119
|
-
options.offset =
|
|
120
|
+
options.offset = offset + data.length;
|
|
120
121
|
ret = await this._select(where, options);
|
|
121
122
|
data = data.concat(ret);
|
|
122
123
|
} while (ret.length === 100);
|
|
@@ -16,7 +16,8 @@ module.exports = class extends Base {
|
|
|
16
16
|
const parseKey = (k) => (k === 'objectId' ? '_id' : k);
|
|
17
17
|
for (const k in where) {
|
|
18
18
|
if (think.isString(where[k])) {
|
|
19
|
-
_where[parseKey(k)] =
|
|
19
|
+
_where[parseKey(k)] =
|
|
20
|
+
k === 'objectId' ? this.db.ObjectId(where[k]) : where[k];
|
|
20
21
|
continue;
|
|
21
22
|
}
|
|
22
23
|
if (where[k] === undefined) {
|
|
@@ -100,8 +101,9 @@ module.exports = class extends Base {
|
|
|
100
101
|
async select(where, options = {}) {
|
|
101
102
|
let data = [];
|
|
102
103
|
let ret = [];
|
|
104
|
+
let offset = options.offset || 0;
|
|
103
105
|
do {
|
|
104
|
-
options.offset =
|
|
106
|
+
options.offset = offset + data.length;
|
|
105
107
|
ret = await this._select(where, options);
|
|
106
108
|
data = data.concat(ret);
|
|
107
109
|
} while (ret.length === 1000);
|
|
@@ -88,8 +88,9 @@ module.exports = class extends Base {
|
|
|
88
88
|
async select(where, options = {}) {
|
|
89
89
|
let data = [];
|
|
90
90
|
let ret = [];
|
|
91
|
+
let offset = options.offset || 0;
|
|
91
92
|
do {
|
|
92
|
-
options.offset =
|
|
93
|
+
options.offset = offset + data.length;
|
|
93
94
|
ret = await this._select(where, options);
|
|
94
95
|
data = data.concat(ret);
|
|
95
96
|
} while (ret.length === 100);
|