Skip to content

Commit c79d775

Browse files
committed
Add tanstackrouter export, remove vendored types
1 parent 6d6c5d0 commit c79d775

File tree

8 files changed

+261
-100
lines changed

8 files changed

+261
-100
lines changed

packages/solid/README.md

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,43 @@ render(
5252
);
5353
```
5454

55+
### Tanstack Router
56+
57+
The Tanstack Router instrumentation uses the Tanstack Router library to create navigation spans to ensure you collect
58+
meaningful performance data about the health of your page loads and associated requests.
59+
60+
Add `tanstackRouterBrowserTracingIntegration` instead of the regular `Sentry.browserTracingIntegration`.
61+
62+
Make sure `tanstackRouterBrowserTracingIntegration` is initialized by your `Sentry.init` call. Otherwise, the routing
63+
instrumentation will not work properly.
64+
65+
Pass your router instance from `createRouter` to the integration.
66+
67+
```js
68+
import * as Sentry from '@sentry/solid';
69+
import { tanstackRouterBrowserTracingIntegration } from '@sentry/solid/tanstackrouter';
70+
import { Route, Router } from '@solidjs/router';
71+
72+
const router = createRouter({
73+
// your router config
74+
// ...
75+
});
76+
77+
declare module '@tanstack/solid-router' {
78+
interface Register {
79+
router: typeof router;
80+
}
81+
}
82+
83+
Sentry.init({
84+
dsn: '__PUBLIC_DSN__',
85+
integrations: [tanstackRouterBrowserTracingIntegration(router)],
86+
tracesSampleRate: 1.0, // Capture 100% of the transactions
87+
});
88+
89+
render(() => <App />, document.getElementById('root'));
90+
```
91+
5592
# Solid ErrorBoundary
5693

5794
To automatically capture exceptions from inside a component tree and render a fallback component, wrap the native Solid

packages/solid/package.json

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@
3939
"default": "./build/cjs/solidrouter.js"
4040
}
4141
},
42-
"./tanstack-router": {
42+
"./tanstackrouter": {
4343
"import": {
4444
"types": "./tanstackrouter.d.ts",
4545
"default": "./build/esm/tanstackrouter.js"
@@ -59,15 +59,20 @@
5959
},
6060
"peerDependencies": {
6161
"@solidjs/router": "^0.13.4",
62+
"@tanstack/solid-router": "^1.132.27",
6263
"solid-js": "^1.8.4"
6364
},
6465
"peerDependenciesMeta": {
6566
"@solidjs/router": {
6667
"optional": true
68+
},
69+
"@tanstack/solid-router": {
70+
"optional": true
6771
}
6872
},
6973
"devDependencies": {
7074
"@solidjs/router": "^0.13.4",
75+
"@tanstack/solid-router": "^1.132.27",
7176
"@solidjs/testing-library": "0.8.5",
7277
"@testing-library/dom": "^7.21.4",
7378
"@testing-library/jest-dom": "^6.4.5",
@@ -80,15 +85,15 @@
8085
"build": "run-p build:transpile build:types",
8186
"build:dev": "yarn build",
8287
"build:transpile": "rollup -c rollup.npm.config.mjs",
83-
"build:types": "run-s build:types:core build:types:solidrouter",
88+
"build:types": "run-s build:types:core build:types:routers",
8489
"build:types:core": "tsc -p tsconfig.types.json",
85-
"build:types:solidrouter": "tsc -p tsconfig.solidrouter-types.json",
90+
"build:types:routers": "tsc -p tsconfig.routers-types.json",
8691
"build:watch": "run-p build:transpile:watch build:types:watch",
8792
"build:dev:watch": "yarn build:watch",
8893
"build:transpile:watch": "rollup -c rollup.npm.config.mjs --watch",
8994
"build:types:watch": "tsc -p tsconfig.types.json --watch",
9095
"build:tarball": "npm pack",
91-
"circularDepCheck": "madge --circular src/index.ts && madge --circular src/solidrouter.ts",
96+
"circularDepCheck": "madge --circular src/index.ts && madge --circular src/solidrouter.ts && madge --circular src/tanstackrouter.ts",
9297
"clean": "rimraf build coverage sentry-solid-*.tgz ./*.d.ts ./*.d.ts.map",
9398
"fix": "eslint . --format stylish --fix",
9499
"lint": "eslint . --format stylish",

packages/solid/rollup.npm.config.mjs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,6 @@ import { makeBaseNPMConfig, makeNPMConfigVariants } from '@sentry-internal/rollu
22

33
export default makeNPMConfigVariants(
44
makeBaseNPMConfig({
5-
entrypoints: ['src/index.ts', 'src/solidrouter.ts'],
5+
entrypoints: ['src/index.ts', 'src/solidrouter.ts', 'src/tanstackrouter.ts'],
66
}),
77
);

packages/solid/src/tanstackrouter.ts

Lines changed: 14 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -10,23 +10,22 @@ import {
1010
SEMANTIC_ATTRIBUTE_SENTRY_ORIGIN,
1111
SEMANTIC_ATTRIBUTE_SENTRY_SOURCE,
1212
} from '@sentry/core';
13-
import type { VendoredTanstackRouter, VendoredTanstackRouterRouteMatch } from './vendor/tanstackrouter-types';
13+
import type { AnyRouter } from '@tanstack/solid-router';
14+
15+
type RouteMatch = ReturnType<AnyRouter['matchRoutes']>[number];
1416

1517
/**
1618
* A custom browser tracing integration for TanStack Router.
1719
*
18-
* The minimum compatible version of `@tanstack/solid-router` is `1.64.0`.
20+
* The minimum compatible version of `@tanstack/solid-router` is `1.64.0
1921
*
2022
* @param router A TanStack Router `Router` instance that should be used for routing instrumentation.
2123
* @param options Sentry browser tracing configuration.
2224
*/
23-
export function tanstackRouterBrowserTracingIntegration(
24-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
25-
router: any, // This is `any` because we don't want any type mismatches if TanStack Router changes their types
25+
export function tanstackRouterBrowserTracingIntegration<R extends AnyRouter>(
26+
router: R,
2627
options: Parameters<typeof originalBrowserTracingIntegration>[0] = {},
2728
): Integration {
28-
const castRouterInstance: VendoredTanstackRouter = router;
29-
3029
const browserTracingIntegrationInstance = originalBrowserTracingIntegration({
3130
...options,
3231
instrumentNavigation: false,
@@ -42,9 +41,9 @@ export function tanstackRouterBrowserTracingIntegration(
4241

4342
const initialWindowLocation = WINDOW.location;
4443
if (instrumentPageLoad && initialWindowLocation) {
45-
const matchedRoutes = castRouterInstance.matchRoutes(
44+
const matchedRoutes = router.matchRoutes(
4645
initialWindowLocation.pathname,
47-
castRouterInstance.options.parseSearch(initialWindowLocation.search),
46+
router.options.parseSearch(initialWindowLocation.search),
4847
{ preload: false, throwOnError: false },
4948
);
5049

@@ -63,13 +62,13 @@ export function tanstackRouterBrowserTracingIntegration(
6362

6463
if (instrumentNavigation) {
6564
// The onBeforeNavigate hook is called at the very beginning of a navigation and is only called once per navigation, even when the user is redirected
66-
castRouterInstance.subscribe('onBeforeNavigate', onBeforeNavigateArgs => {
65+
router.subscribe('onBeforeNavigate', onBeforeNavigateArgs => {
6766
// onBeforeNavigate is called during pageloads. We can avoid creating navigation spans by comparing the states of the to and from arguments.
6867
if (onBeforeNavigateArgs.toLocation.state === onBeforeNavigateArgs.fromLocation?.state) {
6968
return;
7069
}
7170

72-
const onResolvedMatchedRoutes = castRouterInstance.matchRoutes(
71+
const onResolvedMatchedRoutes = router.matchRoutes(
7372
onBeforeNavigateArgs.toLocation.pathname,
7473
onBeforeNavigateArgs.toLocation.search,
7574
{ preload: false, throwOnError: false },
@@ -88,10 +87,10 @@ export function tanstackRouterBrowserTracingIntegration(
8887
});
8988

9089
// In case the user is redirected during navigation we want to update the span with the right value.
91-
const unsubscribeOnResolved = castRouterInstance.subscribe('onResolved', onResolvedArgs => {
90+
const unsubscribeOnResolved = router.subscribe('onResolved', onResolvedArgs => {
9291
unsubscribeOnResolved();
9392
if (navigationSpan) {
94-
const onResolvedMatchedRoutes = castRouterInstance.matchRoutes(
93+
const onResolvedMatchedRoutes = router.matchRoutes(
9594
onResolvedArgs.toLocation.pathname,
9695
onResolvedArgs.toLocation.search,
9796
{ preload: false, throwOnError: false },
@@ -112,14 +111,13 @@ export function tanstackRouterBrowserTracingIntegration(
112111
};
113112
}
114113

115-
function routeMatchToParamSpanAttributes(match: VendoredTanstackRouterRouteMatch | undefined): Record<string, string> {
114+
function routeMatchToParamSpanAttributes(match: RouteMatch | undefined): Record<string, string> {
116115
if (!match) {
117116
return {};
118117
}
119118

120119
const paramAttributes: Record<string, string> = {};
121-
Object.entries(match.params).forEach(([key, value]) => {
122-
paramAttributes[`url.path.params.${key}`] = value; // TODO(v11): remove attribute which does not adhere to Sentry's semantic convention
120+
Object.entries(match.params as Record<string, string>).forEach(([key, value]) => {
123121
paramAttributes[`url.path.parameter.${key}`] = value;
124122
paramAttributes[`params.${key}`] = value; // params.[key] is an alias
125123
});

packages/solid/src/vendor/tanstackrouter-types.ts

Lines changed: 0 additions & 74 deletions
This file was deleted.

packages/solid/tsconfig.solidrouter-types.json renamed to packages/solid/tsconfig.routers-types.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
},
1010

1111
"//": "This type is built separately because it is for a subpath export, which has problems if it is not in the root",
12-
"include": ["src/solidrouter.ts"],
12+
"include": ["src/solidrouter.ts", "src/tanstackrouter.ts"],
1313
"//": "Without this, we cannot output into the root dir",
1414
"exclude": []
1515
}

packages/solid/tsconfig.types.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,6 @@
88
"outDir": "build/types"
99
},
1010

11-
"//": "This is built separately in tsconfig.solidrouter-types.json",
12-
"exclude": ["src/solidrouter.ts"]
11+
"//": "This is built separately in tsconfig.routers-types.json",
12+
"exclude": ["src/solidrouter.ts", "src/tanstackrouter.ts"]
1313
}

0 commit comments

Comments
 (0)