{"version":3,"sources":["../../src/googleai/client.ts"],"sourcesContent":["/**\n * Copyright 2025 Google LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { GenkitError, StatusName, type ErrorResponseMetadata } from 'genkit';\nimport { logger } from 'genkit/logging';\nimport { runInNewSpan } from 'genkit/tracing';\nimport { InteractionStreamResult } from '../common/interaction-types.mjs';\nimport {\n  INTERACTIONS_API_REVISION,\n  buildTraceMetadataInput,\n  extractErrMsg,\n  getGenkitClientHeader,\n  httpStatusToGenkitStatus,\n  interactionErrorCodeToGenkitStatus,\n  interactionProcessStream,\n  isInteractionUrl,\n  parseRetryAfterMs,\n  processStream,\n  withoutHeaders,\n} from '../common/utils.mjs';\nimport { isObject } from './utils.mjs';\n\nimport {\n  ClientOptions,\n  CreateInteractionRequest,\n  EmbedContentRequest,\n  EmbedContentResponse,\n  GeminiInteraction,\n  GenerateContentRequest,\n  GenerateContentResponse,\n  GenerateContentStreamResult,\n  ListModelsResponse,\n  Model,\n  VeoOperation,\n  VeoPredictRequest,\n} from './types.mjs';\n\nexport const tracingHooks = { runInNewSpan };\n\n/**\n * Creates an interaction using the Google AI API.\n *\n * @param apiKey The API key to authenticate the request.\n * @param createInteractionRequest The request object containing the interaction parameters.\n * @param clientOptions Optional options to customize the request\n * @returns A promise that resolves to the interaction response.\n */\nexport async function createInteraction(\n  apiKey: string | undefined,\n  createInteractionRequest: CreateInteractionRequest,\n  clientOptions?: ClientOptions\n): Promise<GeminiInteraction> {\n  const url = getGoogleAIUrl({\n    resourcePath: 'interactions',\n    clientOptions,\n  });\n\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    body: JSON.stringify(createInteractionRequest),\n    isInteraction: true,\n  });\n\n  return maybeTraceRequest<GeminiInteraction>(url, fetchOptions, {\n    request: createInteractionRequest,\n    clientOptions,\n  });\n}\n\nexport async function createInteractionStream(\n  apiKey: string | undefined,\n  createInteractionRequest: CreateInteractionRequest,\n  clientOptions?: ClientOptions\n): Promise<InteractionStreamResult> {\n  const url = getGoogleAIUrl({\n    resourcePath: 'interactions',\n    clientOptions,\n  });\n\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    body: JSON.stringify(createInteractionRequest),\n    isInteraction: true,\n  });\n\n  return maybeTraceRequest<InteractionStreamResult>(url, fetchOptions, {\n    request: createInteractionRequest,\n    streaming: true,\n    clientOptions,\n    processFn: async (response) => {\n      return interactionProcessStream(response);\n    },\n  });\n}\n\n/**\n * Gets an interaction using the Google AI API.\n *\n * @param apiKey The API key to authenticate the request.\n * @param interactionId The ID of the interaction to retrieve.\n * @param clientOptions Optional options to customize the request\n * @returns A promise that resolves to the interaction response.\n */\nexport async function getInteraction(\n  apiKey: string | undefined,\n  interactionId: string,\n  clientOptions?: ClientOptions\n): Promise<GeminiInteraction> {\n  const url = getGoogleAIUrl({\n    resourcePath: `interactions/${interactionId}`,\n    clientOptions,\n  });\n\n  const fetchOptions = getFetchOptions({\n    method: 'GET',\n    apiKey,\n    clientOptions,\n    isInteraction: true,\n  });\n\n  return maybeTraceRequest<GeminiInteraction>(url, fetchOptions, {\n    clientOptions,\n  });\n}\n\n/**\n * Cancels an interaction using the Google AI API.\n *\n * @param apiKey The API key to authenticate the request.\n * @param interactionId The ID of the interaction to cancel.\n * @param clientOptions Optional options to customize the request\n * @returns A promise that resolves to the interaction response.\n */\nexport async function cancelInteraction(\n  apiKey: string | undefined,\n  interactionId: string,\n  clientOptions?: ClientOptions\n): Promise<GeminiInteraction> {\n  const url = getGoogleAIUrl({\n    resourcePath: `interactions/${interactionId}/cancel`,\n    clientOptions,\n  });\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    isInteraction: true,\n  });\n\n  try {\n    await makeRequest(url, fetchOptions);\n    // A successful cancellation will actually throw a\n    // CANCELLED error. If we instead get a 200 OK here, then\n    // it can mean a no-op cancellation (e.g. race condition between finish and cancelled)\n    // We throw an error here so the exit logic is the same for both cases.\n    throw new GenkitError({\n      status: 'CANCELLED',\n      message: 'successfully cancelled',\n    });\n  } catch (e: any) {\n    if (e instanceof GenkitError && e.status === 'CANCELLED') {\n      return {\n        id: interactionId,\n        status: 'cancelled',\n      } as GeminiInteraction;\n    }\n    throw e;\n  }\n}\n\n/**\n * Lists available models.\n *\n * https://ai.google.dev/api/models#method:-models.list\n *\n * @param apiKey The API key to authenticate the request.\n * @param clientOptions Optional options to customize the request\n * @returns A promise that resolves to an array of Model objects.\n */\nexport async function listModels(\n  apiKey: string | undefined,\n  clientOptions?: ClientOptions\n): Promise<Model[]> {\n  const url = getGoogleAIUrl({\n    resourcePath: 'models',\n    queryParams: 'pageSize=1000',\n    clientOptions,\n  });\n  const fetchOptions = getFetchOptions({\n    method: 'GET',\n    apiKey,\n    clientOptions,\n  });\n  const response = await makeRequest(url, fetchOptions);\n  const modelResponse = JSON.parse(await response.text()) as ListModelsResponse;\n  return modelResponse.models;\n}\n\n/**\n * Generates content using the Google AI API.\n *\n * @param {string} apiKey The API key for authentication.\n * @param {string} model The name of the model to use for content generation.\n * @param {GenerateContentRequest} generateContentRequest The request object containing the content generation parameters.\n * @param {ClientOptions} [clientOptions] Optional client options.\n * @returns {Promise<GenerateContentResponse>} A promise that resolves to the content generation response.\n * @throws {Error} If the API request fails or the response cannot be parsed.\n */\nexport async function generateContent(\n  apiKey: string | undefined,\n  model: string,\n  generateContentRequest: GenerateContentRequest,\n  clientOptions?: ClientOptions\n): Promise<GenerateContentResponse> {\n  const url = getGoogleAIUrl({\n    resourcePath: `models/${model}`,\n    resourceMethod: 'generateContent',\n    clientOptions,\n  });\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    body: JSON.stringify(generateContentRequest),\n  });\n\n  return maybeTraceRequest<GenerateContentResponse>(url, fetchOptions, {\n    model: model,\n    request: generateContentRequest,\n    clientOptions,\n  });\n}\n\n/**\n * Generates a stream of content using the Google AI API.\n *\n * @param {string} apiKey The API key for authentication.\n * @param {string} model The name of the model to use for content generation.\n * @param {GenerateContentRequest} generateContentRequest The request object containing the content generation parameters.\n * @param {ClientOptions} [clientOptions] Optional client options.\n * @returns {Promise<GenerateContentStreamResult>} A promise that resolves to an object containing a both the stream and aggregated response.\n * @throws {Error} If the API request fails.\n */\nexport async function generateContentStream(\n  apiKey: string | undefined,\n  model: string,\n  generateContentRequest: GenerateContentRequest,\n  clientOptions?: ClientOptions\n): Promise<GenerateContentStreamResult> {\n  const url = getGoogleAIUrl({\n    resourcePath: `models/${model}`,\n    resourceMethod: 'streamGenerateContent',\n    clientOptions,\n  });\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    body: JSON.stringify(generateContentRequest),\n  });\n\n  return maybeTraceRequest<GenerateContentStreamResult>(url, fetchOptions, {\n    model: model,\n    request: generateContentRequest,\n    streaming: true,\n    clientOptions,\n    processFn: async (response) => {\n      return processStream(response);\n    },\n  });\n}\n\n/**\n * Embeds content using the Google AI API.\n *\n * @param {string} apiKey The API key for authentication.\n * @param {string} model The name of the model to use for content embedding.\n * @param {EmbedContentRequest} embedContentRequest The request object containing the content to embed.\n * @param {ClientOptions} [clientOptions] Optional client options.\n * @returns {Promise<EmbedContentResponse>} A promise that resolves to the embedding response.\n * @throws {Error} If the API request fails or the response cannot be parsed.\n */\nexport async function embedContent(\n  apiKey: string | undefined,\n  model: string,\n  embedContentRequest: EmbedContentRequest,\n  clientOptions?: ClientOptions\n): Promise<EmbedContentResponse> {\n  const url = getGoogleAIUrl({\n    resourcePath: `models/${model}`,\n    resourceMethod: 'embedContent',\n    clientOptions,\n  });\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    body: JSON.stringify(embedContentRequest),\n  });\n\n  return maybeTraceRequest<EmbedContentResponse>(url, fetchOptions, {\n    model: model,\n    request: embedContentRequest,\n    clientOptions,\n  });\n}\n\nexport async function veoPredict(\n  apiKey: string | undefined,\n  model: string,\n  veoPredictRequest: VeoPredictRequest,\n  clientOptions?: ClientOptions\n): Promise<VeoOperation> {\n  const url = getGoogleAIUrl({\n    resourcePath: `models/${model}`,\n    resourceMethod: 'predictLongRunning',\n    clientOptions,\n  });\n\n  const fetchOptions = getFetchOptions({\n    method: 'POST',\n    apiKey,\n    clientOptions,\n    body: JSON.stringify(veoPredictRequest),\n  });\n\n  return maybeTraceRequest<VeoOperation>(url, fetchOptions, {\n    model: model,\n    request: veoPredictRequest,\n    clientOptions,\n  });\n}\n\nexport async function veoCheckOperation(\n  apiKey: string | undefined,\n  operation: string,\n  clientOptions?: ClientOptions\n): Promise<VeoOperation> {\n  const url = getGoogleAIUrl({\n    resourcePath: operation,\n    clientOptions,\n  });\n  const fetchOptions = getFetchOptions({\n    method: 'GET',\n    apiKey,\n    clientOptions,\n  });\n\n  return maybeTraceRequest<VeoOperation>(url, fetchOptions, {\n    clientOptions,\n  });\n}\n\n/**\n * Generates a Google AI URL.\n *\n * @param params - An object containing the parameters for the URL.\n * @param params.path - The path for the URL (the part after the version)\n * @param params.task - An optional task\n * @param params.queryParams - An optional string of '&' delimited query parameters.\n * @param params.clientOptions - An optional object containing client options.\n * @returns The generated Google AI URL.\n */\nexport function getGoogleAIUrl(params: {\n  resourcePath: string;\n  resourceMethod?: string;\n  queryParams?: string;\n  clientOptions?: ClientOptions;\n}): string {\n  // v1beta is the default because all the new experimental models\n  // are found here but not in v1.\n  const DEFAULT_API_VERSION = 'v1beta';\n  const DEFAULT_BASE_URL = 'https://generativelanguage.googleapis.com';\n\n  const apiVersion = params.clientOptions?.apiVersion || DEFAULT_API_VERSION;\n  const baseUrl = params.clientOptions?.baseUrl || DEFAULT_BASE_URL;\n\n  let url = `${baseUrl}/${apiVersion}/${params.resourcePath}`;\n  if (params.resourceMethod) {\n    url += `:${params.resourceMethod}`;\n  }\n  if (params.queryParams) {\n    url += `?${params.queryParams}`;\n  }\n  if (params.resourceMethod === 'streamGenerateContent') {\n    url += `${params.queryParams ? '&' : '?'}alt=sse`;\n  }\n  return url;\n}\n\nfunction getFetchOptions(params: {\n  method: 'POST' | 'GET';\n  apiKey: string | undefined;\n  body?: string;\n  clientOptions?: ClientOptions;\n  isInteraction?: boolean;\n}) {\n  const fetchOptions: RequestInit = {\n    method: params.method,\n    headers: getHeaders(\n      params.apiKey,\n      params.clientOptions,\n      params.isInteraction\n    ),\n    redirect: 'manual',\n  };\n  if (params.body) {\n    fetchOptions.body = params.body;\n  }\n  const signal = getAbortSignal(params.clientOptions);\n  if (signal) {\n    fetchOptions.signal = signal;\n  }\n  return fetchOptions;\n}\n\nfunction getAbortSignal(\n  clientOptions?: ClientOptions\n): AbortSignal | undefined {\n  const hasTimeout = (clientOptions?.timeout ?? -1) >= 0;\n  if (clientOptions?.signal !== undefined || hasTimeout) {\n    const controller = new AbortController();\n    if (hasTimeout) {\n      setTimeout(() => controller.abort(), clientOptions?.timeout);\n    }\n    if (clientOptions?.signal) {\n      clientOptions.signal.addEventListener('abort', () => {\n        controller.abort();\n      });\n    }\n    return controller.signal;\n  }\n  return undefined;\n}\n\n/**\n * Constructs the headers for an API request.\n *\n * @param {string} apiKey The API key for authentication.\n * @param {ClientOptions} [clientOptions] Optional client options, containing custom headers.\n * @returns {HeadersInit} An object containing the headers to be included in the request.\n */\nfunction getHeaders(\n  apiKey?: string,\n  clientOptions?: ClientOptions,\n  isInteraction?: boolean\n): HeadersInit {\n  // Not allowed in user settings (in any letter case). The Interactions\n  // converters only understand INTERACTIONS_API_REVISION's schema, so custom\n  // headers can't change it either.\n  const customHeaders = withoutHeaders(clientOptions?.customHeaders, [\n    'x-goog-api-key',\n    'x-goog-api-client',\n    ...(isInteraction ? ['Api-Revision'] : []),\n  ]);\n  const headers: HeadersInit = {\n    ...customHeaders,\n    'Content-Type': 'application/json',\n    'x-goog-api-client': getGenkitClientHeader(),\n  };\n\n  if (isInteraction) {\n    headers['Api-Revision'] = INTERACTIONS_API_REVISION;\n  }\n\n  if (apiKey) {\n    headers['x-goog-api-key'] = apiKey;\n  }\n\n  return headers;\n}\n\ninterface TraceOptions<T> {\n  request?: unknown;\n  model?: string;\n  streaming?: boolean;\n  processFn?: (resp: Response) => Promise<T>;\n  clientOptions?: ClientOptions;\n}\n\nasync function maybeTraceRequest<T>(\n  url: string,\n  fetchOptions: RequestInit,\n  traceOptions: TraceOptions<T>\n): Promise<T> {\n  const call = async () => {\n    const response = await makeRequest(url, fetchOptions);\n    let processedResponse: Promise<T>;\n    if (traceOptions.processFn) {\n      // This is for streaming etc.\n      processedResponse = traceOptions.processFn(response);\n    } else {\n      // default processing is just get the json response\n      processedResponse = await response.json();\n    }\n    return processedResponse;\n  };\n\n  if (traceOptions.clientOptions?.experimental_debugTraces) {\n    return tracingHooks.runInNewSpan(\n      {\n        metadata: {\n          name: 'httpRequest',\n          // Seed input up front so the realtime \"pending\" span export carries it.\n          input: buildTraceMetadataInput(url, fetchOptions, traceOptions),\n        },\n      },\n      async (metadata) => {\n        const processedResponse = await call();\n\n        if (traceOptions.streaming) {\n          metadata.output = '[Streaming Response]';\n        } else {\n          metadata.output = processedResponse;\n        }\n\n        return processedResponse;\n      }\n    );\n  }\n  return call();\n}\n\n/**\n * Makes a request to the specified URL with the provided options.\n *\n * @param {string} url The URL to make the request to.\n * @param {RequestInit} fetchOptions The options to pass to the `fetch` API.\n * @returns {Promise<Response>} A promise that resolves to the Response\n * @throws {Error} If the request fails\n */\nasync function makeRequest(\n  url: string,\n  fetchOptions: RequestInit\n): Promise<Response> {\n  try {\n    const response = await fetch(url, fetchOptions);\n    if (!response.ok) {\n      let errorText = await response.text();\n      let errorMessage = errorText;\n      let errorDetail: unknown;\n      try {\n        const json = JSON.parse(errorText);\n        errorDetail = json;\n        if (json.error && json.error.message) {\n          errorMessage = json.error.message;\n          if (Array.isArray(json.error.details)) {\n            const detailsText = json.error.details\n              .map((d: any) => {\n                if (d.detail && typeof d.detail === 'string') {\n                  const match = d.detail.match(/\\[ORIGINAL ERROR\\]\\s*([^[]+)/);\n                  const detailText = match ? match[1].trim() : d.detail;\n                  return `${detailText}\\nRaw: ${JSON.stringify(d, null, 2)}`;\n                }\n                return JSON.stringify(d, null, 2);\n              })\n              .filter(Boolean)\n              .join('\\n');\n            if (detailsText) {\n              errorMessage += `\\nDetails:\\n${detailsText}`;\n            }\n          }\n        }\n      } catch (e) {\n        // Not JSON or expected format, use the raw text\n      }\n      let status: StatusName = 'UNKNOWN';\n      switch (response.status) {\n        case 429:\n          status = 'RESOURCE_EXHAUSTED';\n          break;\n        case 400:\n          status = 'INVALID_ARGUMENT';\n          break;\n        case 499:\n          status = 'CANCELLED';\n          break;\n        case 500:\n          status = 'INTERNAL';\n          break;\n        case 503:\n          status = 'UNAVAILABLE';\n          break;\n      }\n      // Interactions API errors carry a specific `error.code` (e.g. `safety`,\n      // `model_not_found`, `quota_exceeded`) that is more precise than the\n      // HTTP status, so prefer it when recognized.\n      if (isInteractionUrl(url)) {\n        const apiError = isObject(errorDetail) ? errorDetail.error : undefined;\n        const codeStatus = interactionErrorCodeToGenkitStatus(\n          isObject(apiError) ? apiError.code : undefined\n        );\n        if (codeStatus) {\n          status = codeStatus;\n        } else if (status === 'UNKNOWN') {\n          status = httpStatusToGenkitStatus(response.status);\n        }\n      }\n      // Capture Retry-After header for retry middleware to use\n      const retryAfterHeader = response.headers.get('retry-after');\n      const retryAfterMs = retryAfterHeader\n        ? parseRetryAfterMs(retryAfterHeader)\n        : undefined;\n      const responseMetadata: ErrorResponseMetadata | undefined =\n        retryAfterMs !== undefined ? { retryAfterMs } : undefined;\n\n      throw new GenkitError({\n        status,\n        message: `Error fetching from ${url}: [${response.status} ${response.statusText}] ${errorMessage}`,\n        detail: errorDetail,\n        responseMetadata,\n      });\n    }\n    return response;\n  } catch (e: unknown) {\n    logger.error(e);\n    if (e instanceof GenkitError) {\n      throw e;\n    }\n    throw new Error(`Failed to fetch from ${url}: ${extractErrMsg(e)}`);\n  }\n}\n\nexport const TEST_ONLY = {\n  getFetchOptions,\n  getAbortSignal,\n  getHeaders,\n  isInteractionUrl,\n  makeRequest,\n  tracingHooks,\n};\n"],"mappings":"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","names":[]}