跳到主要内容

IAdapterContext - 适配器上下文

适配器上下文接口提供与即时通讯平台交互的核心功能,是所有适配器都必须实现的通用接口。

卡死线程问题

该接口由于部分实现端存在差异问题,如果你尝试使用await等待异步返回结果,可能会出现卡死线程的问题,请谨慎使用!

接口定义

declare interface IAdapterContext {
// 消息发送
SendGroupMessageAsync(selfId: string, peerId: string, chain: MessageChain, token?: any): Promise<string>;
SendDirectMessageAsync(selfId: string, peerId: string, chain: MessageChain, groupId?: string | null, token?: any): Promise<string>;
SendForwardMessage(messageType: number, peerId: string, nodes: IList<NodeSegment>, token?: any): Promise<string>;

// 消息编辑与交互
EditMessage(messageId: string, newChain: MessageChain, token?: any): Promise<void>;
EditMessageActions(messageId: string, actions: IList<ActionOption>, token?: any): Promise<void>;
SetMessageInteraction(msgId: string, emojiId: string, add: boolean, token?: any): Promise<void>;

// 交互式会话
WaitForAction(
chain: MessageChain,
actions: IList<ActionOption>,
context?: any | null,
onAction?: (ctx: ActionCallbackContext) => ActionHandleResult | Promise<ActionHandleResult>,
onError?: ((ctx: ActionExceptionContext) => ActionHandleType | Promise<ActionHandleType>) | null,
canCancel?: boolean,
timeoutMs?: number,
maxRetries?: number,
peerId?: string | null,
senderId?: string | null,
isGroup?: boolean,
cancellationToken?: any,
): Promise<ActionHandleResult>;

// 用户信息
GetUserProfileAsync(selfId: string, userId: string, token?: any): Promise<UserProfile>;
GetGroupMemberInfo(groupId: string, userId: string, token?: any): Promise<MemberInfo>;
GetGroupMemberList(groupId: string, token?: any): Promise<IList<MemberInfo>>;

// 群组操作
GetGroupName(groupId: string, noCache?: boolean, cancellationToken?: any): Promise<string>;
SetNickName(selfId: string, userId: string, groupId: string, nickName: string, token?: any): Promise<void>;
SetGroupAddRequest(flag: string, isInvite: boolean, approve: boolean, reason?: string): Promise<void>;
KickMember(groupId: string, userId: string, rejectAddRequest?: boolean): Promise<void>;
SetMute(groupId: string, userId: string, duration: number): Promise<void>;

// 消息操作
DeleteMessage(messageId: string): Promise<void>;

// 原生操作
SendRaw(data: string): Promise<void>;
}

消息发送方法

SendGroupMessageAsync()

发送群组消息。

语法: SendGroupMessageAsync(selfId: string, peerId: string, chain: MessageChain, token?: any): Promise<string>

参数:

  • selfId - 机器人账号ID
  • peerId - 目标群组ID
  • chain - 消息链对象
  • token - 可选取消令牌

返回值: 返回消息ID的Promise

示例:

const messageId = await context.SendGroupMessageAsync(
"bot123",
"group456",
new MessageChain().Text("Hello Group!")
);
logger.info(`消息已发送,ID: ${messageId}`);

SendDirectMessageAsync()

发送私聊消息。

v0.4.0 变更:新增可选 groupId 参数,用于在私聊中关联群组上下文。

语法: SendDirectMessageAsync(selfId: string, peerId: string, chain: MessageChain, groupId?: string | null, token?: any): Promise<string>

参数:

  • selfId - 机器人账号ID
  • peerId - 目标用户ID
  • chain - 消息链对象
  • groupId - 可选的群组上下文ID(v0.4.0 新增)
  • token - 可选取消令牌

返回值: 返回消息ID的Promise

示例:

const messageId = await context.SendDirectMessageAsync(
"bot123",
"user789",
new MessageChain().Text("Hello User!")
);

SendForwardMessage()

发送合并转发消息。

v0.4.0 新增

语法: SendForwardMessage(messageType: number, peerId: string, nodes: IList<NodeSegment>, token?: any): Promise<string>

参数:

  • messageType - 转发消息目标类型(0 = 私聊,1 = 群聊)
  • peerId - 目标对等方ID
  • nodes - 合并转发节点列表
  • token - 可选取消令牌

返回值: 返回原生消息ID的Promise

示例:

const chain = new MessageChain();
chain.Node("node1", "用户A", "123456", new MessageChain().Text("消息1"));
chain.Node("node2", "用户B", "789012", new MessageChain().Text("消息2"));

