@alemonjs/onebot 0.2.1 → 0.2.3

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/lib/sdk/wss.js ADDED
@@ -0,0 +1,292 @@
1
+ import WebSocket, { WebSocketServer } from 'ws';
2
+ import { randomUUID } from 'crypto';
3
+
4
+ /**
5
+ * 连接
6
+ */
7
+ class OneBotClient {
8
+ #options = {
9
+ url: '',
10
+ access_token: '',
11
+ reverse_enable: false,
12
+ reverse_port: 17158
13
+ };
14
+ /**
15
+ * 设置配置
16
+ * @param opstion
17
+ */
18
+ constructor(opstion) {
19
+ for (const key in opstion) {
20
+ if (Object.prototype.hasOwnProperty.call(opstion, key)) {
21
+ this.#options[key] = opstion[key];
22
+ }
23
+ }
24
+ }
25
+ #ws = null;
26
+ #events = {};
27
+ #echo = {};
28
+ timeout = 30000;
29
+ /**
30
+ * 注册事件处理程序
31
+ * @param key 事件名称
32
+ * @param val 事件处理函数
33
+ */
34
+ on(key, val) {
35
+ this.#events[key] = val;
36
+ return this;
37
+ }
38
+ /**
39
+ *
40
+ * @param cfg
41
+ * @param conversation
42
+ */
43
+ async connect() {
44
+ const { url, access_token: token, reverse_enable, reverse_port } = this.#options;
45
+ const c = token == '' || !token
46
+ ? {}
47
+ : {
48
+ headers: {
49
+ ['Authorization']: `Bearer ${token}`
50
+ }
51
+ };
52
+ const onMessage = async (data) => {
53
+ try {
54
+ const event = JSON.parse(data.toString());
55
+ if (!event) {
56
+ if (this.#events['ERROR'])
57
+ this.#events['ERROR'](event);
58
+ return;
59
+ }
60
+ else if (event?.post_type == 'meta_event') {
61
+ if (this.#events['META'])
62
+ this.#events['META'](event);
63
+ return;
64
+ }
65
+ else if (event?.post_type == 'message') {
66
+ if (event?.message_type == 'group') {
67
+ if (this.#events['MESSAGES'])
68
+ this.#events['MESSAGES'](event);
69
+ }
70
+ else if (event?.message_type == 'private') {
71
+ if (this.#events['DIRECT_MESSAGE'])
72
+ this.#events['DIRECT_MESSAGE'](event);
73
+ }
74
+ else {
75
+ // console.info('未知消息类型', event)
76
+ }
77
+ return;
78
+ }
79
+ else if (event?.post_type == 'notice') {
80
+ if (event?.notice_type == 'group_increase') {
81
+ // 群成员增加
82
+ if (this.#events['NOTICE_GROUP_MEMBER_INCREASE'])
83
+ this.#events['NOTICE_GROUP_MEMBER_INCREASE'](event);
84
+ }
85
+ else if (event?.notice_type == 'group_decrease') {
86
+ // 群成员减少
87
+ if (this.#events['NOTICE_GROUP_MEMBER_REDUCE'])
88
+ this.#events['NOTICE_GROUP_MEMBER_REDUCE'](event);
89
+ }
90
+ return;
91
+ }
92
+ else if (event?.post_type == 'request') {
93
+ // 收到加群 或 加好友的请求。
94
+ if (event?.request_type == 'friend') {
95
+ if (this.#events['REQUEST_ADD_FRIEND'])
96
+ this.#events['REQUEST_ADD_FRIEND'](event);
97
+ }
98
+ else if (event?.request_type == 'group') {
99
+ if (this.#events['REQUEST_ADD_GROUP'])
100
+ this.#events['REQUEST_ADD_GROUP'](event);
101
+ }
102
+ return;
103
+ }
104
+ else if (event?.echo === 'get_friend_list' || event?.echo === 'get_group_list' || event?.echo === 'get_group_member_list') {
105
+ // 处理获取好友列表和群列表的响应
106
+ // if (this.#events['META']) this.#events['META'](event)
107
+ // console.debug('响应', event)
108
+ return;
109
+ }
110
+ if (!event?.post_type && event?.echo && this.#echo[event?.echo]) {
111
+ if (![0, 1].includes(event?.retcode))
112
+ this.#echo[event?.echo].reject(Object.assign(this.#echo[event?.echo].request, { error: event }));
113
+ else
114
+ this.#echo[event?.echo].resolve(event?.data
115
+ ? new Proxy(event, {
116
+ get: (target, prop) => target.event[prop] ?? target[prop]
117
+ })
118
+ : event);
119
+ clearTimeout(this.#echo[event?.echo].timeout);
120
+ delete this.#echo[event?.echo];
121
+ }
122
+ }
123
+ catch (err) {
124
+ if (this.#events['ERROR'])
125
+ this.#events['ERROR'](err);
126
+ }
127
+ };
128
+ const onClose = (code, reason) => {
129
+ if (this.#events['ERROR'])
130
+ this.#events['ERROR']({
131
+ de: code,
132
+ reason: reason.toString('utf8')
133
+ });
134
+ };
135
+ if (!this.#ws) {
136
+ if (reverse_enable) {
137
+ // reverse_open
138
+ const server = new WebSocketServer({ port: reverse_port ?? 17158 });
139
+ server.on('connection', ws => {
140
+ this.#ws = ws;
141
+ // message
142
+ this.#ws.on('message', onMessage);
143
+ // close
144
+ this.#ws.on('close', onClose);
145
+ console.info('connected: ws://127.0.0.1:' + reverse_port);
146
+ });
147
+ }
148
+ else {
149
+ // forward_open
150
+ this.#ws = new WebSocket(url, c);
151
+ this.#ws.on('open', () => {
152
+ console.debug(`open:${url}`);
153
+ });
154
+ // message
155
+ this.#ws.on('message', onMessage);
156
+ // close
157
+ this.#ws.on('close', onClose);
158
+ }
159
+ }
160
+ }
161
+ /**
162
+ * 发送私聊消息
163
+ * @param options
164
+ * @returns
165
+ */
166
+ sendPrivateMessage(options) {
167
+ if (!this.#ws)
168
+ return;
169
+ return this.#ws.send(JSON.stringify({
170
+ action: 'send_private_msg',
171
+ params: options,
172
+ echo: randomUUID()
173
+ }));
174
+ }
175
+ /**
176
+ * 发送群消息
177
+ * @param options
178
+ * @returns
179
+ */
180
+ sendGroupMessage(options) {
181
+ if (!this.#ws)
182
+ return;
183
+ return this.#ws.send(JSON.stringify({
184
+ action: 'send_group_msg',
185
+ params: options,
186
+ echo: randomUUID()
187
+ }));
188
+ }
189
+ /**
190
+ * 发送消息
191
+ * @param options
192
+ * @returns
193
+ */
194
+ sendMessage(options) {
195
+ if (!this.#ws)
196
+ return;
197
+ return this.#ws.send(JSON.stringify({
198
+ action: 'send_msg',
199
+ params: options,
200
+ echo: randomUUID()
201
+ }));
202
+ }
203
+ /**
204
+ * 好友列表
205
+ */
206
+ getFriendList() {
207
+ if (!this.#ws)
208
+ return;
209
+ return this.#ws.send(JSON.stringify({
210
+ action: 'get_friend_list',
211
+ params: {},
212
+ echo: 'get_friend_list'
213
+ }));
214
+ }
215
+ /**
216
+ * 群列表
217
+ */
218
+ getGroupList() {
219
+ if (!this.#ws)
220
+ return;
221
+ return this.#ws.send(JSON.stringify({
222
+ action: 'get_group_list',
223
+ params: {},
224
+ echo: 'get_group_list'
225
+ }));
226
+ }
227
+ /**
228
+ * 群成员列表
229
+ * @param options
230
+ * @returns
231
+ */
232
+ getGroupMemberList(options) {
233
+ if (!this.#ws)
234
+ return;
235
+ return this.#ws.send(JSON.stringify({
236
+ action: 'get_group_member_list',
237
+ params: options,
238
+ echo: 'get_group_member_list'
239
+ }));
240
+ }
241
+ /**
242
+ * 处理好友请求
243
+ * @param options
244
+ * @returns
245
+ */
246
+ setFriendAddRequest(options) {
247
+ if (!this.#ws)
248
+ return;
249
+ return this.#ws.send(JSON.stringify({
250
+ action: 'set_friend_add_request',
251
+ params: options,
252
+ echo: randomUUID()
253
+ }));
254
+ }
255
+ /**
256
+ * 处理群请求
257
+ * @param options
258
+ * @returns
259
+ */
260
+ setGroupAddRequest(options) {
261
+ if (!this.#ws)
262
+ return;
263
+ return this.#ws.send(JSON.stringify({
264
+ action: 'set_group_add_request',
265
+ params: options,
266
+ echo: randomUUID()
267
+ }));
268
+ }
269
+ /**
270
+ * @param options
271
+ * @returns
272
+ */
273
+ sendApi(options) {
274
+ if (!this.#ws)
275
+ return;
276
+ if (!options.echo)
277
+ options.echo = randomUUID();
278
+ this.#ws.send(JSON.stringify(options));
279
+ return new Promise((resolve, reject) => (this.#echo[options.echo] = {
280
+ request: options,
281
+ resolve,
282
+ reject,
283
+ timeout: setTimeout(() => {
284
+ reject(Object.assign(options, { timeout: this.timeout }));
285
+ delete this.#echo[options.echo];
286
+ console.error('请求超时:', options);
287
+ }, this.timeout)
288
+ }));
289
+ }
290
+ }
291
+
292
+ export { OneBotClient };
@@ -0,0 +1,41 @@
1
+ import Koa from 'koa';
2
+ import Router from 'koa-router';
3
+
4
+ // 使用koa + router 写 hello world
5
+ const createServer = (client) => {
6
+ const app = new Koa();
7
+ const router = new Router();
8
+ const port = 8080; // 端口号
9
+ // 检测
10
+ router.get('/', (ctx) => {
11
+ ctx.body = 'Hello, World!';
12
+ });
13
+ // 获取群列表
14
+ router.get('/get_group_list', async (ctx) => {
15
+ client.getGroupList();
16
+ ctx.body = 'Hello, World!';
17
+ });
18
+ // 获取好友列表
19
+ router.get('/get_friend_list', async (ctx) => {
20
+ client.getFriendList();
21
+ ctx.body = 'Hello, World!';
22
+ });
23
+ // 获取群成员列表
24
+ router.get('/get_group_member_list', async (ctx) => {
25
+ const group_id = ctx.query.group_id;
26
+ if (!group_id) {
27
+ ctx.status = 400;
28
+ ctx.body = 'group_id is required';
29
+ return;
30
+ }
31
+ client.getGroupMemberList({ group_id: Number(group_id) });
32
+ ctx.body = 'Hello, World!';
33
+ });
34
+ app.use(router.routes());
35
+ app.use(router.allowedMethods());
36
+ app.listen(port, () => {
37
+ console.log(`Server is running at http://localhost:${port}`);
38
+ });
39
+ };
40
+
41
+ export { createServer };
package/package.json CHANGED
@@ -1,24 +1,38 @@
1
1
  {
2
2
  "name": "@alemonjs/onebot",
3
- "version": "0.2.1",
3
+ "version": "0.2.3",
4
4
  "description": "onebot",
5
5
  "author": "lemonade",
6
6
  "license": "MIT",
7
7
  "type": "module",
8
8
  "main": "lib/index.js",
9
9
  "types": "lib",
10
+ "scripts": {
11
+ "build": "node bundle.js"
12
+ },
10
13
  "exports": {
11
14
  ".": {
12
15
  "import": "./lib/index.js",
13
16
  "types": "./lib/index.d.ts"
14
- }
17
+ },
18
+ "./package": "./package.json"
15
19
  },
