Lake's Blog Lake's Blog
首页
HCFrame
  • 博客搭建

    • 搜索引擎
    • SEO优化
    • 问题记录
  • Vue

    • 问题记录
  • uni-app
  • 开发

    • Spring
  • 数据库及中间件

    • Elasticsearch
    • SQL
  • 杂谈

    • 杂谈
  • 微服务

    • nacos
    • CAS
  • 算法说明

    • algorithm
  • leetCode

    • leetCode
  • 代理

    • Nginx
  • Linux

    • ubuntu
  • Docker
  • 数据库
  • 消息队列
  • openwrt
  • 友情链接
关于
  • 网站
  • 资源
  • 分类
  • 标签
  • 归档
GitHub

Lake Liu

很菜的程序员
首页
HCFrame
  • 博客搭建

    • 搜索引擎
    • SEO优化
    • 问题记录
  • Vue

    • 问题记录
  • uni-app
  • 开发

    • Spring
  • 数据库及中间件

    • Elasticsearch
    • SQL
  • 杂谈

    • 杂谈
  • 微服务

    • nacos
    • CAS
  • 算法说明

    • algorithm
  • leetCode

    • leetCode
  • 代理

    • Nginx
  • Linux

    • ubuntu
  • Docker
  • 数据库
  • 消息队列
  • openwrt
  • 友情链接
关于
  • 网站
  • 资源
  • 分类
  • 标签
  • 归档
GitHub
  • 博客搭建

  • VUE

    • 问题记录

      • 前端传值不能带中括号???
      • Vue中使用debounce防抖基于Typescript
      • Vue-typescript项目兼容IE浏览器
      • Vue-typescript Long类型失去精度
      • Vue-typescript 打包成app后如何自动更新
      • Vue typescript 如何极限压缩编译静态资源
        • 前言
        • 一、安装依赖
        • 二、压缩图片
          • 1. 处理图片
          • 2. 打开vue.config.js 文件
          • 3. 编写压缩图片配置
        • 三、压缩资源
          • 1. 打开vue.config.js 文件
          • 2. 编写压缩配置
        • 四、抽取公共代码打包
          • 1. 打开vue.config.js 文件
          • 2. 编写抽取公共代码配置
        • 五、引用CDN
          • 1. 打开vue.config.js 文件
          • 2. 配置CDN
        • 六、配置Nginx
        • 七、完整的配置文件
  • UNIAPP

Vue typescript 如何极限压缩编译静态资源

# Vue typescript 如何极限压缩编译后静态资源

# 前言

近期开发项目,由于资源有限,云服务器只有1m带宽。

vue初始打包的静态资源,通过浏览器加载需要近1分钟的时间。

所以需要将静态资源进行压缩及相应处理,最终浏览器访问时间为5秒钟。

# 一、安装依赖

首先安装依赖 compression-webpack-plugin image-webpack-loader

  • yarn
yarn add compression-webpack-plugin -D
yarn add image-webpack-loader -D
1
2
  • npm
npm install compression-webpack-plugin --save-dev
npm install image-webpack-loader --save-dev
1
2

注意

记住,依赖一定要安装在 devDependencies 下,否则会增大你的打包体积

# 二、压缩图片

提示

图片处理其实有很多种方式,例如引入cdn服务器等。

此处介绍的方式为,需要将图片和静态资源打包在一起时的解决方案。

# 1. 处理图片

  • 首先需要对图片进行处理,处理方式自行选择,例如使用ps将图片质量减小等。
  • 此处推荐在线压缩图片,处理图片的网站https://imagecompressor.com/zh/

提示

此处再推荐一个其他的在线处理图片的网站https://www.websiteplanet.com/zh-hans/webtools/imagecompressor/

Thanks for Katherine Miller suggestion.

注意

不保证网站是否会收集图片数据,如果数据较为敏感,请不要上传,自行进行处理。

此步骤主要是为了将原始图片进一步压缩。

# 2. 打开vue.config.js 文件

打开vue的配置文件

# 3. 编写压缩图片配置

需要在文件中编写相应的压缩,可以对图片进行二次压缩。请根据需求自行配置。

详细使用说明可参考 https://www.npmjs.com/package/image-webpack-loader

