vue-cli2打包前和打包后的css前缀不一致的问题解决


Posted in Javascript onAugust 24, 2018

??乱还?/strong>

最近基于vue-cli2 学习webpack,将vue-cli2的webpack配置强撸了一遍,感觉身体已被掏空。。。但还是收获不少的,起码掌握了webpack的一些基本套路、开发环境和生产环境的概念、根据不同的环境写不同的webpack配置、和一些常用插件的用法等。

问题来了

基于vue-cli不用自己配置webpack开撸项目是十分爽的,但当我在撸得正爽的时候发现一个问题,就是项目打包前和打包后的css前缀不一致的,如下(浏览器:Chrome):

--给app.vue下的img添加样式

img{
 display: flex;
 transform: translateX(200px)
}

--打包前(即开发环境)img的样式

vue-cli2打包前和打包后的css前缀不一致的问题解决

--打包后(即生产环境)img的样式

vue-cli2打包前和打包后的css前缀不一致的问题解决

根据上面可看出打包前和打包后元素所带的css前缀不一致了。当我们给一个元素设置css3属性时,是希望它带有浏览器前缀来兼容的。vue-cli也给我们搭建这样的功能(是通过配置postcss的autoprefixer实现的)

--postcss配置写在.postcssrc.js,

module.exports = {
 "plugins": {
  "postcss-import": {},
  "postcss-url": {},
  // to edit target browsers: use "browserslist" field in package.json
  "autoprefixer": {}
 }
}

--浏览器规则则写在package.json上,

"browserslist": [
  "> 1%",
  "last 2 versions",
  "not ie <= 8"
 ]

--开发环境(build/webpack.dev.conf.js)样式相关的loader

module: {
  rules: utils.styleLoaders({ 
   sourceMap: config.dev.cssSourceMap, 
   usePostCSS: true })
 },

--生产环境(build/webpack.prod.conf.js)样式相关的loader

module: {
  rules: utils.styleLoaders({
   sourceMap: config.build.productionSourceMap,
   extract: true,
   usePostCSS: true
  })
 },

从上面可以看出,vue-cli的开发环境和生产环境都是使用了postcss的,并且配置是一样的,那么为什么打包前和打包后元素所带的css前缀不一致呢,

锁定问题

我们可以分析对比下build/webpack.dev.conf.js和build/webpack.prod.conf.js这两个文件,影响css的无非就module里处理样式的loader和处理css的插件plugin,从上面可以看出影响前缀的postcss的loader在两个环节中是一致的,那么就可以知道问题出在处理css的插件上了。

经过排查发现,webpack.prod.conf.js配置里是多了两个css处理插件的,如下

vue-cli2打包前和打包后的css前缀不一致的问题解决

ExtractTextPlugin这是提取分离css文件,不会影响css前缀,排除,那么问题就锁定到OptimizeCSSPlugin插件身上。再进一步,当我们把OptimizeCSSPlugin插件注释掉,然后打包测试,居然发现这时开发环境和生产环境的css前缀一致了,就是它了!!!

我们打开到npm官网搜一下这家伙https://www.npmjs.com/package/optimize-css-assets-webpack-plugin,这是一个优化压缩css代码的插件,但很失望,文档说明很少

但我们注意到有一句话很关键:

vue-cli2打包前和打包后的css前缀不一致的问题解决

什么鬼,这货里面依赖了cssnano,这插件也是用来优化处理css格式、前缀什么的。同时也有个autoprefixer配置参数,直接到它官网(这个好像需要番墙) https://cssnano.co/ 找到autoprefixer(比较难找得借助翻译):

vue-cli2打包前和打包后的css前缀不一致的问题解决

这里的翻译是:根据browsers选项删除不必要的前缀。请注意,默认情况下,它不会向CSS文件添加新前缀,这就可以解析清除我们的问题了,原来这插件的autoprefixer(默认应该是为true)把它认为不必要的前缀删掉了,而postcss的autoprefixer是将我们设定的浏览器范围的前缀加上,因此完美冲突了

解决问题

最后在github上找到解决方案(忘了复制找不回那地址了,具体为啥这样设置没说,这得深入这个插件的源码了),在build/webpack.prod.conf.js文件中OptimizeCSSPlugin插件的属性cssProcessorOptions加上autoprefixer:false来禁用它,避免冲突

vue-cli2打包前和打包后的css前缀不一致的问题解决

上代码:

new OptimizeCSSPlugin({
   cssProcessorOptions: config.build.productionSourceMap
    ? { safe: true, map: false,autoprefixer:false }
    : { safe: true, autoprefixer: false}
  }),

结论

最后,看看我们dev和build出来的css前缀,应该就一致的了:

