wechaty-web-panel 0.2.12
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/.eslintignore +4 -0
- package/.eslintrc.js +14 -0
- package/.idea/inspectionProfiles/Project_Default.xml +6 -0
- package/.idea/misc.xml +6 -0
- package/.idea/modules.xml +8 -0
- package/.idea/vcs.xml +6 -0
- package/.idea/wechaty-web-panel.iml +12 -0
- package/.prettierrc +8 -0
- package/LICENSE +21 -0
- package/README.md +175 -0
- package/doc/img/async.png +0 -0
- package/doc/img/event.png +0 -0
- package/doc/img/everyday.png +0 -0
- package/doc/img/func.jpeg +0 -0
- package/doc/img/group.jpeg +0 -0
- package/doc/img/index.png +0 -0
- package/doc/img/material.png +0 -0
- package/doc/img/news.jpeg +0 -0
- package/doc/img/qrcode-s.png +0 -0
- package/doc/img/qrcode.png +0 -0
- package/doc/img/roomasync.png +0 -0
- package/doc/img/schedule.png +0 -0
- package/doc/img/user-center.png +0 -0
- package/package.json +67 -0
- package/src/common/aiDb.js +23 -0
- package/src/common/configDb.js +86 -0
- package/src/common/index.js +321 -0
- package/src/common/reply.js +24 -0
- package/src/common/roomAvatarDb.js +24 -0
- package/src/common/userDb.js +24 -0
- package/src/handlers/on-error.js +13 -0
- package/src/handlers/on-friend.js +45 -0
- package/src/handlers/on-heartbeat.js +12 -0
- package/src/handlers/on-login.js +35 -0
- package/src/handlers/on-logout.js +11 -0
- package/src/handlers/on-message.js +127 -0
- package/src/handlers/on-ready.js +18 -0
- package/src/handlers/on-roomjoin.js +36 -0
- package/src/handlers/on-roomleave.js +6 -0
- package/src/handlers/on-roomtopic.js +5 -0
- package/src/handlers/on-scan.js +16 -0
- package/src/index.js +45 -0
- package/src/lib/index.js +816 -0
- package/src/lib/nedb.js +87 -0
- package/src/proxy/aibotk.js +351 -0
- package/src/proxy/api.js +582 -0
- package/src/proxy/config.js +9 -0
- package/src/proxy/mqtt.js +91 -0
- package/src/proxy/superagent.js +117 -0
- package/src/proxy/tencent.js +40 -0
- package/src/service/event-dispatch-service.js +147 -0
- package/src/service/msg-filter-service.js +76 -0
- package/src/service/msg-filters.js +175 -0
- package/src/service/room-async-service.js +395 -0
- package/src/task/index.js +233 -0
- package/verpub.config.js +6 -0
package/src/proxy/api.js
ADDED
|
@@ -0,0 +1,582 @@
|
|
|
1
|
+
const cheerio = require('cheerio')
|
|
2
|
+
const path = require('path')
|
|
3
|
+
const { req, txReq } = require('./superagent')
|
|
4
|
+
const { EMOHOST, TULING, ONE, MEINV } = require('./config')
|
|
5
|
+
const { randomRange, parseBody, MD5, loadFile } = require('../lib/index')
|
|
6
|
+
const { allConfig } = require('../common/configDb')
|
|
7
|
+
const { log, FileBox } = require('wechaty')
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* 获取每日一句
|
|
11
|
+
*/
|
|
12
|
+
async function getOne() {
|
|
13
|
+
try {
|
|
14
|
+
let option = {
|
|
15
|
+
spider: true,
|
|
16
|
+
method: 'GET',
|
|
17
|
+
url: ONE,
|
|
18
|
+
params: '',
|
|
19
|
+
}
|
|
20
|
+
let res = await req(option)
|
|
21
|
+
let $ = cheerio.load(res)
|
|
22
|
+
let todayOneList = $('#carousel-one .carousel-inner .item')
|
|
23
|
+
let todayOne = $(todayOneList[0])
|
|
24
|
+
.find('.fp-one-cita')
|
|
25
|
+
.text()
|
|
26
|
+
.replace(/(^\s*)|(\s*$)/g, '')
|
|
27
|
+
return todayOne
|
|
28
|
+
} catch (error) {
|
|
29
|
+
console.log('获取每日一句失败:', error)
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* 天行图灵聊天机器人
|
|
35
|
+
* @param {*} word 发送内容
|
|
36
|
+
* @param {*} id id
|
|
37
|
+
*/
|
|
38
|
+
async function getResByTXTL(word, id) {
|
|
39
|
+
try {
|
|
40
|
+
let uniqueId = MD5(id)
|
|
41
|
+
let option = {
|
|
42
|
+
method: 'GET',
|
|
43
|
+
url: '/txapi/tuling/',
|
|
44
|
+
params: { question: word, user: uniqueId },
|
|
45
|
+
}
|
|
46
|
+
let content = await txReq(option)
|
|
47
|
+
if (content.code === 200) {
|
|
48
|
+
let response = content.newslist[0].reply
|
|
49
|
+
console.log('天行图灵机器人回复:', response)
|
|
50
|
+
return response
|
|
51
|
+
} else {
|
|
52
|
+
return '我好像迷失在无边的网络中了,接口调用错误:' + content.msg
|
|
53
|
+
}
|
|
54
|
+
} catch (error) {
|
|
55
|
+
console.log('天行图灵聊天机器人请求失败:', error)
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* 天行聊天机器人
|
|
61
|
+
* @param {*} word 内容
|
|
62
|
+
* @param {*} id id
|
|
63
|
+
*/
|
|
64
|
+
async function getResByTX(word, id) {
|
|
65
|
+
try {
|
|
66
|
+
let uniqueId = MD5(id)
|
|
67
|
+
let option = {
|
|
68
|
+
method: 'GET',
|
|
69
|
+
url: '/txapi/robot/',
|
|
70
|
+
params: { question: word, userid: uniqueId },
|
|
71
|
+
}
|
|
72
|
+
let res = await txReq(option)
|
|
73
|
+
if (res.code === 200) {
|
|
74
|
+
let response = ''
|
|
75
|
+
let content = res.newslist[0]
|
|
76
|
+
if (content.datatype === 'text') {
|
|
77
|
+
response = content.reply
|
|
78
|
+
} else if (content.datatype === 'view') {
|
|
79
|
+
response = `虽然我不太懂你说的是什么,但是感觉很高级的样子,因此我也查找了类似的文章去学习,你觉得有用吗<br>
|
|
80
|
+
《${content.title}》${content.url}`
|
|
81
|
+
} else {
|
|
82
|
+
response = '你太厉害了,说的话把我难倒了,我要去学习了,不然没法回答你的问题'
|
|
83
|
+
}
|
|
84
|
+
console.log('天行机器人回复:', response)
|
|
85
|
+
return response
|
|
86
|
+
} else {
|
|
87
|
+
return '我好像迷失在无边的网络中了,你能找回我么'
|
|
88
|
+
}
|
|
89
|
+
} catch (error) {
|
|
90
|
+
console.log('天行聊天机器人请求失败:', error)
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
/**
|
|
95
|
+
* 图灵智能聊天机器人
|
|
96
|
+
* @param {*} word 内容
|
|
97
|
+
* @param {*} id id
|
|
98
|
+
*/
|
|
99
|
+
async function getResByTL(word, id) {
|
|
100
|
+
const config = await allConfig()
|
|
101
|
+
try {
|
|
102
|
+
let uniqueId = MD5(id)
|
|
103
|
+
let data = {
|
|
104
|
+
reqType: 0,
|
|
105
|
+
perception: {
|
|
106
|
+
inputText: {
|
|
107
|
+
text: word,
|
|
108
|
+
},
|
|
109
|
+
},
|
|
110
|
+
userInfo: {
|
|
111
|
+
apiKey: config.tuLingKey,
|
|
112
|
+
userId: uniqueId,
|
|
113
|
+
},
|
|
114
|
+
}
|
|
115
|
+
let option = {
|
|
116
|
+
method: 'POST',
|
|
117
|
+
url: TULING,
|
|
118
|
+
params: data,
|
|
119
|
+
contentType: 'application/json;charset=UTF-8',
|
|
120
|
+
}
|
|
121
|
+
let content = await req(option)
|
|
122
|
+
let reply = content.results[0].values.text
|
|
123
|
+
return reply
|
|
124
|
+
} catch (error) {
|
|
125
|
+
console.log('图灵聊天机器人请求失败:', error)
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
/**
|
|
130
|
+
* 获取垃圾分类结果
|
|
131
|
+
* @param {String} word 垃圾名称
|
|
132
|
+
*/
|
|
133
|
+
async function getRubbishType(word) {
|
|
134
|
+
try {
|
|
135
|
+
let option = {
|
|
136
|
+
method: 'GET',
|
|
137
|
+
url: '/txapi/lajifenlei/',
|
|
138
|
+
params: { word: word },
|
|
139
|
+
}
|
|
140
|
+
let content = await txReq(option)
|
|
141
|
+
if (content.code === 200) {
|
|
142
|
+
let type
|
|
143
|
+
if (content.newslist[0].type == 0) {
|
|
144
|
+
type = '是可回收垃圾'
|
|
145
|
+
} else if (content.newslist[0].type == 1) {
|
|
146
|
+
type = '是有害垃圾'
|
|
147
|
+
} else if (content.newslist[0].type == 2) {
|
|
148
|
+
type = '是厨余(湿)垃圾'
|
|
149
|
+
} else if (content.newslist[0].type == 3) {
|
|
150
|
+
type = '是其他(干)垃圾'
|
|
151
|
+
}
|
|
152
|
+
let response = `${content.newslist[0].name}${type}<br>解释:${content.newslist[0].explain}<br>主要包括:${content.newslist[0].contain}<br>投放提示:${content.newslist[0].tip}`
|
|
153
|
+
return response
|
|
154
|
+
} else {
|
|
155
|
+
console.log('查询失败提示:', content.msg)
|
|
156
|
+
return '暂时还没找到这个分类信息呢'
|
|
157
|
+
}
|
|
158
|
+
} catch (error) {
|
|
159
|
+
console.log('垃圾分类请求失败:', error)
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
/**
|
|
164
|
+
* 土味情话获取
|
|
165
|
+
*/
|
|
166
|
+
async function getSweetWord() {
|
|
167
|
+
try {
|
|
168
|
+
let option = {
|
|
169
|
+
method: 'GET',
|
|
170
|
+
url: '/txapi/saylove/',
|
|
171
|
+
params: {},
|
|
172
|
+
}
|
|
173
|
+
let content = await txReq(option)
|
|
174
|
+
if (content.code === 200) {
|
|
175
|
+
let sweet = content.newslist[0].content
|
|
176
|
+
let str = sweet.replace('\r\n', '<br>')
|
|
177
|
+
return str
|
|
178
|
+
} else {
|
|
179
|
+
console.log('获取土情话接口失败', content.msg)
|
|
180
|
+
}
|
|
181
|
+
} catch (err) {
|
|
182
|
+
console.log('获取土情话接口失败', err)
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
/**
|
|
187
|
+
* 获取天行天气
|
|
188
|
+
*/
|
|
189
|
+
async function getTXweather(city) {
|
|
190
|
+
try {
|
|
191
|
+
let option = {
|
|
192
|
+
method: 'GET',
|
|
193
|
+
url: '/txapi/tianqi/',
|
|
194
|
+
params: { city: city },
|
|
195
|
+
}
|
|
196
|
+
let content = await txReq(option)
|
|
197
|
+
if (content.code === 200) {
|
|
198
|
+
let todayInfo = content.newslist[0]
|
|
199
|
+
let obj = {
|
|
200
|
+
weatherTips: todayInfo.tips,
|
|
201
|
+
todayWeather: `今天:${todayInfo.weather}<br>温度:${todayInfo.lowest}/${todayInfo.highest}<br>${todayInfo.wind} ${todayInfo.windspeed}<br><br>`,
|
|
202
|
+
}
|
|
203
|
+
return obj
|
|
204
|
+
} else {
|
|
205
|
+
console.log('获取天气接口失败', content.msg)
|
|
206
|
+
}
|
|
207
|
+
} catch (err) {
|
|
208
|
+
console.log('获取天气接口失败', err)
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
/**
|
|
213
|
+
* 获取每日新闻内容
|
|
214
|
+
* @param {*} id 新闻频道对应的ID
|
|
215
|
+
*/
|
|
216
|
+
async function getNews(id) {
|
|
217
|
+
try {
|
|
218
|
+
let option = {
|
|
219
|
+
method: 'GET',
|
|
220
|
+
url: '/allnews/',
|
|
221
|
+
params: { num: 10, col: id },
|
|
222
|
+
}
|
|
223
|
+
let content = await txReq(option)
|
|
224
|
+
if (content.code === 200) {
|
|
225
|
+
let newList = content.newslist
|
|
226
|
+
let news = ''
|
|
227
|
+
let shortUrl = 'https://www.tianapi.com/weixin/news/?col=' + id
|
|
228
|
+
for (let i in newList) {
|
|
229
|
+
let num = parseInt(i) + 1
|
|
230
|
+
news = `${news}<br>${num}.${newList[i].title}`
|
|
231
|
+
}
|
|
232
|
+
return `${news}<br>新闻详情查看:${shortUrl}<br>`
|
|
233
|
+
}
|
|
234
|
+
} catch (error) {
|
|
235
|
+
console.log('获取天行新闻失败', error)
|
|
236
|
+
}
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
/**
|
|
240
|
+
* 获取名人名言
|
|
241
|
+
*/
|
|
242
|
+
async function getMingYan() {
|
|
243
|
+
try {
|
|
244
|
+
let option = {
|
|
245
|
+
method: 'GET',
|
|
246
|
+
url: '/txapi/mingyan/',
|
|
247
|
+
params: { num: 1 },
|
|
248
|
+
}
|
|
249
|
+
let content = await txReq(option)
|
|
250
|
+
if (content.code === 200) {
|
|
251
|
+
let newList = content.newslist
|
|
252
|
+
let news = `${newList[0].content}<br>——————————${newList[0].author}`
|
|
253
|
+
return news
|
|
254
|
+
}
|
|
255
|
+
} catch (error) {
|
|
256
|
+
console.log('获取天行名人名言失败', error)
|
|
257
|
+
}
|
|
258
|
+
}
|
|
259
|
+
|
|
260
|
+
/**
|
|
261
|
+
* 获取星座运势
|
|
262
|
+
* @param {string} satro 星座
|
|
263
|
+
*/
|
|
264
|
+
async function getStar(astro) {
|
|
265
|
+
try {
|
|
266
|
+
let option = {
|
|
267
|
+
method: 'GET',
|
|
268
|
+
url: '/txapi/star/',
|
|
269
|
+
params: { astro: astro },
|
|
270
|
+
}
|
|
271
|
+
let content = await txReq(option)
|
|
272
|
+
if (content.code === 200) {
|
|
273
|
+
let newList = content.newslist
|
|
274
|
+
let news = ''
|
|
275
|
+
for (let item of newList) {
|
|
276
|
+
news = `${news}${item.type}:${item.content}<br>`
|
|
277
|
+
}
|
|
278
|
+
return news
|
|
279
|
+
}
|
|
280
|
+
} catch (error) {
|
|
281
|
+
console.log('获取天行星座运势失败', error)
|
|
282
|
+
}
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
/**
|
|
286
|
+
* 获取姓氏起源
|
|
287
|
+
* @param {string} 姓
|
|
288
|
+
*/
|
|
289
|
+
async function getXing(name) {
|
|
290
|
+
try {
|
|
291
|
+
let option = {
|
|
292
|
+
method: 'GET',
|
|
293
|
+
url: '/txapi/surname/',
|
|
294
|
+
params: { xing: name },
|
|
295
|
+
}
|
|
296
|
+
let content = await txReq(option)
|
|
297
|
+
if (content.code === 200) {
|
|
298
|
+
let newList = content.newslist
|
|
299
|
+
let news = `${newList[0].content}`
|
|
300
|
+
return news
|
|
301
|
+
}
|
|
302
|
+
} catch (error) {
|
|
303
|
+
console.log('获取天行姓氏起源失败', error)
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
|
|
307
|
+
/**
|
|
308
|
+
* 获取顺口溜
|
|
309
|
+
*/
|
|
310
|
+
async function getSkl() {
|
|
311
|
+
try {
|
|
312
|
+
let option = {
|
|
313
|
+
method: 'GET',
|
|
314
|
+
url: '/txapi/skl/',
|
|
315
|
+
params: {},
|
|
316
|
+
}
|
|
317
|
+
let content = await txReq(option)
|
|
318
|
+
if (content.code === 200) {
|
|
319
|
+
let newList = content.newslist
|
|
320
|
+
let news = `${newList[0].content}`
|
|
321
|
+
return news
|
|
322
|
+
}
|
|
323
|
+
} catch (error) {
|
|
324
|
+
console.log('获取天行顺口溜失败', error)
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
|
|
328
|
+
/**
|
|
329
|
+
* 获取老黄历
|
|
330
|
+
*/
|
|
331
|
+
async function getLunar(date) {
|
|
332
|
+
try {
|
|
333
|
+
let option = {
|
|
334
|
+
method: 'GET',
|
|
335
|
+
url: '/txapi/lunar/',
|
|
336
|
+
params: { date: date },
|
|
337
|
+
}
|
|
338
|
+
let content = await txReq(option)
|
|
339
|
+
if (content.code === 200) {
|
|
340
|
+
let item = content.newslist[0]
|
|
341
|
+
let news = `<br>阳历:${item.gregoriandate}<br>阴历:${item.lunardate}<br>节日:${item.lunar_festival}<br>适宜:${item.fitness}<br>不宜:${item.taboo}<br>神位:${item.shenwei}<br>胎神:${item.taishen}<br>冲煞:${item.chongsha}<br>岁煞:${item.suisha}`
|
|
342
|
+
return news
|
|
343
|
+
}
|
|
344
|
+
} catch (error) {
|
|
345
|
+
console.log('获取天行老黄历失败', error)
|
|
346
|
+
}
|
|
347
|
+
}
|
|
348
|
+
|
|
349
|
+
/**
|
|
350
|
+
* 天行神回复
|
|
351
|
+
*/
|
|
352
|
+
async function getGoldReply() {
|
|
353
|
+
try {
|
|
354
|
+
let option = {
|
|
355
|
+
method: 'GET',
|
|
356
|
+
url: '/txapi/godreply/',
|
|
357
|
+
params: { num: 1 },
|
|
358
|
+
}
|
|
359
|
+
let content = await txReq(option)
|
|
360
|
+
if (content.code === 200) {
|
|
361
|
+
let item = content.newslist[0]
|
|
362
|
+
let news = `标题:"${item.title}"<br>回复:${item.content}`
|
|
363
|
+
return news
|
|
364
|
+
}
|
|
365
|
+
} catch (error) {
|
|
366
|
+
console.log('获取天行神回复失败', error)
|
|
367
|
+
}
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
/**
|
|
371
|
+
* 天行歇后语
|
|
372
|
+
*/
|
|
373
|
+
async function getXhy() {
|
|
374
|
+
try {
|
|
375
|
+
let option = {
|
|
376
|
+
method: 'GET',
|
|
377
|
+
url: '/txapi/xiehou/',
|
|
378
|
+
params: { num: 1 },
|
|
379
|
+
}
|
|
380
|
+
let content = await txReq(option)
|
|
381
|
+
if (content.code === 200) {
|
|
382
|
+
let item = content.newslist[0]
|
|
383
|
+
let news = `${item.quest}————${item.result}`
|
|
384
|
+
return news
|
|
385
|
+
}
|
|
386
|
+
} catch (error) {
|
|
387
|
+
console.log('获取天行歇后语失败', error)
|
|
388
|
+
}
|
|
389
|
+
}
|
|
390
|
+
|
|
391
|
+
/**
|
|
392
|
+
* 天行绕口令
|
|
393
|
+
*/
|
|
394
|
+
async function getRkl() {
|
|
395
|
+
try {
|
|
396
|
+
let option = {
|
|
397
|
+
method: 'GET',
|
|
398
|
+
url: '/txapi/rkl/',
|
|
399
|
+
params: { num: 1 },
|
|
400
|
+
}
|
|
401
|
+
let content = await txReq(option)
|
|
402
|
+
if (content.code === 200) {
|
|
403
|
+
let item = content.newslist[0]
|
|
404
|
+
let news = `${item.content}`
|
|
405
|
+
return news
|
|
406
|
+
}
|
|
407
|
+
} catch (error) {
|
|
408
|
+
console.log('获取天行绕口令失败', error)
|
|
409
|
+
}
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
/**
|
|
413
|
+
* 天行短连接
|
|
414
|
+
*/
|
|
415
|
+
async function getShortUrl(url) {
|
|
416
|
+
try {
|
|
417
|
+
let option = {
|
|
418
|
+
method: 'GET',
|
|
419
|
+
url: '/txapi/turl/',
|
|
420
|
+
params: { url: url },
|
|
421
|
+
}
|
|
422
|
+
let content = await txReq(option)
|
|
423
|
+
if (content.code === 200) {
|
|
424
|
+
let item = content.newslist[0]
|
|
425
|
+
let shorturl = item.shorturl
|
|
426
|
+
return shorturl
|
|
427
|
+
}
|
|
428
|
+
} catch (error) {
|
|
429
|
+
console.log('获取天行短连接失败', error)
|
|
430
|
+
}
|
|
431
|
+
}
|
|
432
|
+
|
|
433
|
+
/**
|
|
434
|
+
* 获取自定义头像
|
|
435
|
+
* @param {*} base
|
|
436
|
+
* @param type
|
|
437
|
+
*/
|
|
438
|
+
async function getAvatar(base, type) {
|
|
439
|
+
try {
|
|
440
|
+
let option = {
|
|
441
|
+
method: 'POST',
|
|
442
|
+
url: '/txapi/imgtx/index',
|
|
443
|
+
params: {
|
|
444
|
+
createid: type || 2,
|
|
445
|
+
img: 'data:image/jpeg;base64,' + base,
|
|
446
|
+
},
|
|
447
|
+
}
|
|
448
|
+
let content = await txReq(option)
|
|
449
|
+
if (content.code === 200) {
|
|
450
|
+
let item = content.newslist[0]
|
|
451
|
+
return item.picurl
|
|
452
|
+
}
|
|
453
|
+
} catch (e) {
|
|
454
|
+
console.log('获取自定义头像失败', e)
|
|
455
|
+
}
|
|
456
|
+
}
|
|
457
|
+
|
|
458
|
+
/**
|
|
459
|
+
* 获取表情包
|
|
460
|
+
* @param {*} msg
|
|
461
|
+
*/
|
|
462
|
+
async function getEmo(msg) {
|
|
463
|
+
console.log('msg', msg)
|
|
464
|
+
try {
|
|
465
|
+
let option = {
|
|
466
|
+
method: 'get',
|
|
467
|
+
url: `${EMOHOST}keyword=${encodeURIComponent(msg)}`,
|
|
468
|
+
contentType: 'application/json;charset=UTF-8',
|
|
469
|
+
params: {},
|
|
470
|
+
}
|
|
471
|
+
let content = await req(option)
|
|
472
|
+
if (content.totalSize > 0) {
|
|
473
|
+
if (content.items && content.items.length > 0) {
|
|
474
|
+
let arr = []
|
|
475
|
+
for (let i of content.items) {
|
|
476
|
+
if (i.url.includes('.jpg') || i.url.includes('.gif')) {
|
|
477
|
+
arr.push(i)
|
|
478
|
+
}
|
|
479
|
+
}
|
|
480
|
+
let item = arr[randomRange(0, arr.length)]
|
|
481
|
+
if (item.url) {
|
|
482
|
+
return item.url
|
|
483
|
+
} else {
|
|
484
|
+
return 'http://img.doutula.com/production/uploads/image/2017/11/30/20171130047004_PiJlhx.gif'
|
|
485
|
+
}
|
|
486
|
+
} else {
|
|
487
|
+
return 'http://img.doutula.com/production/uploads/image/2017/11/30/20171130047004_PiJlhx.gif'
|
|
488
|
+
}
|
|
489
|
+
}
|
|
490
|
+
} catch (e) {
|
|
491
|
+
console.log('获取表情包失败', e)
|
|
492
|
+
}
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
/**
|
|
496
|
+
* 获取美女图片
|
|
497
|
+
*/
|
|
498
|
+
async function getMeiNv() {
|
|
499
|
+
try {
|
|
500
|
+
let option = {
|
|
501
|
+
method: 'get',
|
|
502
|
+
url: MEINV,
|
|
503
|
+
contentType: 'application/json;charset=UTF-8',
|
|
504
|
+
params: {},
|
|
505
|
+
}
|
|
506
|
+
let content = await req(option)
|
|
507
|
+
if (content.imgurl) {
|
|
508
|
+
let url = content.imgurl
|
|
509
|
+
return url.includes('.jpg') ? url : 'https://tva2.sinaimg.cn/large/0072Vf1pgy1foxkcsx9rmj31hc0u0h9k.jpg'
|
|
510
|
+
}
|
|
511
|
+
} catch (e) {
|
|
512
|
+
console.log('获取美女图片失败', e)
|
|
513
|
+
return 'https://tva2.sinaimg.cn/large/0072Vf1pgy1foxkcsx9rmj31hc0u0h9k.jpg'
|
|
514
|
+
}
|
|
515
|
+
}
|
|
516
|
+
/**
|
|
517
|
+
* 获取疫情信息
|
|
518
|
+
* @returns {Promise<string>}
|
|
519
|
+
*/
|
|
520
|
+
async function getNcov() {
|
|
521
|
+
try {
|
|
522
|
+
let option = {
|
|
523
|
+
method: 'GET',
|
|
524
|
+
url: '/txapi/ncov/index',
|
|
525
|
+
}
|
|
526
|
+
let content = await txReq(option)
|
|
527
|
+
if (content.code === 200) {
|
|
528
|
+
let newList = content.newslist[0].news
|
|
529
|
+
let desc = content.newslist.desc
|
|
530
|
+
let news = ''
|
|
531
|
+
for (let i in newList) {
|
|
532
|
+
let num = parseInt(i) + 1
|
|
533
|
+
news = `${news}<br>>>${newList[i].pubDateStr}: ${newList[i].title}<br><br>${newList[i].summary}----------------${newList[i].infoSource}<br><br>`
|
|
534
|
+
}
|
|
535
|
+
return `${news}<br>`
|
|
536
|
+
}
|
|
537
|
+
} catch (e) {
|
|
538
|
+
console.log('获取疫情数据失败', e)
|
|
539
|
+
}
|
|
540
|
+
}
|
|
541
|
+
/**
|
|
542
|
+
* 天行网络取名
|
|
543
|
+
*/
|
|
544
|
+
async function getCname() {
|
|
545
|
+
try {
|
|
546
|
+
let option = {
|
|
547
|
+
method: 'GET',
|
|
548
|
+
url: '/txapi/cname/index',
|
|
549
|
+
}
|
|
550
|
+
let content = await txReq(option)
|
|
551
|
+
if (content.code === 200) {
|
|
552
|
+
let item = content.newslist[0]
|
|
553
|
+
let cname = item.name
|
|
554
|
+
return cname
|
|
555
|
+
}
|
|
556
|
+
} catch (error) {
|
|
557
|
+
console.log('获取天行短连接失败', error)
|
|
558
|
+
}
|
|
559
|
+
}
|
|
560
|
+
module.exports = {
|
|
561
|
+
getOne,
|
|
562
|
+
getResByTXTL,
|
|
563
|
+
getResByTX,
|
|
564
|
+
getResByTL,
|
|
565
|
+
getTXweather,
|
|
566
|
+
getRubbishType,
|
|
567
|
+
getSweetWord,
|
|
568
|
+
getNews,
|
|
569
|
+
getMingYan,
|
|
570
|
+
getStar,
|
|
571
|
+
getXing,
|
|
572
|
+
getSkl,
|
|
573
|
+
getLunar,
|
|
574
|
+
getGoldReply,
|
|
575
|
+
getXhy,
|
|
576
|
+
getRkl,
|
|
577
|
+
getAvatar,
|
|
578
|
+
getEmo,
|
|
579
|
+
getMeiNv,
|
|
580
|
+
getNcov,
|
|
581
|
+
getCname,
|
|
582
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
module.exports = {
|
|
2
|
+
AIBOTK: 'https://api-bot.aibotk.com/open/v1/api', // 智能微秘书
|
|
3
|
+
ONE: 'http://wufazhuce.com/', // 每日一句网址
|
|
4
|
+
TULING: 'http://openapi.tuling123.com/openapi/api/v2', // 图灵api
|
|
5
|
+
MOJI: 'https://tianqi.moji.com/weather/china/', // 墨迹天气官网
|
|
6
|
+
TXHOST: 'http://api.tianapi.com', // 天行host
|
|
7
|
+
EMOHOST: 'https://doutu.lccyy.com/t/doutu/items?pageNum=1&pageSize=20&', //表情包接口
|
|
8
|
+
MEINV: 'https://api.pixivweb.com/anime18r.php?return=json', // 美女
|
|
9
|
+
}
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
const mqtt = require('mqtt')
|
|
2
|
+
const {allConfig} = require('../common/configDb')
|
|
3
|
+
const {contactSay, roomSay,} = require('../common/index')
|
|
4
|
+
const {getConfig, getMqttConfig} = require('../proxy/aibotk')
|
|
5
|
+
const {dispatchEventContent} = require('../service/event-dispatch-service')
|
|
6
|
+
const {sendRoomTaskMessage, sendContactTaskMessage} = require('../task/index')
|
|
7
|
+
const {randomRange} = require('../lib/index')
|
|
8
|
+
|
|
9
|
+
async function initMqtt(that) {
|
|
10
|
+
try {
|
|
11
|
+
await getConfig() // 获取配置文件
|
|
12
|
+
const config = await allConfig()
|
|
13
|
+
const {userId, name, role} = config.userInfo
|
|
14
|
+
if (role === 'vip') {
|
|
15
|
+
const config = await getMqttConfig()
|
|
16
|
+
const {host, port, username, password, clientId} = config
|
|
17
|
+
let mqttclient = host ? mqtt.connect(`${host}:${port}`, {
|
|
18
|
+
username: username,
|
|
19
|
+
password: password,
|
|
20
|
+
clientId: clientId + randomRange(1, 10000)
|
|
21
|
+
}) : null
|
|
22
|
+
if (mqttclient) {
|
|
23
|
+
mqttclient.on('connect', function () {
|
|
24
|
+
console.debug('connect to Wechaty mqtt----------')
|
|
25
|
+
mqttclient.subscribe(`aibotk/${userId}/+`, function (err) {
|
|
26
|
+
if (err) {
|
|
27
|
+
console.log(err)
|
|
28
|
+
}
|
|
29
|
+
})
|
|
30
|
+
})
|
|
31
|
+
mqttclient.on('reconnect', function (e) {
|
|
32
|
+
console.log('subscriber on reconnect')
|
|
33
|
+
})
|
|
34
|
+
mqttclient.on('disconnect', function (e) {
|
|
35
|
+
console.log('disconnect--------', e)
|
|
36
|
+
})
|
|
37
|
+
mqttclient.on('error', function (e) {
|
|
38
|
+
console.debug('error----------', e)
|
|
39
|
+
})
|
|
40
|
+
mqttclient.on('message', async function (topic, message) {
|
|
41
|
+
const content = JSON.parse(message.toString())
|
|
42
|
+
if (topic === `aibotk/${userId}/say`) {
|
|
43
|
+
if (content.target === 'Room') {
|
|
44
|
+
console.log(`收到群:${content.roomName}发送消息请求: ${content.message.content || content.message.url}`)
|
|
45
|
+
const room = await that.Room.find({topic: content.roomName})
|
|
46
|
+
if (!room) {
|
|
47
|
+
console.log(`查找不到群:${content.roomName},请检查群名是否正确`)
|
|
48
|
+
return
|
|
49
|
+
} else {
|
|
50
|
+
await roomSay(room, '', content.message)
|
|
51
|
+
}
|
|
52
|
+
} else if (content.target === 'Contact') {
|
|
53
|
+
console.log(`收到联系人:${content.alias || content.name}发送消息请求: ${content.message.content || content.message.url}`)
|
|
54
|
+
let contact = (await that.Contact.find({alias: content.alias})) || (await that.Contact.find({name: content.name})) || (await that.Contact.find({weixin: content.weixin})) // 获取你要发送的联系人
|
|
55
|
+
if (!contact) {
|
|
56
|
+
console.log(`查找不到联系人:${content.name || content.alias},请检查联系人名称是否正确`)
|
|
57
|
+
return
|
|
58
|
+
} else {
|
|
59
|
+
await contactSay(contact, content.message)
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
} else if (topic === `aibotk/${userId}/event`) {
|
|
63
|
+
if (content.target === 'system') {
|
|
64
|
+
console.log('触发了内置事件')
|
|
65
|
+
const eventName = content.event
|
|
66
|
+
const res = await dispatchEventContent(that, eventName)
|
|
67
|
+
console.log('事件处理结果', res[0].content)
|
|
68
|
+
} else if (content.target === 'Room') {
|
|
69
|
+
console.log('触发了群事件')
|
|
70
|
+
await sendRoomTaskMessage(that, content)
|
|
71
|
+
} else if (content.target === 'Contact') {
|
|
72
|
+
console.log('触发了好友事件')
|
|
73
|
+
await sendContactTaskMessage(that, content)
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
}
|
|
77
|
+
})
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
} else {
|
|
81
|
+
return false
|
|
82
|
+
}
|
|
83
|
+
} catch (e) {
|
|
84
|
+
console.log('mqtt 创建链接失败', e)
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
|
|
89
|
+
module.exports = {
|
|
90
|
+
initMqtt
|
|
91
|
+
}
|