module.exports = {
  // 省略部分配置项
  ....
  ,
  chainWebpack: config => {
    // 省略部分配置项
    ...
    // 判断环境不为开发环境
    config
      .when(process.env.NODE_ENV !== 'development',
        config => {
      		// 压缩图片配置
          config.module
            .rule('images')
            .use('image-webpack-loader')
            .loader('image-webpack-loader')
            .options({
              mozjpeg: { progressive: true, quality: 65 }, // Compress JPEG images
              optipng: { enabled: false }, // Compress PNG images
              pngquant: { quality: [0.65, 0.9], speed: 4 }, // Compress PNG images
              gifsicle: { interlaced: false } // Compress SVG images
            })
            .end()
        }
     )
  }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27

# 三、压缩资源

# 1. 打开vue.config.js 文件

打开vue的配置文件

# 2. 编写压缩配置

配置压缩资源,具体配置项可参考https://www.npmjs.com/package/compression-webpack-plugin

// 引入压缩依赖
const CompressionPlugin = require('compression-webpack-plugin')
// 需要压缩的文件的正则
const productionGzipExtensions = /\.(js|css|json|txt|html|ico|svg)(\?.*)?$/i

module.exports = {
 // 省略部分配置项
  ....
  ,
  chainWebpack: config => {  
    // 省略部分配置项
    ...
    // 判断环境不为开发环境
    config
      .when(process.env.NODE_ENV !== 'development',
        config => {
          // 打包成gzip压缩文件
          config.plugin('compressionPlugin')
            .use(new CompressionPlugin({
              filename: '[path].gz[query]',
              algorithm: 'gzip',
              test: productionGzipExtensions,
              threshold: 10240,
              minRatio: 0.8,
              deleteOriginalAssets: true
            }))
        }
     )
  }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30

# 四、抽取公共代码打包

# 1. 打开vue.config.js 文件

打开vue的配置文件

# 2. 编写抽取公共代码配置

此处为将代码中的公共部分抽取出来,统一打包,可减小打包后的代码体积。

module.exports = {
  // 省略部分配置项
  ....
  ,
  chainWebpack: config => {
    // 省略部分配置项
    ...
    // 判断环境不为开发环境
    config
      .when(process.env.NODE_ENV !== 'development',        
          config
            .optimization.splitChunks({
              chunks: 'all',
              cacheGroups: {
                libs: {
                  name: 'chunk-libs',
                  test: /[\\/]node_modules[\\/]/,
                  priority: 10,
                  chunks: 'initial' // only package third parties that are initially dependent
                },
                elementUI: {
                  name: 'chunk-elementUI', // split elementUI into a single package
                  priority: 20, // the weight needs to be larger than libs and app or it will be packaged into libs or app
                  test: /[\\/]node_modules[\\/]_?element-ui(.*)/ // in order to adapt to cnpm
                },
                commons: {
                  name: 'chunk-commons',
                  test: path.resolve(__dirname, 'src/components'),
                  minChunks: 3, //  minimum common number
                  priority: 5,
                  reuseExistingChunk: true
                }
              }
            })
          config.optimization.runtimeChunk('single')
        }
      )
  }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39

# 五、引用CDN

注意

此处引用的js和css的公共cdn代码库。

引入cdn后可有效减少从服务获取的资源数量。

但是有风险,一旦cdn服务出问题,你的网站也将无法访问。

此步骤请谨慎选择或使用自己的cdn服务器。

# 1. 打开vue.config.js 文件

打开vue的配置文件

# 2. 配置CDN

const cdn = {
  css: [
    'https://cdn.bootcdn.net/ajax/libs/element-ui/2.15.1/theme-chalk/index.min.css',
    'https://cdn.bootcdn.net/ajax/libs/nprogress/0.2.0/nprogress.min.css'
  ],
  js: [
    // vue必须在第一个
    'https://cdn.bootcss.com/vue/2.6.11/vue.min.js',
    'https://cdn.bootcss.com/vuex/3.2.0/vuex.min.js',
    'https://cdn.bootcss.com/vue-router/3.4.3/vue-router.min.js',
    'https://cdn.bootcss.com/axios/0.19.2/axios.min.js',
    'https://cdn.bootcss.com/qs/6.5.1/qs.min.js',
    'https://cdn.bootcdn.net/ajax/libs/element-ui/2.15.1/index.min.js',
    'https://cdn.bootcdn.net/ajax/libs/echarts/4.7.0/echarts-en.min.js',
    'https://cdn.bootcdn.net/ajax/libs/dexie/3.0.3/dexie.min.js',
    'https://cdn.bootcdn.net/ajax/libs/js-cookie/2.2.1/js.cookie.min.js',
    'https://cdn.bootcdn.net/ajax/libs/nprogress/0.2.0/nprogress.min.js'
  ]
}

module.exports = {
   // 省略部分配置项
  ....
  ,
  chainWebpack: config => {    
    config
      .when(process.env.NODE_ENV !== 'development',
        config => {
      		// 设置不打包的依赖,请根据自己需求进行修改
          const externals = {
            vue: 'Vue',
            vuex: 'Vuex',
            'vue-router': 'VueRouter',
            axios: 'axios',
            qs: 'Qs',
            'element-ui': 'ELEMENT',
            echarts: 'echarts',
            dexie: 'Dexie',
            'js-cookie': 'Cookies',
            nprogress: 'NProgress'
          }
          config.externals(externals)
          // 引入cdn
          config.plugin('html').tap(args => {
            args[0].cdn = cdn
            return args
          })
        }
      )
  }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51

# 六、配置Nginx

提示

如果你使用的ngxin服务器当做静态资源服务,则可以开启gzip配置。

开启后访问速度会获得极大的提升

http {
		# 省略部分配置
    ...
    # 开启gzip
    gzip  on;

    gzip_static on;
    # 设置缓冲区大小
    gzip_buffers 4 16k;

    #压缩级别官网建议是6
    gzip_comp_level 6;
    #压缩的类型
    gzip_types text/plain application/javascript text/css application/xml text/javascript application/x-httpd-php;
    
    # 省略部分配置
    ...
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

# 七、完整的配置文件

// eslint-disable-next-line @typescript-eslint/no-var-requires
const path = require('path')
// eslint-disable-next-line @typescript-eslint/no-var-requires
const CompressionPlugin = require('compression-webpack-plugin')
const name = 'xxxx系统'
const productionGzipExtensions = /\.(js|css|json|txt|html|ico|svg)(\?.*)?$/i
const cdn = {
  css: [
    'https://cdn.bootcdn.net/ajax/libs/element-ui/2.15.1/theme-chalk/index.min.css',
    'https://cdn.bootcdn.net/ajax/libs/nprogress/0.2.0/nprogress.min.css'
  ],
  js: [
    // vue必须在第一个
    'https://cdn.bootcss.com/vue/2.6.11/vue.min.js',
    'https://cdn.bootcss.com/vuex/3.2.0/vuex.min.js',
    'https://cdn.bootcss.com/vue-router/3.4.3/vue-router.min.js',
    'https://cdn.bootcss.com/axios/0.19.2/axios.min.js',
    'https://cdn.bootcss.com/qs/6.5.1/qs.min.js',
    'https://cdn.bootcdn.net/ajax/libs/element-ui/2.15.1/index.min.js',
    'https://cdn.bootcdn.net/ajax/libs/echarts/4.7.0/echarts-en.min.js',
    'https://cdn.bootcdn.net/ajax/libs/dexie/3.0.3/dexie.min.js',
    'https://cdn.bootcdn.net/ajax/libs/js-cookie/2.2.1/js.cookie.min.js',
    'https://cdn.bootcdn.net/ajax/libs/nprogress/0.2.0/nprogress.min.js'
  ]
}

module.exports = {
  publicPath: './',
  outputDir: 'dist',
  // 放置生成的静态资源 (js、css、img、fonts) 的 (相对于 outputDir 的) 目录。    资源放的目录
  assetsDir: './static',
  // 指定生成的 index.html 的输出路径 (相对于 outputDir)。也可以是一个绝对路径    index的路劲和名字
  indexPath: './index.html',
  // publicPath: process.env.NODE_ENV === 'production' ? '/vue-typescript-admin-template/' : '/',
  lintOnSave: process.env.NODE_ENV === 'development',
  transpileDependencies: ['fuse.js', 'vuex-module-decorators', 'clipboard', 'markdown-it-vue'],
  productionSourceMap: false,
  devServer: {
    port: devServerPort,
    open: true,
    overlay: {
      warnings: false,
      errors: true
    },
    progress: false,
    proxy: {
      '/': {
        target: 'http://localhost:8082/',        
        withCredentials: true,
        changeOrigin: true, // needed for virtual hosted sites
        ws: true, // proxy websockets        
      }
    }
  },
  pwa: {
    name: name,
    workboxPluginMode: 'InjectManifest',
    workboxOptions: {
      swSrc: path.resolve(__dirname, 'src/pwa/service-worker.js')
    }
  },
  pluginOptions: {
    'style-resources-loader': {
      preProcessor: 'scss',
      patterns: [
        path.resolve(__dirname, 'src/styles/_variables.scss'),
        path.resolve(__dirname, 'src/styles/_mixins.scss')
      ]
    }
  },
  chainWebpack: config => {
    // provide the app's title in webpack's name field, so that
    // it can be accessed in index.html to inject the correct title.
    config.set('name', name)    
    config
      .when(process.env.NODE_ENV !== 'development',
        config => {
          config.module
            .rule('images')
            .use('image-webpack-loader')
            .loader('image-webpack-loader')
            .options({
              // { bypassOnDebug: true }
              mozjpeg: { progressive: true, quality: 65 }, // ∂Compress JPEG images
              optipng: { enabled: false }, // Compress PNG images
              pngquant: { quality: [0.65, 0.9], speed: 4 }, // Compress PNG images
              gifsicle: { interlaced: false } // Compress SVG images
              // webp: { quality: 75 }
            })
            .end()

          const externals = {
            vue: 'Vue',
            vuex: 'Vuex',
            'vue-router': 'VueRouter',
            axios: 'axios',
            qs: 'Qs',
            'element-ui': 'ELEMENT',
            echarts: 'echarts',
            dexie: 'Dexie',
            'js-cookie': 'Cookies',
            nprogress: 'NProgress'
          }
          config.externals(externals)
          // 引入cdn
          config.plugin('html').tap(args => {
            args[0].cdn = cdn
            return args
          })
          // 打包成gzip压缩文件
          config.plugin('compressionPlugin')
            .use(new CompressionPlugin({
              filename: '[path].gz[query]',
              algorithm: 'gzip',
              test: productionGzipExtensions,
              threshold: 10240,
              minRatio: 0.8,
              deleteOriginalAssets: true
            }))

          config
            .optimization.splitChunks({
              chunks: 'all',
              cacheGroups: {
                libs: {
                  name: 'chunk-libs',
                  test: /[\\/]node_modules[\\/]/,
                  priority: 10,
                  chunks: 'initial' // only package third parties that are initially dependent
                },
                elementUI: {
                  name: 'chunk-elementUI', // split elementUI into a single package
                  priority: 20, // the weight needs to be larger than libs and app or it will be packaged into libs or app
                  test: /[\\/]node_modules[\\/]_?element-ui(.*)/ // in order to adapt to cnpm
                },
                commons: {
                  name: 'chunk-commons',
                  test: path.resolve(__dirname, 'src/components'),
                  minChunks: 3, //  minimum common number
                  priority: 5,
                  reuseExistingChunk: true
                }
              }
            })
          config.optimization.runtimeChunk('single')
        }
      )
  }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
编辑
#Typescript#Vue
上次更新: 2023/06/28, 06:09:41
Vue-typescript 打包成app后如何自动更新
uniapp中实现h5扫码功能(微信版)

← Vue-typescript 打包成app后如何自动更新 uniapp中实现h5扫码功能(微信版)→

最近更新
01
IDEA行号太宽
03-11
02
uniapp中实现h5扫码功能(微信版)
08-12
03
Docker安装Rabbitmq
07-22
更多文章>
本站总访问量次 | 您是本站第位访问者
Theme by Vdoing | Copyright © 2020-2024 Lake Liu | MIT License | 背景图、Logo、头像设计@Drrizzee
  • 跟随系统
  • 深色模式
  • 浅色模式
  • 阅读模式