UNPKG

openclaw

Version:

Multi-channel AI gateway with extensible messaging integrations

161 lines (160 loc) 5.99 kB
import { _ as readReactionParams, b as readStringParam, g as readPositiveIntegerParam, i as createActionGate, l as jsonResult } from "./common-C4yy9V-D.js"; import { n as loadOutboundMediaFromUrl } from "./outbound-media-MHBXtJsJ.js"; import "./channel-actions-BOfvC-Gl.js"; import { t as extractToolSend } from "./tool-send-DzTXHBeR.js"; import { i as resolveGoogleChatAccount, t as listEnabledGoogleChatAccounts } from "./accounts-BedKEwKe.js"; import { a as createGoogleChatReaction, d as sendGoogleChatMessage, i as resolveGoogleChatOutboundSpace, l as listGoogleChatReactions, p as uploadGoogleChatAttachment, s as deleteGoogleChatReaction } from "./targets-BIe3h2UJ.js"; import { t as getGoogleChatRuntime } from "./runtime-api-Dp_Hh2eL.js"; //#region extensions/googlechat/src/actions.ts const providerId = "googlechat"; function listEnabledAccounts(cfg) { return listEnabledGoogleChatAccounts(cfg).filter((account) => account.enabled && account.credentialSource !== "none"); } function isReactionsEnabled(accounts) { for (const account of accounts) if (createActionGate(account.config.actions)("reactions")) return true; return false; } function resolveAppUserNames(account) { return new Set(["users/app", account.config.botUser?.trim()].filter(Boolean)); } async function loadGoogleChatActionMedia(params) { const runtime = getGoogleChatRuntime(); return /^https?:\/\//i.test(params.mediaUrl) ? await runtime.channel.media.readRemoteMediaBuffer({ url: params.mediaUrl, maxBytes: params.maxBytes }) : await loadOutboundMediaFromUrl(params.mediaUrl, { maxBytes: params.maxBytes, mediaAccess: params.mediaAccess, mediaLocalRoots: params.mediaLocalRoots, mediaReadFile: params.mediaReadFile }); } const googlechatMessageActions = { describeMessageTool: ({ cfg, accountId }) => { const accounts = accountId ? [resolveGoogleChatAccount({ cfg, accountId })].filter((account) => account.enabled && account.credentialSource !== "none") : listEnabledAccounts(cfg); if (accounts.length === 0) return null; const actions = /* @__PURE__ */ new Set([]); actions.add("send"); actions.add("upload-file"); if (isReactionsEnabled(accounts)) { actions.add("react"); actions.add("reactions"); } return { actions: Array.from(actions) }; }, extractToolSend: ({ args }) => { return extractToolSend(args, "sendMessage"); }, handleAction: async ({ action, params, cfg, accountId, mediaAccess, mediaLocalRoots, mediaReadFile }) => { const account = resolveGoogleChatAccount({ cfg, accountId }); if (account.credentialSource === "none") throw new Error("Google Chat credentials are missing."); if (action === "send" || action === "upload-file") { const to = readStringParam(params, "to", { required: true }); const content = readStringParam(params, "message", { required: action === "send", allowEmpty: true }) ?? readStringParam(params, "initialComment", { allowEmpty: true }) ?? ""; const mediaUrl = readStringParam(params, "media", { trim: false }) ?? readStringParam(params, "filePath", { trim: false }) ?? readStringParam(params, "path", { trim: false }); const threadId = readStringParam(params, "threadId") ?? readStringParam(params, "replyTo"); const space = await resolveGoogleChatOutboundSpace({ account, target: to }); if (mediaUrl) { const loaded = await loadGoogleChatActionMedia({ mediaUrl, maxBytes: (account.config.mediaMaxMb ?? 20) * 1024 * 1024, mediaAccess, mediaLocalRoots, mediaReadFile }); const uploadFileName = readStringParam(params, "filename") ?? readStringParam(params, "title") ?? loaded.fileName ?? "attachment"; const upload = await uploadGoogleChatAttachment({ account, space, filename: uploadFileName, buffer: loaded.buffer, contentType: loaded.contentType }); await sendGoogleChatMessage({ account, space, text: content, thread: threadId ?? void 0, attachments: upload.attachmentUploadToken ? [{ attachmentUploadToken: upload.attachmentUploadToken, contentName: uploadFileName }] : void 0 }); return jsonResult({ ok: true, to: space }); } if (action === "upload-file") throw new Error("upload-file requires media, filePath, or path"); await sendGoogleChatMessage({ account, space, text: content, thread: threadId ?? void 0 }); return jsonResult({ ok: true, to: space }); } if (action === "react") { const messageName = readStringParam(params, "messageId", { required: true }); const { emoji, remove, isEmpty } = readReactionParams(params, { removeErrorMessage: "Emoji is required to remove a Google Chat reaction." }); if (remove || isEmpty) { const reactions = await listGoogleChatReactions({ account, messageName }); const appUsers = resolveAppUserNames(account); const toRemove = reactions.filter((reaction) => { const userName = reaction.user?.name?.trim(); if (appUsers.size > 0 && !appUsers.has(userName ?? "")) return false; if (emoji) return reaction.emoji?.unicode === emoji; return true; }); for (const reaction of toRemove) { if (!reaction.name) continue; await deleteGoogleChatReaction({ account, reactionName: reaction.name }); } return jsonResult({ ok: true, removed: toRemove.length }); } return jsonResult({ ok: true, reaction: await createGoogleChatReaction({ account, messageName, emoji }) }); } if (action === "reactions") return jsonResult({ ok: true, reactions: await listGoogleChatReactions({ account, messageName: readStringParam(params, "messageId", { required: true }), limit: readPositiveIntegerParam(params, "limit") ?? void 0 }) }); throw new Error(`Action ${action} is not supported for provider ${providerId}.`); } }; //#endregion export { googlechatMessageActions };