feat(telegram): transcribe voice notes and audio with an echo

Content step 3 (InboundMedia.AddSpeechAsync): voice and audio go through ISpeechToText, the transcript is echoed as '🎤 …' and prompted as '[Voice message] …'. Spec §4 edited: audio is transcribed from the file step 2 saved (one download); an oversize or undownloadable voice note sends its notice and isn't prompted.
This commit is contained in:
EugeneTes
2026-09-26 22:13:10 +02:00
parent a0cd2975b8
commit f90731baf0
6 changed files with 334 additions and 8 deletions

View File

@@ -227,9 +227,12 @@ Router changes (`UpdateRouter.OnMessageAsync`), on top of the message-context sp
1. No `ISpeechToText` configured → notice `Voice messages need speech-to-text: set OPENAI_API_KEY (or
Telegram:Speech:ApiKey) on the bot host.` `Audio` is still saved to the inbox as a file (below); `Voice` isn't
prompted unless it has a caption.
2. Over 20 MB → the file-size notice, as for files.
3. Download into memory. Voice arrives as `.oga`, which OpenAI rejects, so it's renamed to `voice.ogg`
(`audio/ogg`). Audio keeps `FileName ?? "audio"` and its `MimeType`.
2. Over 20 MB → the file-size notice, as for files, and the message isn't prompted (for `Audio`, step 2 has already
refused it).
3. Voice is downloaded into memory; a failed download sends `I could not download that file.` and the message isn't
prompted. Audio is read back from the file step 2 saved, so it's downloaded only once. Voice arrives as `.oga`,
which OpenAI rejects, so it's renamed to `voice.ogg` (`audio/ogg`). Audio keeps `FileName ?? "audio"` and its
`MimeType`.
4. `Transcript = await stt.TranscribeAsync(bytes, fileName, mime, ct)`, trimmed. Empty → notice `I couldn't make
out any words in that voice message.` An exception → notice `Could not transcribe the voice message: <reason>`.
5. Echo `🎤 <transcript>` as plain text, cut to 4096 characters with `…`.