Skip to content

Crash with Vercel AI SDK when used in ESM #16137

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
3 tasks done
Jaakkonen opened this issue Apr 25, 2025 · 4 comments
Open
3 tasks done

Crash with Vercel AI SDK when used in ESM #16137

Jaakkonen opened this issue Apr 25, 2025 · 4 comments
Assignees

Comments

@Jaakkonen
Copy link

Is there an existing issue for this?

How do you use Sentry?

Sentry Saas (sentry.io)

Which SDK are you using?

@sentry/node

SDK Version

9.14.0

Framework Version

No response

Link to Sentry event

No response

Reproduction Example/SDK Setup

https://github.com/Jaakkonen/sentry-spotlight-vercel-ai-bug

Steps to Reproduce

  1. Create a new Node.js project
  2. Install the required dependencies:
    npm install @sentry/node ai
    
  3. Create the following files:
// index.js
import * as Sentry from '@sentry/node'

Sentry.init({
  tracesSampler: (ctx) => {
    return 0.01
  },
  spotlight: true,
})

await import("./otherfile.js")
// otherfile.js
import { generateText } from "ai";

console.log(generateText)
  1. Run the application with:
    $ node index.js
    

Expected Result

Code to not crash. With spotlight disabled the code runs fine

[AsyncFunction: generateText]

Actual Result

❯ node index.js
TypeError: setters.get(...)[name] is not a function
    at Object.set (/home/jaakko/Code/opentelemetryairepro/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:13:37)
    at callHookFn (/home/jaakko/Code/opentelemetryairepro/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/index.js:31:23)
    at Hook._iitmHook (/home/jaakko/Code/opentelemetryairepro/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/index.js:150:11)
    at /home/jaakko/Code/opentelemetryairepro/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:42:31
    at Array.forEach (<anonymous>)
    at register (/home/jaakko/Code/opentelemetryairepro/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:42:15)
    at file:///home/jaakko/Code/opentelemetryairepro/node_modules/.pnpm/ai@4.3.10_react@19.1.0_zod@3.24.3/node_modules/ai/dist/index.mjs?iitm=true:1075:1
    at ModuleJob.run (node:internal/modules/esm/module_job:271:25)
    at async onImport.tracePromise.__proto__ (node:internal/modules/esm/loader:578:26)
    at async file:///home/jaakko/Code/opentelemetryairepro/index.js:10:1
@getsantry getsantry bot moved this to Waiting for: Product Owner in GitHub Issues with 👀 3 Apr 25, 2025
@linear linear bot added the Bug label Apr 25, 2025
@Lms24 Lms24 self-assigned this Apr 28, 2025
@Lms24
Copy link
Member

Lms24 commented Apr 28, 2025

Hey, thanks for writing in and for the reproduction! I'll take a look and might forward the issue to the Spotlight team, depending on results :)

@Lms24
Copy link
Member

Lms24 commented Apr 28, 2025

Some initial findings:

I was able to further narrow this down to the following SDK config:

import * as Sentry from '@sentry/node'

Sentry.init({
  dsn: '_any_valid_dsn_',
  defaultIntegrations: false,
  integrations: [
    Sentry.vercelAIIntegration(),
  ],
})

await import("./otherfile.js") // which imports 'ai'

which means that my suspicion as of this moment is that something breaks as soon as Sentry imports from node:http.

This happens

  • when you specify a dsn as then we initialize the Sentry transport which uses node:http to send events to Sentry
  • when you add spotlightIntegration which uses node:http to send events to Spotlight

I still have to find out why exactly this is happening but I'd bet on import-in-the-middle patching doing something weird with ai~ornode:http`~ .

UPDATE: node:http has nothing to do with this, see #16137 (comment)

Some more questions:

  • did this start happening after a specific change you made? Maybe you bumped a package version or the node runtime?

@Lms24
Copy link
Member

Lms24 commented Apr 28, 2025

I gotta stand corrected: The reason why both, setting dsn or adding spotlightIntegration triggers the bug is because in both cases, we call setupOnce of all integrations (so also of the vercelAi integration).

So my now changed slightly: I think patching the ai package in general throws this error in ESM. So neither node:http nor spotlightIntegration are factors in this.

@Lms24
Copy link
Member

Lms24 commented Apr 28, 2025

Okay, so I debugged this a bit further and created a new, reproduction. One that takes the general Sentry SDK out of the equation but only has 3 important components:

  • registering import-in-the-middle/hooks.mjs
  • Initializing Sentry's vercelAiIntegration
  • importing ai in a dynamic import

Here's a new reproduction (thanks @Jaakkonen for the original one! I based mine on yours): https://github.com/Lms24/gh-sentry-javascript-16137-vercel-ai-esm

I threw in a couple of logs in the IITM method where the error is thrown:

  set (target, name, value) {
    console.trace('set');
    console.log('> target', target);
    console.log('> name', name);
    console.log('> value', value);
    console.log('> setters', setters);
    console.log('> setters.get(target)', setters.get(target));
    console.log('> setters.get(target)[name]', setters.get(target)[name]);
    return setters.get(target)[name](value)
  },

and I'm getting the following output:

Log Output
Trace: set
    at Object.set (/Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:13:13)
    at callHookFn (/Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/index.js:31:23)
    at Hook._iitmHook (/Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/index.js:150:11)
    at /Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:50:31
    at Array.forEach (<anonymous>)
    at register (/Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:50:15)
    at file:///Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/ai@4.0.0_react@19.1.0_zod@3.24.3/node_modules/ai/dist/index.mjs?iitm=true:655:1
    at ModuleJob.run (node:internal/modules/esm/module_job:274:25)
    at async onImport.tracePromise.__proto__ (node:internal/modules/esm/loader:644:26)
    at async file:///Users/lukas/code/test-projects/gh-sentry-javascript-16137/index.js:17:1
