diff --git a/packages/tanstackstart-react/src/client/index.ts b/packages/tanstackstart-react/src/client/index.ts index c45aad673ad0..7c603d040693 100644 --- a/packages/tanstackstart-react/src/client/index.ts +++ b/packages/tanstackstart-react/src/client/index.ts @@ -1 +1,3 @@ export * from '@sentry/react'; + +export { init } from './sdk'; diff --git a/packages/tanstackstart-react/src/client/sdk.ts b/packages/tanstackstart-react/src/client/sdk.ts new file mode 100644 index 000000000000..b0ee3b53053f --- /dev/null +++ b/packages/tanstackstart-react/src/client/sdk.ts @@ -0,0 +1,20 @@ +import type { Client } from '@sentry/core'; +import { applySdkMetadata } from '@sentry/core'; +import type { BrowserOptions as ReactBrowserOptions } from '@sentry/react'; +import { getDefaultIntegrations as getReactDefaultIntegrations, init as initReactSDK } from '@sentry/react'; + +/** + * Initializes the TanStack Start React SDK + * + * @param options Configuration options for the SDK. + */ +export function init(options: ReactBrowserOptions): Client | undefined { + const sentryOptions: ReactBrowserOptions = { + defaultIntegrations: [...getReactDefaultIntegrations(options)], + ...options, + }; + + applySdkMetadata(sentryOptions, 'tanstackstart-react', ['tanstackstart-react', 'react']); + + return initReactSDK(sentryOptions); +} diff --git a/packages/tanstackstart-react/src/server/index.ts b/packages/tanstackstart-react/src/server/index.ts index c79572a7f318..f377305d429f 100644 --- a/packages/tanstackstart-react/src/server/index.ts +++ b/packages/tanstackstart-react/src/server/index.ts @@ -1,5 +1,7 @@ export * from '@sentry/node'; +export { init } from './sdk'; + /** * A passthrough error boundary for the server that doesn't depend on any react. Error boundaries don't catch SSR errors * so they should simply be a passthrough. diff --git a/packages/tanstackstart-react/src/server/sdk.ts b/packages/tanstackstart-react/src/server/sdk.ts new file mode 100644 index 000000000000..1bf2b5e65be2 --- /dev/null +++ b/packages/tanstackstart-react/src/server/sdk.ts @@ -0,0 +1,17 @@ +import { applySdkMetadata } from '@sentry/core'; +import type { NodeClient, NodeOptions } from '@sentry/node'; +import { getDefaultIntegrations as getDefaultNodeIntegrations, init as initNodeSdk } from '@sentry/node'; + +/** + * Initializes the server side of the TanStack Start React SDK + */ +export function init(options: NodeOptions): NodeClient | undefined { + const sentryOptions: NodeOptions = { + defaultIntegrations: [...getDefaultNodeIntegrations(options)], + ...options, + }; + + applySdkMetadata(sentryOptions, 'tanstackstart-react', ['tanstackstart-react', 'node']); + + return initNodeSdk(sentryOptions); +} diff --git a/packages/tanstackstart-react/test/client/sdk.test.ts b/packages/tanstackstart-react/test/client/sdk.test.ts new file mode 100644 index 000000000000..4cba4a199ef5 --- /dev/null +++ b/packages/tanstackstart-react/test/client/sdk.test.ts @@ -0,0 +1,45 @@ +import * as SentryReact from '@sentry/react'; +import { SDK_VERSION } from '@sentry/react'; +import { beforeEach, describe, expect, it, vi } from 'vitest'; +import { init } from '../../src/client'; + +const reactInit = vi.spyOn(SentryReact, 'init'); + +describe('TanStack Start React Client SDK', () => { + describe('init', () => { + beforeEach(() => { + vi.clearAllMocks(); + }); + + it('Adds TanStack Start React client metadata to the SDK options', () => { + expect(reactInit).not.toHaveBeenCalled(); + + init({ + dsn: 'https://public@dsn.ingest.sentry.io/1337', + }); + + const expectedMetadata = { + _metadata: { + sdk: { + name: 'sentry.javascript.tanstackstart-react', + version: SDK_VERSION, + packages: [ + { name: 'npm:@sentry/tanstackstart-react', version: SDK_VERSION }, + { name: 'npm:@sentry/react', version: SDK_VERSION }, + ], + settings: { + infer_ip: 'never', + }, + }, + }, + }; + + expect(reactInit).toHaveBeenCalledTimes(1); + expect(reactInit).toHaveBeenLastCalledWith(expect.objectContaining(expectedMetadata)); + }); + + it('returns client from init', () => { + expect(init({})).not.toBeUndefined(); + }); + }); +}); diff --git a/packages/tanstackstart-react/test/server/sdk.test.ts b/packages/tanstackstart-react/test/server/sdk.test.ts new file mode 100644 index 000000000000..f95d970ce8cc --- /dev/null +++ b/packages/tanstackstart-react/test/server/sdk.test.ts @@ -0,0 +1,42 @@ +import * as SentryNode from '@sentry/node'; +import { SDK_VERSION } from '@sentry/node'; +import { beforeEach, describe, expect, it, vi } from 'vitest'; +import { init } from '../../src/server'; + +const nodeInit = vi.spyOn(SentryNode, 'init'); + +describe('TanStack Start React Server SDK', () => { + describe('init', () => { + beforeEach(() => { + vi.clearAllMocks(); + }); + + it('Adds TanStack Start React server metadata to the SDK options', () => { + expect(nodeInit).not.toHaveBeenCalled(); + + init({ + dsn: 'https://public@dsn.ingest.sentry.io/1337', + }); + + const expectedMetadata = { + _metadata: { + sdk: { + name: 'sentry.javascript.tanstackstart-react', + version: SDK_VERSION, + packages: [ + { name: 'npm:@sentry/tanstackstart-react', version: SDK_VERSION }, + { name: 'npm:@sentry/node', version: SDK_VERSION }, + ], + }, + }, + }; + + expect(nodeInit).toHaveBeenCalledTimes(1); + expect(nodeInit).toHaveBeenLastCalledWith(expect.objectContaining(expectedMetadata)); + }); + + it('returns client from init', () => { + expect(init({})).not.toBeUndefined(); + }); + }); +}); diff --git a/packages/tanstackstart-react/test/temp.test.ts b/packages/tanstackstart-react/test/temp.test.ts deleted file mode 100644 index dc8614cad037..000000000000 --- a/packages/tanstackstart-react/test/temp.test.ts +++ /dev/null @@ -1,7 +0,0 @@ -import { describe, expect, it } from 'vitest'; - -describe('Basic test suite', () => { - it('should pass', () => { - expect(true).toBe(true); - }); -});