@zhin.js/adapter-onebot11 6.0.2 → 6.0.5

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/CHANGELOG.md CHANGED
@@ -1,5 +1,100 @@
1
1
  # @zhin.js/adapter-onebot11
2
2
 
3
+ ## 6.0.5
4
+
5
+ ### Patch Changes
6
+
7
+ - 51015d6: refactor(adapters): migrate platform-permit to PermissionSubject
8
+
9
+ All adapter platform-permit checkers now accept PermissionSubject
10
+ (duck-typed from Message/CommandSession) instead of Message directly.
11
+ registerPlatformPermitChecker is replaced by host.registerPlatform in
12
+ the adapter plugin setup. activity-feedback service updated for new
13
+ PermissionHost integration.
14
+
15
+ - Updated dependencies [6f9c366]
16
+ - Updated dependencies [373a56b]
17
+ - Updated dependencies [0de46a8]
18
+ - Updated dependencies [c106ecc]
19
+ - Updated dependencies [ca92e03]
20
+ - Updated dependencies [b0f37ae]
21
+ - Updated dependencies [ba08a2f]
22
+ - Updated dependencies [b08f7fe]
23
+ - Updated dependencies [daffd4c]
24
+ - Updated dependencies [36c7400]
25
+ - Updated dependencies [a9fa72e]
26
+ - Updated dependencies [c8de3ef]
27
+ - Updated dependencies [60f0fc8]
28
+ - Updated dependencies [574c990]
29
+ - Updated dependencies [d096f16]
30
+ - Updated dependencies [3f29623]
31
+ - Updated dependencies [2916852]
32
+ - Updated dependencies [d047869]
33
+ - Updated dependencies [162fa34]
34
+ - Updated dependencies [e62561e]
35
+ - Updated dependencies [3eeeb46]
36
+ - Updated dependencies [85d0f82]
37
+ - Updated dependencies [61bfc1c]
38
+ - Updated dependencies [04bad47]
39
+ - Updated dependencies [e40b048]
40
+ - Updated dependencies [5a5b1bb]
41
+ - Updated dependencies [f1708c3]
42
+ - Updated dependencies [d254a81]
43
+ - Updated dependencies [7123c47]
44
+ - Updated dependencies [05befc1]
45
+ - Updated dependencies [0663b6a]
46
+ - Updated dependencies [f28f9b3]
47
+ - Updated dependencies [9f340f7]
48
+ - Updated dependencies [e53444f]
49
+ - Updated dependencies [5eedd26]
50
+ - Updated dependencies [92b0dd7]
51
+ - Updated dependencies [f919b6f]
52
+ - Updated dependencies [098e411]
53
+ - Updated dependencies [e1b7c01]
54
+ - Updated dependencies [9b94f87]
55
+ - Updated dependencies [a7df753]
56
+ - @zhin.js/agent@1.1.5
57
+ - @zhin.js/host-http@1.0.8
58
+ - @zhin.js/permission@1.0.1
59
+ - @zhin.js/im-contract@1.0.3
60
+ - @zhin.js/adapter@1.1.7
61
+ - @zhin.js/plugin-runtime@1.1.5
62
+ - @zhin.js/command@1.0.9
63
+ - @zhin.js/core@1.5.4
64
+ - zhin.js@6.0.4
65
+
66
+ ## 6.0.4
67
+
68
+ ### Patch Changes
69
+
70
+ - f8c7a54: fix: im
71
+ - Updated dependencies [f8c7a54]
72
+ - @zhin.js/logger@1.0.76
73
+ - @zhin.js/host-http@1.0.7
74
+ - @zhin.js/adapter@1.1.6
75
+ - @zhin.js/agent@1.1.4
76
+ - @zhin.js/command@1.0.8
77
+ - @zhin.js/core@1.5.3
78
+ - @zhin.js/im-contract@1.0.2
79
+ - @zhin.js/plugin-runtime@1.1.4
80
+ - zhin.js@6.0.3
81
+
82
+ ## 6.0.3
83
+
84
+ ### Patch Changes
85
+
86
+ - Updated dependencies [afc0e66]
87
+ - Updated dependencies [2e41ad5]
88
+ - Updated dependencies [9f57124]
89
+ - @zhin.js/core@1.5.2
90
+ - @zhin.js/adapter@1.1.5
91
+ - @zhin.js/im-contract@1.0.1
92
+ - @zhin.js/plugin-runtime@1.1.3
93
+ - @zhin.js/command@1.0.7
94
+ - @zhin.js/host-http@1.0.6
95
+ - @zhin.js/agent@1.1.3
96
+ - zhin.js@6.0.2
97
+
3
98
  ## 6.0.2
