Skip to content

feat(speech): add async and WebSocket TTS operations - #223

Open
octo-patch wants to merge 1 commit into
MiniMax-AI:mainfrom
octo-patch:octo/20260804-tts-tool-recvreiL1BRGZG
Open

feat(speech): add async and WebSocket TTS operations#223
octo-patch wants to merge 1 commit into
MiniMax-AI:mainfrom
octo-patch:octo/20260804-tts-tool-recvreiL1BRGZG

Conversation

@octo-patch

@octo-patch octo-patch commented Aug 4, 2026

Copy link
Copy Markdown

Reason: Add the missing async and WebSocket TTS operations to the speech CLI and SDK.

Changes

  • Add mmx speech async — create a long-form async TTS task via POST /v1/t2a_async_v2 (textToAudioAsyncCreate). With --wait it polls until completion and downloads the audio.
  • Add mmx speech task get — query async TTS task status via GET /v1/query/t2a_async_query_v2 (textToAudioAsyncQuery).
  • Add mmx speech websocket — synchronous streaming TTS over WSS /ws/v1/t2a_v2 (textToAudioWebSocket). Supports --out to save the audio and --stream to pipe raw audio chunks to stdout.
  • Add SpeechSDK.createAsync, SpeechSDK.queryAsync, SpeechSDK.downloadAsyncFile, and SpeechSDK.synthesizeWebSocket.
  • Add tests for the SDK async/WebSocket methods and the new CLI commands; document the commands in README, SDK.md, and docs/cli-design.md.

Checks

  • bun run typecheck — pass
  • bun run lint — pass
  • bun test — 460 passing
  • bun run build — pass

View with [code]smith Autofix with [code]smith
Need help on this PR? Tag @codesmith-bot with what you need. Autofix is disabled.

Add the missing MiniMax TTS operations to the speech command and SDK:
- mmx speech async: create a long-form async TTS task (POST /v1/t2a_async_v2)
- mmx speech task get: query async task status (GET /v1/query/t2a_async_query_v2)
- mmx speech websocket: synchronous streaming TTS over WSS (/ws/v1/t2a_v2)
- SpeechSDK: createAsync, queryAsync, downloadAsyncFile, synthesizeWebSocket

The async flow polls the task to completion and downloads the resulting
audio file; the WebSocket flow streams hex-encoded audio chunks as they
arrive and saves or pipes them.

@NianJiuZst NianJiuZst left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for adding the missing async and WebSocket TTS surfaces. I do not think this is ready to merge yet because the async path diverges from the current official API contract in three blocking places:

  1. The speech async --wait download is unauthenticated.
    src/commands/speech/async.ts passes the protected /v1/files/retrieve_content URL to the generic downloadFile helper, which performs a bare fetch without an Authorization header. A successful async task will therefore fail at the final download step with 401. The official Retrieve Content API requires Bearer authentication:
    https://platform.minimax.io/docs/api-reference/file-management-retrieve-content

  2. The async request uses the wrong sample-rate field.
    The new async request type reuses the synchronous HTTP TTS audio_setting shape and sends sample_rate. The async endpoint expects audio_sample_rate, so the new --sample-rate option is not wired to the documented request contract. See the official async-create request example:
    https://platform.minimax.io/docs/api-reference/speech-t2a-async-create

  3. The advertised 1M-character path is not implemented.
    --text-file currently reads the local file and sends its contents as text. The official API limits direct text input to 50,000 characters; the larger long-form path requires uploading a file with purpose t2a_async_input and passing text_file_id. Neither the CLI nor SpeechAsyncRequest currently supports that path:
    https://platform.minimax.io/docs/api-reference/speech-t2a-async-create

I verified this on head ed939d1. Typecheck, lint, build, the 11 new focused tests, and GitHub CI pass, but the tests only exercise permissive mocks. A request-capture reproduction on the actual command path observed audio_setting.sample_rate and a null download authorization header.

Please fix these contracts and add regression coverage that asserts audio_sample_rate, authenticated content retrieval, and the text_file_id long-text flow before merging.

@NianJiuZst NianJiuZst self-assigned this Aug 4, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants