mirror of https://github.com/openclaw/openclaw.git
84 lines
2.5 KiB
TypeScript
84 lines
2.5 KiB
TypeScript
import type { WebhookRequestBody } from "@line/bot-sdk";
|
|
import type { Request, Response, NextFunction } from "express";
|
|
import { DEFAULT_GROUP_HISTORY_LIMIT, type HistoryEntry } from "../auto-reply/reply/history.js";
|
|
import type { OpenClawConfig } from "../config/config.js";
|
|
import { loadConfig } from "../config/config.js";
|
|
import { logVerbose } from "../globals.js";
|
|
import { createNonExitingRuntime, type RuntimeEnv } from "../runtime.js";
|
|
import { resolveLineAccount } from "./accounts.js";
|
|
import { createLineWebhookReplayCache, handleLineWebhookEvents } from "./bot-handlers.js";
|
|
import type { LineInboundContext } from "./bot-message-context.js";
|
|
import type { ResolvedLineAccount } from "./types.js";
|
|
import { startLineWebhook } from "./webhook.js";
|
|
|
|
export interface LineBotOptions {
|
|
channelAccessToken: string;
|
|
channelSecret: string;
|
|
accountId?: string;
|
|
runtime?: RuntimeEnv;
|
|
config?: OpenClawConfig;
|
|
mediaMaxMb?: number;
|
|
onMessage?: (ctx: LineInboundContext) => Promise<void>;
|
|
}
|
|
|
|
export interface LineBot {
|
|
handleWebhook: (body: WebhookRequestBody) => Promise<void>;
|
|
account: ResolvedLineAccount;
|
|
}
|
|
|
|
export function createLineBot(opts: LineBotOptions): LineBot {
|
|
const runtime: RuntimeEnv = opts.runtime ?? createNonExitingRuntime();
|
|
|
|
const cfg = opts.config ?? loadConfig();
|
|
const account = resolveLineAccount({
|
|
cfg,
|
|
accountId: opts.accountId,
|
|
});
|
|
|
|
const mediaMaxBytes = (opts.mediaMaxMb ?? account.config.mediaMaxMb ?? 10) * 1024 * 1024;
|
|
|
|
const processMessage =
|
|
opts.onMessage ??
|
|
(async () => {
|
|
logVerbose("line: no message handler configured");
|
|
});
|
|
const replayCache = createLineWebhookReplayCache();
|
|
const groupHistories = new Map<string, HistoryEntry[]>();
|
|
|
|
const handleWebhook = async (body: WebhookRequestBody): Promise<void> => {
|
|
if (!body.events || body.events.length === 0) {
|
|
return;
|
|
}
|
|
|
|
await handleLineWebhookEvents(body.events, {
|
|
cfg,
|
|
account,
|
|
runtime,
|
|
mediaMaxBytes,
|
|
processMessage,
|
|
replayCache,
|
|
groupHistories,
|
|
historyLimit: cfg.messages?.groupChat?.historyLimit ?? DEFAULT_GROUP_HISTORY_LIMIT,
|
|
});
|
|
};
|
|
|
|
return {
|
|
handleWebhook,
|
|
account,
|
|
};
|
|
}
|
|
|
|
export function createLineWebhookCallback(
|
|
bot: LineBot,
|
|
channelSecret: string,
|
|
path = "/line/webhook",
|
|
): { path: string; handler: (req: Request, res: Response, _next: NextFunction) => Promise<void> } {
|
|
const { handler } = startLineWebhook({
|
|
channelSecret,
|
|
onEvents: bot.handleWebhook,
|
|
path,
|
|
});
|
|
|
|
return { path, handler };
|
|
}
|