Compare commits

...

26 Commits

Author SHA1 Message Date
Jelmer e9b7394ab5
Merge 81ef3c247d into 73accb5ac1 2024-09-21 13:37:57 +01:00
Daniel Roe 73accb5ac1
fix(kit,vite,webpack): resolve postcss paths from each modules dir (#29096) 2024-09-21 13:37:49 +01:00
Daniel Roe 097105fb2b
fix(kit): try resolving module path from each node_modules dir 2024-09-21 13:37:48 +01:00
Daniel Roe 33e2d0a5f3
fix(kit): handle passing 'bare' relative paths to modules 2024-09-21 13:37:48 +01:00
renovate[bot] 01e00963bc
chore(deps): update all non-major dependencies (main) (#29101) 2024-09-21 12:10:59 +01:00
Matej Černý d970da6da5
docs: add a section about `useRequestFetch` and `event.$fetch` (#29099) 2024-09-21 11:39:54 +01:00
renovate[bot] 61b5ef7850
chore(deps): update all non-major dependencies (main) (#29093) 2024-09-21 09:32:18 +01:00
Matej Černý 00ad2b8233
docs: move custom directories note to the correct place (#29100) 2024-09-21 09:32:00 +01:00
Daniel Roe 81ef3c247d
refactor: warn when setting `useResponseHeader` on client 2024-09-19 15:07:00 +01:00
Daniel Roe f19f208ded
Merge branch 'main' into feat/useResponseHeader 2024-09-19 14:55:25 +01:00
Daniel Roe 529ed0ba00
chore: update `@since` tag 2024-09-19 14:55:09 +01:00
Jelmer e9f29ebb4a
Merge branch 'main' into feat/useResponseHeader 2024-09-17 15:58:30 +02:00
Jelmer cc17923169
Merge branch 'main' into feat/useResponseHeader 2024-09-16 11:52:29 +02:00
Jelmer b92703425a
Merge branch 'main' into feat/useResponseHeader 2024-09-13 18:04:09 +02:00
Jelmer de Maat d9f675af21 Merge branch 'main' of github.com:nuxt/nuxt into feat/useResponseHeader 2024-09-06 09:26:33 +02:00
Jelmer de Maat 269d16e461 feat(composables): add basic test for 'useResponseHeader' composable 2024-09-06 09:26:23 +02:00
Jelmer de Maat f3bbe813d0 Merge branch 'main' of github.com:nuxt/nuxt into feat/useResponseHeader 2024-09-05 12:29:08 +02:00
Jelmer de Maat 7a720df53d Merge branch 'main' of github.com:nuxt/nuxt into feat/useResponseHeader 2024-09-04 22:13:43 +02:00
Jelmer de Maat 4243b2b0ca feat(composables): drop plural "useResponseHeaders" 2024-09-04 22:06:30 +02:00
Jelmer 1f9d07caf0
Merge branch 'main' into feat/useResponseHeader 2024-09-04 21:22:37 +02:00
Jelmer 77e9f2ded9
Merge branch 'main' into feat/useResponseHeader 2024-08-28 12:07:37 +02:00
Jelmer de Maat a982106631 docs(composables): update new useResponseHeader examples 2024-08-23 23:08:08 +02:00
Jelmer de Maat 280443c1e4 Merge branch 'main' into feat/useResponseHeader 2024-08-23 22:48:30 +02:00
Jelmer de Maat 867275c198 feat(composables): change new useResponseHeader composable to return computed value 2024-08-23 22:43:37 +02:00
Jelmer de Maat 22cb24865b docs(composables): document new useResponseHeader and useResponseHeaders composables 2024-05-09 16:22:13 +02:00
Jelmer de Maat cff7f5987a feat(composables): start new useResponseHeader and useResponseHeaders composables 2024-05-09 16:21:04 +02:00
23 changed files with 833 additions and 719 deletions

View File

@ -166,6 +166,10 @@ export default defineNuxtConfig({
})
```
::note
Any nested directories need to be added first as they are scanned in order.
::
## npm Packages
If you want to auto-import components from an npm package, you can use [`addComponent`](/docs/api/kit/components#addcomponent) in a [local module](/docs/guide/directory-structure/modules) to register them.
@ -198,10 +202,6 @@ export default defineNuxtModule({
::
::note
Any nested directories need to be added first as they are scanned in order.
::
## Component Extensions
By default, any file with an extension specified in the [extensions key of `nuxt.config.ts`](/docs/api/nuxt-config#extensions) is treated as a component.

View File

@ -347,6 +347,22 @@ export default defineEventHandler((event) => {
})
```
### Forwarding Context & Headers
By default, neither the headers from the incoming request nor the request context are forwarded when
making fetch requests in server routes. You can use `event.$fetch` to forward the request context and headers when making fetch requests in server routes.
```ts [server/api/forward.ts]
export default defineEventHandler((event) => {
return event.$fetch('/api/forwarded')
})
```
::note
Headers that are **not meant to be forwarded** will **not be included** in the request. These headers include, for example:
`transfer-encoding`, `connection`, `keep-alive`, `upgrade`, `expect`, `host`, `accept`
::
## Advanced Usage
### Nitro Config

View File

@ -0,0 +1,52 @@
---
title: 'useRequestFetch'
description: 'Forward the request context and headers for server-side fetch requests with the useRequestFetch composable.'
links:
- label: Source
icon: i-simple-icons-github
to: https://github.com/nuxt/nuxt/blob/main/packages/nuxt/src/app/composables/ssr.ts
size: xs
---
You can use `useRequestFetch` to forward the request context and headers when making server-side fetch requests.
When making a client-side fetch request, the browser automatically sends the necessary headers.
However, when making a request during server-side rendering, because the request is made on the server, we need to forward the headers manually.
::note
Headers that are **not meant to be forwarded** will **not be included** in the request. These headers include, for example:
`transfer-encoding`, `connection`, `keep-alive`, `upgrade`, `expect`, `host`, `accept`
::
::tip
The [`useFetch`](/docs/api/composables/use-fetch) composable uses `useRequestFetch` under the hood to automatically forward the request context and headers.
::
::code-group
```vue [pages/index.vue]
<script setup lang="ts">
// This will forward the user's headers to the `/api/foo` event handler
// Result: { cookies: { foo: 'bar' } }
const requestFetch = useRequestFetch()
const { data: forwarded } = await useAsyncData(() => requestFetch('/api/cookies'))
// This will NOT forward anything
// Result: { cookies: {} }
const { data: notForwarded } = await useAsyncData(() => $fetch('/api/cookies'))
</script>
```
```ts [server/api/cookies.ts]
export default defineEventHandler((event) => {
const cookies = parseCookies(event)
return { cookies }
})
```
::
::tip
In the browser during client-side navigation, `useRequestFetch` will behave just like regular [`$fetch`](/docs/api/utils/dollarfetch).
::

View File

@ -0,0 +1,44 @@
---
title: "useResponseHeader"
description: "Use useResponseHeader to set a server response header."
links:
- label: Source
icon: i-simple-icons-github
to: https://github.com/nuxt/nuxt/blob/main/packages/nuxt/src/app/composables/ssr.ts
size: xs
---
You can use the built-in [`useResponseHeader`](/docs/api/composables/use-response-header) composable to set any server response header within your pages, components, and plugins.
```ts
// Set the a custom response header
const header = useResponseHeader('X-My-Header');
header.value = 'my-value';
```
## Example
We can use `useResponseHeader` to easily set a response header on a per-page basis.
```vue [pages/test.vue]
<script setup>
// pages/test.vue
const header = useResponseHeader('X-My-Header');
header.value = 'my-value';
</script>
<template>
<h1>Test page with custom header</h1>
<p>The response from the server for this "/test" page will have a custom "X-My-Header" header.</p>
</template>
```
We can use `useResponseHeader` for example in Nuxt [middleware](/docs/guide/directory-structure/middleware) to set a response header for all pages.
```ts [middleware/my-header-middleware.ts]
export default defineNuxtRouteMiddleware((to, from) => {
const header = useResponseHeader('X-My-Always-Header');
header.value = `I'm Always here!`;
});
```

View File

@ -39,9 +39,9 @@
"@nuxt/ui-templates": "workspace:*",
"@nuxt/vite-builder": "workspace:*",
"@nuxt/webpack-builder": "workspace:*",
"@vue/compiler-core": "3.5.6",
"@vue/compiler-dom": "3.5.6",
"@vue/shared": "3.5.6",
"@vue/compiler-core": "3.5.7",
"@vue/compiler-dom": "3.5.7",
"@vue/shared": "3.5.7",
"@types/node": "20.16.5",
"c12": "2.0.0-beta.2",
"h3": "npm:h3-nightly@2.0.0-1718872656.6765a6e",
@ -51,16 +51,16 @@
"nuxt": "workspace:*",
"ohash": "1.1.4",
"postcss": "8.4.47",
"rollup": "4.22.2",
"rollup": "4.22.4",
"send": ">=0.19.0",
"typescript": "5.6.2",
"ufo": "1.5.4",
"unbuild": "3.0.0-rc.7",
"vite": "5.4.6",
"vue": "3.5.6"
"vite": "5.4.7",
"vue": "3.5.7"
},
"devDependencies": {
"@eslint/js": "9.10.0",
"@eslint/js": "9.11.0",
"@nuxt/eslint-config": "0.5.7",
"@nuxt/kit": "workspace:*",
"@nuxt/test-utils": "3.14.2",
@ -81,7 +81,7 @@
"cssnano": "7.0.6",
"destr": "2.0.3",
"devalue": "5.0.0",
"eslint": "9.10.0",
"eslint": "9.11.0",
"eslint-plugin-no-only-tests": "3.3.0",
"eslint-plugin-perfectionist": "3.6.0",
"eslint-typegen": "0.3.2",
@ -93,9 +93,9 @@
"nuxi": "3.13.2",
"nuxt": "workspace:*",
"nuxt-content-twoslash": "0.1.1",
"ofetch": "1.3.4",
"ofetch": "1.4.0",
"pathe": "1.1.2",
"playwright-core": "1.47.1",
"playwright-core": "1.47.2",
"rimraf": "6.0.1",
"semver": "7.6.3",
"sherif": "1.0.0",
@ -106,18 +106,13 @@
"ufo": "1.5.4",
"vitest": "2.1.1",
"vitest-environment-nuxt": "1.0.1",
"vue": "3.5.6",
"vue": "3.5.7",
"vue-router": "4.4.5",
"vue-tsc": "2.1.6"
},
"packageManager": "pnpm@9.10.0",
"packageManager": "pnpm@9.11.0",
"engines": {
"node": "^16.10.0 || >=18.0.0"
},
"version": "",
"pnpm": {
"patchedDependencies": {
"ofetch@1.3.4": "patches/ofetch@1.3.4.patch"
}
}
"version": ""
}

View File

@ -52,7 +52,7 @@
"@types/semver": "7.5.8",
"nitro": "npm:nitro-nightly@3.0.0-beta-28665895.e727afda",
"unbuild": "3.0.0-rc.7",
"vite": "5.4.6",
"vite": "5.4.7",
"vitest": "2.1.1",
"webpack": "5.94.0"
},

View File

@ -79,27 +79,30 @@ export async function loadNuxtModuleInstance (nuxtModule: string | NuxtModule, n
// Import if input is string
if (typeof nuxtModule === 'string') {
const paths = [join(nuxtModule, 'nuxt'), join(nuxtModule, 'module'), nuxtModule]
let error: unknown
for (const path of paths) {
try {
const src = jiti.esmResolve(path)
nuxtModule = await jiti.import(src) as NuxtModule
const paths = [join(nuxtModule, 'nuxt'), join(nuxtModule, 'module'), nuxtModule, join(nuxt.options.rootDir, nuxtModule)]
// nuxt-module-builder generates a module.json with metadata including the version
const moduleMetadataPath = join(dirname(src), 'module.json')
if (existsSync(moduleMetadataPath)) {
buildTimeModuleMeta = JSON.parse(await fsp.readFile(moduleMetadataPath, 'utf-8'))
for (const parentURL of nuxt.options.modulesDir) {
for (const path of paths) {
try {
const src = jiti.esmResolve(path, { parentURL })
nuxtModule = await jiti.import(src) as NuxtModule
// nuxt-module-builder generates a module.json with metadata including the version
const moduleMetadataPath = join(dirname(src), 'module.json')
if (existsSync(moduleMetadataPath)) {
buildTimeModuleMeta = JSON.parse(await fsp.readFile(moduleMetadataPath, 'utf-8'))
}
break
} catch (error: unknown) {
const code = (error as Error & { code?: string }).code
if (code === 'MODULE_NOT_FOUND' || code === 'ERR_PACKAGE_PATH_NOT_EXPORTED' || code === 'ERR_MODULE_NOT_FOUND' || code === 'ERR_UNSUPPORTED_DIR_IMPORT') {
continue
}
logger.error(`Error while importing module \`${nuxtModule}\`: ${error}`)
throw error
}
break
} catch (_err: unknown) {
error = _err
continue
}
}
if (typeof nuxtModule !== 'function' && error) {
logger.error(`Error while importing module \`${nuxtModule}\`: ${error}`)
throw error
if (typeof nuxtModule !== 'string') { break }
}
}