16
20
  "keywords": [
17
- "alemonjs",
18
- "onebot",
19
- "bot",
20
- "chat-bot"
21
+ "alemonjs"
21
22
  ],
23
+ "dependencies": {
24
+ "ws": "^8.18.1"
25
+ },
26
+ "alemonjs": {
27
+ "desktop": {
28
+ "platform": [
29
+ {
30
+ "name": "onebot"
31
+ }
32
+ ],
33
+ "logo": "antd.RobotOutlined"
34
+ }
35
+ },
22
36
  "publishConfig": {
23
37
  "registry": "https://registry.npmjs.org",
24
38
  "access": "public"
package/lib/index-11.js DELETED
@@ -1,160 +0,0 @@
1
- import { defineBot, getConfig, useUserHashKey, OnProcessor } from 'alemonjs';
2
- import { OneBotClient } from './sdk-v11/wss.js';
3
-
4
- const platform = 'onebot';
5
- var INDEXV11 = defineBot(() => {
6
- const cfg = getConfig();
7
- const config = cfg.value?.onebot;
8
- if (!config)
9
- return;
10
- //
11
- const client = new OneBotClient({
12
- // url
13
- url: config?.url ?? '',
14
- // token
15
- access_token: config?.token ?? ''
16
- });
17
- //
18
- client.connect();
19
- //
20
- client.on('META', event => {
21
- if (event?.self_id) {
22
- String(event.self_id);
23
- }
24
- });
25
- //
26
- client.on('MESSAGES', event => {
27
- const uis = config.master_uids ?? [];
28
- let msg = '';
29
- const arr = [];
30
- // let at_users = []
31
- for (const item of event.message) {
32
- if (item.type == 'text') {
33
- msg = item.data.text;
34
- }
35
- }
36
- for (const item of arr) {
37
- msg = msg.replace(item.text, '').trim();
38
- }
39
- const url = `https://q1.qlogo.cn/g?b=qq&s=0&nk=${event.user_id}`;
40
- const UserAvatar = {
41
- toBuffer: async () => {
42
- const arrayBuffer = await fetch(url).then(res => res.arrayBuffer());
43
- return Buffer.from(arrayBuffer);
44
- },
45
- toBase64: async () => {
46
- const arrayBuffer = await fetch(url).then(res => res.arrayBuffer());
47
- return Buffer.from(arrayBuffer).toString('base64');
48
- },
49
- toURL: async () => {
50
- return url;
51
- }
52
- };
53
- const UserId = String(event.user_id);
54
- const UserKey = useUserHashKey({
55
- Platform: platform,
56
- UserId
57
- });
58
- // 定义消
59
- const e = {
60
- // 平台类型
61
- Platform: platform,
62
- // 频道
63
- GuildId: String(event.group_id),
64
- // guild_name: event.group_name,
65
- // 子频道
66
- ChannelId: String(event.group_id),
67
- IsMaster: uis.includes(String(event.user_id)),
68
- IsBot: false,
69
- UserId: UserId,
70
- UserName: event.sender.nickname,
71
- UserKey,
72
- UserAvatar: UserAvatar,
73
- // message
74
- MessageId: String(event.message_id),
75
- MessageText: msg,
76
- // 用户openId
77
- OpenId: String(event.user_id),
78
- // 创建时间
79
- CreateAt: Date.now(),
80
- // 标签
81
- tag: 'MESSAGES',
82
- //
83
- value: null
84
- };
85
- // 当访问的时候获取
86
- Object.defineProperty(e, 'value', {
87
- get() {
88
- return event;
89
- }
90
- });
91
- // 处理消息
92
- OnProcessor(e, 'message.create');
93
- });
94
- client.on('DIRECT_MESSAGE', () => {
95
- // const e = {
96
- // isMaster: event.user_id == masterId,
97
- // msg_txt: event.raw_message,
98
- // msg: event.raw_message.trim(),
99
- // msg_id: event.message_id,
100
- // open_id: event.user_id,
101
- // user_id: event.user_id,
102
- // user_avatar:
103
- // event.platform == 'qq'
104
- // ? `https://q1.qlogo.cn/g?b=qq&s=0&nk=${event.user_id}`
105
- // : '',
106
- // user_name: event.sender.nickname,
107
- });
108
- // 错误处理
109
- client.on('ERROR', event => {
110
- console.error('ERROR', event);
111
- });
112
- global.client = client;
113
- return {
114
- api: {
115
- use: {
116
- send: (event, val) => {
117
- if (val.length < 0)
118
- return Promise.all([]);
119
- const content = val
120
- .filter(item => item.type == 'Link' || item.type == 'Mention' || item.type == 'Text')
121
- .map(item => item.value)
122
- .join('');
123
- if (content) {
124
- return Promise.all([content].map(item => client.sendGroupMessage({
125
- group_id: event.ChannelId,
126
- message: [
127
- {
128
- type: 'text',
129
- data: {
130
- text: item
131
- }
132
- }
133
- ]
134
- })));
135
- }
136
- const images = val.filter(item => item.type == 'Image').map(item => item.value);
137
- if (images) {
138
- return Promise.all(images.map(item => client.sendGroupMessage({
139
- group_id: event.ChannelId,
140
- message: [
141
- {
142
- type: 'image',
143
- data: {
144
- file: `base64://${item.toString('base64')}`
145
- }
146
- }
147
- ]
148
- })));
149
- }
150
- return Promise.all([]);
151
- },
152
- mention: async () => {
153
- return [];
154
- }
155
- }
156
- }
157
- };
158
- });
159
-
160
- export { INDEXV11 as default };