问题原因就是:OptimizeCSSPlugin里面依赖了cssnano,而cssnano里面也有一个autoprefixer配置参数,它的作用是删除不必要的前缀(会误删在某些浏览器必要的前缀),这与postcss的autoprefixer效果冲突了,因此禁用它。

现在打包出来的与我们设定的浏览器范围对应的前缀一致,感觉整篇文章有点??铝耍??馐俏医饩稣馕适碧獾难?罚??锹家幌掳桑?缬蟹治霾欢缘穆榉持赋觯?恍唬?/p>

 以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
getElementsByTagName vs selectNodes效率 及兼容的selectNodes实现
Feb 26 Javascript
jQuery数据缓存用法分析
Feb 20 Javascript
浅谈jquery上下滑动的注意事项
Oct 13 Javascript
详解jquery easyui之datagrid使用参考
Dec 05 Javascript
浅谈Postman解决token传参的问题
Mar 31 Javascript
Vue.js 2.x之组件的定义和注册图文详解
Jun 19 Javascript
微信小程序项目实践之验证码倒计时功能
Jul 18 Javascript
微信小程序支付前端源码
Aug 29 Javascript
全面分析JavaScript 继承
May 30 Javascript
详解钉钉小程序组件之自定义模态框(弹窗封装实现)
Mar 07 Javascript
javascript实现滚轮轮播图片
Dec 13 Javascript
vue实现倒计时功能
Mar 24 Vue.js
解决vue2.0 element-ui中el-upload的before-upload方法返回false时submit()不生效问题
Aug 24 #Javascript
AngularJS自定义表单验证功能实例详解
Aug 24 #Javascript
Vue源码解读之Component组件注册的实现
Aug 24 #Javascript
element-ui 关于获取select 的label值方法
Aug 24 #Javascript
微信小程序用户信息encryptedData详解
Aug 24 #Javascript
element-ui 中的table的列隐藏问题解决
Aug 24 #Javascript
实例详解ztree在vue项目中使用并且带有搜索功能
Aug 24 #Javascript
You might like
大师制作的中短波矿石收音机
2020/04/02 无线电
php自动加载autoload机制示例分享
2014/02/20 PHP
php基于socket实现SMTP发送邮件的方法
2015/03/05 PHP
PHP模板引擎Smarty中变量的使用方法示例
2016/04/11 PHP
PHP合并数组的2种方法小结
2016/11/24 PHP
在textarea中显示html页面的javascript代码
2007/04/20 Javascript
拉动滚动条加载数据的jquery代码
2012/05/03 Javascript
artDialog双击会关闭对话框的修改过程分享
2013/08/05 Javascript
jQuery实现拖拽效果插件的方法
2015/03/23 Javascript
bootstrap datepicker限定可选时间范围实现方法
2016/09/28 Javascript
Restify中接入Socket.io报Error:Can’t set headers的错误解决
2017/03/28 Javascript
js评分组件使用详解
2017/06/06 Javascript
vue动态路由配置及路由传参的方式
2018/05/23 Javascript
vue配置文件实现代理v2版本的方法
2019/06/21 Javascript
Vue中axios的封装(报错、鉴权、跳转、拦截、提示)
2019/08/20 Javascript
微信小程序实现手势滑动效果
2019/08/26 Javascript
Vue项目配置跨域访问和代理proxy设置方式
2020/09/08 Javascript
解决idea开发遇到javascript动态添加html元素时中文乱码的问题
2020/09/29 Javascript
[06:20]2015国际邀请赛第三日top10
2015/08/08 DOTA
Python易忽视知识点小结
2015/05/25 Python
通过Python 获取Android设备信息的轻量级框架
2017/12/18 Python
Python学习笔记之抓取某只基金历史净值数据实战案例
2019/06/03 Python
pyqt5 从本地选择图片 并显示在label上的实例
2019/06/13 Python
python basemap 画出经纬度并标定的实例
2019/07/09 Python
PyTorch 普通卷积和空洞卷积实例
2020/01/07 Python
详解Python多线程下的list
2020/07/03 Python
Python常用外部指令执行代码实例
2020/11/05 Python
Currentbody澳大利亚:美容仪专家
2019/11/11 全球购物
集体备课反思
2014/02/12 职场文书
毕业典礼主持词大全
2014/03/26 职场文书
化工工艺设计求职信
2014/06/25 职场文书
社团活动总结报告
2014/06/27 职场文书
高速铁道技术专业求职信
2014/08/09 职场文书
寒山寺导游词
2015/02/03 职场文书
mysql升级到5.7时,wordpress导数据报错1067的问题
2021/05/27 MySQL
SQL Server查询某个字段在哪些表中存在
2022/03/03 SQL Server