const nodes = chain.AsArray(); // 获取 NodeSegment 列表
await context.SendForwardMessage(1, "group456", nodes);

消息编辑与交互

EditMessage()

编辑已发送消息的文本内容。平台不支持时降级为删除并重发。

v0.4.0 新增

语法: EditMessage(messageId: string, newChain: MessageChain, token?: any): Promise<void>

参数:

  • messageId - 原生平台消息ID
  • newChain - 新的消息内容链
  • token - 可选取消令牌

示例:

await context.EditMessage("msg123", new MessageChain().Text("已更新的消息内容"));

EditMessageActions()

编辑已发送消息的操作按钮。平台不支持时降级为删除并重发。

v0.4.0 新增

语法: EditMessageActions(messageId: string, actions: IList<ActionOption>, token?: any): Promise<void>

参数:

  • messageId - 原生平台消息ID
  • actions - 新的操作按钮列表
  • token - 可选取消令牌

示例:

const actions = [
{ Id: "btn1", Label: "选项A", IsCancel: false, IsEnabled: true, IsClicked: false },
{ Id: "btn2", Label: "选项B", IsCancel: false, IsEnabled: true, IsClicked: false },
];
await context.EditMessageActions("msg123", actions);

SetMessageInteraction()

设置消息表情回应(点赞/踩等)。

v0.4.0 变更:新增 token 参数。

语法: SetMessageInteraction(msgId: string, emojiId: string, add: boolean, token?: any): Promise<void>

参数:

  • msgId - 原生平台消息ID
  • emojiId - 表情标识
  • add - true 为添加,false 为移除
  • token - 可选取消令牌(v0.4.0 新增)

示例:

await context.SetMessageInteraction("msg123", "128077", true);

交互式会话 (Action Session)

v0.4.0 新增:交互式消息 Action Session 框架,支持发送带按钮的消息并阻塞等待用户操作。

核心概念

Action Session 允许插件发送带有可点击按钮的消息,并进入阻塞等待循环,直到用户点击按钮、会话超时或被取消。同一对等方 + 发送者下仅允许存在一个活跃会话,新会话会取代旧会话。

WaitForAction()

发送交互式消息并进入阻塞等待循环。

语法:

WaitForAction(
chain: MessageChain,
actions: IList<ActionOption>,
context?: any | null,
onAction?: (ctx: ActionCallbackContext) => ActionHandleResult | Promise<ActionHandleResult>,
onError?: ((ctx: ActionExceptionContext) => ActionHandleType | Promise<ActionHandleType>) | null,
canCancel?: boolean,
timeoutMs?: number,
maxRetries?: number,
peerId?: string | null,
senderId?: string | null,
isGroup?: boolean,
cancellationToken?: any,
): Promise<ActionHandleResult>

