Skip to content

Commit

Permalink
feat: support base option during dev, deprecate build.base (#1556)
Browse files Browse the repository at this point in the history
  • Loading branch information
bompus authored Jan 22, 2021
1 parent 6e7f652 commit 809d4bd
Show file tree
Hide file tree
Showing 25 changed files with 384 additions and 153 deletions.
14 changes: 7 additions & 7 deletions docs/config/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,13 @@ export default ({ command, mode }) => {

See [Project Root](/guide/#project-root) for more details.

### base

- **Type:** `string`
- **Default:** `/`

Base public path when served in development or production. Note the path should start and end with `/`. See [Public Base Path](/guide/build#public-base-path) for more details.

### mode

- **Type:** `string`
Expand Down Expand Up @@ -322,13 +329,6 @@ export default ({ command, mode }) => {

## Build Options

### build.base

- **Type:** `string`
- **Default:** `/`

Base public path when served in production. Note the path should start and end with `/`. See [Public Base Path](/guide/build#public-base-path) for more details.

### build.target

- **Type:** `string`
Expand Down
2 changes: 1 addition & 1 deletion docs/guide/build.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ Legacy browsers can be supported via [@vitejs/plugin-legacy](https://github.com/

- Related: [Asset Handling](./features#asset-handling)

If you are deploying your project under a nested public path, simply specify the [`build.base` config option](/config/#build-base) and all asset paths will be rewritten accordingly. This option can also be specified as a command line flag, e.g. `vite build --base=/my/public/path/`.
If you are deploying your project under a nested public path, simply specify the [`base` config option](/config/#base) and all asset paths will be rewritten accordingly. This option can also be specified as a command line flag, e.g. `vite build --base=/my/public/path/`.

JS-imported asset URLs, CSS `url()` references, and asset references in your `.html` files are all automatically adjusted to respect this option during build.

Expand Down
2 changes: 1 addition & 1 deletion docs/guide/env-and-mode.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ Vite exposes env variables on the special **`import.meta.env`** object. Some bui

- **`import.meta.env.MODE`**: {string} the [mode](#modes) the app is running in.

- **`import.meta.env.BASE_URL`**: {string} the base url the app is being served from. In development, this is always `/`. In production, this is determined by the [`build.base` config option](/config/#build-base).
- **`import.meta.env.BASE_URL`**: {string} the base url the app is being served from. This is determined by the [`base` config option](/config/#base).

- **`import.meta.env.PROD`**: {boolean} whether the app is running in production.

Expand Down
30 changes: 27 additions & 3 deletions packages/playground/assets/__tests__/assets.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,16 +10,40 @@ import {

const assetMatch = isBuild
? /\/foo\/assets\/asset\.\w{8}\.png/
: '/nested/asset.png'
: '/foo/nested/asset.png'

const iconMatch = isBuild ? `/foo/icon.png` : `icon.png`
const iconMatch = `/foo/icon.png`

test('should have no 404s', () => {
browserLogs.forEach((msg) => {
expect(msg).not.toMatch('404')
})
})

describe('injected scripts', () => {
test('@vite/client', async () => {
const hasClient = await page.$(
'script[type="module"][src="/foo/@vite/client"]'
)
if (isBuild) {
expect(hasClient).toBeFalsy()
} else {
expect(hasClient).toBeTruthy()
}
})

test('html-proxy', async () => {
const hasHtmlProxy = await page.$(
'script[type="module"][src="/foo/index.html?html-proxy&index=0.js"]'
)
if (isBuild) {
expect(hasHtmlProxy).toBeFalsy()
} else {
expect(hasHtmlProxy).toBeTruthy()
}
})
})

describe('raw references from /public', () => {
test('load raw js from /public', async () => {
expect(await page.textContent('.raw-js')).toMatch('[success]')
Expand Down Expand Up @@ -70,7 +94,7 @@ describe('css url() references', () => {
})

test('base64 inline', async () => {
const match = isBuild ? `data:image/png;base64` : `/icon.png`
const match = isBuild ? `data:image/png;base64` : `/foo/nested/icon.png`
expect(await getBg('.css-url-base64-inline')).toMatch(match)
expect(await getBg('.css-url-quotes-base64-inline')).toMatch(match)
})
Expand Down
2 changes: 1 addition & 1 deletion packages/playground/assets/vite.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@
* @type {import('vite').UserConfig}
*/
module.exports = {
base: '/foo/',
build: {
base: '/foo/',
outDir: 'dist/foo'
}
}
6 changes: 3 additions & 3 deletions packages/plugin-legacy/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -265,7 +265,7 @@ function viteLegacyPlugin(options = {}) {
tag: 'script',
attrs: {
type: 'module',
src: `${config.build.base}${modernPolyfillFilename}`
src: `${config.base}${modernPolyfillFilename}`

This comment has been minimized.

Copy link
@bompus

bompus Jan 24, 2021

Author Contributor

Can you release a new version of plugin-legacy? current version outputs the config.build.base deprecation warning

}
})
} else if (modernPolyfills.size) {
Expand Down Expand Up @@ -295,7 +295,7 @@ function viteLegacyPlugin(options = {}) {
tag: 'script',
attrs: {
nomodule: true,
src: `${config.build.base}${legacyPolyfillFilename}`
src: `${config.base}${legacyPolyfillFilename}`
},
injectTo: 'body'
})
Expand All @@ -318,7 +318,7 @@ function viteLegacyPlugin(options = {}) {
// script content will stay consistent - which allows using a constant
// hash value for CSP.
id: legacyEntryId,
'data-src': config.build.base + legacyEntryFilename
'data-src': config.base + legacyEntryFilename
},
children: systemJSInlineCode,
injectTo: 'body'
Expand Down
4 changes: 3 additions & 1 deletion packages/plugin-vue/src/template.ts
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,9 @@ export function resolveTemplateCompilerOptions(
// request
if (filename.startsWith(options.root)) {
assetUrlOptions = {
base: '/' + slash(path.relative(options.root, path.dirname(filename)))
base:
options.devServer.config.base +
slash(path.relative(options.root, path.dirname(filename)))
}
}
} else {
Expand Down
11 changes: 9 additions & 2 deletions packages/vite/src/client/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { ErrorOverlay, overlayId } from './overlay'

// injected by the hmr plugin when served
declare const __ROOT__: string
declare const __BASE__: string
declare const __MODE__: string
declare const __DEFINES__: Record<string, any>
declare const __HMR_PROTOCOL__: string
Expand Down Expand Up @@ -38,6 +39,8 @@ const socketProtocol =
__HMR_PROTOCOL__ || (location.protocol === 'https:' ? 'wss' : 'ws')
const socketHost = `${__HMR_HOSTNAME__ || location.hostname}:${__HMR_PORT__}`
const socket = new WebSocket(`${socketProtocol}://${socketHost}`, 'vite-hmr')
const base = __BASE__ || '/'
const baseNoSlash = base.replace(/\/$/, '')

function warnFailedFetch(err: Error, path: string | string[]) {
if (!err.message.match('fetch')) {
Expand Down Expand Up @@ -107,9 +110,10 @@ async function handleMessage(payload: HMRPayload) {
// if html file is edited, only reload the page if the browser is
// currently on that page.
const pagePath = location.pathname
const payloadPath = baseNoSlash + payload.path
if (
pagePath === payload.path ||
(pagePath.endsWith('/') && pagePath + 'index.html' === payload.path)
pagePath === payloadPath ||
(pagePath.endsWith('/') && pagePath + 'index.html' === payloadPath)
) {
location.reload()
}
Expand Down Expand Up @@ -259,6 +263,9 @@ export function removeStyle(id: string) {
}

async function fetchUpdate({ path, acceptedPath, timestamp }: Update) {
path = baseNoSlash + path
acceptedPath = baseNoSlash + acceptedPath

const mod = hotModulesMap.get(path)
if (!mod) {
// In a code-splitting project,
Expand Down
14 changes: 5 additions & 9 deletions packages/vite/src/node/build.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ import { ssrManifestPlugin } from './ssr/ssrManifestPlugin'
export interface BuildOptions {
/**
* Base public path when served in production.
* @default '/'
* @deprecated `base` is now a root-level config option.
*/
base?: string
/**
Expand Down Expand Up @@ -168,11 +168,10 @@ export interface LibraryOptions {

export type LibraryFormats = 'es' | 'cjs' | 'umd' | 'iife'

export function resolveBuildOptions(
raw?: BuildOptions
): Required<BuildOptions> {
const resolved: Required<BuildOptions> = {
base: '/',
export type ResolvedBuildOptions = Required<Omit<BuildOptions, 'base'>>

export function resolveBuildOptions(raw?: BuildOptions): ResolvedBuildOptions {
const resolved: ResolvedBuildOptions = {
target: 'modules',
polyfillDynamicImport: raw?.target !== 'esnext' && !raw?.lib,
outDir: 'dist',
Expand Down Expand Up @@ -207,9 +206,6 @@ export function resolveBuildOptions(
resolved.target = 'es2019'
}

// ensure base ending slash
resolved.base = resolved.base.replace(/([^/])$/, '$1/')

// normalize false string into actual false
if ((resolved.minify as any) === 'false') {
resolved.minify = false
Expand Down
7 changes: 6 additions & 1 deletion packages/vite/src/node/cli.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ interface GlobalCLIOptions {
config?: string
c?: boolean | string
root?: string
base?: string
r?: string
mode?: string
m?: string
Expand All @@ -38,6 +39,7 @@ function cleanOptions(options: GlobalCLIOptions) {
delete ret.config
delete ret.c
delete ret.root
delete ret.base
delete ret.r
delete ret.mode
delete ret.m
Expand All @@ -50,6 +52,7 @@ function cleanOptions(options: GlobalCLIOptions) {
cli
.option('-c, --config <file>', `[string] use specified config file`)
.option('-r, --root <path>', `[string] use specified root directory`)
.option('--base <path>', `[string] public base path (default: /)`)
.option('-l, --logLevel <level>', `[string] silent | error | warn | all`)
.option('--clearScreen', `[boolean] allow/disable clear screen when logging`)
.option('-d, --debug [feat]', `[string | boolean] show debug logs`)
Expand Down Expand Up @@ -77,6 +80,7 @@ cli
try {
const server = await createServer({
root,
base: options.base,
mode: options.mode,
configFile: options.config,
logLevel: options.logLevel,
Expand All @@ -95,7 +99,6 @@ cli
// build
cli
.command('build [root]')
.option('--base <path>', `[string] public base path (default: /)`)
.option('--target <target>', `[string] transpile target (default: 'modules')`)
.option('--outDir <dir>', `[string] output directory (default: dist)`)
.option(
Expand Down Expand Up @@ -141,6 +144,7 @@ cli
try {
await build({
root,
base: options.base,
mode: options.mode,
configFile: options.config,
logLevel: options.logLevel,
Expand Down Expand Up @@ -169,6 +173,7 @@ cli
const config = await resolveConfig(
{
root,
base: options.base,
configFile: options.config,
logLevel: options.logLevel
},
Expand Down
Loading

0 comments on commit 809d4bd

Please sign in to comment.