> target [Object: null prototype] [Module] {
  AISDKError: [class _AISDKError extends Error],
  APICallError: [class APICallError extends _AISDKError],
  AssistantResponse: [Function: AssistantResponse],
  DownloadError: [class DownloadError extends _AISDKError],
  EmptyResponseBodyError: [class EmptyResponseBodyError extends _AISDKError],
  InvalidArgumentError: [class InvalidArgumentError extends _AISDKError],
  InvalidDataContentError: [class InvalidDataContentError extends _AISDKError],
  InvalidMessageRoleError: [class InvalidMessageRoleError extends _AISDKError],
  InvalidPromptError: [class InvalidPromptError extends _AISDKError],
  InvalidResponseDataError: [class InvalidResponseDataError extends _AISDKError],
  InvalidToolArgumentsError: [class InvalidToolArgumentsError extends _AISDKError],
  JSONParseError: [class JSONParseError extends _AISDKError],
  LangChainAdapter: { toDataStream: [Getter], toDataStreamResponse: [Getter] },
  LlamaIndexAdapter: { toDataStream: [Getter], toDataStreamResponse: [Getter] },
  LoadAPIKeyError: [class LoadAPIKeyError extends _AISDKError],
  MessageConversionError: [class MessageConversionError extends _AISDKError],
  NoContentGeneratedError: [class NoContentGeneratedError extends _AISDKError],
  NoObjectGeneratedError: [class NoObjectGeneratedError extends _AISDKError],
  NoSuchModelError: [class NoSuchModelError extends _AISDKError],
  NoSuchProviderError: [class NoSuchProviderError extends NoSuchModelError],
  NoSuchToolError: [class NoSuchToolError extends _AISDKError],
  RetryError: [class RetryError extends _AISDKError],
  StreamData: [class StreamData],
  TypeValidationError: [class _TypeValidationError extends _AISDKError],
  UnsupportedFunctionalityError: [class UnsupportedFunctionalityError extends _AISDKError],
  convertToCoreMessages: [Function: convertToCoreMessages],
  cosineSimilarity: [Function: cosineSimilarity],
  createStreamDataTransformer: [Function: createStreamDataTransformer],
  embed: [AsyncFunction: embed],
  embedMany: [AsyncFunction: embedMany],
  experimental_createProviderRegistry: [Function: experimental_createProviderRegistry],
  experimental_customProvider: [Function: experimental_customProvider],
  experimental_wrapLanguageModel: [Function: experimental_wrapLanguageModel],
  formatAssistantStreamPart: [Function: formatAssistantStreamPart],
  formatDataStreamPart: [Function: formatDataStreamPart],
  generateId: [Function (anonymous)],
  generateObject: [AsyncFunction: generateObject],
  generateText: [AsyncFunction: generateText],
  jsonSchema: [Function: jsonSchema],
  parseAssistantStreamPart: [Function: parseAssistantStreamPart],
  parseDataStreamPart: [Function: parseDataStreamPart],
  processDataStream: [AsyncFunction: processDataStream],
  processTextStream: [AsyncFunction: processTextStream],
  streamObject: [Function: streamObject],
  streamText: [Function: streamText],
  tool: [Function: tool]
}
> name default
> value {
  AISDKError: [class _AISDKError extends Error],
  APICallError: [class APICallError extends _AISDKError],
  AssistantResponse: [Function: AssistantResponse],
  DownloadError: [class DownloadError extends _AISDKError],
  EmptyResponseBodyError: [class EmptyResponseBodyError extends _AISDKError],
  InvalidArgumentError: [class InvalidArgumentError extends _AISDKError],
  InvalidDataContentError: [class InvalidDataContentError extends _AISDKError],
  InvalidMessageRoleError: [class InvalidMessageRoleError extends _AISDKError],
  InvalidPromptError: [class InvalidPromptError extends _AISDKError],
  InvalidResponseDataError: [class InvalidResponseDataError extends _AISDKError],
  InvalidToolArgumentsError: [class InvalidToolArgumentsError extends _AISDKError],
  JSONParseError: [class JSONParseError extends _AISDKError],
  LangChainAdapter: { toDataStream: [Getter], toDataStreamResponse: [Getter] },
  LlamaIndexAdapter: { toDataStream: [Getter], toDataStreamResponse: [Getter] },
  LoadAPIKeyError: [class LoadAPIKeyError extends _AISDKError],
  MessageConversionError: [class MessageConversionError extends _AISDKError],
  NoContentGeneratedError: [class NoContentGeneratedError extends _AISDKError],
  NoObjectGeneratedError: [class NoObjectGeneratedError extends _AISDKError],
  NoSuchModelError: [class NoSuchModelError extends _AISDKError],
  NoSuchProviderError: [class NoSuchProviderError extends NoSuchModelError],
  NoSuchToolError: [class NoSuchToolError extends _AISDKError],
  RetryError: [class RetryError extends _AISDKError],
  StreamData: [class StreamData],
  TypeValidationError: [class _TypeValidationError extends _AISDKError],
  UnsupportedFunctionalityError: [class UnsupportedFunctionalityError extends _AISDKError],
  convertToCoreMessages: [Function: convertToCoreMessages],
  cosineSimilarity: [Function: cosineSimilarity],
  createStreamDataTransformer: [Function: createStreamDataTransformer],
  embed: [Function (anonymous)],
  embedMany: [Function (anonymous)],
  experimental_createProviderRegistry: [Function: experimental_createProviderRegistry],
  experimental_customProvider: [Function: experimental_customProvider],
  experimental_wrapLanguageModel: [Function: experimental_wrapLanguageModel],
  formatAssistantStreamPart: [Function: formatAssistantStreamPart],
  formatDataStreamPart: [Function: formatDataStreamPart],
  generateId: [Function (anonymous)],
  generateObject: [Function (anonymous)],
  generateText: [Function (anonymous)],
  jsonSchema: [Function: jsonSchema],
  parseAssistantStreamPart: [Function: parseAssistantStreamPart],
  parseDataStreamPart: [Function: parseDataStreamPart],
  processDataStream: [AsyncFunction: processDataStream],
  processTextStream: [AsyncFunction: processTextStream],
  streamObject: [Function (anonymous)],
  streamText: [Function (anonymous)],
  tool: [Function: tool]
}
> setters WeakMap { <items unknown> }
> setters.get(target) {
  AISDKError: [Function (anonymous)],
  APICallError: [Function (anonymous)],
  AssistantResponse: [Function (anonymous)],
  DownloadError: [Function (anonymous)],
  EmptyResponseBodyError: [Function (anonymous)],
  InvalidArgumentError: [Function (anonymous)],
  InvalidDataContentError: [Function (anonymous)],
  InvalidMessageRoleError: [Function (anonymous)],
  InvalidPromptError: [Function (anonymous)],
  InvalidResponseDataError: [Function (anonymous)],
  InvalidToolArgumentsError: [Function (anonymous)],
  JSONParseError: [Function (anonymous)],
  LangChainAdapter: [Function (anonymous)],
  LlamaIndexAdapter: [Function (anonymous)],
  LoadAPIKeyError: [Function (anonymous)],
  MessageConversionError: [Function (anonymous)],
  NoContentGeneratedError: [Function (anonymous)],
  NoObjectGeneratedError: [Function (anonymous)],
  NoSuchModelError: [Function (anonymous)],
  NoSuchProviderError: [Function (anonymous)],
  NoSuchToolError: [Function (anonymous)],
  RetryError: [Function (anonymous)],
  StreamData: [Function (anonymous)],
  TypeValidationError: [Function (anonymous)],
  UnsupportedFunctionalityError: [Function (anonymous)],
  convertToCoreMessages: [Function (anonymous)],
  cosineSimilarity: [Function (anonymous)],
  createStreamDataTransformer: [Function (anonymous)],
  embed: [Function (anonymous)],
  embedMany: [Function (anonymous)],
  experimental_createProviderRegistry: [Function (anonymous)],
  experimental_customProvider: [Function (anonymous)],
  experimental_wrapLanguageModel: [Function (anonymous)],
  formatAssistantStreamPart: [Function (anonymous)],
  formatDataStreamPart: [Function (anonymous)],
  generateId: [Function (anonymous)],
  generateObject: [Function (anonymous)],
  generateText: [Function (anonymous)],
  jsonSchema: [Function (anonymous)],
  parseAssistantStreamPart: [Function (anonymous)],
  parseDataStreamPart: [Function (anonymous)],
  processDataStream: [Function (anonymous)],
  processTextStream: [Function (anonymous)],
  streamObject: [Function (anonymous)],
  streamText: [Function (anonymous)],
  tool: [Function (anonymous)]
}
> setters.get(target)[name] undefined
/Users/lukas/code/test-projects/gh-sentry-javascript-16137/node_modules/.pnpm/import-in-the-middle@1.13.1/node_modules/import-in-the-middle/lib/register.js:21
    return setters.get(target)[name](value)

So based on my limited understanding of IITM, it seems like for some reason it is trying to set a default export but the ai library doesn't export a default export.

I will ask @timfish and @AbhiPrasad - could you please take a look at this? I'm not sure if this is an IITM bug or our instrumentation is causing this.

@Lms24 Lms24 changed the title Crash with Vercel AI SDK when spotlight is enabled Crash with Vercel AI SDK when used in ESM Apr 28, 2025
@Lms24 Lms24 changed the title Crash with Vercel AI SDK when used in ESM Crash with Vercel AI SDK when spotlight is enabled Apr 28, 2025
@Lms24 Lms24 assigned timfish and unassigned Lms24 Apr 28, 2025
@Lms24 Lms24 changed the title Crash with Vercel AI SDK when spotlight is enabled Crash with Vercel AI SDK when used in ESM Apr 28, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
Status: No status
Development

No branches or pull requests

3 participants