{"record":{"id":"711abfdf6655cfc7","repo":"vercel/ai","slug":"google-generative-ai-api-key-is-required-for-strea","errorCode":null,"errorMessage":"Google Generative AI API key is required for streaming translation.","messagePattern":"Google Generative AI API key is required for streaming translation\\.","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/google/src/speech-translation/google-speech-translation-model.ts","lineNumber":165,"sourceCode":"      warnings.push({\n        type: 'unsupported',\n        feature: 'outputAudioFormat',\n        details:\n          'The Gemini Live API always outputs 24kHz 16-bit PCM audio and does not accept an output audio format.',\n      });\n    }\n\n    const headers = combineHeaders(this.config.headers(), options.headers);\n    // last case-variant wins: combineHeaders keeps case-distinct keys and\n    // spreads per-call headers after configuration headers\n    let apiKey: string | undefined;\n    for (const [key, value] of Object.entries(headers)) {\n      if (key.toLowerCase() === 'x-goog-api-key' && value != null) {\n        apiKey = value;\n      }\n    }\n    if (apiKey == null) {\n      throw new Error(\n        'Google Generative AI API key is required for streaming translation.',\n      );\n    }\n    const webSocketHeaders = Object.fromEntries(\n      Object.entries(headers).filter(\n        ([key]) => key.toLowerCase() !== 'x-goog-api-key',\n      ),\n    );\n\n    const setup = buildGoogleLiveSpeechTranslationSetup({\n      modelId: this.modelId,\n      targetLanguage: options.targetLanguage,\n      providerOptions: googleOptions,\n    });\n\n    return {\n      request: { body: setup },\n      response: {","sourceCodeStart":147,"sourceCodeEnd":183,"githubUrl":"https://github.com/vercel/ai/blob/69428b1f8b037e4d118fb4853428d5c4e620493c/packages/google/src/speech-translation/google-speech-translation-model.ts#L147-L183","documentation":"The speech-translation doStream scans the configured headers for 'x-goog-api-key' (case-insensitive) to authenticate the WebSocket connection; browsers cannot send custom headers on WebSocket, so the key is moved out of headers and the connection relies on it being extracted. If no key is found in the config headers it throws before connecting. Like error 363, this reflects a provider configured without an API key.","triggerScenarios":"Streaming speech translation when the provider config's headers() contains no x-goog-api-key entry — apiKey env var unset, apiKey undefined passed to createGoogleGenerativeAI, or custom headers that omit the key.","commonSituations":"Missing GOOGLE_GENERATIVE_AI_API_KEY in the deployment environment; header set under a wrong name (e.g. 'x-goog-key'); custom headers() returning a record without the key.","solutions":["Set GOOGLE_GENERATIVE_AI_API_KEY or pass apiKey to createGoogleGenerativeAI({ apiKey }).","Confirm the header name is exactly 'x-goog-api-key' when using custom headers.","Check that headers() is not filtering the key out (e.g. a whitelist of header names).","Verify env loading at startup in the runtime where streaming executes."],"exampleFix":"// before\nconst google = createGoogleGenerativeAI(); // env var not set in this env\n// after\nconst google = createGoogleGenerativeAI({\n  apiKey: process.env.GOOGLE_GENERATIVE_AI_API_KEY,\n});","handlingStrategy":"validation","validationCode":"if (!process.env.GOOGLE_GENERATIVE_AI_API_KEY) {\n  throw new Error('GOOGLE_GENERATIVE_AI_API_KEY must be set for streaming translation');\n}","typeGuard":null,"tryCatchPattern":"try {\n  await model.doStream(options);\n} catch (error) {\n  if (error instanceof Error && error.message.includes('API key is required')) {\n    // report missing-provider-config to operators\n  } else { throw error; }\n}","preventionTips":["Configure the key via createGoogleGenerativeAI({ apiKey }) or the standard env var.","Keep the header name exactly 'x-goog-api-key' when supplying custom headers.","Check env presence at process start, not on first request.","Remember the key is extracted from headers for WebSocket auth — don't strip it in header filters."],"tags":["api-key","authentication","google","websocket","speech-translation"],"backgroundTag":"missing-api-key","analyzedSha":"69428b1f8b037e4d118fb4853428d5c4e620493c","analyzedAt":"2026-08-30T12:32:21.016Z","schemaVersion":2},"datasetVersion":"2026-08-30T13:17:10.514Z"}