View File

@ -60,7 +60,7 @@
},
"dependencies": {
"@nuxt/devalue": "^2.0.2",
"@nuxt/devtools": "^1.4.2",
"@nuxt/devtools": "^1.5.0",
"@nuxt/kit": "workspace:*",
"@nuxt/schema": "workspace:*",
"@nuxt/telemetry": "^2.6.0",
@ -69,7 +69,7 @@
"@unhead/shared": "^1.11.6",
"@unhead/ssr": "^1.11.6",
"@unhead/vue": "^1.11.6",
"@vue/shared": "^3.5.6",
"@vue/shared": "^3.5.7",
"acorn": "8.12.1",
"c12": "^2.0.0-beta.2",
"chokidar": "^3.6.0",
@ -97,7 +97,7 @@
"nitro": "npm:nitro-nightly@3.0.0-beta-28665895.e727afda",
"nuxi": "^3.13.2",
"nypm": "^0.3.11",
"ofetch": "^1.3.4",
"ofetch": "^1.4.0",
"ohash": "^1.1.4",
"pathe": "^1.1.2",
"perfect-debounce": "^1.0.0",
@ -119,7 +119,7 @@
"unplugin-vue-router": "^0.10.8",
"unstorage": "^1.12.0",
"untyped": "^1.4.2",
"vue": "^3.5.6",
"vue": "^3.5.7",
"vue-bundle-renderer": "^2.1.0",
"vue-devtools-stub": "^0.1.0",
"vue-router": "^4.4.5"
@ -130,9 +130,9 @@
"@parcel/watcher": "2.4.1",
"@types/estree": "1.0.6",
"@vitejs/plugin-vue": "5.1.4",
"@vue/compiler-sfc": "3.5.6",
"@vue/compiler-sfc": "3.5.7",
"unbuild": "3.0.0-rc.7",
"vite": "5.4.6",
"vite": "5.4.7",
"vitest": "2.1.1"
},
"peerDependencies": {

View File

@ -24,7 +24,7 @@ export { useFetch, useLazyFetch } from './fetch'
export type { FetchResult, UseFetchOptions } from './fetch'
export { useCookie, refreshCookie } from './cookie'
export type { CookieOptions, CookieRef } from './cookie'
export { onPrehydrate, prerenderRoutes, useRequestHeaders, useRequestEvent, useRequestFetch, setResponseStatus } from './ssr'
export { onPrehydrate, prerenderRoutes, useRequestHeaders, useRequestEvent, useRequestFetch, setResponseStatus, useResponseHeader } from './ssr'
export { onNuxtReady } from './ready'
export { abortNavigation, addRouteMiddleware, defineNuxtRouteMiddleware, onBeforeRouteLeave, onBeforeRouteUpdate, setPageLayout, navigateTo, useRoute, useRouter } from './router'
export type { AddRouteMiddlewareOptions, RouteMiddleware } from './router'

View File

@ -1,6 +1,6 @@
import type { H3Event } from 'h3'
import { setResponseStatus as _setResponseStatus, appendHeader, getRequestHeader, getRequestHeaders } from 'h3'
import { getCurrentInstance } from 'vue'
import { setResponseStatus as _setResponseStatus, appendHeader, getRequestHeader, getRequestHeaders, getResponseHeader, removeResponseHeader, setResponseHeader } from 'h3'
import { computed, getCurrentInstance, ref } from 'vue'
import { useServerHead } from '@unhead/vue'
import type { NuxtApp } from '../nuxt'
@ -61,6 +61,43 @@ export function setResponseStatus (arg1: H3Event | number | undefined, arg2?: nu
}
}
/** @since 3.14.0 */
export function useResponseHeader (header: string) {
if (import.meta.client) {
if (import.meta.dev) {
return computed({
get: () => undefined,
set: () => console.warn('[nuxt] Setting response headers is not supported in the browser.'),
})
}
return ref()
}
const event = useRequestEvent()
if (!event) {
if (import.meta.dev) {
return computed({
get: () => undefined,
set: () => console.warn('[nuxt] Setting response headers is not supported in the browser.'),
})
}
return ref()
}
return computed({
get () {
return getResponseHeader(event, header)
},
set (newValue) {
if (!newValue) {
return removeResponseHeader(event, header)
}
return setResponseHeader(event, header, newValue)
},
})
}
/** @since 3.8.0 */
export function prerenderRoutes (path: string | string[]) {
if (!import.meta.server || !import.meta.prerender) { return }

View File

@ -1,7 +1,7 @@
export { applyPlugin, applyPlugins, callWithNuxt, createNuxtApp, defineAppConfig, defineNuxtPlugin, definePayloadPlugin, isNuxtPlugin, registerPluginHooks, tryUseNuxtApp, useNuxtApp, useRuntimeConfig } from './nuxt'
export type { CreateOptions, NuxtApp, NuxtPayload, NuxtPluginIndicator, NuxtSSRContext, ObjectPlugin, Plugin, PluginEnvContext, PluginMeta, ResolvedPluginMeta, RuntimeNuxtHooks } from './nuxt'
export { defineNuxtComponent, useAsyncData, useLazyAsyncData, useNuxtData, refreshNuxtData, clearNuxtData, useHydration, callOnce, useState, clearNuxtState, clearError, createError, isNuxtError, showError, useError, useFetch, useLazyFetch, useCookie, refreshCookie, onPrehydrate, prerenderRoutes, useRequestHeaders, useRequestEvent, useRequestFetch, setResponseStatus, onNuxtReady, abortNavigation, addRouteMiddleware, defineNuxtRouteMiddleware, onBeforeRouteLeave, onBeforeRouteUpdate, setPageLayout, navigateTo, useRoute, useRouter, preloadComponents, prefetchComponents, preloadRouteComponents, isPrerendered, loadPayload, preloadPayload, definePayloadReducer, definePayloadReviver, getAppManifest, getRouteRules, reloadNuxtApp, useRequestURL, usePreviewMode, useId, useRouteAnnouncer, useHead, useSeoMeta, useServerSeoMeta } from './composables/index'
export { defineNuxtComponent, useAsyncData, useLazyAsyncData, useNuxtData, refreshNuxtData, clearNuxtData, useHydration, callOnce, useState, clearNuxtState, clearError, createError, isNuxtError, showError, useError, useFetch, useLazyFetch, useCookie, refreshCookie, onPrehydrate, prerenderRoutes, useRequestHeaders, useRequestEvent, useRequestFetch, setResponseStatus, useResponseHeader, onNuxtReady, abortNavigation, addRouteMiddleware, defineNuxtRouteMiddleware, onBeforeRouteLeave, onBeforeRouteUpdate, setPageLayout, navigateTo, useRoute, useRouter, preloadComponents, prefetchComponents, preloadRouteComponents, isPrerendered, loadPayload, preloadPayload, definePayloadReducer, definePayloadReviver, getAppManifest, getRouteRules, reloadNuxtApp, useRequestURL, usePreviewMode, useId, useRouteAnnouncer, useHead, useSeoMeta, useServerSeoMeta } from './composables/index'
export type { AddRouteMiddlewareOptions, AsyncData, AsyncDataOptions, AsyncDataRequestStatus, CookieOptions, CookieRef, FetchResult, NuxtAppManifest, NuxtAppManifestMeta, NuxtError, ReloadNuxtAppOptions, RouteMiddleware, UseFetchOptions } from './composables/index'
export { defineNuxtLink } from './components/index'

View File

@ -66,7 +66,7 @@ const granularAppPresets: InlinePreset[] = [
from: '#app/composables/cookie',
},
{
imports: ['onPrehydrate', 'prerenderRoutes', 'useRequestHeader', 'useRequestHeaders', 'useRequestEvent', 'useRequestFetch', 'setResponseStatus'],
imports: ['onPrehydrate', 'prerenderRoutes', 'useRequestHeader', 'useRequestHeaders', 'useResponseHeader', 'useRequestEvent', 'useRequestFetch', 'setResponseStatus'],
from: '#app/composables/ssr',
},
{

View File

@ -42,20 +42,20 @@
"@unhead/schema": "1.11.6",
"@vitejs/plugin-vue": "5.1.4",
"@vitejs/plugin-vue-jsx": "4.0.1",
"@vue/compiler-core": "3.5.6",
"@vue/compiler-sfc": "3.5.6",
"@vue/compiler-core": "3.5.7",
"@vue/compiler-sfc": "3.5.7",
"@vue/language-core": "2.1.6",
"c12": "2.0.0-beta.2",
"esbuild-loader": "4.2.2",
"h3": "npm:h3-nightly@2.0.0-1718872656.6765a6e",
"ignore": "6.0.2",
"nitro": "npm:nitro-nightly@3.0.0-beta-28665895.e727afda",
"ofetch": "1.3.4",
"ofetch": "1.4.0",
"unbuild": "3.0.0-rc.7",
"unctx": "2.3.1",
"unenv": "1.10.0",
"vite": "5.4.6",
"vue": "3.5.6",
"vite": "5.4.7",
"vue": "3.5.7",
"vue-bundle-renderer": "2.1.0",
"vue-loader": "17.4.2",
"vue-router": "4.4.5",

View File

@ -30,6 +30,6 @@
"tinyexec": "0.3.0",
"tinyglobby": "0.2.6",
"unocss": "0.62.4",
"vite": "5.4.6"
"vite": "5.4.7"
}
}

