diff --git a/docs/README.md b/docs/README.md index e2930a8a0..15ac58631 100644 --- a/docs/README.md +++ b/docs/README.md @@ -57,8 +57,6 @@ See [CLI Service docs](./cli-service.md) for all available commands. The file `public/index.html` is a template that will be processed with [html-webpack-plugin](https://github.com/jantimon/html-webpack-plugin). During build, asset links will be injected automatically. In addition, Vue CLI also automatically injects resource hints (`preload/prefetch`), manifest/icon links (when PWA plugin is used) and inlines the webpack runtime / chunk manifest for optimal performance. -You can edit the file to add your own tags, but note one thing: you need to prefix links to assets with `<%= webpackConfig.output.publicPath %>` in case you are not deploying your app at the root of a domain. - ### Static Assets Handling Static assets can be handled in two different ways: diff --git a/docs/assets.md b/docs/assets.md index d23509bf9..018a57d99 100644 --- a/docs/assets.md +++ b/docs/assets.md @@ -1 +1,78 @@ -## [TODO] Static Asset Handling +## Static Asset Handling + +- [Relative Path Imports](#relative-path-imports) + - [URL Transform Rules](#url-transform-rules) +- [The `public` Folder](#the-public-folder) + - [When to use the `public` folder](#when-to-use-the-public-folder) + +### Relative Path Imports + +When you reference a static asset using relative path inside JavaScript, CSS or `*.vue` files, the asset will be included into webpack's dependency graph. During this compilation process, all asset URLs such as ``, `background: url(...)` and CSS `@import` are **resolved as module dependencies**. + +For example, `url(./image.png)` will be translated into `require('./image.png')`, and + +``` html + +``` + +will be compiled into: + +``` js +createElement('img', { attrs: { src: require('../image.png') }}) +``` + +Internally, we use `file-loader` to determine the final file location with version hashes and correct public base paths, and use `url-loader` to conditional inline assets that are smaller than 10kb, reducing the amount of HTTP requests. + +#### URL Transform Rules + +- If the URL is an absolute path (e.g. `/images/foo.png`), it will be preserved as-is. + +- If the URL starts with `.`, it's interpreted as a relative module request and resolved based on the folder structure on your file system. + +- If the URL starts with `~`, anything after it is interpreted as a module request. This means you can even reference assets inside node modules: + + ``` html + + ``` + +- If the URL starts with `@`, it's also interpreted as a module request. This is useful because Vue CLI by default aliases `@` to `/src`. + +### The `public` Folder + +Any static assets placed in the `public` folder will simply be copied and not go through webpack. You need to reference to them using absolute paths. + +Note we recommended importing assets as part of your module dependency graph so that they will go through webpack with the following benefits: + +- Scripts and stylesheets get minified and bundled together to avoid extra network requests. +- Missing files cause compilation errors instead of 404 errors for your users. +- Result filenames include content hashes so you don’t need to worry about browsers caching their old versions. + +The `public` directory is provided as an **escape hatch**, and when you reference it via absolute path, you need to take into account where your app will be deployed. If your app is not deployed at the root of a domain, you will need to prefix your URLs with the base path: + +- In `public/index.html`, you need to prefix the link with `<%= webpackConfig.output.publicPath %>`: + + ``` html + + ``` + +- In templates, you will need to first pass the base URL to your component: + + ``` js + data () { + return { + baseUrl: process.env.BASE_URL + } + } + ``` + + Then: + + ``` html + + ``` + +#### When to use the `public` folder + +- You need a file with a specific name in the build output. +- You have thousands of images and need to dynamically reference their paths. +- Some library may be incompatible with Webpack and you have no other option but to include it as a ` + + + + +``` + +#### Bundle that Registers Multiple Web Components + +When building a web component bundle, you can also target multiple components by using a glob as entry: + +``` +vue-cli-service build --target wc --name foo 'src/components/*.vue' +``` + +When building multiple web components, `--name` will be used as the prefix and the custom element name will be inferred from the component filename. For example, with `--name foo` and a component named `HelloWorld.vue`, the resulting custom element will be registered as ``. + +### Async Web Component + +> [Compatibility](https://github.com/vuejs/vue-web-component-wrapper#compatibility) + +When targeting multiple web components, the bundle may become quite large, and the user may only use a few of the components your bundle registers. The async web component mode produces a code-split bundle with a small entry file that provides the shared runtime between all the components, and registers all the custom elements upfront. The actual implementation of a component is then fetched on-demand only when an instance of the corresponding custom element is used on the page: + +``` +vue-cli-service build --target wc-async --name foo 'src/components/*.vue' +``` + +``` +File Size Gzipped + +dist/foo.0.min.js 12.80 kb 8.09 kb +dist/foo.min.js 7.45 kb 3.17 kb +dist/foo.1.min.js 2.91 kb 1.02 kb +dist/foo.js 22.51 kb 6.67 kb +dist/foo.0.js 17.27 kb 8.83 kb +dist/foo.1.js 5.24 kb 1.64 kb +``` + +Now on the page, the user only needs to include Vue and the entry file: + +``` html + + + + + +```