doc: fix the problem of font file loading failure (#985)

* doc: fix the problem of font file loading failure

* doc: Improve the solution of font file and background image loading failure

* doc: recommend static resources to upload to CDN

* Update docs/faq/README.md

* Update docs/faq/README.md

Co-authored-by: gongshun <gongshun@gridsum.com>
Co-authored-by: Kuitos <kuitos.lau@gmail.com>
This commit is contained in:
gongshun 2020-10-12 13:42:34 +08:00 committed by GitHub
parent efe5d2bf87
commit b7d5adeb2a
2 changed files with 419 additions and 46 deletions

View File

@ -116,6 +116,215 @@ You need to set your publicPath configuration to an absolute url, and in develop
}
```
### After the micro-app is bundled, the font files and images in the css load 404
The reason is that `qiankun` changed the external link style to the inline style, but the loading path of the font file and background image is a relative path.
Once the `css` file is packaged, you cannot modify the path of the font file and background image by dynamically modifying the `publicPath`.
There are mainly the following solutions:
1. Upload all static resources such as pictures to `cdn`, and directly reference the address of `cdn` in `css` (**recommended**)
2. Use the `url-loader` of `webpack` to package font files and images as `base64` (suitable for projects with small font files and images)(**recommended**)
```js
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|webp|woff2?|eot|ttf|otf)$/i,
use: [
{
loader: 'url-loader',
options: {},
},
],
},
],
},
};
```
`vue-cli3` project:
```js
module.exports = {
chainWebpack: (config) => {
config.module
.rule('fonts')
.use('url-loader')
.loader('url-loader')
.options({})
.end()
config.module
.rule('images')
.use('url-loader')
.loader('url-loader')
.options({})
.end()
},
}
3. Use the `file-loader` of `webpack` to inject the full path when packaging it (suitable for projects with large font files and images)
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|webp)$/i,
use: [
{
loader: 'file-loader',
options: {
name: 'img/[name].[hash:8].[ext]',
publicPath
},
},
],
},
{
test: /\.(woff2?|eot|ttf|otf)$/i,
use: [
{
loader: 'file-loader',
options: {
name: 'fonts/[name].[hash:8].[ext]',
publicPath
},
},
],
},
],
},
};
```
`vue-cli3` project:
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
chainWebpack: (config) => {
const fontRule = config.module.rule('fonts');
fontRule.uses.clear();
fontRule
.use('file-loader')
.loader('file-loader')
.options({
name: 'fonts/[name].[hash:8].[ext]',
publicPath
})
.end()
const imgRule = config.module.rule('images');
imgRule.uses.clear();
imgRule
.use('file-loader')
.loader('file-loader')
.options({
name: 'img/[name].[hash:8].[ext]',
publicPath
})
.end()
},
}
```
4. Combine the two schemes, convert small files to `base64`, and inject path prefixes for large files
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|webp)$/i,
use: [
{
loader: 'url-loader',
options: {},
fallback: {
loader: 'file-loader',
options: {
name: 'img/[name].[hash:8].[ext]',
publicPath
}
}
},
],
},
{
test: /\.(woff2?|eot|ttf|otf)$/i,
use: [
{
loader: 'url-loader',
options: {},
fallback: {
loader: 'file-loader',
options: {
name: 'fonts/[name].[hash:8].[ext]',
publicPath
}
}
},
],
},
],
},
};
```
`vue-cli3` project
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
chainWebpack: (config) => {
config.module.rule('fonts')
.use('url-loader')
.loader('url-loader')
.options({
limit: 4096, // Less than 4kb will be packaged as base64
fallback: {
loader: 'file-loader',
options: {
name: 'fonts/[name].[hash:8].[ext]',
publicPath
}
}
})
.end();
config.module.rule('images')
.use('url-loader')
.loader('url-loader')
.options({
limit: 4096, // Less than 4kb will be packaged as base64
fallback: {
loader: 'file-loader',
options: {
name: 'img/[name].[hash:8].[ext]',
publicPath
}
}
})
},
}
```
5. The `vue-cli3` project can package `css` into `js` without generating files separately (not recommended, only suitable for projects with less `css`)
Configuration reference [vue-cli3 official website](https://cli.vuejs.org/zh/config/#css-extract):
```js
module.exports = {
css: {
extract: false
},
}
```
## Must a sub app asset support cors?
Yes it is.
@ -315,29 +524,6 @@ location = /index.html {
}
```
## Font file loading error after micro application packaging
The reason is that `qiankun` changed the external link style to the inline style, but the loading path of the font file is a relative path.
Modify the `webpack` package and inject the path prefix to the font file:
```js
module.exports = {
chainWebpack: (config) => {
config.module
.rule('fonts')
.test(/.(ttf|otf|eot|woff|woff2)$/)
.use('url-loader')
.loader('url-loader')
.tap(options => ({
name:'/fonts/[name].[hash:8].[ext]',
limit: 4096, // Fonts smaller than 4KB will be packaged as base64
}))
.end()
},
}
```
## micro app styles was lost when using config entry
Some scenarios we had to use config entry to load micro app (** not recommended **):

View File

@ -118,6 +118,216 @@ runtime publicPath 主要解决的是微应用动态载入的 脚本、样式、
}
```
### 微应用打包之后 css 中的字体文件和图片加载 404
原因是 `qiankun` 将外链样式改成了内联样式,但是字体文件和背景图片的加载路径是相对路径。
`css` 文件一旦打包完成,就无法通过动态修改 `publicPath` 来修正其中的字体文件和背景图片的路径。
主要有以下几个解决方案:
1. 所有图片等静态资源上传至 `cdn``css` 中直接引用 `cdn` 地址(**推荐**
2. 借助 `webpack``url-loader` 将字体文件和图片打包成 `base64`(适用于字体文件和图片体积小的项目)(**推荐**
```js
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|webp|woff2?|eot|ttf|otf)$/i,
use: [
{
loader: 'url-loader',
options: {},
},
],
},
],
},
};
```
`vue-cli3` 项目写法:
```js
module.exports = {
chainWebpack: (config) => {
config.module
.rule('fonts')
.use('url-loader')
.loader('url-loader')
.options({})
.end()
config.module
.rule('images')
.use('url-loader')
.loader('url-loader')
.options({})
.end()
},
}
```
3. 借助 `webpack``file-loader` ,在打包时给其注入完整路径(适用于字体文件和图片体积比较大的项目)
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|webp)$/i,
use: [
{
loader: 'file-loader',
options: {
name: 'img/[name].[hash:8].[ext]',
publicPath
},
},
],
},
{
test: /\.(woff2?|eot|ttf|otf)$/i,
use: [
{
loader: 'file-loader',
options: {
name: 'fonts/[name].[hash:8].[ext]',
publicPath
},
},
],
},
],
},
};
```
`vue-cli3` 项目写法:
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
chainWebpack: (config) => {
const fontRule = config.module.rule('fonts');
fontRule.uses.clear();
fontRule
.use('file-loader')
.loader('file-loader')
.options({
name: 'fonts/[name].[hash:8].[ext]',
publicPath
})
.end()
const imgRule = config.module.rule('images');
imgRule.uses.clear();
imgRule
.use('file-loader')
.loader('file-loader')
.options({
name: 'img/[name].[hash:8].[ext]',
publicPath
})
.end()
},
}
```
4. 将两种方案结合起来,小文件转 `base64` ,大文件注入路径前缀
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|webp)$/i,
use: [
{
loader: 'url-loader',
options: {},
fallback: {
loader: 'file-loader',
options: {
name: 'img/[name].[hash:8].[ext]',
publicPath
}
}
},
],
},
{
test: /\.(woff2?|eot|ttf|otf)$/i,
use: [
{
loader: 'url-loader',
options: {},
fallback: {
loader: 'file-loader',
options: {
name: 'fonts/[name].[hash:8].[ext]',
publicPath
}
}
},
],
},
],
},
};
```
`vue-cli3` 项目写法:
```js
const publicPath = process.env.NODE_ENV === "production" ? 'https://qiankun.umijs.org/' : `http://localhost:${port}`;
module.exports = {
chainWebpack: (config) => {
config.module.rule('fonts')
.use('url-loader')
.loader('url-loader')
.options({
limit: 4096, // 小于4kb将会被打包成 base64
fallback: {
loader: 'file-loader',
options: {
name: 'fonts/[name].[hash:8].[ext]',
publicPath
}
}
})
.end();
config.module.rule('images')
.use('url-loader')
.loader('url-loader')
.options({
limit: 4096, // 小于4kb将会被打包成 base64
fallback: {
loader: 'file-loader',
options: {
name: 'img/[name].[hash:8].[ext]',
publicPath
}
}
})
},
}
```
5. `vue-cli3` 项目可以将 `css` 打包到 `js`里面,不单独生成文件(不推荐,仅适用于 `css` 较少的项目)
配置参考 [vue-cli3 官网](https://cli.vuejs.org/zh/config/#css-extract):
```js
module.exports = {
css: {
extract: false
},
}
```
## 微应用静态资源一定要支持跨域吗?
是的。
@ -385,29 +595,6 @@ location = /index.html {
}
```
## 微应用打包之后字体文件加载出错
原因是 `qiankun` 将外链样式改成了内联样式,但是字体文件的加载路径是相对路径。
修改一下 `webpack` 打包,给字体文件注入路径前缀即可:
```js
module.exports = {
chainWebpack: (config) => {
config.module
.rule('fonts')
.test(/.(ttf|otf|eot|woff|woff2)$/)
.use('url-loader')
.loader('url-loader')
.tap(options => ({
name: '/fonts/[name].[hash:8].[ext]',
limit: 4096, // 小于4KB的字体将会被打包成 base64
}))
.end()
},
}
```
## 使用 config entry 时微应用样式丢失
有些场景下我们会使用 config entry 的方式加载微应用(**不推荐**