View File

@ -27,9 +27,9 @@
"@nuxt/schema": "workspace:*",
"@types/clear": "0.1.4",
"@types/estree": "1.0.6",
"rollup": "4.22.2",
"rollup": "4.22.4",
"unbuild": "3.0.0-rc.7",
"vue": "3.5.6"
"vue": "3.5.7"
},
"dependencies": {
"@nuxt/kit": "workspace:*",
@ -62,7 +62,7 @@
"ufo": "^1.5.4",
"unenv": "^1.10.0",
"unplugin": "^1.14.1",
"vite": "^5.4.6",
"vite": "^5.4.7",
"vite-node": "^2.1.1",
"vite-plugin-checker": "^0.8.0",
"vue-bundle-renderer": "^2.1.0"

View File

@ -27,11 +27,16 @@ export async function resolveCSSOptions (nuxt: Nuxt): Promise<ViteConfig['css']>
const pluginOptions = postcssOptions.plugins[pluginName]
if (!pluginOptions) { continue }
const path = jiti.esmResolve(pluginName)
const pluginFn = (await jiti.import(path)) as (opts: Record<string, any>) => Plugin
if (typeof pluginFn === 'function') {
css.postcss.plugins.push(pluginFn(pluginOptions))
} else {
let pluginFn: ((opts: Record<string, any>) => Plugin) | undefined
for (const parentURL of nuxt.options.modulesDir) {
pluginFn = await jiti.import(pluginName, { parentURL, try: true }) as (opts: Record<string, any>) => Plugin
if (typeof pluginFn === 'function') {
css.postcss.plugins.push(pluginFn(pluginOptions))
break
}
}
if (typeof pluginFn !== 'function') {
console.warn(`[nuxt] could not import postcss plugin \`${pluginName}\`. Please report this as a bug.`)
}
}

View File

@ -7,7 +7,6 @@ export const viteNodeOptions = JSON.parse(process.env.NUXT_VITE_NODE_OPTIONS ||
export const viteNodeFetch = $fetch.create({
baseURL: viteNodeOptions.baseURL,
// @ts-expect-error https://github.com/node-fetch/node-fetch#custom-agent
agent: viteNodeOptions.baseURL.startsWith('https://')
? new HTTPSAgent({ rejectUnauthorized: false })
: null,

View File

@ -78,9 +78,9 @@
"@types/pify": "5.0.4",
"@types/webpack-bundle-analyzer": "4.7.0",
"@types/webpack-hot-middleware": "2.25.9",
"rollup": "4.22.2",
"rollup": "4.22.4",
"unbuild": "3.0.0-rc.7",
"vue": "3.5.6"
"vue": "3.5.7"
},
"peerDependencies": {
"vue": "^3.3.4"

View File

@ -49,11 +49,16 @@ export async function getPostcssConfig (nuxt: Nuxt) {
const pluginOptions = postcssOptions.plugins[pluginName]
if (!pluginOptions) { continue }
const path = jiti.esmResolve(pluginName)
const pluginFn = (await jiti.import(path)) as (opts: Record<string, any>) => Plugin
if (typeof pluginFn === 'function') {
plugins.push(pluginFn(pluginOptions))
} else {
let pluginFn: ((opts: Record<string, any>) => Plugin) | undefined
for (const parentURL of nuxt.options.modulesDir) {
pluginFn = await jiti.import(pluginName, { parentURL, try: true }) as (opts: Record<string, any>) => Plugin
if (typeof pluginFn === 'function') {
plugins.push(pluginFn(pluginOptions))
break
}
}
if (typeof pluginFn !== 'function') {
console.warn(`[nuxt] could not import postcss plugin \`${pluginName}\`. Please report this as a bug.`)
}
}

View File

@ -1,33 +0,0 @@
diff --git a/dist/node.d.cts b/dist/node.d.cts
index d3a39ff53717d267ff4581af714533ff7229799c..4e3db1f3d6defb7b0c40d11589c0ff6cb8391ad5 100644
--- a/dist/node.d.cts
+++ b/dist/node.d.cts
@@ -1,5 +1,5 @@
import { $ as $Fetch } from './shared/ofetch.8459ad38.cjs';
-export { F as FetchError, c as createFetch, a as createFetchError } from './shared/ofetch.8459ad38.cjs';
+export { C as CreateFetchOptions, g as Fetch, b as FetchContext, F as FetchError, d as FetchOptions, h as FetchRequest, f as FetchResponse, G as GlobalOptions, I as IFetchError, M as MappedResponseType, R as ResponseMap, e as ResponseType, S as SearchParameters, c as createFetch, a as createFetchError } from './shared/ofetch.8459ad38.mjs';
declare function createNodeFetch(): (input: RequestInfo, init?: RequestInit) => any;
declare const fetch: typeof globalThis.fetch;
diff --git a/dist/node.d.mts b/dist/node.d.mts
index 3d8b330375ce60178c05292179ec8bac764ae516..bdcc322bd8554fc7e61d5d9760cb9991560560eb 100644
--- a/dist/node.d.mts
+++ b/dist/node.d.mts
@@ -1,5 +1,5 @@
import { $ as $Fetch } from './shared/ofetch.8459ad38.mjs';
-export { F as FetchError, c as createFetch, a as createFetchError } from './shared/ofetch.8459ad38.mjs';
+export { C as CreateFetchOptions, g as Fetch, b as FetchContext, F as FetchError, d as FetchOptions, h as FetchRequest, f as FetchResponse, G as GlobalOptions, I as IFetchError, M as MappedResponseType, R as ResponseMap, e as ResponseType, S as SearchParameters, c as createFetch, a as createFetchError } from './shared/ofetch.8459ad38.mjs';
declare function createNodeFetch(): (input: RequestInfo, init?: RequestInit) => any;
declare const fetch: typeof globalThis.fetch;
diff --git a/dist/node.d.ts b/dist/node.d.ts
index 6a5419d1939000a15958b362f44bf49fb1800207..4b319d2c3051e966274268670e243c5f99e2904d 100644
--- a/dist/node.d.ts
+++ b/dist/node.d.ts
@@ -1,5 +1,5 @@
import { $ as $Fetch } from './shared/ofetch.8459ad38.js';
-export { F as FetchError, c as createFetch, a as createFetchError } from './shared/ofetch.8459ad38.js';
+export { C as CreateFetchOptions, g as Fetch, b as FetchContext, F as FetchError, d as FetchOptions, h as FetchRequest, f as FetchResponse, G as GlobalOptions, I as IFetchError, M as MappedResponseType, R as ResponseMap, e as ResponseType, S as SearchParameters, c as createFetch, a as createFetchError } from './shared/ofetch.8459ad38.mjs';
declare function createNodeFetch(): (input: RequestInfo, init?: RequestInit) => any;
declare const fetch: typeof globalThis.fetch;

File diff suppressed because it is too large Load Diff

View File

@ -37,10 +37,10 @@ describe.skipIf(process.env.SKIP_BUNDLE_SIZE === 'true' || process.env.ECOSYSTEM
const serverDir = join(rootDir, '.output/server')
const serverStats = await analyzeSizes(['**/*.mjs', '!node_modules'], serverDir)
expect.soft(roundToKilobytes(serverStats.totalBytes)).toMatchInlineSnapshot(`"207k"`)
expect.soft(roundToKilobytes(serverStats.totalBytes)).toMatchInlineSnapshot(`"208k"`)
const modules = await analyzeSizes(['node_modules/**/*'], serverDir)
expect.soft(roundToKilobytes(modules.totalBytes)).toMatchInlineSnapshot(`"1387k"`)
expect.soft(roundToKilobytes(modules.totalBytes)).toMatchInlineSnapshot(`"1388k"`)
const packages = modules.files
.filter(m => m.endsWith('package.json'))
@ -78,7 +78,7 @@ describe.skipIf(process.env.SKIP_BUNDLE_SIZE === 'true' || process.env.ECOSYSTEM
const serverDir = join(rootDir, '.output-inline/server')
const serverStats = await analyzeSizes(['**/*.mjs', '!node_modules'], serverDir)
expect.soft(roundToKilobytes(serverStats.totalBytes)).toMatchInlineSnapshot(`"555k"`)
expect.soft(roundToKilobytes(serverStats.totalBytes)).toMatchInlineSnapshot(`"557k"`)
const modules = await analyzeSizes(['node_modules/**/*'], serverDir)
expect.soft(roundToKilobytes(modules.totalBytes)).toMatchInlineSnapshot(`"88.2k"`)

View File

@ -12,7 +12,7 @@ import * as composables from '#app/composables'
import { clearNuxtData, refreshNuxtData, useAsyncData, useNuxtData } from '#app/composables/asyncData'
import { clearError, createError, isNuxtError, showError, useError } from '#app/composables/error'
import { onNuxtReady } from '#app/composables/ready'
import { setResponseStatus, useRequestEvent, useRequestFetch, useRequestHeaders } from '#app/composables/ssr'
import { setResponseStatus, useRequestEvent, useRequestFetch, useRequestHeaders, useResponseHeader } from '#app/composables/ssr'
import { clearNuxtState, useState } from '#app/composables/state'
import { useRequestURL } from '#app/composables/url'
import { getAppManifest, getRouteRules } from '#app/composables/manifest'
@ -83,6 +83,7 @@ describe('composables', () => {
'useRequestFetch',
'isPrerendered',
'useRequestHeaders',
'useResponseHeader',
'useCookie',
'clearNuxtState',
'useState',
@ -394,6 +395,7 @@ describe('ssr composables', () => {
expect(useRequestFetch()).toEqual($fetch)
expect(useRequestHeaders()).toEqual({})
expect(prerenderRoutes('/')).toBeUndefined()
expect(useResponseHeader('x-test').value).toBeUndefined()
})
})