Skip to content

Commit 1be3b4a

Browse files
ziyadkhalilLuca Forstner
andauthored
fix(nextjs): Support automatic instrumentation for app directory with custom page extensions (#12858)
Co-authored-by: Luca Forstner <[email protected]>
1 parent 0e6d802 commit 1be3b4a

File tree

4 files changed

+45
-11
lines changed

4 files changed

+45
-11
lines changed

packages/nextjs/src/config/loaders/wrappingLoader.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -182,7 +182,8 @@ export default function wrappingLoader(
182182

183183
const componentTypeMatch = path.posix
184184
.normalize(path.relative(appDir, this.resourcePath))
185-
.match(/\/?([^/]+)\.(?:js|ts|jsx|tsx)$/);
185+
// eslint-disable-next-line @sentry-internal/sdk/no-regexp-constructor
186+
.match(new RegExp(`/\\/?([^/]+)\\.(?:${pageExtensionRegex})$`));
186187

187188
if (componentTypeMatch && componentTypeMatch[1]) {
188189
let componentType: ServerComponentContext['componentType'];

packages/nextjs/src/config/webpack.ts

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -147,7 +147,7 @@ export function constructWebpackConfigFunction(
147147
);
148148
};
149149

150-
const possibleMiddlewareLocations = ['js', 'jsx', 'ts', 'tsx'].map(middlewareFileEnding => {
150+
const possibleMiddlewareLocations = pageExtensions.map(middlewareFileEnding => {
151151
return path.join(middlewareLocationFolder, `middleware.${middlewareFileEnding}`);
152152
});
153153
const isMiddlewareResource = (resourcePath: string): boolean => {
@@ -163,7 +163,10 @@ export function constructWebpackConfigFunction(
163163
return (
164164
appDirPath !== undefined &&
165165
normalizedAbsoluteResourcePath.startsWith(appDirPath + path.sep) &&
166-
!!normalizedAbsoluteResourcePath.match(/[\\/](page|layout|loading|head|not-found)\.(js|jsx|tsx)$/)
166+
!!normalizedAbsoluteResourcePath.match(
167+
// eslint-disable-next-line @sentry-internal/sdk/no-regexp-constructor
168+
new RegExp(`[\\\\/](page|layout|loading|head|not-found)\\.(${pageExtensionRegex})$`),
169+
)
167170
);
168171
};
169172

@@ -172,7 +175,10 @@ export function constructWebpackConfigFunction(
172175
return (
173176
appDirPath !== undefined &&
174177
normalizedAbsoluteResourcePath.startsWith(appDirPath + path.sep) &&
175-
!!normalizedAbsoluteResourcePath.match(/[\\/]route\.(js|jsx|ts|tsx)$/)
178+
!!normalizedAbsoluteResourcePath.match(
179+
// eslint-disable-next-line @sentry-internal/sdk/no-regexp-constructor
180+
new RegExp(`[\\\\/]route\\.(${pageExtensionRegex})$`),
181+
)
176182
);
177183
};
178184

@@ -285,10 +291,12 @@ export function constructWebpackConfigFunction(
285291
}
286292

287293
if (appDirPath) {
288-
const hasGlobalErrorFile = ['global-error.js', 'global-error.jsx', 'global-error.ts', 'global-error.tsx'].some(
289-
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
290-
globalErrorFile => fs.existsSync(path.join(appDirPath!, globalErrorFile)),
291-
);
294+
const hasGlobalErrorFile = pageExtensions
295+
.map(extension => `global-error.${extension}`)
296+
.some(
297+
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
298+
globalErrorFile => fs.existsSync(path.join(appDirPath!, globalErrorFile)),
299+
);
292300

293301
if (
294302
!hasGlobalErrorFile &&

packages/nextjs/test/config/fixtures.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ export const EDGE_SDK_CONFIG_FILE = 'sentry.edge.config.js';
1313
/** Mock next config object */
1414
export const userNextConfig: NextConfigObject = {
1515
publicRuntimeConfig: { location: 'dogpark', activities: ['fetch', 'chasing', 'digging'] },
16+
pageExtensions: ['jsx', 'js', 'tsx', 'ts', 'custom.jsx', 'custom.js', 'custom.tsx', 'custom.ts'],
1617
webpack: (incomingWebpackConfig: WebpackConfigObject, _options: BuildContext) => ({
1718
...incomingWebpackConfig,
1819
mode: 'universal-sniffing',

packages/nextjs/test/config/loaders.test.ts

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,10 @@ describe('webpack loaders', () => {
9696
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/pages/testPage.tsx',
9797
expectedWrappingTargetKind: 'page',
9898
},
99+
{
100+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/pages/testPage.custom.tsx',
101+
expectedWrappingTargetKind: 'page',
102+
},
99103
{
100104
resourcePath: './src/pages/testPage.tsx',
101105
expectedWrappingTargetKind: 'page',
@@ -133,6 +137,10 @@ describe('webpack loaders', () => {
133137
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/middleware.js',
134138
expectedWrappingTargetKind: 'middleware',
135139
},
140+
{
141+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/middleware.custom.js',
142+
expectedWrappingTargetKind: 'middleware',
143+
},
136144
{
137145
resourcePath: './src/middleware.js',
138146
expectedWrappingTargetKind: 'middleware',
@@ -162,25 +170,41 @@ describe('webpack loaders', () => {
162170
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/pages/api/nested/testApiRoute.js',
163171
expectedWrappingTargetKind: 'api-route',
164172
},
173+
{
174+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/pages/api/nested/testApiRoute.custom.js',
175+
expectedWrappingTargetKind: 'api-route',
176+
},
177+
{
178+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/nested/route.ts',
179+
expectedWrappingTargetKind: 'route-handler',
180+
},
181+
{
182+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/nested/route.custom.ts',
183+
expectedWrappingTargetKind: 'route-handler',
184+
},
165185
{
166186
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/page.js',
167187
expectedWrappingTargetKind: 'server-component',
168188
},
189+
{
190+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/page.custom.js',
191+
expectedWrappingTargetKind: 'server-component',
192+
},
169193
{
170194
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/nested/page.js',
171195
expectedWrappingTargetKind: 'server-component',
172196
},
173197
{
174-
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/nested/page.ts', // ts is not a valid file ending for pages in the app dir
175-
expectedWrappingTargetKind: undefined,
198+
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/nested/page.ts',
199+
expectedWrappingTargetKind: 'server-component',
176200
},
177201
{
178202
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/(group)/nested/page.tsx',
179203
expectedWrappingTargetKind: 'server-component',
180204
},
181205
{
182206
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/(group)/nested/loading.ts',
183-
expectedWrappingTargetKind: undefined,
207+
expectedWrappingTargetKind: 'server-component',
184208
},
185209
{
186210
resourcePath: '/Users/Maisey/projects/squirrelChasingSimulator/src/app/layout.js',

0 commit comments

Comments
 (0)