From e885f1999f866aefa8bc1eb4b8e0af6e7c399e36 Mon Sep 17 00:00:00 2001 From: Peter Steinberger Date: Sat, 14 Mar 2026 02:05:27 +0000 Subject: [PATCH] refactor: reduce extension channel setup duplication --- extensions/irc/src/channel.ts | 7 ++----- .../matrix/src/matrix/monitor/handler.ts | 3 ++- .../mattermost/src/mattermost/slash-http.ts | 3 ++- extensions/nextcloud-talk/src/channel.ts | 7 ++----- extensions/shared/passive-monitor.ts | 18 ++++++++++++++++++ 5 files changed, 26 insertions(+), 12 deletions(-) create mode 100644 extensions/shared/passive-monitor.ts diff --git a/extensions/irc/src/channel.ts b/extensions/irc/src/channel.ts index c598a9a0ef3..62d64fb0866 100644 --- a/extensions/irc/src/channel.ts +++ b/extensions/irc/src/channel.ts @@ -14,10 +14,10 @@ import { deleteAccountFromConfigSection, getChatChannelMeta, PAIRING_APPROVED_MESSAGE, - runPassiveAccountLifecycle, setAccountEnabledInConfigSection, type ChannelPlugin, } from "openclaw/plugin-sdk/irc"; +import { runStoppablePassiveMonitor } from "../../shared/passive-monitor.js"; import { listIrcAccountIds, resolveDefaultIrcAccountId, @@ -367,7 +367,7 @@ export const ircPlugin: ChannelPlugin = { ctx.log?.info( `[${account.accountId}] starting IRC provider (${account.host}:${account.port}${account.tls ? " tls" : ""})`, ); - await runPassiveAccountLifecycle({ + await runStoppablePassiveMonitor({ abortSignal: ctx.abortSignal, start: async () => await monitorIrcProvider({ @@ -377,9 +377,6 @@ export const ircPlugin: ChannelPlugin = { abortSignal: ctx.abortSignal, statusSink, }), - stop: async (monitor) => { - monitor.stop(); - }, }); }, }, diff --git a/extensions/matrix/src/matrix/monitor/handler.ts b/extensions/matrix/src/matrix/monitor/handler.ts index 0adc9fa2886..22ee16275cf 100644 --- a/extensions/matrix/src/matrix/monitor/handler.ts +++ b/extensions/matrix/src/matrix/monitor/handler.ts @@ -686,6 +686,7 @@ export function createMatrixRoomMessageHandler(params: MatrixMonitorHandlerParam channel: "matrix", accountId: route.accountId, }); + const humanDelay = core.channel.reply.resolveHumanDelayConfig(cfg, route.agentId); const typingCallbacks = createTypingCallbacks({ start: () => sendTypingMatrix(roomId, true, undefined, client), stop: () => sendTypingMatrix(roomId, false, undefined, client), @@ -711,7 +712,7 @@ export function createMatrixRoomMessageHandler(params: MatrixMonitorHandlerParam const { dispatcher, replyOptions, markDispatchIdle } = core.channel.reply.createReplyDispatcherWithTyping({ ...prefixOptions, - humanDelay: core.channel.reply.resolveHumanDelayConfig(cfg, route.agentId), + humanDelay, typingCallbacks, deliver: async (payload) => { await deliverMatrixReplies({ diff --git a/extensions/mattermost/src/mattermost/slash-http.ts b/extensions/mattermost/src/mattermost/slash-http.ts index 36a5643e3fd..468f5c3584c 100644 --- a/extensions/mattermost/src/mattermost/slash-http.ts +++ b/extensions/mattermost/src/mattermost/slash-http.ts @@ -475,6 +475,7 @@ async function handleSlashCommandAsync(params: { channel: "mattermost", accountId: account.accountId, }); + const humanDelay = core.channel.reply.resolveHumanDelayConfig(cfg, route.agentId); const typingCallbacks = createTypingCallbacks({ start: () => sendMattermostTyping(client, { channelId }), @@ -491,7 +492,7 @@ async function handleSlashCommandAsync(params: { const { dispatcher, replyOptions, markDispatchIdle } = core.channel.reply.createReplyDispatcherWithTyping({ ...prefixOptions, - humanDelay: core.channel.reply.resolveHumanDelayConfig(cfg, route.agentId), + humanDelay, deliver: async (payload: ReplyPayload) => { await deliverMattermostReplyPayload({ core, diff --git a/extensions/nextcloud-talk/src/channel.ts b/extensions/nextcloud-talk/src/channel.ts index 8a908b7e0ac..473299b74e0 100644 --- a/extensions/nextcloud-talk/src/channel.ts +++ b/extensions/nextcloud-talk/src/channel.ts @@ -5,7 +5,6 @@ import { createAccountStatusSink, formatAllowFromLowercase, mapAllowFromEntries, - runPassiveAccountLifecycle, } from "openclaw/plugin-sdk/compat"; import { applyAccountNameToChannelSection, @@ -21,6 +20,7 @@ import { type OpenClawConfig, type ChannelSetupInput, } from "openclaw/plugin-sdk/nextcloud-talk"; +import { runStoppablePassiveMonitor } from "../../shared/passive-monitor.js"; import { listNextcloudTalkAccountIds, resolveDefaultNextcloudTalkAccountId, @@ -344,7 +344,7 @@ export const nextcloudTalkPlugin: ChannelPlugin = setStatus: ctx.setStatus, }); - await runPassiveAccountLifecycle({ + await runStoppablePassiveMonitor({ abortSignal: ctx.abortSignal, start: async () => await monitorNextcloudTalkProvider({ @@ -354,9 +354,6 @@ export const nextcloudTalkPlugin: ChannelPlugin = abortSignal: ctx.abortSignal, statusSink, }), - stop: async (monitor) => { - monitor.stop(); - }, }); }, logoutAccount: async ({ accountId, cfg }) => { diff --git a/extensions/shared/passive-monitor.ts b/extensions/shared/passive-monitor.ts new file mode 100644 index 00000000000..e5ffb3f03ff --- /dev/null +++ b/extensions/shared/passive-monitor.ts @@ -0,0 +1,18 @@ +import { runPassiveAccountLifecycle } from "openclaw/plugin-sdk"; + +type StoppableMonitor = { + stop: () => void; +}; + +export async function runStoppablePassiveMonitor(params: { + abortSignal: AbortSignal; + start: () => Promise; +}): Promise { + await runPassiveAccountLifecycle({ + abortSignal: params.abortSignal, + start: params.start, + stop: async (monitor) => { + monitor.stop(); + }, + }); +}