参数:

  • chain - 初始消息内容链
  • actions - 操作按钮列表
  • context - 用户自定义上下文,透传给 onAction 回调的 ActionTag
  • onAction - 用户点击回调,返回 ActionHandleResult 控制会话行为
  • onError - 异常处理回调,返回 ActionHandleType 决定后续行为(null 时异常直接中止会话)
  • canCancel - 是否自动追加取消按钮(默认 true
  • timeoutMs - 单次点击等待超时毫秒(默认 60000
  • maxRetries - 异常时最大重试次数(默认 3
  • peerId - 目标对等方标识(默认使用当前上下文)
  • senderId - 交互发起者标识(默认使用当前上下文)
  • isGroup - 是否为群聊场景(默认 true
  • cancellationToken - 外部取消令牌

返回: 最终的会话处理结果 ActionHandleResult

ActionOption 接口

表示交互式消息中的一个可点击操作按钮:

interface ActionOption {
Id: string; // 操作唯一标识
Label: string; // 按钮显示文本
Emoji?: string | null; // 平台表情标识(可选)
IsCancel: boolean; // 是否为取消操作
IsEnabled: boolean; // 是否可点击
IsClicked: boolean; // 是否已被点击过
}

ActionHandleResult 类

决定会话的后续行为:

class ActionHandleResult {
Type: ActionHandleType; // 处理结果类型
UpdatedActions?: IList<ActionOption> | null; // 更新后的按钮列表
UpdatedMessage?: MessageChain | null; // 更新后的消息内容

static Continue: ActionHandleResult; // 预置:继续等待
static Complete: ActionHandleResult; // 预置:正常结束
}

ActionHandleType 枚举

enum ActionHandleType {
Continue = 0, // 继续等待下一次点击
Complete = 1, // 会话正常完成
Aborted = 2, // 会话异常中止
Retry = 3, // 请求重试当前操作
TimedOut = 4, // 等待点击超时
Cancelled = 5, // 用户点击了取消按钮
Superseded = 6, // 被同一会话键的新会话取代
}

ActionCallbackContext 类

在 onAction 回调中接收的上下文对象,提供丰富的辅助方法:

属性类型描述
AdapterIAdapter当前适配器实例
AdapterPlatformstring适配器平台标识
InstanceIdstring适配器实例 ID
PeerIdstring消息来源的对等方标识
SenderIdstring交互发起者标识
ClickedBystring | null本次点击的实际用户标识
IsGroupboolean是否为群聊场景
NativeMessageIdstring交互消息的原生平台消息 ID
ChainMessageChain当前消息内容链
ClickedActionActionOption本次被点击的操作选项
AllActionsIList<ActionOption>当前所有操作选项
RecordsIList<ActionRecord>历史点击记录
ActionTagany用户自定义上下文对象
方法返回值描述
UpdateActions(newActions)ActionHandleResult返回 Continue 并更新全部按钮
UpdateAction(updatedAction)ActionHandleResult返回 Continue 并替换被点击的同 ID 按钮
UpdateClicked()ActionHandleResult返回 Continue 并标记被点击按钮为已点击
UpdateMessage(newChain)ActionHandleResult返回 Continue 并更新消息内容
Done()ActionHandleResult返回 Complete,正常结束会话

使用示例

基础交互式确认

const actions = [
{ Id: "confirm", Label: "确认", IsCancel: false, IsEnabled: true, IsClicked: false },
{ Id: "reject", Label: "拒绝", IsCancel: false, IsEnabled: true, IsClicked: false },
];

const result = await context.WaitForAction(
new MessageChain().Text("是否确认执行此操作?"),
actions,
null, // context
(ctx) => {
if (ctx.ClickedAction.Id === "confirm") {
// 执行确认逻辑...
return ctx.Done();
}
return ctx.UpdateMessage(new MessageChain().Text("操作已取消"));
}
);

if (result.Type === 1) { // Complete
logger.info("用户已确认");
}

多步骤交互向导

const steps = [
{ question: "请选择你的年龄段:", options: [
{ Id: "young", Label: "18岁以下", IsCancel: false, IsEnabled: true, IsClicked: false },
{ Id: "adult", Label: "18-30岁", IsCancel: false, IsEnabled: true, IsClicked: false },
{ Id: "senior", Label: "30岁以上", IsCancel: false, IsEnabled: true, IsClicked: false },
]},
{ question: "请选择你的性别:", options: [
{ Id: "male", Label: "男", IsCancel: false, IsEnabled: true, IsClicked: false },
{ Id: "female", Label: "女", IsCancel: false, IsEnabled: true, IsClicked: false },
]},
];

let stepIndex = 0;

const result = await context.WaitForAction(
new MessageChain().Text(steps[stepIndex].question),
steps[stepIndex].options,
{ stepIndex },
(ctx) => {
const tag = ctx.ActionTag;
logger.info(`步骤 ${tag.stepIndex + 1}: 选择了 ${ctx.ClickedAction.Label}`);

tag.stepIndex++;
if (tag.stepIndex < steps.length) {
return ctx.UpdateActions(steps[tag.stepIndex].options);
}
return ctx.Done();
}
);

用户信息方法

GetUserProfileAsync()

获取用户资料。

语法: GetUserProfileAsync(selfId: string, userId: string, token?: any): Promise<UserProfile>

参数:

  • selfId - 机器人账号ID
  • userId - 目标用户ID
  • token - 可选取消令牌

返回值: 返回用户资料的Promise

示例:

const profile = await context.GetUserProfileAsync("bot123", "user789");
logger.info(`用户: ${profile.Name} (${profile.Id})`);

GetGroupMemberInfo()

获取群成员信息。

语法: GetGroupMemberInfo(groupId: string, userId: string, token?: any): Promise<MemberInfo>

参数:

  • groupId - 目标群组ID
  • userId - 目标成员ID
  • token - 可选取消令牌

返回值: 返回成员信息的Promise

示例:

const member = await context.GetGroupMemberInfo("group456", "user789");
logger.info(`${member.NickName} 的角色是 ${member.Role}`);

GetGroupMemberList()

获取群成员列表。

语法: GetGroupMemberList(groupId: string, token?: any): Promise<IList<MemberInfo>>

参数:

  • groupId - 目标群组ID
  • token - 可选取消令牌

返回值: 返回成员信息列表的Promise

示例:

const members = await context.GetGroupMemberList("group456");
logger.info(`群组共有 ${members.length} 个成员`);

群组操作方法

GetGroupName()

获取群名称。

语法: GetGroupName(groupId: string, noCache?: boolean, any?: any): Promise<string>

参数:

  • groupId - 目标群组ID
  • noCache - 是否禁用缓存
  • any - 可选取消令牌

返回值: 返回群名称的Promise

示例:

const groupName = await context.GetGroupName("group456");
logger.info(`群名称: ${groupName}`);

SetNickName()

设置群成员昵称。

语法: SetNickName(selfId: string, userId: string, groupId: string, nickName: string, token?: any): Promise<void>

参数:

  • selfId - 机器人账号ID
  • userId - 目标成员ID
  • groupId - 目标群组ID
  • nickName - 新昵称
  • token - 可选取消令牌

返回值: 无返回值的Promise

示例:

await context.SetNickName("bot123", "user789", "group456", "新昵称");

SetGroupAddRequest()

处理群组加群请求。

语法: SetGroupAddRequest(flag: string, isInvite: boolean, approve: boolean, reason?: string): Promise<void>

参数:

  • flag - 请求标识符
  • isInvite - 是否为邀请请求
  • approve - 是否批准请求
  • reason - 拒绝理由(可选)

返回值: 无返回值的Promise

示例:

// 批准加群请求
await context.SetGroupAddRequest("request123", false, true);

// 拒绝加群请求
await context.SetGroupAddRequest("request456", false, false, "不符合入群条件");

KickMember()

踢出群成员。

语法: KickMember(groupId: string, userId: string, rejectAddRequest?: boolean): Promise<void>

参数:

  • groupId - 目标群组ID
  • userId - 目标成员ID
  • rejectAddRequest - 是否拒绝再次加群请求(可选)

返回值: 无返回值的Promise

示例:

await context.KickMember("group456", "user789", true);

SetMute()

禁言群成员。

语法: SetMute(groupId: string, userId: string, duration: number): Promise<void>

参数:

  • groupId - 目标群组ID
  • userId - 目标成员ID
  • duration - 禁言时长(秒)

返回值: 无返回值的Promise

示例:

// 禁言10分钟
await context.SetMute("group456", "user789", 600);

// 解除禁言
await context.SetMute("group456", "user789", 0);

消息操作方法

DeleteMessage()

撤回消息。

语法: DeleteMessage(messageId: string): Promise<void>

参数:

  • messageId - 目标消息ID

返回值: 无返回值的Promise

示例:

await context.DeleteMessage("msg123");

原生操作方法

SendRaw()

发送原生数据包。

语法: SendRaw(data: string): Promise<void>

参数:

  • data - 原生数据包

返回值: 无返回值的Promise

示例:

const rawData = JSON.stringify({
action: "custom_action",
params: { key: "value" }
});
await context.SendRaw(rawData);

使用示例

群组管理机器人

// 处理群消息事件
bus.on("group_message_event", async (event) => {
const { AdapterContext: context, SelfId, PeerId, SenderId, RawMessage } = event;

if (RawMessage === "/群信息") {
const groupName = await context.GetGroupName(PeerId);
const members = await context.GetGroupMemberList(PeerId);

const reply = new MessageChain()
.Text(`群名称: ${groupName}`)
.NextLine()
.Text(`成员数量: ${members.length}`);

await context.SendGroupMessageAsync(SelfId, PeerId, reply);
}
});

注意事项

  1. 异步操作: 所有方法都返回 Promise,需要使用 await
  2. 错误处理: 建议使用 try-catch 处理可能的异常
  3. 权限检查: 某些操作需要机器人具有相应权限
  4. 平台差异: 不同适配器可能对某些功能有不同的实现
  5. 类型变更: v0.4.0 起所有 C# 集合类型映射统一为 IList<T>
  6. 破坏性变更: SendDirectMessageAsync 新增 groupId 参数,请注意调用签名

遇到麻烦了?

有偿服务

我们提供有偿代安装服务,解决您的环境配置烦恼。

了解详情
Miku

少年,买服务器吗?

持证经营

专注高性价比游戏云VPS,铂金 / I7 / R9 / 物理机

💰 最低六元起、买不了吃亏买不了上当,快来看看吧~

快来看看