4
99
 
5
100
  ### Patch Changes
package/README.md CHANGED
@@ -8,7 +8,7 @@ Zhin.js [OneBot 11](https://github.com/botuniverse/onebot-11) 适配器(Plugin
8
8
  - 约定式 `defineAdapter` / `definePlugin`(无需 `usePlugin`)
9
9
  - **正向 WebSocket**(`connection: ws`):应用连 OneBot 实现的 WS 服务器
10
10
  - `access_token` 鉴权(Bearer + query)
11
- - 入站经 `messageGatewayToken`;出站 `send({ target, payload })`
11
+ - 入站经 `messageGatewayToken`;出站 `send({ conversation, payload })`
12
12
 
13
13
  ## 安装
14
14
 
@@ -23,8 +23,8 @@ pnpm add @zhin.js/adapter-onebot11
23
23
  - `@zhin.js/plugin-runtime` — `plugin.ts`(`definePlugin`)
24
24
  - 配置经插件 `schema.json` 落到 `plugins.<instanceKey>`
25
25
 
26
- 入站:`gateway.receive({ adapter, target: "private:uid"|"group:gid", content, sender, metadata })`
27
- 出站:`send({ target, payload })` → WS `send_private_msg` / `send_group_msg`(payload 已由 gateway/core 渲染;无 segment-mapper)
26
+ 入站:`gateway.receive({ conversation, message, content, sender, metadata })`(`conversation.kind` 为 `private`/`group`,`id` 为 uid/gid)
27
+ 出站:`send({ conversation, payload })` → WS `send_private_msg` / `send_group_msg`(payload 已由 gateway/core 渲染;无 segment-mapper)
28
28
 
29
29
  ## 最小配置
30
30
 
@@ -22,8 +22,8 @@ export default defineAdapter({
22
22
  const config = resolveOneBot11Config(context.config);
23
23
  const gateway = context.use(messageGatewayToken);
24
24
  // 注册到插件运行时状态(onebot11.endpoint list 的"运行中"数据源)
25
- context.use(onebot11RuntimeStateToken).endpoints.set(config.name, {
26
- name: config.name,
25
+ context.use(onebot11RuntimeStateToken).endpoints.set(config.id, {
26
+ id: config.id,
27
27
  mode: config.connection,
28
28
  });
29
29
  if (config.connection === 'wss') {
@@ -29,8 +29,8 @@ export default defineAdapter<OneBot11AdapterConfig>({
29
29
  const config = resolveOneBot11Config(context.config);
30
30
  const gateway = context.use(messageGatewayToken);
31
31
  // 注册到插件运行时状态(onebot11.endpoint list 的"运行中"数据源)
32
- context.use(onebot11RuntimeStateToken).endpoints.set(config.name, {
33
- name: config.name,
32
+ context.use(onebot11RuntimeStateToken).endpoints.set(config.id, {
33
+ id: config.id,
34
34
  mode: config.connection,
35
35
  });
36
36
  if (config.connection === 'wss') {
package/lib/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- export { buildSendAction, buildWsConnectOptions, extractQuoteId, formatInboundContent, formatInboundMetadata, formatInboundTarget, formatOutboundSegments, getChannelId, isMessageEvent, isOneBot11BotMentioned, mediaRefToOneBotFile, parseSendTarget, resolveOneBot11Config, senderDisplayName, senderNickname, senderUserId, type OneBot11ActionRequest, type OneBot11ActionResponse, type OneBot11AdapterConfig, type OneBot11ConfigBase, type OneBot11EndpointConfig, type OneBot11Event, type OneBot11Segment, type OneBot11Sender, type OneBot11WireSegment, type OneBot11WsConfig, type OneBot11WssConfig, type ParsedSendTarget, type ResolvedOneBot11Config, } from './protocol.js';
1
+ export { buildSendAction, buildWsConnectOptions, extractQuoteId, formatInboundContent, formatInboundMetadata, formatOutboundSegments, getChannelId, isMessageEvent, isOneBot11BotMentioned, mediaRefToOneBotFile, onebot11InboundConversation, resolveOneBot11Config, senderDisplayName, senderNickname, senderUserId, type OneBot11ActionRequest, type OneBot11ActionResponse, type OneBot11AdapterConfig, type OneBot11ConfigBase, type OneBot11EndpointConfig, type OneBot11Event, type OneBot11Segment, type OneBot11Sender, type OneBot11WireSegment, type OneBot11WsConfig, type OneBot11WssConfig, type ResolvedOneBot11Config, } from './protocol.js';
2
2
  export { OneBot11WsEndpoint, type OneBot11WsEndpointOptions, } from './ws-endpoint.js';
3
3
  export { OneBot11WssEndpoint, type OneBot11WssEndpointOptions, } from './wss-endpoint.js';
4
4
  export type { OneBot11WsSocket, OneBot11WsCreateOptions } from './ws-types.js';
package/lib/index.js CHANGED
@@ -1,4 +1,4 @@
1
- export { buildSendAction, buildWsConnectOptions, extractQuoteId, formatInboundContent, formatInboundMetadata, formatInboundTarget, formatOutboundSegments, getChannelId, isMessageEvent, isOneBot11BotMentioned, mediaRefToOneBotFile, parseSendTarget, resolveOneBot11Config, senderDisplayName, senderNickname, senderUserId, } from './protocol.js';
1
+ export { buildSendAction, buildWsConnectOptions, extractQuoteId, formatInboundContent, formatInboundMetadata, formatOutboundSegments, getChannelId, isMessageEvent, isOneBot11BotMentioned, mediaRefToOneBotFile, onebot11InboundConversation, resolveOneBot11Config, senderDisplayName, senderNickname, senderUserId, } from './protocol.js';
2
2
  export { OneBot11WsEndpoint, } from './ws-endpoint.js';
3
3
  export { OneBot11WssEndpoint, } from './wss-endpoint.js';
4
4
  export { callOneBot11WsAction, decodeWsPayload, handleOneBot11WsMessage, rejectAllPending, startOneBot11Heartbeat, } from './ws-transport.js';
@@ -7,9 +7,9 @@ export interface Onebot11AgentEndpoint {
7
7
  callApi(action: string, params?: Record<string, unknown>): Promise<unknown>;
8
8
  }
9
9
  export interface Onebot11AgentDeps {
10
- getEndpoint: (endpointId: string) => Onebot11AgentEndpoint;
10
+ getEndpoint: (endpointKey: string) => Onebot11AgentEndpoint;
11
11
  }
12
- export declare function registerOnebot11AgentEndpoint(endpointId: string, endpoint: Onebot11AgentEndpoint): () => void;
12
+ export declare function registerOnebot11AgentEndpoint(endpointKey: string, endpoint: Onebot11AgentEndpoint): () => void;
13
13
  /** Optional override used by tests / transitional callers. */
14
14
  export declare function setOnebot11AgentDeps(deps: Onebot11AgentDeps): void;
15
15
  export declare function getOnebot11AgentDeps(): Onebot11AgentDeps;
@@ -4,11 +4,11 @@
4
4
  */
5
5
  const endpoints = new Map();
6
6
  let override = null;
7
- export function registerOnebot11AgentEndpoint(endpointId, endpoint) {
8
- endpoints.set(endpointId, endpoint);
7
+ export function registerOnebot11AgentEndpoint(endpointKey, endpoint) {
8
+ endpoints.set(endpointKey, endpoint);
9
9
  return () => {
10
- if (endpoints.get(endpointId) === endpoint) {
11
- endpoints.delete(endpointId);
10
+ if (endpoints.get(endpointKey) === endpoint) {
11
+ endpoints.delete(endpointKey);
12
12
  }
13
13
  };
14
14
  }
@@ -20,10 +20,10 @@ export function getOnebot11AgentDeps() {
20
20
  if (override)
21
21
  return override;
22
22
  return {
23
- getEndpoint(endpointId) {
24
- const registered = endpoints.get(endpointId);
23
+ getEndpoint(endpointKey) {
24
+ const registered = endpoints.get(endpointKey);
25
25
  if (!registered)
26
- throw new Error(`Endpoint ${endpointId} 不存在`);
26
+ throw new Error(`Endpoint ${endpointKey} 不存在`);
27
27
  return registered;
28
28
  },
29
29
  };
package/lib/protocol.d.ts CHANGED
@@ -4,13 +4,14 @@
4
4
  * Spec: https://github.com/botuniverse/onebot-11
5
5
  */
6
6
  import { type MediaRef } from '@zhin.js/core';
7
+ import type { ConversationRef } from '@zhin.js/im-contract';
7
8
  /** Transitional legacy endpoint row (`endpoints[]` with `context: onebot11`). */
8
9
  export interface OneBot11LegacyEndpointRow {
9
10
  readonly context?: string;
10
11
  readonly connection?: 'ws' | 'wss';
11
12
  /** Legacy alias: `type: 'ws' | 'ws_reverse'` */
12
13
  readonly type?: string;
13
- readonly name?: string;
14
+ readonly id?: string;
14
15
  readonly access_token?: string;
15
16
  readonly url?: string;
16
17
  readonly path?: string;
@@ -20,7 +21,7 @@ export interface OneBot11LegacyEndpointRow {
20
21
  /** Plugin Runtime owner config (`plugins.<instanceKey>` / schema.json). */
21
22
  export interface OneBot11AdapterConfig {
22
23
  readonly connection?: 'ws' | 'wss';
23
- readonly name?: string;
24
+ readonly id?: string;
24
25
  readonly access_token?: string;
25
26
  readonly url?: string;
26
27
  readonly path?: string;
@@ -31,7 +32,7 @@ export interface OneBot11AdapterConfig {
31
32
  }
32
33
  export interface OneBot11ConfigBase {
33
34
  readonly context: 'onebot11';
34
- readonly name: string;
35
+ readonly id: string;
35
36
  readonly access_token?: string;
36
37
  }
37
38
  /** 正向 WebSocket:应用连 OneBot 实现的 WS 服务器 */
@@ -90,10 +91,6 @@ export interface OneBot11WireSegment {
90
91
  readonly type: string;
91
92
  readonly data?: Record<string, unknown>;
92
93
  }
93
- export interface ParsedSendTarget {
94
- readonly message_type: 'private' | 'group';
95
- readonly id: string;
96
- }
97
94
  export declare function resolveOneBot11Config(config?: OneBot11AdapterConfig): ResolvedOneBot11Config;
98
95
  /** 判断是否为消息事件(post_type=message) */
99
96
  export declare function isMessageEvent(ev: OneBot11Event): ev is OneBot11Event & {
@@ -102,10 +99,11 @@ export declare function isMessageEvent(ev: OneBot11Event): ev is OneBot11Event &
102
99
  /** 从事件得到场景 id:私聊 user_id,群 group_id */
103
100
  export declare function getChannelId(ev: OneBot11Event): string;
104
101
  /**
105
- * Gateway reply target:`private:uid` / `group:gid`,便于 send() 还原动作参数。
102
+ * 入站归一化 → ConversationRef:OneBot 11 `group` 消息 → kind 'group',
103
+ * 其余(private 及带 group_id 的非 private 事件按群处理)→ kind 'private'。
104
+ * OneBot 11 无 guild/temp 容器概念,不填 parent。
106
105
  */
107
- export declare function formatInboundTarget(ev: OneBot11Event): string;
108
- export declare function parseSendTarget(target: string): ParsedSendTarget;
106
+ export declare function onebot11InboundConversation(endpointKey: string, ev: OneBot11Event): ConversationRef;
109
107
  /** Build inbound text for MessageGateway.receive */
110
108
  export declare function formatInboundContent(ev: OneBot11Event): string;
111
109
  export declare function senderDisplayName(ev: OneBot11Event): string;
@@ -126,8 +124,17 @@ export declare function isOneBot11BotMentioned(input: {
126
124
  readonly selfId: string | undefined;
127
125
  readonly message?: readonly OneBot11Segment[];
128
126
  }): boolean;
129
- /** 构造 gateway.receive 的 metadata(ws / wss 两个 endpoint 共用)。 */
130
- export declare function formatInboundMetadata(ev: OneBot11Event, endpoint: string): Readonly<Record<string, unknown>>;
127
+ /** Inbound fields extracted from an event for gateway.receive (ws / wss 两个 endpoint 共用). */
128
+ export interface OneBot11InboundFields {
129
+ readonly metadata: Readonly<Record<string, unknown>>;
130
+ readonly endpointId: string;
131
+ readonly mentioned: boolean;
132
+ readonly replyTo: {
133
+ readonly id: string;
134
+ } | undefined;
135
+ }
136
+ /** 构造 gateway.receive 的 metadata 与提升字段(ws / wss 两个 endpoint 共用)。 */
137
+ export declare function formatInboundMetadata(ev: OneBot11Event, endpoint: string): OneBot11InboundFields;
131
138
  /**
132
139
  * canonical MediaRef → OneBot `file` 参数:url 直传、base64 → `base64://`、
133
140
  * 本地路径 → `file://`(路径在 OneBot 实现侧解析)、kind=file 不透明引用原样透传。
@@ -140,7 +147,7 @@ export declare function mediaRefToOneBotFile(media: MediaRef): string;
140
147
  * 其余 wire 形状段(at / 平台扩展段)原样透传。
141
148
  */
142
149
  export declare function formatOutboundSegments(payload: unknown): OneBot11Segment[];
143
- export declare function buildSendAction(target: string, message: OneBot11Segment[]): {
150
+ export declare function buildSendAction(conversation: ConversationRef, message: OneBot11Segment[]): {
144
151
  action: string;
145
152
  params: Record<string, unknown>;
146
153
  };
package/lib/protocol.js CHANGED
@@ -18,8 +18,8 @@ function normalizeConnection(connection, legacyType) {
18
18
  export function resolveOneBot11Config(config = {}) {
19
19
  const entry = config.endpoints?.find((item) => item.context === 'onebot11');
20
20
  const connection = normalizeConnection(config.connection ?? entry?.connection, entry?.type);
21
- const name = (typeof config.name === 'string' && config.name)
22
- || (typeof entry?.name === 'string' && entry.name)
21
+ const id = (typeof config.id === 'string' && config.id)
22
+ || (typeof entry?.id === 'string' && entry.id)
23
23
  || process.env.ONEBOT11_BOT_NAME
24
24
  || 'onebot11-bot';
25
25
  const access_token = config.access_token ?? entry?.access_token;
@@ -31,7 +31,7 @@ export function resolveOneBot11Config(config = {}) {
31
31
  return {
32
32
  context: 'onebot11',
33
33
  connection: 'ws',
34
- name,
34
+ id,
35
35
  access_token,
36
36
  url,
37
37
  reconnect_interval: config.reconnect_interval ?? entry?.reconnect_interval ?? 5000,
@@ -46,7 +46,7 @@ export function resolveOneBot11Config(config = {}) {
46
46
  return {
47
47
  context: 'onebot11',
48
48
  connection: 'wss',
49
- name,
49
+ id,
50
50
  access_token,
51
51
  path,
52
52
  heartbeat_interval: config.heartbeat_interval ?? entry?.heartbeat_interval ?? 30_000,
@@ -69,28 +69,19 @@ export function getChannelId(ev) {
69
69
  return '';
70
70
  }
71
71
  /**
72
- * Gateway reply target:`private:uid` / `group:gid`,便于 send() 还原动作参数。
72
+ * 入站归一化 → ConversationRef:OneBot 11 `group` 消息 → kind 'group',
73
+ * 其余(private 及带 group_id 的非 private 事件按群处理)→ kind 'private'。
74
+ * OneBot 11 无 guild/temp 容器概念,不填 parent。
73
75
  */
74
- export function formatInboundTarget(ev) {
75
- const messageType = ev.message_type === 'group' || (ev.group_id != null && ev.message_type !== 'private')
76
+ export function onebot11InboundConversation(endpointKey, ev) {
77
+ const kind = ev.message_type === 'group' || (ev.group_id != null && ev.message_type !== 'private')
76
78
  ? 'group'
77
79
  : 'private';
78
- return `${messageType}:${getChannelId(ev)}`;
79
- }
80
- export function parseSendTarget(target) {
81
- const sep = target.indexOf(':');
82
- if (sep <= 0) {
83
- return { message_type: 'private', id: target };
84
- }
85
- const head = target.slice(0, sep);
86
- const rest = target.slice(sep + 1);
87
- if (head === 'group') {
88
- return { message_type: 'group', id: rest };
89
- }
90
- if (head === 'private') {
91
- return { message_type: 'private', id: rest };
92
- }
93
- return { message_type: 'private', id: target };
80
+ return {
81
+ endpoint: { id: endpointKey, adapter: endpointKey.split('\0')[0] ?? endpointKey },
82
+ kind,
83
+ id: getChannelId(ev),
84
+ };
94
85
  }
95
86
  /** Build inbound text for MessageGateway.receive */
96
87
  export function formatInboundContent(ev) {
@@ -153,24 +144,26 @@ export function isOneBot11BotMentioned(input) {
153
144
  return qq !== 'all' && qq === input.selfId;
154
145
  });
155
146
  }
156
- /** 构造 gateway.receive 的 metadata(ws / wss 两个 endpoint 共用)。 */
147
+ /** 构造 gateway.receive 的 metadata 与提升字段(ws / wss 两个 endpoint 共用)。 */
157
148
  export function formatInboundMetadata(ev, endpoint) {
158
149
  const selfId = ev.self_id != null ? String(ev.self_id) : undefined;
159
150
  const nickname = senderNickname(ev);
160
151
  const quoteId = extractQuoteId(ev);
161
152
  const mentioned = isOneBot11BotMentioned({ selfId, message: ev.message });
162
- return Object.freeze({
163
- message_type: ev.message_type,
164
- user_id: ev.user_id != null ? String(ev.user_id) : undefined,
165
- group_id: ev.group_id != null ? String(ev.group_id) : undefined,
166
- endpoint,
167
- time: ev.time,
168
- self_id: selfId,
169
- role: ev.sender?.role,
170
- ...(nickname ? { nickname } : {}),
171
- ...(quoteId ? { quote_id: quoteId } : {}),
172
- ...(mentioned ? { mentioned: true } : {}),
173
- });
153
+ return {
154
+ metadata: Object.freeze({
155
+ message_type: ev.message_type,
156
+ user_id: ev.user_id != null ? String(ev.user_id) : undefined,
157
+ group_id: ev.group_id != null ? String(ev.group_id) : undefined,
158
+ time: ev.time,
159
+ self_id: selfId,
160
+ role: ev.sender?.role,
161
+ ...(nickname ? { nickname } : {}),
162
+ }),
163
+ endpointId: endpoint,
164
+ mentioned,
165
+ replyTo: quoteId ? { id: quoteId } : undefined,
166
+ };
174
167
  }
175
168
  /**
176
169
  * canonical MediaRef → OneBot `file` 参数:url 直传、base64 → `base64://`、
@@ -289,13 +282,12 @@ export function formatOutboundSegments(payload) {
289
282
  }
290
283
  return segs.length ? segs : [{ type: 'text', data: { text: '' } }];
291
284
  }
292
- export function buildSendAction(target, message) {
293
- const parsed = parseSendTarget(target);
294
- if (parsed.message_type === 'group') {
285
+ export function buildSendAction(conversation, message) {
286
+ if (conversation.kind === 'group') {
295
287
  return {
296
288
  action: 'send_group_msg',
297
289
  params: {
298
- group_id: Number(parsed.id) || parsed.id,
290
+ group_id: Number(conversation.id) || conversation.id,
299
291
  message,
300
292
  },
301
293
  };
@@ -303,7 +295,7 @@ export function buildSendAction(target, message) {
303
295
  return {
304
296
  action: 'send_private_msg',
305
297
  params: {
306
- user_id: Number(parsed.id) || parsed.id,
298
+ user_id: Number(conversation.id) || conversation.id,
307
299
  message,
308
300
  },
309
301
  };
@@ -1,4 +1,4 @@
1
- import { type EndpointInstance, type EndpointManagement } from '@zhin.js/adapter';
1
+ import { type EndpointInstance, type EndpointManagement, type EndpointSendRequest } from '@zhin.js/adapter';
2
2
  import type { MessageGateway } from '@zhin.js/core/runtime';
3
3
  import type { CapabilityId } from '@zhin.js/plugin-runtime';
4
4
  import { type OneBot11Event, type OneBot11WsConfig } from './protocol.js';
@@ -17,10 +17,7 @@ export declare class OneBot11WsEndpoint implements EndpointInstance {
17
17
  open(): void;
18
18
  close(): void;
19
19
  stop(): Promise<void>;
20
- send({ target, payload }: {
21
- readonly target: string;
22
- readonly payload: unknown;
23
- }): Promise<string>;
20
+ send({ conversation, payload }: EndpointSendRequest): Promise<string>;
24
21
  recallMessage(messageId: string): Promise<void>;
25
22
  /** Public API for agent tools / callers. */
26
23
  callApi(action: string, params?: Record<string, unknown>): Promise<unknown>;
@@ -3,13 +3,13 @@
3
3
  */
4
4
  import WebSocket from 'ws';
5
5
  import { createEndpointLifecycle, } from '@zhin.js/adapter';
6
- import { formatCompact, getLogger } from '@zhin.js/logger';
6
+ import { formatCompact, getAdapterLogger } from '@zhin.js/logger';
7
7
  import { createOneBot11EndpointManagement } from './endpoint-management.js';
8
8
  import { registerOnebot11AgentEndpoint } from './onebot11-agent-deps.js';
9
- import { buildSendAction, buildWsConnectOptions, formatInboundContent, formatInboundMetadata, formatInboundTarget, formatOutboundSegments, isMessageEvent, senderUserId, } from './protocol.js';
9
+ import { buildSendAction, buildWsConnectOptions, formatInboundContent, formatInboundMetadata, formatOutboundSegments, isMessageEvent, onebot11InboundConversation, senderDisplayName, senderUserId, } from './protocol.js';
10
10
  import { callOneBot11WsAction, handleOneBot11WsMessage, rejectAllPending, } from './ws-transport.js';
11
- const logger = getLogger('onebot11');
12
11
  export class OneBot11WsEndpoint {
12
+ #logger;
13
13
  #options;
14
14
  management = createOneBot11EndpointManagement(this);
15
15
  #lifecycle;
@@ -19,10 +19,11 @@ export class OneBot11WsEndpoint {
19
19
  #open = false;
20
20
  #unregisterAgent;
21
21
  constructor(options) {
22
+ this.#logger = getAdapterLogger('onebot11', options.config.id);
22
23
  this.#options = options;
23
24
  const { config } = options;
24
25
  this.#lifecycle = createEndpointLifecycle({
25
- name: config.name,
26
+ name: config.id,
26
27
  reconnect: {
27
28
  initialIntervalMs: config.reconnect_interval,
28
29
  // 固定间隔(multiplier 1、无抖动),对齐旧 reconnect_interval 语义
@@ -37,7 +38,7 @@ export class OneBot11WsEndpoint {
37
38
  if (this.#lifecycle.started)
38
39
  return;
39
40
  // agent 注册/反注册是适配器专有依赖,留在适配器侧(见 endpoint-lifecycle 迁移指引)
40
- this.#unregisterAgent = registerOnebot11AgentEndpoint(this.#options.config.name, this);
41
+ this.#unregisterAgent = registerOnebot11AgentEndpoint(this.#options.config.id, this);
41
42
  try {
42
43
  await this.#lifecycle.start((handle) => this.#connect(handle));
43
44
  }
@@ -72,15 +73,15 @@ export class OneBot11WsEndpoint {
72
73
  rejectAllPending(this.#pending);
73
74
  this.#ws = undefined;
74
75
  }
75
- async send({ target, payload }) {
76
+ async send({ conversation, payload }) {
76
77
  const message = formatOutboundSegments(payload);
77
- const { action, params } = buildSendAction(target, message);
78
+ const { action, params } = buildSendAction(conversation, message);
78
79
  const data = await this.callApi(action, params);
79
80
  const messageId = data?.message_id != null ? String(data.message_id) : '';
80
- logger.debug(formatCompact({
81
+ this.#logger.debug(formatCompact({
81
82
  op: 'onebot11_send',
82
- endpoint: this.#options.config.name,
83
- target,
83
+ endpoint: this.#options.config.id,
84
+ target: `${conversation.kind}:${conversation.id}`,
84
85
  messageId,
85
86
  }));
86
87
  return messageId;
@@ -107,19 +108,26 @@ export class OneBot11WsEndpoint {
107
108
  admit(ev) {
108
109
  if (!this.#open || !isMessageEvent(ev))
109
110
  return;
110
- const target = formatInboundTarget(ev);
111
+ const conversation = onebot11InboundConversation(String(this.#options.id), ev);
111
112
  const content = formatInboundContent(ev);
113
+ const inbound = formatInboundMetadata(ev, this.#options.config.id);
112
114
  void this.#options.gateway.receive({
113
- adapter: this.#options.id,
114
- target,
115
+ conversation,
116
+ message: { conversation, id: String(ev.message_id) },
115
117
  content,
116
- sender: senderUserId(ev),
117
- id: String(ev.message_id),
118
- metadata: formatInboundMetadata(ev, this.#options.config.name),
118
+ sender: {
119
+ id: senderUserId(ev),
120
+ name: senderDisplayName(ev) || undefined,
121
+ ...(ev.sender?.role ? { roles: [ev.sender.role] } : {}),
122
+ },
123
+ endpointId: inbound.endpointId,
124
+ ...(inbound.mentioned ? { mentioned: true } : {}),
125
+ ...(inbound.replyTo ? { replyTo: inbound.replyTo } : {}),
126
+ metadata: inbound.metadata,
119
127
  }).catch((err) => {
120
- logger.warn(formatCompact({
128
+ this.#logger.warn(formatCompact({
121
129
  op: 'onebot11_gateway_receive_failed',
122
- target,
130
+ target: `${conversation.kind}:${conversation.id}`,
123
131
  error: err instanceof Error ? err.message : String(err),
124
132
  }));
125
133
  });
@@ -145,14 +153,14 @@ export class OneBot11WsEndpoint {
145
153
  return;
146
154
  settled = true;
147
155
  if (!this.#options.config.access_token) {
148
- logger.warn(formatCompact({
149
- endpoint: this.#options.config.name,
156
+ this.#logger.warn(formatCompact({
157
+ endpoint: this.#options.config.id,
150
158
  ok: false,
151
159
  error: 'missing access_token',
152
160
  }));
153
161
  }
154
- logger.debug(formatCompact({
155
- endpoint: this.#options.config.name,
162
+ this.#logger.debug(formatCompact({
163
+ endpoint: this.#options.config.id,
156
164
  mode: 'ws',
157
165
  url: safeUrl,
158
166
  }));
@@ -161,7 +169,7 @@ export class OneBot11WsEndpoint {
161
169
  });
162
170
  ws.on('message', (data) => {
163
171
  handleOneBot11WsMessage(data, {
164
- endpointName: this.#options.config.name,
172
+ endpointId: this.#options.config.id,
165
173
  pending: this.#pending,
166
174
  admit: (ev) => this.admit(ev),
167
175
  });
@@ -188,9 +196,9 @@ export class OneBot11WsEndpoint {
188
196
  });
189
197
  ws.on('error', (err) => {
190
198
  const error = err instanceof Error ? err : new Error(String(err));
191
- logger.warn(formatCompact({
199
+ this.#logger.warn(formatCompact({
192
200
  op: 'ws_error',
193
- endpoint: this.#options.config.name,
201
+ endpoint: this.#options.config.id,
194
202
  ok: false,
195
203
  error: error.message,
196
204
  }));
@@ -2,7 +2,7 @@ import { type OneBot11Event } from './protocol.js';
2
2
  import { type OneBot11PendingAction, type OneBot11WsSocket } from './ws-types.js';
3
3
  export declare function decodeWsPayload(data: unknown): string;
4
4
  export declare function handleOneBot11WsMessage(data: unknown, options: {
5
- readonly endpointName: string;
5
+ readonly endpointId: string;
6
6
  readonly pending: Map<string, OneBot11PendingAction>;
7
7
  readonly admit: (ev: OneBot11Event) => void;
8
8
  }): void;
@@ -33,7 +33,7 @@ export function handleOneBot11WsMessage(data, options) {
33
33
  catch (error) {
34
34
  logger.warn(formatCompact({
35
35
  op: 'onebot11_parse_failed',
36
- endpoint: options.endpointName,
36
+ endpoint: options.endpointId,
37
37
  error: error instanceof Error ? error.message : String(error),
38
38
  }));
39
39
  }
@@ -1,4 +1,4 @@
1
- import type { EndpointInstance, EndpointManagement } from '@zhin.js/adapter';
1
+ import type { EndpointInstance, EndpointManagement, EndpointSendRequest } from '@zhin.js/adapter';
2
2
  import type { MessageGateway } from '@zhin.js/core/runtime';
3
3
  import type { HttpHost } from '@zhin.js/host-http';
4
4
  import type { CapabilityId } from '@zhin.js/plugin-runtime';
@@ -17,10 +17,7 @@ export declare class OneBot11WssEndpoint implements EndpointInstance {
17
17
  open(): void;
18
18
  close(): void;
19
19
  stop(): Promise<void>;
20
- send({ target, payload }: {
21
- readonly target: string;
22
- readonly payload: unknown;
23
- }): Promise<string>;
20
+ send({ conversation, payload }: EndpointSendRequest): Promise<string>;
24
21
  recallMessage(messageId: string): Promise<void>;
25
22
  callApi(action: string, params?: Record<string, unknown>): Promise<unknown>;
26
23
  setTitle(groupId: number, userId: number, title: string, duration?: number): Promise<boolean>;