From 1f1e3aa51bc3cc4470452bcdc68e551047b8f2a2 Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Fri, 16 Jun 2023 08:01:19 +0000 Subject: [PATCH 1/8] check for type of route handler returned value at runtime Signed-off-by: GitHub --- .../future/route-modules/app-route/module.ts | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/packages/next/src/server/future/route-modules/app-route/module.ts b/packages/next/src/server/future/route-modules/app-route/module.ts index bcc7e19a8095..e00458b2eaac 100644 --- a/packages/next/src/server/future/route-modules/app-route/module.ts +++ b/packages/next/src/server/future/route-modules/app-route/module.ts @@ -68,7 +68,8 @@ type AppRouteHandlerFnContext = { } /** - * Handler function for app routes. + * Handler function for app routes. If a non-Response value is returned, an empty + * 200 response will be used as the HTTP response instead. */ export type AppRouteHandlerFn = ( /** @@ -80,7 +81,7 @@ export type AppRouteHandlerFn = ( * dynamic route). */ ctx: AppRouteHandlerFnContext -) => Promise | Response +) => any /** * AppRouteHandlers describes the handlers for app routes that is provided by @@ -356,9 +357,18 @@ export class AppRouteRouteModule extends RouteModule< staticGenerationAsyncStorage: this.staticGenerationAsyncStorage, }) - const res = await handler(wrappedRequest, { + const rawRes = await handler(wrappedRequest, { params: context.params, }) + const rawResIsResponse = rawRes instanceof Response + if (!rawResIsResponse) { + Log.warn( + `Route handler ${context.staticGenerationContext.originalPathname} resolved without returning a \`Response\` or a \`NextResponse\`` + ) + } + const res: Response = rawResIsResponse + ? rawRes + : new Response(null) ;(context.staticGenerationContext as any).fetchMetrics = staticGenerationStore.fetchMetrics From 3fb6742a5b0b74ae141aea098294edbbb4bba7aa Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Fri, 16 Jun 2023 08:14:04 +0000 Subject: [PATCH 2/8] use unknown for the returned type of AppRouteHandlerFn Signed-off-by: GitHub --- .../next/src/server/future/route-modules/app-route/module.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/next/src/server/future/route-modules/app-route/module.ts b/packages/next/src/server/future/route-modules/app-route/module.ts index e00458b2eaac..b45d72c61312 100644 --- a/packages/next/src/server/future/route-modules/app-route/module.ts +++ b/packages/next/src/server/future/route-modules/app-route/module.ts @@ -81,7 +81,7 @@ export type AppRouteHandlerFn = ( * dynamic route). */ ctx: AppRouteHandlerFnContext -) => any +) => unknown /** * AppRouteHandlers describes the handlers for app routes that is provided by From 75870a4a065571caa70f957c2d4ba42b283f5014 Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Sat, 24 Jun 2023 01:57:50 +0000 Subject: [PATCH 3/8] throw an error if route handler doesn't return a `Response` Signed-off-by: GitHub --- .../future/route-modules/app-route/module.ts | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/packages/next/src/server/future/route-modules/app-route/module.ts b/packages/next/src/server/future/route-modules/app-route/module.ts index b45d72c61312..5f82b7efd088 100644 --- a/packages/next/src/server/future/route-modules/app-route/module.ts +++ b/packages/next/src/server/future/route-modules/app-route/module.ts @@ -68,8 +68,8 @@ type AppRouteHandlerFnContext = { } /** - * Handler function for app routes. If a non-Response value is returned, an empty - * 200 response will be used as the HTTP response instead. + * Handler function for app routes. If a non-Response value is returned, an error + * will be thrown. */ export type AppRouteHandlerFn = ( /** @@ -357,18 +357,14 @@ export class AppRouteRouteModule extends RouteModule< staticGenerationAsyncStorage: this.staticGenerationAsyncStorage, }) - const rawRes = await handler(wrappedRequest, { + const res = await handler(wrappedRequest, { params: context.params, }) - const rawResIsResponse = rawRes instanceof Response - if (!rawResIsResponse) { - Log.warn( + if (!(res instanceof Response)) { + throw new Error( `Route handler ${context.staticGenerationContext.originalPathname} resolved without returning a \`Response\` or a \`NextResponse\`` ) } - const res: Response = rawResIsResponse - ? rawRes - : new Response(null) ;(context.staticGenerationContext as any).fetchMetrics = staticGenerationStore.fetchMetrics From 66c60eb2ba56881b1c1593ae8f071c76665104d7 Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Sat, 24 Jun 2023 02:46:58 +0000 Subject: [PATCH 4/8] add tests Signed-off-by: GitHub --- .../server/future/route-modules/app-route/module.ts | 2 +- .../app-dir/app-routes/app-custom-routes.test.ts | 13 +++++++++++++ .../e2e/app-dir/app-routes/app/no-response/route.ts | 1 + 3 files changed, 15 insertions(+), 1 deletion(-) create mode 100644 test/e2e/app-dir/app-routes/app/no-response/route.ts diff --git a/packages/next/src/server/future/route-modules/app-route/module.ts b/packages/next/src/server/future/route-modules/app-route/module.ts index 5f82b7efd088..17b162780895 100644 --- a/packages/next/src/server/future/route-modules/app-route/module.ts +++ b/packages/next/src/server/future/route-modules/app-route/module.ts @@ -362,7 +362,7 @@ export class AppRouteRouteModule extends RouteModule< }) if (!(res instanceof Response)) { throw new Error( - `Route handler ${context.staticGenerationContext.originalPathname} resolved without returning a \`Response\` or a \`NextResponse\`` + `No response is returned from route handler '${this.resolvedPagePath}'. Ensure you return a \`Response\` or a \`NextResponse\` in all branches of your handler.` ) } ;(context.staticGenerationContext as any).fetchMetrics = diff --git a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts index 2b63b1492907..b8ea230e9024 100644 --- a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts +++ b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts @@ -584,5 +584,18 @@ createNextDescribe( }) }) } + + describe('no response returned', () => { + it('should print an error when no response is returned', async () => { + await next.fetch('/no-response', { method: 'POST' }) + + await check(() => { + expect(next.cliOutput).toMatch( + /No response is returned from route handler '.+\/route\.ts'\. Ensure you return a `Response` or a `NextResponse` in all branches of your handler\./ + ) + return 'yes' + }, 'yes') + }) + }) } ) diff --git a/test/e2e/app-dir/app-routes/app/no-response/route.ts b/test/e2e/app-dir/app-routes/app/no-response/route.ts new file mode 100644 index 000000000000..18e2e85f0699 --- /dev/null +++ b/test/e2e/app-dir/app-routes/app/no-response/route.ts @@ -0,0 +1 @@ +export function POST() {} From 07923d8832256b0d53d346ddeef8b752deb36ac2 Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Sat, 24 Jun 2023 03:23:44 +0000 Subject: [PATCH 5/8] check for return type of route handlers in the TS plugin Signed-off-by: GitHub --- .../src/build/webpack/plugins/next-types-plugin.ts | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/packages/next/src/build/webpack/plugins/next-types-plugin.ts b/packages/next/src/build/webpack/plugins/next-types-plugin.ts index 81118585efaf..9f5846dbc845 100644 --- a/packages/next/src/build/webpack/plugins/next-types-plugin.ts +++ b/packages/next/src/build/webpack/plugins/next-types-plugin.ts @@ -105,6 +105,19 @@ if ('${method}' in entry) { '${method}' > >() + checkFields< + Diff< + { + __tag__: '${method}', + __return_type__: Response | Promise + }, + { + __tag__: '${method}', + __return_type__: ReturnType> + }, + '${method}' + > + >() } ` ).join('') From 3c3715436a75e847407f6ca3c89321836ebbfcb2 Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Sun, 23 Jul 2023 11:47:13 +0700 Subject: [PATCH 6/8] update test after changes from #52910 Signed-off-by: Vu Van Dung --- test/e2e/app-dir/app-routes/app-custom-routes.test.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts index 73156e6706f0..a10aac133fbe 100644 --- a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts +++ b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts @@ -632,7 +632,7 @@ createNextDescribe( describe('no response returned', () => { it('should print an error when no response is returned', async () => { - await next.fetch('/no-response', { method: 'POST' }) + await next.fetch(bathPath + '/no-response', { method: 'POST' }) await check(() => { expect(next.cliOutput).toMatch( From 39a8facc3635b7711f622769a3ba9594c5f90bd2 Mon Sep 17 00:00:00 2001 From: Vu Van Dung Date: Sun, 23 Jul 2023 11:48:04 +0700 Subject: [PATCH 7/8] rename variable 'bathPath' -> 'basePath' Signed-off-by: Vu Van Dung --- .../app-routes/app-custom-routes.test.ts | 86 +++++++++---------- 1 file changed, 43 insertions(+), 43 deletions(-) diff --git a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts index a10aac133fbe..ad8d9374effc 100644 --- a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts +++ b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts @@ -8,7 +8,7 @@ import { cookieWithRequestMeta, } from './helpers' -const bathPath = process.env.BASE_PATH ?? '' +const basePath = process.env.BASE_PATH ?? '' createNextDescribe( 'app-custom-routes', @@ -27,7 +27,7 @@ createNextDescribe( ).toBeTruthy() } expect( - JSON.parse(await next.render(bathPath + '/api/hello.json')) + JSON.parse(await next.render(basePath + '/api/hello.json')) ).toEqual({ pathname: '/api/hello.json', }) @@ -47,7 +47,7 @@ createNextDescribe( ).toBeFalsy() } expect( - JSON.parse(await next.render(bathPath + '/api/dynamic')) + JSON.parse(await next.render(basePath + '/api/dynamic')) ).toEqual({ pathname: '/api/dynamic', query: {}, @@ -61,7 +61,7 @@ createNextDescribe( '/static/second/data.json', '/static/three/data.json', ])('responds correctly on %s', async (path) => { - expect(JSON.parse(await next.render(bathPath + path))).toEqual({ + expect(JSON.parse(await next.render(basePath + path))).toEqual({ params: { slug: path.split('/')[2] }, now: expect.any(Number), }) @@ -83,7 +83,7 @@ createNextDescribe( '/revalidate-1/second/data.json', '/revalidate-1/three/data.json', ])('revalidates correctly on %s', async (path) => { - const data = JSON.parse(await next.render(bathPath + path)) + const data = JSON.parse(await next.render(basePath + path)) expect(data).toEqual({ params: { slug: path.split('/')[2] }, now: expect.any(Number), @@ -91,7 +91,7 @@ createNextDescribe( await check(async () => { expect(data).not.toEqual( - JSON.parse(await next.render(bathPath + path)) + JSON.parse(await next.render(basePath + path)) ) return 'success' }, 'success') @@ -117,7 +117,7 @@ createNextDescribe( it.each(['/basic/endpoint', '/basic/vercel/endpoint'])( 'responds correctly on %s', async (path) => { - const res = await next.fetch(bathPath + path, { method }) + const res = await next.fetch(basePath + path, { method }) expect(res.status).toEqual(200) expect(await res.text()).toContain('hello, world') @@ -131,7 +131,7 @@ createNextDescribe( describe('route groups', () => { it('routes to the correct handler', async () => { - const res = await next.fetch(bathPath + '/basic/endpoint/nested') + const res = await next.fetch(basePath + '/basic/endpoint/nested') expect(res.status).toEqual(200) const meta = getRequestMeta(res.headers) @@ -141,7 +141,7 @@ createNextDescribe( describe('request', () => { it('can read query parameters', async () => { - const res = await next.fetch(bathPath + '/advanced/query?ping=pong') + const res = await next.fetch(basePath + '/advanced/query?ping=pong') expect(res.status).toEqual(200) const meta = getRequestMeta(res.headers) @@ -150,7 +150,7 @@ createNextDescribe( it('can read query parameters (edge)', async () => { const res = await next.fetch( - bathPath + '/edge/advanced/query?ping=pong' + basePath + '/edge/advanced/query?ping=pong' ) expect(res.status).toEqual(200) @@ -162,7 +162,7 @@ createNextDescribe( describe('response', () => { // TODO-APP: re-enable when rewrites are supported again it.skip('supports the NextResponse.rewrite() helper', async () => { - const res = await next.fetch(bathPath + '/hooks/rewrite') + const res = await next.fetch(basePath + '/hooks/rewrite') expect(res.status).toEqual(200) @@ -173,7 +173,7 @@ createNextDescribe( }) it('supports the NextResponse.redirect() helper', async () => { - const res = await next.fetch(bathPath + '/hooks/redirect/response', { + const res = await next.fetch(basePath + '/hooks/redirect/response', { // "Manually" perform the redirect, we want to inspect the // redirection response, so don't actually follow it. redirect: 'manual', @@ -186,7 +186,7 @@ createNextDescribe( it('supports the NextResponse.json() helper', async () => { const meta = { ping: 'pong' } - const res = await next.fetch(bathPath + '/hooks/json', { + const res = await next.fetch(basePath + '/hooks/json', { headers: withRequestMeta(meta), }) @@ -212,7 +212,7 @@ createNextDescribe( }, }) - const res = await next.fetch(bathPath + '/advanced/body/streaming', { + const res = await next.fetch(basePath + '/advanced/body/streaming', { method: 'POST', body: stream, }) @@ -235,7 +235,7 @@ createNextDescribe( }) const res = await next.fetch( - bathPath + '/edge/advanced/body/streaming', + basePath + '/edge/advanced/body/streaming', { method: 'POST', body: stream, @@ -248,7 +248,7 @@ createNextDescribe( it('can read a JSON encoded body', async () => { const body = { ping: 'pong' } - const res = await next.fetch(bathPath + '/advanced/body/json', { + const res = await next.fetch(basePath + '/advanced/body/json', { method: 'POST', body: JSON.stringify(body), }) @@ -260,7 +260,7 @@ createNextDescribe( it('can read a JSON encoded body (edge)', async () => { const body = { ping: 'pong' } - const res = await next.fetch(bathPath + '/edge/advanced/body/json', { + const res = await next.fetch(basePath + '/edge/advanced/body/json', { method: 'POST', body: JSON.stringify(body), }) @@ -272,7 +272,7 @@ createNextDescribe( it('can read a JSON encoded body for DELETE requests', async () => { const body = { name: 'foo' } - const res = await next.fetch(bathPath + '/advanced/body/json', { + const res = await next.fetch(basePath + '/advanced/body/json', { method: 'DELETE', body: JSON.stringify(body), }) @@ -283,7 +283,7 @@ createNextDescribe( it('can read a JSON encoded body for OPTIONS requests', async () => { const body = { name: 'bar' } - const res = await next.fetch(bathPath + '/advanced/body/json', { + const res = await next.fetch(basePath + '/advanced/body/json', { method: 'OPTIONS', body: JSON.stringify(body), }) @@ -306,7 +306,7 @@ createNextDescribe( index++ }, }) - const res = await next.fetch(bathPath + '/advanced/body/json', { + const res = await next.fetch(basePath + '/advanced/body/json', { method: 'POST', body: stream, }) @@ -329,7 +329,7 @@ createNextDescribe( index++ }, }) - const res = await next.fetch(bathPath + '/edge/advanced/body/json', { + const res = await next.fetch(basePath + '/edge/advanced/body/json', { method: 'POST', body: stream, }) @@ -341,7 +341,7 @@ createNextDescribe( it('can read the text body', async () => { const body = 'hello, world' - const res = await next.fetch(bathPath + '/advanced/body/text', { + const res = await next.fetch(basePath + '/advanced/body/text', { method: 'POST', body, }) @@ -353,7 +353,7 @@ createNextDescribe( it('can read the text body (edge)', async () => { const body = 'hello, world' - const res = await next.fetch(bathPath + '/edge/advanced/body/text', { + const res = await next.fetch(basePath + '/edge/advanced/body/text', { method: 'POST', body, }) @@ -366,7 +366,7 @@ createNextDescribe( describe('context', () => { it('provides params to routes with dynamic parameters', async () => { - const res = await next.fetch(bathPath + '/basic/vercel/endpoint') + const res = await next.fetch(basePath + '/basic/vercel/endpoint') expect(res.status).toEqual(200) const meta = getRequestMeta(res.headers) @@ -375,7 +375,7 @@ createNextDescribe( it('provides params to routes with catch-all routes', async () => { const res = await next.fetch( - bathPath + '/basic/vercel/some/other/resource' + basePath + '/basic/vercel/some/other/resource' ) expect(res.status).toEqual(200) @@ -387,7 +387,7 @@ createNextDescribe( }) it('does not provide params to routes without dynamic parameters', async () => { - const res = await next.fetch(bathPath + '/basic/endpoint') + const res = await next.fetch(basePath + '/basic/endpoint') expect(res.ok).toBeTrue() @@ -399,7 +399,7 @@ createNextDescribe( describe('hooks', () => { describe('headers', () => { it('gets the correct values', async () => { - const res = await next.fetch(bathPath + '/hooks/headers', { + const res = await next.fetch(basePath + '/hooks/headers', { headers: withRequestMeta({ ping: 'pong' }), }) @@ -412,7 +412,7 @@ createNextDescribe( describe('cookies', () => { it('gets the correct values', async () => { - const res = await next.fetch(bathPath + '/hooks/cookies', { + const res = await next.fetch(basePath + '/hooks/cookies', { headers: cookieWithRequestMeta({ ping: 'pong' }), }) @@ -425,7 +425,7 @@ createNextDescribe( describe('redirect', () => { it('can respond correctly', async () => { - const res = await next.fetch(bathPath + '/hooks/redirect', { + const res = await next.fetch(basePath + '/hooks/redirect', { // "Manually" perform the redirect, we want to inspect the // redirection response, so don't actually follow it. redirect: 'manual', @@ -439,7 +439,7 @@ createNextDescribe( describe('notFound', () => { it('can respond correctly', async () => { - const res = await next.fetch(bathPath + '/hooks/not-found') + const res = await next.fetch(basePath + '/hooks/not-found') expect(res.status).toEqual(404) expect(await res.text()).toBeEmpty() @@ -449,7 +449,7 @@ createNextDescribe( describe('error conditions', () => { it('responds with 400 (Bad Request) when the requested method is not a valid HTTP method', async () => { - const res = await next.fetch(bathPath + '/status/405', { + const res = await next.fetch(basePath + '/status/405', { method: 'HEADER', }) @@ -458,7 +458,7 @@ createNextDescribe( }) it('responds with 405 (Method Not Allowed) when method is not implemented', async () => { - const res = await next.fetch(bathPath + '/status/405', { + const res = await next.fetch(basePath + '/status/405', { method: 'POST', }) @@ -467,7 +467,7 @@ createNextDescribe( }) it('responds with 500 (Internal Server Error) when the handler throws an error', async () => { - const res = await next.fetch(bathPath + '/status/500') + const res = await next.fetch(basePath + '/status/500') expect(res.status).toEqual(500) expect(await res.text()).toBeEmpty() @@ -481,7 +481,7 @@ createNextDescribe( // testing that the specific route throws this error in the console. expect(next.cliOutput).not.toContain(error) - const res = await next.fetch(bathPath + '/status/500/next') + const res = await next.fetch(basePath + '/status/500/next') expect(res.status).toEqual(500) expect(await res.text()).toBeEmpty() @@ -497,7 +497,7 @@ createNextDescribe( describe('automatic implementations', () => { it('implements HEAD on routes with GET already implemented', async () => { - const res = await next.fetch(bathPath + '/methods/head', { + const res = await next.fetch(basePath + '/methods/head', { method: 'HEAD', }) @@ -506,7 +506,7 @@ createNextDescribe( }) it('implements OPTIONS on routes', async () => { - const res = await next.fetch(bathPath + '/methods/options', { + const res = await next.fetch(basePath + '/methods/options', { method: 'OPTIONS', }) @@ -521,7 +521,7 @@ createNextDescribe( describe('edge functions', () => { it('returns response using edge runtime', async () => { - const res = await next.fetch(bathPath + '/edge') + const res = await next.fetch(basePath + '/edge') expect(res.status).toEqual(200) expect(await res.text()).toContain('hello, world') @@ -529,7 +529,7 @@ createNextDescribe( it('returns a response when headers are accessed', async () => { const meta = { ping: 'pong' } - const res = await next.fetch(bathPath + '/edge/headers', { + const res = await next.fetch(basePath + '/edge/headers', { headers: withRequestMeta(meta), }) @@ -540,7 +540,7 @@ createNextDescribe( describe('dynamic = "force-static"', () => { it('strips search, headers, and domain from request', async () => { - const res = await next.fetch(bathPath + '/dynamic?query=true', { + const res = await next.fetch(basePath + '/dynamic?query=true', { headers: { accept: 'application/json', cookie: 'session=true', @@ -569,7 +569,7 @@ createNextDescribe( describe('customized metadata routes', () => { it('should work if conflict with metadata routes convention', async () => { - const res = await next.fetch(bathPath + '/robots.txt') + const res = await next.fetch(basePath + '/robots.txt') expect(res.status).toEqual(200) expect(await res.text()).toBe( @@ -591,7 +591,7 @@ createNextDescribe( ])( 'should print an error when using lowercase %p in dev', async (method: string) => { - await next.fetch(bathPath + '/lowercase/' + method) + await next.fetch(basePath + '/lowercase/' + method) await check(() => { expect(next.cliOutput).toContain( @@ -611,7 +611,7 @@ createNextDescribe( describe('invalid exports', () => { it('should print an error when exporting a default handler in dev', async () => { - const res = await next.fetch(bathPath + '/default') + const res = await next.fetch(basePath + '/default') // Ensure we get a 405 (Method Not Allowed) response when there is no // exported handler for the GET method. @@ -632,7 +632,7 @@ createNextDescribe( describe('no response returned', () => { it('should print an error when no response is returned', async () => { - await next.fetch(bathPath + '/no-response', { method: 'POST' }) + await next.fetch(basePath + '/no-response', { method: 'POST' }) await check(() => { expect(next.cliOutput).toMatch( From 3d67c743c29bfd683394e6e85b5b15e5fea1b328 Mon Sep 17 00:00:00 2001 From: JJ Kasper Date: Thu, 7 Sep 2023 20:17:39 -0700 Subject: [PATCH 8/8] fix types --- .../app-routes/app-custom-routes.test.ts | 2 +- test/e2e/app-dir/app-routes/tsconfig.json | 24 ------------------- 2 files changed, 1 insertion(+), 25 deletions(-) delete mode 100644 test/e2e/app-dir/app-routes/tsconfig.json diff --git a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts index 2280eab9a64c..83596d1bcc04 100644 --- a/test/e2e/app-dir/app-routes/app-custom-routes.test.ts +++ b/test/e2e/app-dir/app-routes/app-custom-routes.test.ts @@ -425,7 +425,7 @@ createNextDescribe( describe('cookies().has()', () => { it('gets the correct values', async () => { - const res = await next.fetch(bathPath + '/hooks/cookies/has') + const res = await next.fetch(basePath + '/hooks/cookies/has') expect(res.status).toEqual(200) diff --git a/test/e2e/app-dir/app-routes/tsconfig.json b/test/e2e/app-dir/app-routes/tsconfig.json deleted file mode 100644 index 3af94bb2971c..000000000000 --- a/test/e2e/app-dir/app-routes/tsconfig.json +++ /dev/null @@ -1,24 +0,0 @@ -{ - "compilerOptions": { - "lib": ["dom", "dom.iterable", "esnext"], - "allowJs": true, - "skipLibCheck": true, - "strict": false, - "forceConsistentCasingInFileNames": true, - "noEmit": true, - "incremental": true, - "esModuleInterop": true, - "module": "esnext", - "moduleResolution": "bundler", - "resolveJsonModule": true, - "isolatedModules": true, - "jsx": "preserve", - "plugins": [ - { - "name": "next" - } - ] - }, - "include": ["next-env.d.ts", ".next/types/**/*.ts", "**/*.ts", "**/*.tsx"], - "exclude": ["node_modules", "**/*.test.ts"] -}