mirror of
https://github.com/nuxt/nuxt.git
synced 2024-11-11 08:33:53 +00:00
fix: sanitize import filenames in generated imports (#2216)
This commit is contained in:
parent
614e87e9f0
commit
29171bd105
@ -38,6 +38,7 @@
|
|||||||
"globby": "^13.1.1",
|
"globby": "^13.1.1",
|
||||||
"h3": "^0.3.9",
|
"h3": "^0.3.9",
|
||||||
"hash-sum": "^2.0.0",
|
"hash-sum": "^2.0.0",
|
||||||
|
"knitwork": "^0.1.0",
|
||||||
"magic-string": "^0.25.7",
|
"magic-string": "^0.25.7",
|
||||||
"mlly": "^0.4.1",
|
"mlly": "^0.4.1",
|
||||||
"murmurhash-es": "^0.1.1",
|
"murmurhash-es": "^0.1.1",
|
||||||
|
@ -2,6 +2,7 @@ import hash from 'hash-sum'
|
|||||||
import { resolve } from 'pathe'
|
import { resolve } from 'pathe'
|
||||||
|
|
||||||
import type { Nuxt, NuxtApp } from '@nuxt/schema'
|
import type { Nuxt, NuxtApp } from '@nuxt/schema'
|
||||||
|
import { genImport, genObjectFromRawEntries } from 'knitwork'
|
||||||
|
|
||||||
type TemplateContext = {
|
type TemplateContext = {
|
||||||
nuxt: Nuxt;
|
nuxt: Nuxt;
|
||||||
@ -24,10 +25,8 @@ export const middlewareTemplate = {
|
|||||||
id: m.name || m.src.replace(/[\\/]/g, '/').replace(/\.(js|ts)$/, '')
|
id: m.name || m.src.replace(/[\\/]/g, '/').replace(/\.(js|ts)$/, '')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
return `${_middleware.map(m => `import $${hash(m.id)} from '${m.filePath}'`).join('\n')}
|
return `${_middleware.map(m => genImport(m.filePath, `$${hash(m.id)}`)).join('\n')}
|
||||||
const middleware = {
|
const middleware = ${genObjectFromRawEntries(_middleware.map(m => [m.id, `$${hash(m.id)}`]))}
|
||||||
${_middleware.map(m => ` ['${m.id}']: $${hash(m.id)}`).join(',\n')}
|
|
||||||
}
|
|
||||||
export default middleware`
|
export default middleware`
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -49,14 +48,12 @@ export const storeTemplate = {
|
|||||||
|
|
||||||
return `import Vue from 'vue'
|
return `import Vue from 'vue'
|
||||||
import Vuex from 'vuex'
|
import Vuex from 'vuex'
|
||||||
${_storeModules.map(s => `import * as $${hash(s.id)} from '${s.filePath}'`).join('\n')}
|
${_storeModules.map(s => genImport(s.filePath, { name: '*', as: `$${hash(s.id)}` })).join('\n')}
|
||||||
Vue.use(Vuex)
|
Vue.use(Vuex)
|
||||||
|
|
||||||
const VUEX_PROPERTIES = ['state', 'getters', 'actions', 'mutations']
|
const VUEX_PROPERTIES = ['state', 'getters', 'actions', 'mutations']
|
||||||
|
|
||||||
const storeModules = {
|
const storeModules = ${genObjectFromRawEntries(_storeModules.map(m => [m.id, `$${hash(m.id)}`]))}
|
||||||
${_storeModules.map(m => ` ['${m.id}']: $${hash(m.id)}`).join(',\n')}
|
|
||||||
}
|
|
||||||
|
|
||||||
export function createStore() {
|
export function createStore() {
|
||||||
let store = normalizeRoot(storeModules.root || {})
|
let store = normalizeRoot(storeModules.root || {})
|
||||||
|
@ -20,6 +20,7 @@
|
|||||||
"globby": "^13.1.1",
|
"globby": "^13.1.1",
|
||||||
"hash-sum": "^2.0.0",
|
"hash-sum": "^2.0.0",
|
||||||
"jiti": "^1.12.15",
|
"jiti": "^1.12.15",
|
||||||
|
"knitwork": "^0.1.0",
|
||||||
"lodash.template": "^4.5.0",
|
"lodash.template": "^4.5.0",
|
||||||
"mlly": "^0.4.1",
|
"mlly": "^0.4.1",
|
||||||
"pathe": "^0.2.0",
|
"pathe": "^0.2.0",
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import { pascalCase, kebabCase } from 'scule'
|
import { pascalCase, kebabCase } from 'scule'
|
||||||
import type { ComponentsDir, Component } from '@nuxt/schema'
|
import type { ComponentsDir, Component } from '@nuxt/schema'
|
||||||
|
import { genDynamicImport } from 'knitwork'
|
||||||
import { useNuxt } from './context'
|
import { useNuxt } from './context'
|
||||||
import { assertNuxtCompatibility } from './compatibility'
|
import { assertNuxtCompatibility } from './compatibility'
|
||||||
|
|
||||||
@ -43,8 +44,8 @@ export async function addComponent (opts: AddComponentOptions) {
|
|||||||
shortPath: opts.filePath,
|
shortPath: opts.filePath,
|
||||||
async: false,
|
async: false,
|
||||||
level: 0,
|
level: 0,
|
||||||
asyncImport: `() => import('${opts.filePath}').then(r => r['${opts.export || 'default'}'])`,
|
asyncImport: `${genDynamicImport(opts.filePath)}.then(r => r['${opts.export || 'default'}'])`,
|
||||||
import: `require('${opts.filePath}')['${opts.export || 'default'}']`,
|
import: `require(${JSON.stringify(opts.filePath)})['${opts.export || 'default'}']`,
|
||||||
|
|
||||||
...opts
|
...opts
|
||||||
}
|
}
|
||||||
|
@ -3,6 +3,7 @@ import lodashTemplate from 'lodash.template'
|
|||||||
import hash from 'hash-sum'
|
import hash from 'hash-sum'
|
||||||
import { camelCase } from 'scule'
|
import { camelCase } from 'scule'
|
||||||
import { basename, extname } from 'pathe'
|
import { basename, extname } from 'pathe'
|
||||||
|
import { genDynamicImport, genImport } from 'knitwork'
|
||||||
|
|
||||||
import type { NuxtTemplate } from '@nuxt/schema'
|
import type { NuxtTemplate } from '@nuxt/schema'
|
||||||
|
|
||||||
@ -23,7 +24,7 @@ export async function compileTemplate (template: NuxtTemplate, ctx: any) {
|
|||||||
throw new Error('Invalid template: ' + JSON.stringify(template))
|
throw new Error('Invalid template: ' + JSON.stringify(template))
|
||||||
}
|
}
|
||||||
|
|
||||||
const serialize = (data: any) => JSON.stringify(data, null, 2).replace(/"{(.+)}"/g, '$1')
|
const serialize = (data: any) => JSON.stringify(data, null, 2).replace(/"{(.+)}"(?=,?$)/gm, r => JSON.parse(r).replace(/^{(.*)}$/, '$1'))
|
||||||
|
|
||||||
const importName = (src: string) => `${camelCase(basename(src, extname(src))).replace(/[^a-zA-Z?\d\s:]/g, '')}_${hash(src)}`
|
const importName = (src: string) => `${camelCase(basename(src, extname(src))).replace(/[^a-zA-Z?\d\s:]/g, '')}_${hash(src)}`
|
||||||
|
|
||||||
@ -33,9 +34,9 @@ const importSources = (sources: string | string[], { lazy = false } = {}) => {
|
|||||||
}
|
}
|
||||||
return sources.map((src) => {
|
return sources.map((src) => {
|
||||||
if (lazy) {
|
if (lazy) {
|
||||||
return `const ${importName(src)} = () => import('${src}' /* webpackChunkName: '${src}' */)`
|
return `const ${importName(src)} = ${genDynamicImport(src, { comment: `webpackChunkName: ${JSON.stringify(src)}` })}`
|
||||||
}
|
}
|
||||||
return `import ${importName(src)} from '${src}'`
|
return genImport(src, importName(src))
|
||||||
}).join('\n')
|
}).join('\n')
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -48,6 +48,7 @@
|
|||||||
"http-proxy": "^1.18.1",
|
"http-proxy": "^1.18.1",
|
||||||
"is-primitive": "^3.0.1",
|
"is-primitive": "^3.0.1",
|
||||||
"jiti": "^1.12.15",
|
"jiti": "^1.12.15",
|
||||||
|
"knitwork": "^0.1.0",
|
||||||
"listhen": "^0.2.6",
|
"listhen": "^0.2.6",
|
||||||
"mime": "^3.0.0",
|
"mime": "^3.0.0",
|
||||||
"mlly": "^0.4.1",
|
"mlly": "^0.4.1",
|
||||||
|
@ -2,6 +2,7 @@ import { relative, resolve, join } from 'pathe'
|
|||||||
import consola from 'consola'
|
import consola from 'consola'
|
||||||
import * as rollup from 'rollup'
|
import * as rollup from 'rollup'
|
||||||
import fse from 'fs-extra'
|
import fse from 'fs-extra'
|
||||||
|
import { genDynamicImport } from 'knitwork'
|
||||||
import { printFSTree } from './utils/tree'
|
import { printFSTree } from './utils/tree'
|
||||||
import { getRollupConfig } from './rollup/config'
|
import { getRollupConfig } from './rollup/config'
|
||||||
import { hl, prettyPath, serializeTemplate, writeFile, isDirectory, replaceAll } from './utils'
|
import { hl, prettyPath, serializeTemplate, writeFile, isDirectory, replaceAll } from './utils'
|
||||||
@ -73,7 +74,7 @@ export async function writeTypes (nitroContext: NitroContext) {
|
|||||||
if (typeof mw.handle !== 'string') { continue }
|
if (typeof mw.handle !== 'string') { continue }
|
||||||
const relativePath = relative(nitroContext._nuxt.buildDir, mw.handle).replace(/\.[a-z]+$/, '')
|
const relativePath = relative(nitroContext._nuxt.buildDir, mw.handle).replace(/\.[a-z]+$/, '')
|
||||||
routeTypes[mw.route] = routeTypes[mw.route] || []
|
routeTypes[mw.route] = routeTypes[mw.route] || []
|
||||||
routeTypes[mw.route].push(`Awaited<ReturnType<typeof import('${relativePath}').default>>`)
|
routeTypes[mw.route].push(`Awaited<ReturnType<typeof ${genDynamicImport(relativePath, { wrapper: false })}.default>>`)
|
||||||
}
|
}
|
||||||
|
|
||||||
const lines = [
|
const lines = [
|
||||||
|
@ -2,6 +2,7 @@ import { existsSync, promises as fsp } from 'fs'
|
|||||||
import { resolve } from 'pathe'
|
import { resolve } from 'pathe'
|
||||||
import consola from 'consola'
|
import consola from 'consola'
|
||||||
import { joinURL } from 'ufo'
|
import { joinURL } from 'ufo'
|
||||||
|
import { genString } from 'knitwork'
|
||||||
import { extendPreset, prettyPath } from '../utils'
|
import { extendPreset, prettyPath } from '../utils'
|
||||||
import { NitroPreset, NitroContext, NitroInput } from '../context'
|
import { NitroPreset, NitroContext, NitroInput } from '../context'
|
||||||
import { worker } from './worker'
|
import { worker } from './worker'
|
||||||
@ -13,7 +14,7 @@ export const browser: NitroPreset = extendPreset(worker, (input: NitroInput) =>
|
|||||||
const script = `<script>
|
const script = `<script>
|
||||||
if ('serviceWorker' in navigator) {
|
if ('serviceWorker' in navigator) {
|
||||||
window.addEventListener('load', function () {
|
window.addEventListener('load', function () {
|
||||||
navigator.serviceWorker.register('${joinURL(baseURL, 'sw.js')}');
|
navigator.serviceWorker.register(${genString(joinURL(baseURL, 'sw.js'))});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
</script>`
|
</script>`
|
||||||
@ -27,7 +28,7 @@ if ('serviceWorker' in navigator) {
|
|||||||
<link rel="prefetch" href="${joinURL(baseURL, '_server/index.mjs')}">
|
<link rel="prefetch" href="${joinURL(baseURL, '_server/index.mjs')}">
|
||||||
<script>
|
<script>
|
||||||
async function register () {
|
async function register () {
|
||||||
const registration = await navigator.serviceWorker.register('${joinURL(baseURL, 'sw.js')}')
|
const registration = await navigator.serviceWorker.register(${genString(joinURL(baseURL, 'sw.js'))})
|
||||||
await navigator.serviceWorker.ready
|
await navigator.serviceWorker.ready
|
||||||
registration.active.addEventListener('statechange', (event) => {
|
registration.active.addEventListener('statechange', (event) => {
|
||||||
if (event.target.state === 'activated') {
|
if (event.target.state === 'activated') {
|
||||||
@ -64,7 +65,7 @@ if ('serviceWorker' in navigator) {
|
|||||||
tmpl.contents = tmpl.contents.replace('</body>', script + '</body>')
|
tmpl.contents = tmpl.contents.replace('</body>', script + '</body>')
|
||||||
},
|
},
|
||||||
async 'nitro:compiled' ({ output }: NitroContext) {
|
async 'nitro:compiled' ({ output }: NitroContext) {
|
||||||
await fsp.writeFile(resolve(output.publicDir, 'sw.js'), `self.importScripts('${joinURL(baseURL, '_server/index.mjs')}');`, 'utf8')
|
await fsp.writeFile(resolve(output.publicDir, 'sw.js'), `self.importScripts(${genString(joinURL(baseURL, '_server/index.mjs'))});`, 'utf8')
|
||||||
|
|
||||||
// Temp fix
|
// Temp fix
|
||||||
if (!existsSync(resolve(output.publicDir, 'index.html'))) {
|
if (!existsSync(resolve(output.publicDir, 'index.html'))) {
|
||||||
|
@ -18,6 +18,7 @@ import devalue from '@nuxt/devalue'
|
|||||||
|
|
||||||
import type { Preset } from 'unenv'
|
import type { Preset } from 'unenv'
|
||||||
import { sanitizeFilePath } from 'mlly'
|
import { sanitizeFilePath } from 'mlly'
|
||||||
|
import { genImport } from 'knitwork'
|
||||||
import { NitroContext } from '../context'
|
import { NitroContext } from '../context'
|
||||||
import { resolvePath } from '../utils'
|
import { resolvePath } from '../utils'
|
||||||
import { pkgDir } from '../dirs'
|
import { pkgDir } from '../dirs'
|
||||||
@ -215,7 +216,7 @@ export const getRollupConfig = (nitroContext: NitroContext) => {
|
|||||||
|
|
||||||
// Polyfill
|
// Polyfill
|
||||||
rollupConfig.plugins.push(virtual({
|
rollupConfig.plugins.push(virtual({
|
||||||
'#polyfill': env.polyfill.map(p => `import '${p}';`).join('\n')
|
'#polyfill': env.polyfill.map(p => genImport(p)).join('\n')
|
||||||
}))
|
}))
|
||||||
|
|
||||||
// https://github.com/rollup/plugins/tree/master/packages/alias
|
// https://github.com/rollup/plugins/tree/master/packages/alias
|
||||||
|
@ -4,6 +4,7 @@ import createEtag from 'etag'
|
|||||||
import mime from 'mime'
|
import mime from 'mime'
|
||||||
import { resolve } from 'pathe'
|
import { resolve } from 'pathe'
|
||||||
import { globby } from 'globby'
|
import { globby } from 'globby'
|
||||||
|
import { genDynamicImport, genObjectFromRawEntries } from 'knitwork'
|
||||||
import virtual from './virtual'
|
import virtual from './virtual'
|
||||||
|
|
||||||
export interface AssetOptions {
|
export interface AssetOptions {
|
||||||
@ -81,9 +82,12 @@ function normalizeKey (key) {
|
|||||||
|
|
||||||
function getAssetProd (assets: Record<string, Asset>) {
|
function getAssetProd (assets: Record<string, Asset>) {
|
||||||
return `
|
return `
|
||||||
const _assets = {\n${Object.entries(assets).map(([id, asset]) =>
|
const _assets = ${genObjectFromRawEntries(
|
||||||
` ['${normalizeKey(id)}']: {\n import: () => import('${asset.fsPath}').then(r => r.default || r),\n meta: ${JSON.stringify(asset.meta)}\n }`
|
Object.entries(assets).map(([id, asset]) => [normalizeKey(id), {
|
||||||
).join(',\n')}\n}
|
import: genDynamicImport(asset.fsPath, { interopDefault: true }),
|
||||||
|
meta: asset.meta
|
||||||
|
}])
|
||||||
|
)}
|
||||||
|
|
||||||
${normalizeKey.toString()}
|
${normalizeKey.toString()}
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@ import { pathToFileURL } from 'url'
|
|||||||
import { resolve } from 'pathe'
|
import { resolve } from 'pathe'
|
||||||
import { globby } from 'globby'
|
import { globby } from 'globby'
|
||||||
import type { Plugin } from 'rollup'
|
import type { Plugin } from 'rollup'
|
||||||
|
import { genDynamicImport, genObjectFromRawEntries, genImport } from 'knitwork'
|
||||||
import { serializeImportName } from '../../utils'
|
import { serializeImportName } from '../../utils'
|
||||||
|
|
||||||
const PLUGIN_NAME = 'dynamic-require'
|
const PLUGIN_NAME = 'dynamic-require'
|
||||||
@ -36,7 +37,7 @@ export function dynamicRequire ({ dir, ignore, inline }: Options): Plugin {
|
|||||||
name: PLUGIN_NAME,
|
name: PLUGIN_NAME,
|
||||||
transform (code: string, _id: string) {
|
transform (code: string, _id: string) {
|
||||||
return {
|
return {
|
||||||
code: code.replace(DYNAMIC_REQUIRE_RE, `import('${HELPER_DYNAMIC}').then(r => r.default || r).then(dynamicRequire => dynamicRequire($1)).then`),
|
code: code.replace(DYNAMIC_REQUIRE_RE, `${genDynamicImport(HELPER_DYNAMIC, { wrapper: false, interopDefault: true })}.then(dynamicRequire => dynamicRequire($1)).then`),
|
||||||
map: null
|
map: null
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -89,10 +90,8 @@ async function getWebpackChunkMeta (src: string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function TMPL_INLINE ({ chunks }: TemplateContext) {
|
function TMPL_INLINE ({ chunks }: TemplateContext) {
|
||||||
return `${chunks.map(i => `import * as ${i.name} from '${i.src}'`).join('\n')}
|
return `${chunks.map(i => genImport(i.src, { name: '*', as: i.name })).join('\n')}
|
||||||
const dynamicChunks = {
|
const dynamicChunks = ${genObjectFromRawEntries(chunks.map(i => [i.id, i.name]))};
|
||||||
${chunks.map(i => ` ['${i.id}']: ${i.name}`).join(',\n')}
|
|
||||||
};
|
|
||||||
|
|
||||||
export default function dynamicRequire(id) {
|
export default function dynamicRequire(id) {
|
||||||
return Promise.resolve(dynamicChunks[id]);
|
return Promise.resolve(dynamicChunks[id]);
|
||||||
@ -101,9 +100,7 @@ export default function dynamicRequire(id) {
|
|||||||
|
|
||||||
function TMPL_LAZY ({ chunks }: TemplateContext) {
|
function TMPL_LAZY ({ chunks }: TemplateContext) {
|
||||||
return `
|
return `
|
||||||
const dynamicChunks = {
|
const dynamicChunks = ${genObjectFromRawEntries(chunks.map(i => [i.id, genDynamicImport(i.src)]))};
|
||||||
${chunks.map(i => ` ['${i.id}']: () => import('${i.src}')`).join(',\n')}
|
|
||||||
};
|
|
||||||
|
|
||||||
export default function dynamicRequire(id) {
|
export default function dynamicRequire(id) {
|
||||||
return dynamicChunks[id]();
|
return dynamicChunks[id]();
|
||||||
|
@ -3,6 +3,7 @@ import { relative } from 'pathe'
|
|||||||
import table from 'table'
|
import table from 'table'
|
||||||
import isPrimitive from 'is-primitive'
|
import isPrimitive from 'is-primitive'
|
||||||
import { isDebug } from 'std-env'
|
import { isDebug } from 'std-env'
|
||||||
|
import { genArrayFromRaw, genDynamicImport, genImport } from 'knitwork'
|
||||||
import type { ServerMiddleware } from '../../server/middleware'
|
import type { ServerMiddleware } from '../../server/middleware'
|
||||||
import virtual from './virtual'
|
import virtual from './virtual'
|
||||||
|
|
||||||
@ -35,15 +36,18 @@ export function middleware (getMiddleware: () => ServerMiddleware[]) {
|
|||||||
const lazyImports = unique(middleware.filter(m => m.lazy !== false && !imports.includes(m.handle)).map(m => m.handle))
|
const lazyImports = unique(middleware.filter(m => m.lazy !== false && !imports.includes(m.handle)).map(m => m.handle))
|
||||||
|
|
||||||
return `
|
return `
|
||||||
${imports.map(handle => `import ${getImportId(handle)} from '${handle}';`).join('\n')}
|
${imports.map(handle => `${genImport(handle, getImportId(handle))};`).join('\n')}
|
||||||
|
|
||||||
${lazyImports.map(handle => `const ${getImportId(handle)} = () => import('${handle}');`).join('\n')}
|
${lazyImports.map(handle => `const ${getImportId(handle)} = ${genDynamicImport(handle)};`).join('\n')}
|
||||||
|
|
||||||
const middleware = [
|
const middleware = ${genArrayFromRaw(middleware.map(m => ({
|
||||||
${middleware.map(m => `{ route: '${m.route}', handle: ${getImportId(m.handle)}, lazy: ${m.lazy || true}, promisify: ${m.promisify !== undefined ? m.promisify : true} }`).join(',\n')}
|
route: JSON.stringify(m.route),
|
||||||
];
|
handle: getImportId(m.handle),
|
||||||
|
lazy: m.lazy || true,
|
||||||
|
promisify: m.promisify !== undefined ? m.promisify : true
|
||||||
|
})))};
|
||||||
|
|
||||||
export default middleware
|
export default middleware
|
||||||
`
|
`
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
import virtual from '@rollup/plugin-virtual'
|
import virtual from '@rollup/plugin-virtual'
|
||||||
|
import { genImport, genString } from 'knitwork'
|
||||||
import { serializeImportName } from '../../utils'
|
import { serializeImportName } from '../../utils'
|
||||||
|
|
||||||
export interface StorageOptions {
|
export interface StorageOptions {
|
||||||
@ -35,13 +36,13 @@ export function storage (opts: StorageOptions) {
|
|||||||
import { createStorage } from 'unstorage'
|
import { createStorage } from 'unstorage'
|
||||||
import { assets } from '#assets'
|
import { assets } from '#assets'
|
||||||
|
|
||||||
${driverImports.map(i => `import ${serializeImportName(i)} from '${i}'`).join('\n')}
|
${driverImports.map(i => genImport(i, serializeImportName(i))).join('\n')}
|
||||||
|
|
||||||
export const storage = createStorage({})
|
export const storage = createStorage({})
|
||||||
|
|
||||||
storage.mount('/assets', assets)
|
storage.mount('/assets', assets)
|
||||||
|
|
||||||
${mounts.map(m => `storage.mount('${m.path}', ${serializeImportName(m.driver)}(${JSON.stringify(m.opts)}))`).join('\n')}
|
${mounts.map(m => `storage.mount(${genString(m.path)}, ${serializeImportName(m.driver)}(${JSON.stringify(m.opts)}))`).join('\n')}
|
||||||
`
|
`
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -39,6 +39,7 @@
|
|||||||
"hash-sum": "^2.0.0",
|
"hash-sum": "^2.0.0",
|
||||||
"hookable": "^5.1.1",
|
"hookable": "^5.1.1",
|
||||||
"ignore": "^5.2.0",
|
"ignore": "^5.2.0",
|
||||||
|
"knitwork": "^0.1.0",
|
||||||
"mlly": "^0.4.1",
|
"mlly": "^0.4.1",
|
||||||
"murmurhash-es": "^0.1.1",
|
"murmurhash-es": "^0.1.1",
|
||||||
"nuxi": "3.0.0",
|
"nuxi": "3.0.0",
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import { addVitePlugin, addWebpackPlugin, defineNuxtModule, addTemplate, resolveAlias, addPluginTemplate, useNuxt } from '@nuxt/kit'
|
import { addVitePlugin, addWebpackPlugin, defineNuxtModule, addTemplate, resolveAlias, addPluginTemplate, useNuxt } from '@nuxt/kit'
|
||||||
import type { AutoImportsOptions } from '@nuxt/schema'
|
import type { AutoImportsOptions } from '@nuxt/schema'
|
||||||
import { isAbsolute, join, relative, resolve, normalize } from 'pathe'
|
import { isAbsolute, join, relative, resolve, normalize } from 'pathe'
|
||||||
|
import { genDynamicImport } from 'knitwork'
|
||||||
import { TransformPlugin } from './transform'
|
import { TransformPlugin } from './transform'
|
||||||
import { Nuxt3AutoImports } from './imports'
|
import { Nuxt3AutoImports } from './imports'
|
||||||
import { scanForComposables } from './composables'
|
import { scanForComposables } from './composables'
|
||||||
@ -132,7 +133,7 @@ function generateDts (ctx: AutoImportContext) {
|
|||||||
write: true,
|
write: true,
|
||||||
getContents: () => `// Generated by auto imports
|
getContents: () => `// Generated by auto imports
|
||||||
declare global {
|
declare global {
|
||||||
${ctx.autoImports.map(i => ` const ${i.as}: typeof import('${r(i.from)}')['${i.name}']`).join('\n')}
|
${ctx.autoImports.map(i => ` const ${i.as}: typeof ${genDynamicImport(r(i.from), { wrapper: false })}['${i.name}']`).join('\n')}
|
||||||
}
|
}
|
||||||
|
|
||||||
export {}
|
export {}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
import type { AutoImport } from '@nuxt/schema'
|
import type { AutoImport } from '@nuxt/schema'
|
||||||
|
import { genExport, genImport, genString } from 'knitwork'
|
||||||
|
|
||||||
export function toImportModuleMap (autoImports: AutoImport[], isCJS = false) {
|
export function toImportModuleMap (autoImports: AutoImport[], isCJS = false) {
|
||||||
const aliasKeyword = isCJS ? ' : ' : ' as '
|
const aliasKeyword = isCJS ? ' : ' : ' as '
|
||||||
@ -20,11 +21,11 @@ export function toImports (autoImports: AutoImport[], isCJS = false) {
|
|||||||
const map = toImportModuleMap(autoImports, isCJS)
|
const map = toImportModuleMap(autoImports, isCJS)
|
||||||
if (isCJS) {
|
if (isCJS) {
|
||||||
return Object.entries(map)
|
return Object.entries(map)
|
||||||
.map(([name, imports]) => `const { ${Array.from(imports).join(', ')} } = require('${name}');`)
|
.map(([name, imports]) => `const { ${Array.from(imports).join(', ')} } = require(${genString(name)});`)
|
||||||
.join('\n')
|
.join('\n')
|
||||||
} else {
|
} else {
|
||||||
return Object.entries(map)
|
return Object.entries(map)
|
||||||
.map(([name, imports]) => `import { ${Array.from(imports).join(', ')} } from '${name}';`)
|
.map(([name, imports]) => genImport(name, Array.from(imports)))
|
||||||
.join('\n')
|
.join('\n')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -32,7 +33,7 @@ export function toImports (autoImports: AutoImport[], isCJS = false) {
|
|||||||
export function toExports (autoImports: AutoImport[]) {
|
export function toExports (autoImports: AutoImport[]) {
|
||||||
const map = toImportModuleMap(autoImports, false)
|
const map = toImportModuleMap(autoImports, false)
|
||||||
return Object.entries(map)
|
return Object.entries(map)
|
||||||
.map(([name, imports]) => `export { ${Array.from(imports).join(', ')} } from '${name}';`)
|
.map(([name, imports]) => genExport(name, Array.from(imports)))
|
||||||
.join('\n')
|
.join('\n')
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import { createUnplugin } from 'unplugin'
|
import { createUnplugin } from 'unplugin'
|
||||||
import { parseQuery, parseURL } from 'ufo'
|
import { parseQuery, parseURL } from 'ufo'
|
||||||
import { Component } from '@nuxt/schema'
|
import { Component } from '@nuxt/schema'
|
||||||
|
import { genImport } from 'knitwork'
|
||||||
|
|
||||||
interface LoaderOptions {
|
interface LoaderOptions {
|
||||||
getComponents(): Component[]
|
getComponents(): Component[]
|
||||||
@ -36,7 +37,7 @@ function transform (content: string, components: Component[]) {
|
|||||||
if (component) {
|
if (component) {
|
||||||
const identifier = map.get(component) || `__nuxt_component_${num++}`
|
const identifier = map.get(component) || `__nuxt_component_${num++}`
|
||||||
map.set(component, identifier)
|
map.set(component, identifier)
|
||||||
imports += `import ${identifier} from "${component.filePath}";`
|
imports += genImport(component.filePath, identifier)
|
||||||
return ` ${identifier}`
|
return ` ${identifier}`
|
||||||
}
|
}
|
||||||
// no matched
|
// no matched
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
|
|
||||||
import { isAbsolute, join, relative } from 'pathe'
|
import { isAbsolute, join, relative } from 'pathe'
|
||||||
import type { Component } from '@nuxt/schema'
|
import type { Component } from '@nuxt/schema'
|
||||||
|
import { genDynamicImport, genObjectFromRawEntries } from 'knitwork'
|
||||||
|
|
||||||
export type ComponentsTemplateOptions = {
|
export type ComponentsTemplateOptions = {
|
||||||
buildDir?: string
|
buildDir?: string
|
||||||
@ -27,14 +28,12 @@ export const componentsTemplate = {
|
|||||||
getContents ({ options }: { options: ComponentsTemplateOptions }) {
|
getContents ({ options }: { options: ComponentsTemplateOptions }) {
|
||||||
return `import { defineAsyncComponent } from 'vue'
|
return `import { defineAsyncComponent } from 'vue'
|
||||||
|
|
||||||
const components = {
|
const components = ${genObjectFromRawEntries(options.components.filter(c => c.global !== false).map((c) => {
|
||||||
${options.components.filter(c => c.global !== false).map((c) => {
|
|
||||||
const exp = c.export === 'default' ? 'c.default || c' : `c['${c.export}']`
|
const exp = c.export === 'default' ? 'c.default || c' : `c['${c.export}']`
|
||||||
const magicComments = createImportMagicComments(c)
|
const comment = createImportMagicComments(c)
|
||||||
|
|
||||||
return ` '${c.pascalName}': defineAsyncComponent(() => import('${c.filePath}' /* ${magicComments} */).then(c => ${exp}))`
|
return [c.pascalName, `defineAsyncComponent(${genDynamicImport(c.filePath, { comment })}.then(c => ${exp}))`]
|
||||||
}).join(',\n')}
|
}))}
|
||||||
}
|
|
||||||
|
|
||||||
export default function (nuxtApp) {
|
export default function (nuxtApp) {
|
||||||
for (const name in components) {
|
for (const name in components) {
|
||||||
@ -51,7 +50,7 @@ export const componentsTypeTemplate = {
|
|||||||
getContents: ({ options }: { options: ComponentsTemplateOptions }) => `// Generated by components discovery
|
getContents: ({ options }: { options: ComponentsTemplateOptions }) => `// Generated by components discovery
|
||||||
declare module 'vue' {
|
declare module 'vue' {
|
||||||
export interface GlobalComponents {
|
export interface GlobalComponents {
|
||||||
${options.components.map(c => ` '${c.pascalName}': typeof import('${isAbsolute(c.filePath) ? relative(join(options.buildDir, 'types'), c.filePath) : c.filePath}')['${c.export}']`).join(',\n')}
|
${options.components.map(c => ` '${c.pascalName}': typeof ${genDynamicImport(isAbsolute(c.filePath) ? relative(join(options.buildDir, 'types'), c.filePath) : c.filePath, { wrapper: false })}['${c.export}']`).join(',\n')}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
export {}
|
export {}
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import { templateUtils } from '@nuxt/kit'
|
import { templateUtils } from '@nuxt/kit'
|
||||||
import type { Nuxt, NuxtApp } from '@nuxt/schema'
|
import type { Nuxt, NuxtApp } from '@nuxt/schema'
|
||||||
|
import { genArrayFromRaw, genDynamicImport, genExport, genImport } from 'knitwork'
|
||||||
|
|
||||||
import { isAbsolute, join, relative } from 'pathe'
|
import { isAbsolute, join, relative } from 'pathe'
|
||||||
import escapeRE from 'escape-string-regexp'
|
import escapeRE from 'escape-string-regexp'
|
||||||
@ -24,23 +25,17 @@ export const vueShim = {
|
|||||||
// TODO: Use an alias
|
// TODO: Use an alias
|
||||||
export const appComponentTemplate = {
|
export const appComponentTemplate = {
|
||||||
filename: 'app-component.mjs',
|
filename: 'app-component.mjs',
|
||||||
getContents (ctx: TemplateContext) {
|
getContents: (ctx: TemplateContext) => genExport(ctx.app.mainComponent, ['default'])
|
||||||
return `export { default } from '${ctx.app.mainComponent}'`
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
// TODO: Use an alias
|
// TODO: Use an alias
|
||||||
export const rootComponentTemplate = {
|
export const rootComponentTemplate = {
|
||||||
filename: 'root-component.mjs',
|
filename: 'root-component.mjs',
|
||||||
getContents (ctx: TemplateContext) {
|
getContents: (ctx: TemplateContext) => genExport(ctx.app.rootComponent, ['default'])
|
||||||
return `export { default } from '${ctx.app.rootComponent}'`
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const cssTemplate = {
|
export const cssTemplate = {
|
||||||
filename: 'css.mjs',
|
filename: 'css.mjs',
|
||||||
getContents (ctx: TemplateContext) {
|
getContents: (ctx: TemplateContext) => ctx.nuxt.options.css.map(i => genImport(i.src || i)).join('\n')
|
||||||
return ctx.nuxt.options.css.map(i => `import '${i.src || i}';`).join('\n')
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const clientPluginTemplate = {
|
export const clientPluginTemplate = {
|
||||||
@ -49,9 +44,7 @@ export const clientPluginTemplate = {
|
|||||||
const clientPlugins = ctx.app.plugins.filter(p => !p.mode || p.mode !== 'server')
|
const clientPlugins = ctx.app.plugins.filter(p => !p.mode || p.mode !== 'server')
|
||||||
return [
|
return [
|
||||||
templateUtils.importSources(clientPlugins.map(p => p.src)),
|
templateUtils.importSources(clientPlugins.map(p => p.src)),
|
||||||
'export default [',
|
`export default ${genArrayFromRaw(clientPlugins.map(p => templateUtils.importName(p.src)))}`
|
||||||
clientPlugins.map(p => templateUtils.importName(p.src)).join(',\n '),
|
|
||||||
']'
|
|
||||||
].join('\n')
|
].join('\n')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -63,10 +56,10 @@ export const serverPluginTemplate = {
|
|||||||
return [
|
return [
|
||||||
"import preload from '#app/plugins/preload.server'",
|
"import preload from '#app/plugins/preload.server'",
|
||||||
templateUtils.importSources(serverPlugins.map(p => p.src)),
|
templateUtils.importSources(serverPlugins.map(p => p.src)),
|
||||||
'export default [',
|
`export default ${genArrayFromRaw([
|
||||||
' preload,',
|
'preload',
|
||||||
serverPlugins.map(p => templateUtils.importName(p.src)).join(',\n '),
|
...serverPlugins.map(p => templateUtils.importName(p.src))
|
||||||
']'
|
])}`
|
||||||
].join('\n')
|
].join('\n')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -103,7 +96,7 @@ type Decorate<T extends Record<string, any>> = { [K in keyof T as K extends stri
|
|||||||
|
|
||||||
type InjectionType<A extends Plugin> = A extends Plugin<infer T> ? Decorate<T> : unknown
|
type InjectionType<A extends Plugin> = A extends Plugin<infer T> ? Decorate<T> : unknown
|
||||||
|
|
||||||
type NuxtAppInjections = \n ${tsImports.map(p => `InjectionType<typeof import('${p}').default>`).join(' &\n ')}
|
type NuxtAppInjections = \n ${tsImports.map(p => `InjectionType<typeof ${genDynamicImport(p, { wrapper: false })}.default>`).join(' &\n ')}
|
||||||
|
|
||||||
declare module '#app' {
|
declare module '#app' {
|
||||||
interface NuxtApp extends NuxtAppInjections { }
|
interface NuxtApp extends NuxtAppInjections { }
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import { existsSync } from 'fs'
|
import { existsSync } from 'fs'
|
||||||
import { defineNuxtModule, addTemplate, addPlugin, templateUtils, addVitePlugin, addWebpackPlugin } from '@nuxt/kit'
|
import { defineNuxtModule, addTemplate, addPlugin, addVitePlugin, addWebpackPlugin } from '@nuxt/kit'
|
||||||
import { resolve } from 'pathe'
|
import { resolve } from 'pathe'
|
||||||
|
import { genDynamicImport, genString, genArrayFromRaw, genImport, genObjectFromRawEntries } from 'knitwork'
|
||||||
import escapeRE from 'escape-string-regexp'
|
import escapeRE from 'escape-string-regexp'
|
||||||
import { distDir } from '../dirs'
|
import { distDir } from '../dirs'
|
||||||
import { resolveLayouts, resolvePagesRoutes, normalizeRoutes, resolveMiddleware, getImportName } from './utils'
|
import { resolveLayouts, resolvePagesRoutes, normalizeRoutes, resolveMiddleware, getImportName } from './utils'
|
||||||
@ -80,8 +81,8 @@ export default defineNuxtModule({
|
|||||||
async getContents () {
|
async getContents () {
|
||||||
const pages = await resolvePagesRoutes(nuxt)
|
const pages = await resolvePagesRoutes(nuxt)
|
||||||
await nuxt.callHook('pages:extend', pages)
|
await nuxt.callHook('pages:extend', pages)
|
||||||
const { routes: serializedRoutes, imports } = normalizeRoutes(pages)
|
const { routes, imports } = normalizeRoutes(pages)
|
||||||
return [...imports, `export default ${templateUtils.serialize(serializedRoutes)}`].join('\n')
|
return [...imports, `export default ${routes}`].join('\n')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -92,11 +93,11 @@ export default defineNuxtModule({
|
|||||||
const middleware = await resolveMiddleware()
|
const middleware = await resolveMiddleware()
|
||||||
const globalMiddleware = middleware.filter(mw => mw.global)
|
const globalMiddleware = middleware.filter(mw => mw.global)
|
||||||
const namedMiddleware = middleware.filter(mw => !mw.global)
|
const namedMiddleware = middleware.filter(mw => !mw.global)
|
||||||
const namedMiddlewareObject = Object.fromEntries(namedMiddleware.map(mw => [mw.name, `{() => import('${mw.path}')}`]))
|
const namedMiddlewareObject = genObjectFromRawEntries(namedMiddleware.map(mw => [mw.name, genDynamicImport(mw.path)]))
|
||||||
return [
|
return [
|
||||||
...globalMiddleware.map(mw => `import ${getImportName(mw.name)} from '${mw.path}'`),
|
...globalMiddleware.map(mw => genImport(mw.path, getImportName(mw.name))),
|
||||||
`export const globalMiddleware = [${globalMiddleware.map(mw => getImportName(mw.name)).join(', ')}]`,
|
`export const globalMiddleware = ${genArrayFromRaw(globalMiddleware.map(mw => getImportName(mw.name)))}`,
|
||||||
`export const namedMiddleware = ${templateUtils.serialize(namedMiddlewareObject)}`
|
`export const namedMiddleware = ${namedMiddlewareObject}`
|
||||||
].join('\n')
|
].join('\n')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
@ -109,8 +110,8 @@ export default defineNuxtModule({
|
|||||||
const namedMiddleware = middleware.filter(mw => !mw.global)
|
const namedMiddleware = middleware.filter(mw => !mw.global)
|
||||||
return [
|
return [
|
||||||
'import type { NavigationGuard } from \'vue-router\'',
|
'import type { NavigationGuard } from \'vue-router\'',
|
||||||
`export type MiddlewareKey = ${namedMiddleware.map(mw => `"${mw.name}"`).join(' | ') || 'string'}`,
|
`export type MiddlewareKey = ${namedMiddleware.map(mw => genString(mw.name)).join(' | ') || 'string'}`,
|
||||||
`declare module '${composablesFile}' {`,
|
`declare module ${genString(composablesFile)} {`,
|
||||||
' interface PageMeta {',
|
' interface PageMeta {',
|
||||||
' middleware?: MiddlewareKey | NavigationGuard | Array<MiddlewareKey | NavigationGuard>',
|
' middleware?: MiddlewareKey | NavigationGuard | Array<MiddlewareKey | NavigationGuard>',
|
||||||
' }',
|
' }',
|
||||||
@ -126,8 +127,8 @@ export default defineNuxtModule({
|
|||||||
const layouts = await resolveLayouts(nuxt)
|
const layouts = await resolveLayouts(nuxt)
|
||||||
return [
|
return [
|
||||||
'import { ComputedRef, Ref } from \'vue\'',
|
'import { ComputedRef, Ref } from \'vue\'',
|
||||||
`export type LayoutKey = ${layouts.map(layout => `"${layout.name}"`).join(' | ') || 'string'}`,
|
`export type LayoutKey = ${layouts.map(layout => genString(layout.name)).join(' | ') || 'string'}`,
|
||||||
`declare module '${composablesFile}' {`,
|
`declare module ${genString(composablesFile)} {`,
|
||||||
' interface PageMeta {',
|
' interface PageMeta {',
|
||||||
' layout?: false | LayoutKey | Ref<LayoutKey> | ComputedRef<LayoutKey>',
|
' layout?: false | LayoutKey | Ref<LayoutKey> | ComputedRef<LayoutKey>',
|
||||||
' }',
|
' }',
|
||||||
@ -141,12 +142,12 @@ export default defineNuxtModule({
|
|||||||
filename: 'layouts.mjs',
|
filename: 'layouts.mjs',
|
||||||
async getContents () {
|
async getContents () {
|
||||||
const layouts = await resolveLayouts(nuxt)
|
const layouts = await resolveLayouts(nuxt)
|
||||||
const layoutsObject = Object.fromEntries(layouts.map(({ name, file }) => {
|
const layoutsObject = genObjectFromRawEntries(layouts.map(({ name, file }) => {
|
||||||
return [name, `{defineAsyncComponent({ suspensible: false, loader: () => import('${file}') })}`]
|
return [name, `defineAsyncComponent({ suspensible: false, loader: ${genDynamicImport(file)} })`]
|
||||||
}))
|
}))
|
||||||
return [
|
return [
|
||||||
'import { defineAsyncComponent } from \'vue\'',
|
'import { defineAsyncComponent } from \'vue\'',
|
||||||
`export default ${templateUtils.serialize(layoutsObject)}`
|
`export default ${layoutsObject}`
|
||||||
].join('\n')
|
].join('\n')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
@ -3,6 +3,7 @@ import { encodePath } from 'ufo'
|
|||||||
import type { Nuxt, NuxtMiddleware, NuxtPage } from '@nuxt/schema'
|
import type { Nuxt, NuxtMiddleware, NuxtPage } from '@nuxt/schema'
|
||||||
import { resolveFiles, useNuxt } from '@nuxt/kit'
|
import { resolveFiles, useNuxt } from '@nuxt/kit'
|
||||||
import { kebabCase, pascalCase } from 'scule'
|
import { kebabCase, pascalCase } from 'scule'
|
||||||
|
import { genImport, genDynamicImport, genArrayFromRaw } from 'knitwork'
|
||||||
import escapeRE from 'escape-string-regexp'
|
import escapeRE from 'escape-string-regexp'
|
||||||
|
|
||||||
enum SegmentParserState {
|
enum SegmentParserState {
|
||||||
@ -225,20 +226,20 @@ export async function resolveLayouts (nuxt: Nuxt) {
|
|||||||
return layouts
|
return layouts
|
||||||
}
|
}
|
||||||
|
|
||||||
export function normalizeRoutes (routes: NuxtPage[], metaImports: Set<string> = new Set()): { imports: Set<string>, routes: NuxtPage[]} {
|
export function normalizeRoutes (routes: NuxtPage[], metaImports: Set<string> = new Set()): { imports: Set<string>, routes: string } {
|
||||||
return {
|
return {
|
||||||
imports: metaImports,
|
imports: metaImports,
|
||||||
routes: routes.map((route) => {
|
routes: genArrayFromRaw(routes.map((route) => {
|
||||||
const file = normalize(route.file)
|
const file = normalize(route.file)
|
||||||
const metaImportName = getImportName(file) + 'Meta'
|
const metaImportName = getImportName(file) + 'Meta'
|
||||||
metaImports.add(`import { meta as ${metaImportName} } from '${file}?macro=true'`)
|
metaImports.add(genImport(`${file}?macro=true`, [{ name: 'meta', as: metaImportName }]))
|
||||||
return {
|
return {
|
||||||
...route,
|
...Object.fromEntries(Object.entries(route).map(([key, value]) => [key, JSON.stringify(value)])),
|
||||||
children: route.children ? normalizeRoutes(route.children, metaImports).routes : [],
|
children: route.children ? normalizeRoutes(route.children, metaImports).routes : [],
|
||||||
meta: route.meta || `{${metaImportName}}` as any,
|
meta: route.meta ? JSON.stringify(route.meta) : metaImportName,
|
||||||
component: `{() => import('${file}')}`
|
component: genDynamicImport(file)
|
||||||
}
|
}
|
||||||
})
|
}))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -28,8 +28,8 @@ describe('auto-imports:transform', () => {
|
|||||||
const transform = (code: string) => transformPlugin.transform.call({ error: null, warn: null }, code, '')
|
const transform = (code: string) => transformPlugin.transform.call({ error: null, warn: null }, code, '')
|
||||||
|
|
||||||
it('should correct inject', async () => {
|
it('should correct inject', async () => {
|
||||||
expect(await transform('const a = ref(0)')).to.equal('import { ref } from \'vue\';const a = ref(0)')
|
expect(await transform('const a = ref(0)')).to.equal('import { ref } from "vue";const a = ref(0)')
|
||||||
expect(await transform('import { computed as ref } from "foo"; const a = ref(0)')).to.include('import { computed } from \'bar\';')
|
expect(await transform('import { computed as ref } from "foo"; const a = ref(0)')).to.include('import { computed } from "bar";')
|
||||||
})
|
})
|
||||||
|
|
||||||
it('should ignore existing imported', async () => {
|
it('should ignore existing imported', async () => {
|
||||||
@ -43,7 +43,7 @@ describe('auto-imports:transform', () => {
|
|||||||
|
|
||||||
it('should ignore comments', async () => {
|
it('should ignore comments', async () => {
|
||||||
const result = await transform('// import { computed } from "foo"\n;const a = computed(0)')
|
const result = await transform('// import { computed } from "foo"\n;const a = computed(0)')
|
||||||
expect(result).to.equal('import { computed } from \'bar\';// import { computed } from "foo"\n;const a = computed(0)')
|
expect(result).to.equal('import { computed } from "bar";// import { computed } from "foo"\n;const a = computed(0)')
|
||||||
})
|
})
|
||||||
|
|
||||||
it('should exclude files from transform', () => {
|
it('should exclude files from transform', () => {
|
||||||
|
@ -29,6 +29,7 @@
|
|||||||
"escape-string-regexp": "^5.0.0",
|
"escape-string-regexp": "^5.0.0",
|
||||||
"externality": "^0.1.6",
|
"externality": "^0.1.6",
|
||||||
"fs-extra": "^10.0.0",
|
"fs-extra": "^10.0.0",
|
||||||
|
"knitwork": "^0.1.0",
|
||||||
"magic-string": "^0.25.7",
|
"magic-string": "^0.25.7",
|
||||||
"mlly": "^0.4.1",
|
"mlly": "^0.4.1",
|
||||||
"p-debounce": "^4.0.0",
|
"p-debounce": "^4.0.0",
|
||||||
|
@ -4,6 +4,7 @@ import { builtinModules } from 'module'
|
|||||||
import { resolve } from 'pathe'
|
import { resolve } from 'pathe'
|
||||||
import * as vite from 'vite'
|
import * as vite from 'vite'
|
||||||
import { ExternalsOptions, isExternal as _isExternal, ExternalsDefaults } from 'externality'
|
import { ExternalsOptions, isExternal as _isExternal, ExternalsDefaults } from 'externality'
|
||||||
|
import { genDynamicImport, genObjectFromRawEntries } from 'knitwork'
|
||||||
import { hashId, uniq } from './utils'
|
import { hashId, uniq } from './utils'
|
||||||
|
|
||||||
export interface TransformChunk {
|
export interface TransformChunk {
|
||||||
@ -78,7 +79,7 @@ async function transformRequest (opts: TransformOptions, id: string) {
|
|||||||
? withoutVersionQuery
|
? withoutVersionQuery
|
||||||
: pathToFileURL(withoutVersionQuery)
|
: pathToFileURL(withoutVersionQuery)
|
||||||
return {
|
return {
|
||||||
code: `(global, exports, importMeta, ssrImport, ssrDynamicImport, ssrExportAll) => import('${path}').then(r => { exports.default = r.default; ssrExportAll(r) }).catch(e => { console.error(e); throw new Error('[vite dev] Error loading external "${id}".') })`,
|
code: `(global, exports, importMeta, ssrImport, ssrDynamicImport, ssrExportAll) => ${genDynamicImport(path, { wrapper: false })}.then(r => { exports.default = r.default; ssrExportAll(r) }).catch(e => { console.error(e); throw new Error(${JSON.stringify(`[vite dev] Error loading external "${id}".`)}) })`,
|
||||||
deps: [],
|
deps: [],
|
||||||
dynamicDeps: []
|
dynamicDeps: []
|
||||||
}
|
}
|
||||||
@ -131,8 +132,9 @@ export async function bundleRequest (opts: TransformOptions, entryURL: string) {
|
|||||||
const ${hashId(chunk.id)} = ${chunk.code}
|
const ${hashId(chunk.id)} = ${chunk.code}
|
||||||
`).join('\n')
|
`).join('\n')
|
||||||
|
|
||||||
const manifestCode = 'const __modules__ = {\n' +
|
const manifestCode = `const __modules__ = ${
|
||||||
chunks.map(chunk => ` '${chunk.id}': ${hashId(chunk.id)}`).join(',\n') + '\n}'
|
genObjectFromRawEntries(chunks.map(chunk => [chunk.id, hashId(chunk.id)]))
|
||||||
|
}`
|
||||||
|
|
||||||
// https://github.com/vitejs/vite/blob/main/packages/vite/src/node/ssr/ssrModuleLoader.ts
|
// https://github.com/vitejs/vite/blob/main/packages/vite/src/node/ssr/ssrModuleLoader.ts
|
||||||
const ssrModuleLoader = `
|
const ssrModuleLoader = `
|
||||||
@ -213,7 +215,7 @@ async function __instantiateModule__(url, urlStack) {
|
|||||||
chunksCode,
|
chunksCode,
|
||||||
manifestCode,
|
manifestCode,
|
||||||
ssrModuleLoader,
|
ssrModuleLoader,
|
||||||
`export default await __ssrLoadModule__('${entryURL}')`
|
`export default await __ssrLoadModule__(${JSON.stringify(entryURL)})`
|
||||||
].join('\n\n')
|
].join('\n\n')
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
12
yarn.lock
12
yarn.lock
@ -2589,6 +2589,7 @@ __metadata:
|
|||||||
globby: ^13.1.1
|
globby: ^13.1.1
|
||||||
h3: ^0.3.9
|
h3: ^0.3.9
|
||||||
hash-sum: ^2.0.0
|
hash-sum: ^2.0.0
|
||||||
|
knitwork: ^0.1.0
|
||||||
magic-string: ^0.25.7
|
magic-string: ^0.25.7
|
||||||
mlly: ^0.4.1
|
mlly: ^0.4.1
|
||||||
murmurhash-es: ^0.1.1
|
murmurhash-es: ^0.1.1
|
||||||
@ -2900,6 +2901,7 @@ __metadata:
|
|||||||
globby: ^13.1.1
|
globby: ^13.1.1
|
||||||
hash-sum: ^2.0.0
|
hash-sum: ^2.0.0
|
||||||
jiti: ^1.12.15
|
jiti: ^1.12.15
|
||||||
|
knitwork: ^0.1.0
|
||||||
lodash.template: ^4.5.0
|
lodash.template: ^4.5.0
|
||||||
mlly: ^0.4.1
|
mlly: ^0.4.1
|
||||||
pathe: ^0.2.0
|
pathe: ^0.2.0
|
||||||
@ -2993,6 +2995,7 @@ __metadata:
|
|||||||
http-proxy: ^1.18.1
|
http-proxy: ^1.18.1
|
||||||
is-primitive: ^3.0.1
|
is-primitive: ^3.0.1
|
||||||
jiti: ^1.12.15
|
jiti: ^1.12.15
|
||||||
|
knitwork: ^0.1.0
|
||||||
listhen: ^0.2.6
|
listhen: ^0.2.6
|
||||||
mime: ^3.0.0
|
mime: ^3.0.0
|
||||||
mlly: ^0.4.1
|
mlly: ^0.4.1
|
||||||
@ -3265,6 +3268,7 @@ __metadata:
|
|||||||
escape-string-regexp: ^5.0.0
|
escape-string-regexp: ^5.0.0
|
||||||
externality: ^0.1.6
|
externality: ^0.1.6
|
||||||
fs-extra: ^10.0.0
|
fs-extra: ^10.0.0
|
||||||
|
knitwork: ^0.1.0
|
||||||
magic-string: ^0.25.7
|
magic-string: ^0.25.7
|
||||||
mlly: ^0.4.1
|
mlly: ^0.4.1
|
||||||
p-debounce: ^4.0.0
|
p-debounce: ^4.0.0
|
||||||
@ -12956,6 +12960,13 @@ __metadata:
|
|||||||
languageName: node
|
languageName: node
|
||||||
linkType: hard
|
linkType: hard
|
||||||
|
|
||||||
|
"knitwork@npm:^0.1.0":
|
||||||
|
version: 0.1.0
|
||||||
|
resolution: "knitwork@npm:0.1.0"
|
||||||
|
checksum: 36782ee8fcfb78a18684ff28ab6e829381d45a02cb8eb9efa192b3c521d9f6ff6d1ba3fbc28bdae471a9d251821ea99018a1f3e224e7b3cb62f72bbdb3a4cbd6
|
||||||
|
languageName: node
|
||||||
|
linkType: hard
|
||||||
|
|
||||||
"kolorist@npm:^1.5.0":
|
"kolorist@npm:^1.5.0":
|
||||||
version: 1.5.1
|
version: 1.5.1
|
||||||
resolution: "kolorist@npm:1.5.1"
|
resolution: "kolorist@npm:1.5.1"
|
||||||
@ -14979,6 +14990,7 @@ __metadata:
|
|||||||
hash-sum: ^2.0.0
|
hash-sum: ^2.0.0
|
||||||
hookable: ^5.1.1
|
hookable: ^5.1.1
|
||||||
ignore: ^5.2.0
|
ignore: ^5.2.0
|
||||||
|
knitwork: ^0.1.0
|
||||||
mlly: ^0.4.1
|
mlly: ^0.4.1
|
||||||
murmurhash-es: ^0.1.1
|
murmurhash-es: ^0.1.1
|
||||||
nuxi: 3.0.0
|
nuxi: 3.0.0
|
||||||
|
Loading…
Reference in New Issue
Block a user