Skip to content

Commit

Permalink
perf: optimize URL constructors with relative paths
Browse files Browse the repository at this point in the history
  • Loading branch information
kherock committed May 3, 2022
1 parent cce41df commit 50c19ca
Show file tree
Hide file tree
Showing 3 changed files with 54 additions and 28 deletions.
2 changes: 1 addition & 1 deletion packages/playground/worker/worker/main-module.js
Expand Up @@ -80,7 +80,7 @@ w.addEventListener('message', (ev) =>

// url import worker with alias path
const wResolve = new Worker(
new URL('@/url-worker', import.meta.url),
new URL('@/url-worker.js', import.meta.url),
/* @vite-ignore */ workerOptions
)
wResolve.addEventListener('message', (ev) =>
Expand Down
58 changes: 37 additions & 21 deletions packages/vite/src/node/plugins/assetImportMetaUrl.ts
@@ -1,10 +1,11 @@
import type { Plugin } from '../plugin'
import MagicString from 'magic-string'
import path from 'path'
import { fileToUrl } from './asset'
import type { ResolvedConfig } from '../config'
import { emptyString } from '../cleanString'
import type { ResolveFn } from '../'
import { isParentDirectory, normalizePath } from '../utils'
import { isParentDirectory, normalizePath, slash } from '../utils'

/**
* Convert `new URL('./foo.png', import.meta.url)` to its resolved built URL
Expand All @@ -17,6 +18,7 @@ import { isParentDirectory, normalizePath } from '../utils'
* ```
*/
export function assetImportMetaUrlPlugin(config: ResolvedConfig): Plugin {
const normalizedPublicDir = normalizePath(config.publicDir)
let assetResolver: ResolveFn

return {
Expand Down Expand Up @@ -65,31 +67,45 @@ export function assetImportMetaUrlPlugin(config: ResolvedConfig): Plugin {
}

const url = rawUrl.slice(1, -1)
assetResolver ??= config.createResolver({
root: config.publicDir,
extensions: [],
mainFields: [],
tryIndex: false,
preferRelative: true
})
const resolved = await assetResolver(url, id)
if (!resolved) {
let file: string | undefined
if (url.startsWith('.')) {
file = slash(path.resolve(path.dirname(id), url))
} else {
assetResolver ??= config.createResolver({
extensions: [],
mainFields: [],
tryIndex: false,
preferRelative: true
})
file = await assetResolver(url, id)
file ??= url.startsWith('/')
? slash(path.join(config.publicDir, url))
: slash(path.resolve(path.dirname(id), url))
}

// Get final asset URL. If the file does not exist,
// we fall back to the initial URL and let it resolve in runtime
let builtUrl: string | undefined
if (file) {
try {
if (isParentDirectory(normalizedPublicDir, file)) {
const publicPath =
'/' + path.posix.relative(normalizedPublicDir, file)
builtUrl = await fileToUrl(publicPath, config, this)
} else {
builtUrl = await fileToUrl(file, config, this)
}
} catch {
// do nothing, we'll log a warning after this
}
}
if (!builtUrl) {
const rawExp = code.slice(index, index + exp.length)
config.logger.warnOnce(
`\n${rawExp} doesn't exist at build time, it will remain unchanged to be resolved at runtime`
)
builtUrl = url
}
// Get final asset URL. If the file does not exist,
// we fall back to the initial URL and let it resolve in runtime
const builtUrl = resolved
? await fileToUrl(
isParentDirectory(normalizePath(config.publicDir), resolved)
? url
: resolved,
config,
this
)
: url
s.overwrite(
index,
index + exp.length,
Expand Down
22 changes: 16 additions & 6 deletions packages/vite/src/node/plugins/workerImportMetaUrl.ts
@@ -1,8 +1,9 @@
import JSON5 from 'json5'
import path from 'path'
import type { ResolvedConfig } from '../config'
import type { Plugin } from '../plugin'
import { fileToUrl } from './asset'
import { injectQuery } from '../utils'
import { injectQuery, slash } from '../utils'
import { workerFileToUrl } from './worker'
import { parseRequest } from '../utils'
import { ENV_ENTRY, ENV_PUBLIC_PATH } from '../constants'
Expand Down Expand Up @@ -145,11 +146,20 @@ export function workerImportMetaUrlPlugin(config: ResolvedConfig): Plugin {
index + allExp.length
)
const url = rawUrl.slice(1, -1)
workerResolver ??= config.createResolver({
tryIndex: false,
preferRelative: true
})
const file = (await workerResolver(url, id)) ?? url
let file: string | undefined
if (url.startsWith('.')) {
file = path.resolve(path.dirname(id), url)
} else {
workerResolver ??= config.createResolver({
extensions: [],
tryIndex: false,
preferRelative: true
})
file = await workerResolver(url, id)
file ??= url.startsWith('/')
? slash(path.join(config.publicDir, url))
: slash(path.resolve(path.dirname(id), url))
}

let builtUrl: string
if (isBuild) {
Expand Down

0 comments on commit 50c19ca

Please sign in to comment.