mirror of
https://github.com/wassname/pi-telegram.git
synced 2026-06-27 16:46:21 +08:00
Translate dashes to underscores for Telegram bot commands
Pi command names like compact-now were silently dropped from
setMyCommands because Telegram requires names to match
^[a-z0-9_]{1,32}$ - no dashes. They showed up in /help (which
iterates pi.getCommands() directly) but were untypable via
autocomplete and, even when typed manually, fell through to the
agent as plain text rather than dispatching.
Now: register the underscore-translated form with Telegram, show the
underscore form in /help so it matches what the user sees in the
menu, and on dispatch rewrite the message text from /foo_bar back to
/foo-bar before enqueueing so the harness's slash-command parser
finds the registered command.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
@@ -76,9 +76,11 @@ import {
|
|||||||
} from "./lib/queue.ts";
|
} from "./lib/queue.ts";
|
||||||
import {
|
import {
|
||||||
buildTelegramBotCommands,
|
buildTelegramBotCommands,
|
||||||
|
fromTelegramCommandName,
|
||||||
registerTelegramAttachmentTool,
|
registerTelegramAttachmentTool,
|
||||||
registerTelegramCommands,
|
registerTelegramCommands,
|
||||||
registerTelegramLifecycleHooks,
|
registerTelegramLifecycleHooks,
|
||||||
|
toTelegramCommandName,
|
||||||
} from "./lib/registration.ts";
|
} from "./lib/registration.ts";
|
||||||
import {
|
import {
|
||||||
MAX_MESSAGE_LENGTH,
|
MAX_MESSAGE_LENGTH,
|
||||||
@@ -1892,7 +1894,9 @@ export default function (pi: ExtensionAPI) {
|
|||||||
);
|
);
|
||||||
for (const c of sorted) {
|
for (const c of sorted) {
|
||||||
const desc = c.description ? ` — ${c.description}` : "";
|
const desc = c.description ? ` — ${c.description}` : "";
|
||||||
lines.push(`/${c.name}${desc}`);
|
// Show the Telegram-form (dashes -> underscores) since that's what
|
||||||
|
// the user has to type. The bridge translates back on dispatch.
|
||||||
|
lines.push(`/${toTelegramCommandName(c.name)}${desc}`);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
lines.push("", "/help re-syncs Telegram's command menu.");
|
lines.push("", "/help re-syncs Telegram's command menu.");
|
||||||
@@ -1973,6 +1977,25 @@ export default function (pi: ExtensionAPI) {
|
|||||||
);
|
);
|
||||||
if (handled) return;
|
if (handled) return;
|
||||||
|
|
||||||
|
// Pi commands with dashes are exposed in Telegram with underscores
|
||||||
|
// (Telegram bot command names disallow dashes). If the user typed the
|
||||||
|
// underscore form, rewrite the message text to the original dashed form
|
||||||
|
// so the harness's slash-command parser dispatches it correctly.
|
||||||
|
if (command) {
|
||||||
|
const piCommandNames = new Set(pi.getCommands().map((c) => c.name));
|
||||||
|
const original = fromTelegramCommandName(command.name, piCommandNames);
|
||||||
|
if (original !== command.name) {
|
||||||
|
const rewritten = command.args
|
||||||
|
? `/${original} ${command.args}`
|
||||||
|
: `/${original}`;
|
||||||
|
if (firstMessage.text !== undefined) {
|
||||||
|
firstMessage.text = rewritten;
|
||||||
|
} else if (firstMessage.caption !== undefined) {
|
||||||
|
firstMessage.caption = rewritten;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
await enqueueTelegramTurn(messages, ctx);
|
await enqueueTelegramTurn(messages, ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+19
-1
@@ -73,8 +73,26 @@ export interface TelegramBotCommand {
|
|||||||
|
|
||||||
export const TELEGRAM_BOT_COMMAND_LIMIT = 100;
|
export const TELEGRAM_BOT_COMMAND_LIMIT = 100;
|
||||||
|
|
||||||
|
// Telegram requires command names to match ^[a-z0-9_]{1,32}$ (no dashes).
|
||||||
|
// Pi commands frequently use dashes (e.g. "compact-now"), so we transform
|
||||||
|
// dash -> underscore for the Telegram-facing name and reverse it on the way
|
||||||
|
// back so the harness still receives its original name.
|
||||||
const telegramCommandNamePattern = /^[a-z0-9_]{1,32}$/;
|
const telegramCommandNamePattern = /^[a-z0-9_]{1,32}$/;
|
||||||
|
|
||||||
|
export function toTelegramCommandName(name: string): string {
|
||||||
|
return name.replace(/-/g, "_");
|
||||||
|
}
|
||||||
|
|
||||||
|
export function fromTelegramCommandName(
|
||||||
|
telegramName: string,
|
||||||
|
piCommandNames: ReadonlySet<string>,
|
||||||
|
): string {
|
||||||
|
if (piCommandNames.has(telegramName)) return telegramName;
|
||||||
|
const dashed = telegramName.replace(/_/g, "-");
|
||||||
|
if (piCommandNames.has(dashed)) return dashed;
|
||||||
|
return telegramName;
|
||||||
|
}
|
||||||
|
|
||||||
const bridgeLocalBotCommands: TelegramBotCommand[] = [
|
const bridgeLocalBotCommands: TelegramBotCommand[] = [
|
||||||
{ command: "start", description: "Show help and refresh this menu" },
|
{ command: "start", description: "Show help and refresh this menu" },
|
||||||
{ command: "help", description: "Show help" },
|
{ command: "help", description: "Show help" },
|
||||||
@@ -104,7 +122,7 @@ export function buildTelegramBotCommands(
|
|||||||
}
|
}
|
||||||
for (const command of piCommands) {
|
for (const command of piCommands) {
|
||||||
addCommand({
|
addCommand({
|
||||||
command: command.name,
|
command: toTelegramCommandName(command.name),
|
||||||
description: command.description ?? command.name,
|
description: command.description ?? command.name,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user