谈谈vue及webpack在项目中的一些优化

18922次浏览

前言

我觉得前端性能优化是前端工程化的一部分,做前端性能优化有很多可以做的地方,我在很久之前写过一些文章,可以在博客搜索优化,查看相关文章。其实很多性能优化的地方都要把我一个最佳的度。今天主要写一下vue及webpack在项目中的一些优化。

vue项目中的性能优化

其实vue的性能本身就是很good了,要说再进一步优化,可能有一下几个注意点,仅仅是注意点哦!

1、不要在模板里面写过多表达式

如下:

v-if="isShow && isAdmin && (a || b) "

{{haorooms?haorooms:(resource?resource:"haoroomsresource")}}

类似上面这样的表达式,可以是可以,但是过多,就要通过其他方式,例如可以通过methods 或computed 封装方法。用方法的好处是方便我们在多处判断相同的表达式,其他权限相同的元素再判断展示的时候调用同一个方法即可。

2、循环调用子组件时添加 key

这一点相信很多人都能做的到,用vscode开发的时候,假如不加key,编辑器也会出现警告!循环key最好如下: (item, index) in arr,然后 :key="index",假如数组数据是这样的 ['a' , 'b', 'c', 'a'],使用 :key="item" 显然没有意义。

3、v-show,v-if 的使用

频繁切换的使用 v-show,不频繁切换的使用 v-if。

注意:v-if一个组件,可以让组件重新渲染,通过v-if,我们可以让组件按照一定执行循序执行。

4、尽量不使用 float 布局

尽量少用float,可以用flex或者grid布局。

5、Object.freeze()去除Observer

长久不变的大数据,可以用Object.freeze()去除Observer监听。使用了Object.freeze()这个方法,更改数据,视图也是会变的。例如如下:

export default {
  name: 'haorooms test',
  data () {
    return {
      list: Object.freeze([
            { value: 1 },
            { value: 2 }
        ])
    }
  },
   created(){
       this.list[0].value = 100;
       console.log(this.list);
       this.list=[];
       console.log(this.list);
    }
}

enter image description here

如上图输出,Object.freeze可以取消监听,但是还是可以改变数值改变dom的。

给list重新赋值之后,又恢复了监听。

6、慎用deep watch

数量量大,开启deep监听的话,很可能造成更大的开销。

7、vue-router

路由优化,可以看路由懒加载

或者如下:

const Foo = r => require.ensure([], () => r(require('./Foo.vue')), 'haorooms-foo')
const Bar = r => require.ensure([], () => r(require('./Bar.vue')), 'haorooms-foo')
const Baz = r => require.ensure([], () => r(require('./Baz.vue')), 'haorooms-foo')

8、减少不必要的依赖包

例如有些项目用到了图表(echarts),可以选择加载依赖包,不用加载整个echarts库。

9、按需加载

可以用require或者import()按需加载你需要的组件,关于require和import,请看:http://www.haorooms.com/post/vue_project_cg 最后的动态加载依赖项。

10、vue中使用keep-alive

vue2.0提供了一个keep-alive组件,用来缓存组件,避免多次加载相应的组件,减少性能消耗

<keep-alive>
<component>
  <!-- 组件将被缓存 -->
</component>
</keep-alive>

使用router. meta属性

// 这是目前用的比较多的方式
<keep-alive>
    <router-view v-if="$route.meta.keepAlive"></router-view>
</keep-alive>
<router-view v-if="!$route.meta.keepAlive"></router-view>

router设置

... 
  routes: [
    { path: '/', redirect: '/index',  component: Index, meta: { keepAlive: true }},
    {
      path: '/common',
      component: TestParent,
      children: [
        { path: '/test2', component: Test2, meta: { keepAlive: true } } 
      ]
    }
    ....
    // 表示index和test2都使用keep-alive

keep-alive是一把双刃剑,确实需要缓存组件的时候才使用!

11、善于运用事件代理

我们用 v-for 渲染大量的同样的 DOM 结构时,每个上面都加一个点击事件,这样不是很好,可以考虑通过 HTML5 的 data 的自定义属性做事件代理。,方式如下:

<template>
  <div  @click="clickfn">
     <component v-for="(item,index) in 1000" :key="index"  data-click="clickName"></component>
  </div>
</template>

<script>
  export default {
    data () {
      return {
      }
    },
    methods: {
      clickfn(e) {
        if(e.target.dataset.click == 'clickName') {
            console.log('通过事件委托拿到了自定义属性,这里可以写事件了!')
        }
      }
    }
  }
</script>

注:具体情况具体分析,假如click事件要传递参数等,这种方式可能不是很适合了!

webpack相关

webpack功能太强大的,关于跨域,webpack提供了http-proxy-middleware。webpack也提供了css打包去重的一些方法:optimize-css-assets-webpack-plugin

如何减少webpack打包体积,加快webpack的打包速度呢?

解决方法很简单,打包 vender 时不打包 vue、vuex、vue-router、axios 等,换用国内的 bootcdn 直接引入到根目录的 index.html 中。

例如:

<script src="//cdn.bootcss.com/vue/2.2.5/vue.min.js"></script>
<script src="//cdn.bootcss.com/vue-router/2.3.0/vue-router.min.js"></script>
<script src="//cdn.bootcss.com/vuex/2.2.1/vuex.min.js"></script>
<script src="//cdn.bootcss.com/axios/0.15.3/axios.min.js"></script>

在 webpack 里有个 externals,可以忽略不需要打包的库

externals: {
  'vue': 'Vue',
  'vue-router': 'VueRouter',
  'vuex': 'Vuex',
  'axios': 'axios'
}

此时的 vender 包会非常小,如果不够小还可以拆分其他的库,此时虽然增加了请求的数量,但是远比原来的快了很多!

Tags: vuewebpack

相关文章:

  1. web
    1
    vue 保存完 编译速度太慢
  2. web
    2
    编译设置是在哪个文件