From 11a5a3e14f739761fd4ad65e60290b3abc7a9692 Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 16 Jun 2021 20:42:58 +0800 Subject: [PATCH] feat(app): make `asyncData` working with ` ``` +When using with the ` + + +``` + diff --git a/examples/async-data-setup/nuxt.config.ts b/examples/async-data-setup/nuxt.config.ts new file mode 100644 index 0000000000..e50dc842b0 --- /dev/null +++ b/examples/async-data-setup/nuxt.config.ts @@ -0,0 +1,5 @@ +import { defineNuxtConfig } from '@nuxt/kit' + +export default defineNuxtConfig({ + // vite: true +}) diff --git a/examples/async-data-setup/package.json b/examples/async-data-setup/package.json new file mode 100644 index 0000000000..a58dd374f1 --- /dev/null +++ b/examples/async-data-setup/package.json @@ -0,0 +1,12 @@ +{ + "name": "example-async-data-setup", + "private": true, + "devDependencies": { + "nuxt3": "latest" + }, + "scripts": { + "dev": "nu dev", + "build": "nu build", + "start": "node .output/server" + } +} diff --git a/examples/async-data-setup/pages/index.vue b/examples/async-data-setup/pages/index.vue new file mode 100644 index 0000000000..1267e3f011 --- /dev/null +++ b/examples/async-data-setup/pages/index.vue @@ -0,0 +1,12 @@ + + + diff --git a/examples/async-data-setup/server/api/count.js b/examples/async-data-setup/server/api/count.js new file mode 100644 index 0000000000..678b2b2700 --- /dev/null +++ b/examples/async-data-setup/server/api/count.js @@ -0,0 +1,3 @@ +let ctr = 0 + +export default () => ({ count: ++ctr }) diff --git a/packages/vite/src/client.ts b/packages/vite/src/client.ts index fc8a85046f..d723e0c29f 100644 --- a/packages/vite/src/client.ts +++ b/packages/vite/src/client.ts @@ -4,6 +4,7 @@ import vitePlugin from '@vitejs/plugin-vue' import { cacheDirPlugin } from './plugins/cache-dir' import { replace } from './plugins/replace' import { ViteBuildContext, ViteOptions } from './vite' +import { transformNuxtSetup } from './plugins/transformSetup' export async function buildClient (ctx: ViteBuildContext) { const clientConfig: vite.InlineConfig = vite.mergeConfig(ctx.config, { @@ -23,7 +24,8 @@ export async function buildClient (ctx: ViteBuildContext) { plugins: [ replace({ 'process.env': 'import.meta.env' }), cacheDirPlugin(ctx.nuxt.options.rootDir, 'client'), - vitePlugin(ctx.config.vue) + vitePlugin(ctx.config.vue), + transformNuxtSetup() ], server: { middlewareMode: true diff --git a/packages/vite/src/plugins/transformSetup.ts b/packages/vite/src/plugins/transformSetup.ts new file mode 100644 index 0000000000..81400684a1 --- /dev/null +++ b/packages/vite/src/plugins/transformSetup.ts @@ -0,0 +1,31 @@ +import type { Plugin } from 'vite' +import { getQuery } from 'ufo' +import MagicString from 'magic-string' + +const DEFINE_COMPONENT_VUE = '_defineComponent(' +const DEFINE_COMPONENT_NUXT = '_defineNuxtComponent(' + +export function transformNuxtSetup () { + return { + name: 'nuxt:transform-setup', + transform (code, id) { + const query = getQuery(id) + if (!(id.endsWith('.vue') || (query.nuxt && query.setup && query.type === 'script'))) { + return + } + + const index = code.indexOf(DEFINE_COMPONENT_VUE) + if (index < 0) { + return + } + + const s = new MagicString(code) + s.overwrite(index, index + DEFINE_COMPONENT_VUE.length, DEFINE_COMPONENT_NUXT) + s.prepend('import { defineNuxtComponent as _defineNuxtComponent } from "@nuxt/app"\n') + return { + code: s.toString(), + map: s.generateMap() + } + } + } +} diff --git a/packages/vite/src/server.ts b/packages/vite/src/server.ts index ef64176241..a86c2dcb4c 100644 --- a/packages/vite/src/server.ts +++ b/packages/vite/src/server.ts @@ -7,6 +7,7 @@ import consola from 'consola' import { ViteBuildContext, ViteOptions } from './vite' import { wpfs } from './utils/wpfs' import { cacheDirPlugin } from './plugins/cache-dir' +import { transformNuxtSetup } from './plugins/transformSetup' export async function buildServer (ctx: ViteBuildContext) { const serverConfig: vite.InlineConfig = vite.mergeConfig(ctx.config, { @@ -41,7 +42,8 @@ export async function buildServer (ctx: ViteBuildContext) { }, plugins: [ cacheDirPlugin(ctx.nuxt.options.rootDir, 'server'), - vuePlugin() + vuePlugin(), + transformNuxtSetup() ] } as ViteOptions) diff --git a/packages/webpack/build.config.ts b/packages/webpack/build.config.ts index b80af3a8bb..bb6ef44860 100644 --- a/packages/webpack/build.config.ts +++ b/packages/webpack/build.config.ts @@ -3,7 +3,8 @@ import { defineBuildConfig } from 'unbuild' export default defineBuildConfig({ declaration: false, entries: [ - 'src/index' + 'src/index', + 'src/loaders/nuxt-setup' ], dependencies: [ '@nuxt/kit', diff --git a/packages/webpack/src/loaders/nuxt-setup.ts b/packages/webpack/src/loaders/nuxt-setup.ts new file mode 100644 index 0000000000..b8b0092275 --- /dev/null +++ b/packages/webpack/src/loaders/nuxt-setup.ts @@ -0,0 +1,10 @@ +const DEFINE_COMPONENT_VUE = '_defineComponent(' +const DEFINE_COMPONENT_NUXT = '_defineNuxtComponent(' + +export default function NuxtSetupLoader (code: string) { + if (code && code.includes(DEFINE_COMPONENT_VUE)) { + // TODO: Add sourcemap hints + code = 'import { defineNuxtComponent as _defineNuxtComponent } from "@nuxt/app"\n' + code.replace(DEFINE_COMPONENT_VUE, DEFINE_COMPONENT_NUXT) + } + return code +} diff --git a/packages/webpack/src/plugins/transform-setup.ts b/packages/webpack/src/plugins/transform-setup.ts new file mode 100644 index 0000000000..f583c5bb2d --- /dev/null +++ b/packages/webpack/src/plugins/transform-setup.ts @@ -0,0 +1,17 @@ +import { getQuery } from 'ufo' + +export default class NuxtSetupTransformerPlugin { + apply (compiler) { + compiler.options.module.rules.push({ + include (id) { + const query = getQuery(id) + return id.endsWith('.vue') || (query.nuxt && query.setup && query.type === 'script') + }, + enforce: 'post', + use: [{ + ident: 'NuxtSetupTransformerPlugin', + loader: require.resolve('@nuxt/webpack-builder/dist/nuxt-setup') + }] + }) + } +} diff --git a/packages/webpack/src/presets/vue.ts b/packages/webpack/src/presets/vue.ts index 06bfcc2620..ae8560a21d 100644 --- a/packages/webpack/src/presets/vue.ts +++ b/packages/webpack/src/presets/vue.ts @@ -1,6 +1,7 @@ import { resolve } from 'path' import VueLoaderPlugin from 'vue-loader/dist/pluginWebpack5' import { DefinePlugin } from 'webpack' +import NuxtSetupTransformerPlugin from '../plugins/transform-setup' import VueSSRClientPlugin from '../plugins/vue/client' import VueSSRServerPlugin from '../plugins/vue/server' import { WebpackConfigContext } from '../utils/config' @@ -26,6 +27,8 @@ export function vue (ctx: WebpackConfigContext) { })) } + config.plugins.push(new NuxtSetupTransformerPlugin()) + // Feature flags // https://github.com/vuejs/vue-next/tree/master/packages/vue#bundler-build-feature-flags // TODO: Provide options to toggle diff --git a/yarn.lock b/yarn.lock index a2fcd62aaa..977f07a9fd 100644 --- a/yarn.lock +++ b/yarn.lock @@ -5957,6 +5957,14 @@ __metadata: languageName: node linkType: hard +"example-async-data-setup@workspace:examples/async-data-setup": + version: 0.0.0-use.local + resolution: "example-async-data-setup@workspace:examples/async-data-setup" + dependencies: + nuxt3: latest + languageName: unknown + linkType: soft + "example-async-data@workspace:examples/async-data": version: 0.0.0-use.local resolution: "example-async-data@workspace:examples/async-data"