diff --git a/packages/nuxt/src/app/composables/router.ts b/packages/nuxt/src/app/composables/router.ts index 22982a984f..4d07272f0f 100644 --- a/packages/nuxt/src/app/composables/router.ts +++ b/packages/nuxt/src/app/composables/router.ts @@ -2,7 +2,7 @@ import { getCurrentInstance, inject } from 'vue' import type { Router, RouteLocationNormalizedLoaded, NavigationGuard, RouteLocationNormalized, RouteLocationRaw, NavigationFailure, RouteLocationPathRaw } from 'vue-router' import { sendRedirect } from 'h3' import { hasProtocol, joinURL, parseURL } from 'ufo' -import { useNuxtApp, useRuntimeConfig, useState } from '#app' +import { useNuxtApp, useRuntimeConfig, useState, createError, NuxtError } from '#app' export const useRouter = () => { return useNuxtApp()?.$router as Router @@ -105,12 +105,12 @@ export const navigateTo = (to: RouteLocationRaw | undefined | null, options?: Na } /** This will abort navigation within a Nuxt route middleware handler. */ -export const abortNavigation = (err?: Error | string) => { +export const abortNavigation = (err?: string | Partial) => { if (process.dev && !isProcessingMiddleware()) { throw new Error('abortNavigation() is only usable inside a route middleware handler.') } if (err) { - throw err instanceof Error ? err : new Error(err) + throw createError(err) } return false } diff --git a/test/basic.test.ts b/test/basic.test.ts index 8f2d9ed904..9cade4e2e3 100644 --- a/test/basic.test.ts +++ b/test/basic.test.ts @@ -236,6 +236,15 @@ describe('middlewares', () => { expect(html).toContain('Hello Nuxt 3!') }) + it('should allow aborting navigation on server-side', async () => { + const res = await fetch('/?abort', { + headers: { + accept: 'application/json' + } + }) + expect(res.status).toEqual(401) + }) + it('should inject auth', async () => { const html = await $fetch('/auth') diff --git a/test/fixtures/basic/middleware/abort.global.ts b/test/fixtures/basic/middleware/abort.global.ts new file mode 100644 index 0000000000..efc4f51753 --- /dev/null +++ b/test/fixtures/basic/middleware/abort.global.ts @@ -0,0 +1,7 @@ +export default defineNuxtRouteMiddleware((to) => { + if ('abort' in to.query) { + return abortNavigation({ + statusCode: 401 + }) + } +})