iOfficeAI/AionUi · error

STT_REQUEST_FAILED

STT_REQUEST_FAILED

Error message

payload.msg || 'STT_REQUEST_FAILED'

What it means

`parseSuccessResponse` inspects the STT backend's JSON envelope; if `success` is false or `data` is missing it throws with the backend `msg` (or the generic `STT_REQUEST_FAILED`). This is the server-side rejection path for transcription requests that completed at HTTP level but failed logically.

Source

Thrown at packages/desktop/src/renderer/services/SpeechToTextService.ts:52

const createAudioFileName = (mimeType: string) => {
  return `speech-input.${getAudioExtension(mimeType)}`;
};

const ensureAudioSize = (blob: Blob) => {
  if (blob.size > MAX_AUDIO_FILE_SIZE_BYTES) {
    throw new Error('STT_FILE_TOO_LARGE');
  }
};

const parseSuccessResponse = (response: XMLHttpRequest): SpeechToTextResult => {
  const payload = JSON.parse(response.responseText) as {
    data?: SpeechToTextResult;
    msg?: string;
    success: boolean;
  };

  if (!payload.success || !payload.data) {
    throw new Error(payload.msg || 'STT_REQUEST_FAILED');
  }

  return payload.data;
};

// Surface the backend error code (STT_DISABLED, STT_OPENAI_NOT_CONFIGURED, ...)
// so useSpeechInput can map it to a localized error state.
const parseErrorResponse = (response: XMLHttpRequest): Error => {
  if (response.status === 413) {
    return new Error('STT_FILE_TOO_LARGE');
  }

  try {
    const payload = JSON.parse(response.responseText) as { code?: string; error?: string; msg?: string };
    const code = payload.code;
    const detail = payload.error || payload.msg;
    if (code || detail) {
      return new Error([code, detail].filter(Boolean).join(': '));

View on GitHub (pinned to 711aa0550e)

Solutions

  1. Read the thrown message — it usually carries the backend code (STT_DISABLED, STT_OPENAI_NOT_CONFIGURED, etc.) and tells you exactly what to configure
  2. Enable STT and configure the required provider credentials in backend settings
  3. Verify network/proxy isn't mangling the JSON response
  4. Retry after fixing config; transient provider errors can justify one retry with backoff

Example fix

// before
if (!payload.success || !payload.data) {
  throw new Error(payload.msg || 'STT_REQUEST_FAILED');
}

// after (map backend codes to user-facing messages)
if (!payload.success || !payload.data) {
  throw new Error(payload.msg || 'STT_REQUEST_FAILED'); // wrap caller:
}
// caller: catch (e) { showToast(mapSttErrorCode(e.message)); }
Defensive patterns

Strategy: fallback

Validate before calling

// nothing client-side can guarantee backend success; verify config first
await ensureSttEnabled(); // checks backend STT config before recording

Type guard

type SttEnvelope = { success: boolean; data?: SpeechToTextResult; msg?: string };
const isSttSuccess = (p: SttEnvelope): p is { success: true; data: SpeechToTextResult } => p.success && !!p.data;

Try / catch

catch (e) { showToast(mapSttErrorCode(e.message)); // handles STT_DISABLED, STT_OPENAI_NOT_CONFIGURED, ... }

Prevention

When it happens

Trigger: The STT HTTP request returns 200 with `{success:false, msg?}` or a payload lacking `data` — e.g. backend STT disabled, OpenAI key not configured, transcription provider error, or malformed response JSON.

Common situations: STT not enabled in backend config (STT_DISABLED); OpenAI credentials missing (STT_OPENAI_NOT_CONFIGURED); upstream transcription provider outage or quota exhaustion; proxy/gateway stripping the response body so data is absent.

Related errors


AI-assisted analysis of iOfficeAI/AionUi@711aa0550e (2026-08-28). Data as JSON: /api/errors/1fa2860272a04ab9. Report an issue: GitHub.