脚手架vue-cli工程webpack的基本用法详解


Posted in Javascript onSeptember 29, 2018

webpack的打包依赖于它的一个重要配置文件webpack.config.js,在这个配置文件中就可以指定所有在源代码编译过程中的工作了,就一个配置就可以与冗长的Gruntfile或者Gulpfile说再见了。

一个完整的工程项目中的webpack的配置远远没有这么简单,随着工程的构建要求的增加,webpack.config.js内的配置项目也会随之增加,webpack还有许许多多的选项提供给我们进行灵活配置,它只是一个构建工具,我们只需要了解在Vue项目中它基本能为我们做到的工作、最小化的配置是如何的就足够了,在以后需要对它进行扩展与优化时,带着问题去查官方文档也是非常容易的事。

●  样式表引用

某些页面或者组件可能具有特定的样式定义,这些样式对于其他页面来说是冗余的,我们只希望这些组件在应用时才自动加载这些特定的样式,此时用webpack我们就能在源代码中加入以下代码来动态加载CSS:

import Vue from 'vue'
// ... 省略
// 引用指定的样式源文件
import './app/assets/less/dark.less'
export default {
 // ... 省略
}

此时我们只需要在webpack的配置中加入less-loader,那么webpack在打包的时候就会自动将less转换为CSS,并将CSS的动态代码生成到JS文件中。当Vue组件被加载到页面并实例化后,将在DOM内插入这个特定的行内样式<style>以实现动态样式的应用。

对于*.css文件同样也是适用的,例如导入某个第三方库中必需的样式表:

import 'uikit/dist/css/components/tabs.css'

●  字体的引用

假设在dark.less内加入对自定义字体文件的样式定义:

@font-face {
  font-family: 'Darkenstone';
  src: url('./Darkenstone.eot');
  src: url('./Darkenstone.eot?#iefix') format('embedded-opentype'),
   url('./Darkenstone.woff2') format('woff2'),
   url('./Darkenstone.woff') format('woff'),
   url('./Darkenstone.ttf') format('truetype'),
   url('./Darkenstone.svg#Darkenstone') format('svg');
   font-weight: normal;   
   font-style: normal;
}
.header{
  display: flex;
  flex-flow: row nowrap;
  & > h1 {
   font: 16pt 'Darkenstone';
  }
}

这里.header>h1指定了一个Darkenstone的自定义字体,这个字体浏览器一定是不能识别的,以前我们在样式表中先定义这个字体样式并指定加载位置(如上文@font-face的定义),然后在页面中引用这个样式表,这是多么麻烦的一件事,不是吗?

如果用了webpack后,我们只是在配置文件内加入了一个url-loader:

{
  test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
  loader: 'url'
}

我们并不需要在源代码中做任何改变,因为之前已经引用过样式表dark.less,而字体是在样式表中的,webpack将在打包的时候为我们识别并在代码中引入字体的动态加载。这样一来极大地解决了我们对资源引用的依赖问题!

vue-cli的webpack模板已经为我们配置好了绝大多数常用的loader,在实际运用中我们只需要了解它们是怎么来的,应该怎么用,需要的时候如何修改就够了。

●  用别名取代路径引用

在项目开发过程中有可能有许多包是没有放在npm上的,有一些较老的可能还依然只存在于bower上,某些甚至在bower与npm上都找不到,而不得不通过下载的方式在项目内引用,这样一来我们的代码可能通过require就得在代码内引用一段很长的文件路径,如下所示

{
  test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
  loader: 'url'
}

这种包的引用方式明显违反了CommonJS的编程规范,对于这些长路径,甚至还具有“../..”这些相对路径搜索的定义,我们可以通过webpack的resolve配置项来解决。就以select这个组件为例,在webpack.base.config.js中加入以下的这个别名的定义:

module.exports = {
 entry:{ ... },
 output: { ... },
 module:{ ... },
 resolve: {
  extensions:['','.js'],
  alias:{ // 别名
   'bs-select':'bower_components/bootstrap-select/dist/js/select.js'
  }
 }
}

有了这个定义以后,我们就可以将上面那个长引用改为下面的写法:

import Selector from 'bs-select';

绝对不要让路径引用进入到我们的代码,因为这是代码的“癌症”,一旦开始植入并生长起来,以前的代码将难以维护!

●  配置多入口程序

多数情况下我们的程序入口不单单只有一个,举一个最简单的例子,前台提供给最终用户使用(http://www.domain.com/index),后台提供给登录用户使用(http://www.domain.com/admin/),那么自然需要多个与main.js类似的程序入口了。

首先在build/webpack.base.conf.js配置文件中的entry配置属性上加上新的入口文件:

module.exports = {
 entry: {
 app: './src/main.js',
 admin : './src/admin-main.js'
 },
 // ... 省略
}

这是用于告诉webpack哪几个是入口文件,这些文件需要被生成到启动页的<script>内。

vue-cli的webpack模板使用HtmlWebpackPlugin插件,生成HTML入口页面并自动将生成后的JS文件和CSS文件的引用地址写入到页内的<script>中。

这里就需要在build/webpack.dev.config.js文件内的plugins配置项内多配置一个HtmlWebpackPlugin插件,用于生成admin.html入口页。

plugins:[
 // ... 省略
 // 这是原有的配置项,用于匹配注入app.js的输出脚本
 new HtmlWebpackPlugin({
 filename: process.env.NODE_ENV === 'testing'
  ? 'index.html'
  : config.build.index,
 template: 'index.html',
 chunks: ['app'], // 与原配置的不同的是要用chunks指定对应的entry
 inject: true,
 minify: {
  removeComments: true,
  collapseWhitespace: true,
  removeAttributeQuotes: true
 },
 chunksSortMode: 'dependency'
 }),
 // 这是新增项,用于匹配注入admin.js的输出脚本
 new HtmlWebpackPlugin({
 filename: process.env.NODE_ENV === 'testing'
  ? 'admin.html'
  : config.build.admin,
 template: 'index.html',
 chunks: ['admin'],
 inject: true,
 minify: {
  removeComments: true,
  collapseWhitespace: true,
  removeAttributeQuotes: true
 },
 chunksSortMode: 'dependency'
 }),
]

需要强调一点的是,这里的HtmlWebpackPlugin配置必须用chunks指定在上文entry内对应的入口文件的别名。

关于HtmlWebpackPlugin更多配置内容可以参考:https://github.com/kangax/html-minifier#options-quick-reference。

还有就是得将同样的配置加入到生产环境专用的webpack配置文件webpack.prod.conf.js中,否则当我们运行npm run build时是不会输出admin.js和admin.html这两个入口文件的(由于配置内容相同这里就不再重复了)。

最后,如果使用了vue-router就得对connect-history-api-fallback插件的配置进行修改,否则原有的默认配置只会将所有的请求转发给index.html,这样就会导致History API没有办法正确地将请求指向admin.html,导致热加载失败,具体做法如下所述。

打开dev-server.js文件,将app.use(require('connect-history-api-fallback')())配置改为以下的方式:

// handle fallback for HTML5 history API
var history = require('connect-history-api-fallback')
// app.use(require('connect-history-api-fallback')())
app.use(history({
 rewrites: [
 { from: /^\/admin\/.*$/, to: '/admin.html' }
 ]
}));

新入口需要有明确区分的路由规则,否则还是会产生热加载失败的情况,这样就非常不便于开发了。

总结

以上所述是小编给大家介绍的脚手架vue-cli工程webpack的基本用法详解,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
JavaScript Event学习第十一章 按键的检测
Feb 10 Javascript
js读取本地excel文档数据的代码
Nov 11 Javascript
基于jquery实现的可编辑下拉框实现代码
Aug 02 Javascript
jQuery中not()方法用法实例
Jan 06 Javascript
jQuery解析XML 详解及方法总结
Sep 28 Javascript
jQuery实现隔行变色的方法分析(对比原生JS)
Nov 18 Javascript
JavaScript定时器setTimeout()和setInterval()详解
Aug 18 Javascript
javascript高级模块化require.js的具体使用方法
Oct 31 Javascript
Vue-Router的使用方法
Sep 05 Javascript
vue实现带过渡效果的下拉菜单功能
Feb 19 Javascript
Vue ​v-model相关知识总结
Jan 28 Vue.js
vue仿携程轮播图效果(滑动轮播,下方高度自适应)
Feb 11 Vue.js
vue实现条件判断动态绑定样式的方法
Sep 29 #Javascript
vue根据值给予不同class的实例
Sep 29 #Javascript
vue实现重置表单信息为空的方法
Sep 29 #Javascript
Vue中的Props(不可变状态)
Sep 29 #Javascript
vue动态删除从数据库倒入列表的某一条方法
Sep 29 #Javascript
使用vue根据状态添加列表数据和删除列表数据的实例
Sep 29 #Javascript
vue-cli脚手架搭建的项目去除eslint验证的方法
Sep 29 #Javascript
You might like
PHP 修复未正常关闭的HTML标签实现代码(支持嵌套和就近闭合)
2012/06/07 PHP
PHP使用json_encode函数时不转义中文的解决方法
2014/11/12 PHP
PHP模板引擎smarty详细介绍
2015/05/26 PHP
老司机传授Ubuntu下Apache+PHP+MySQL环境搭建攻略
2016/03/20 PHP
PHP入门教程之PHP操作MySQL的方法分析
2016/09/11 PHP
PHP在线打包下载功能示例
2016/10/15 PHP
PHP中localeconv()函数的用法
2019/03/26 PHP
PHP PDO和消息队列的个人理解与应用实例分析
2019/11/25 PHP
Javascript开发包大全整理
2006/12/22 Javascript
Javascript Cookie读写删除操作的函数
2010/03/02 Javascript
24款非常有用的 jQuery 插件分享
2011/04/06 Javascript
鼠标经过tr时,改变tr当前背景颜色
2014/01/13 Javascript
JS实现的鼠标跟随代码(卡通手型点击效果)
2015/10/26 Javascript
Angular 2 ngForm中的ngModel、[ngModel]和[(ngModel)]的写法
2017/06/29 Javascript
vue实现样式之间的切换及vue动态样式的实现方法
2017/12/19 Javascript
JS 中可以提升幸福度的小技巧(可以识别更多另类写法)
2018/07/28 Javascript
wx-charts 微信小程序图表插件的具体使用
2019/08/18 Javascript
[39:11]DOTA2上海特级锦标赛C组资格赛#2 LGD VS Newbee第二局
2016/02/28 DOTA
Python实现Kmeans聚类算法
2020/06/10 Python
Tensorflow之Saver的用法详解
2018/04/23 Python
用python写扫雷游戏实例代码分享
2018/05/27 Python
python如何爬取个性签名
2018/06/19 Python
基于Python实现大文件分割和命名脚本过程解析
2019/09/29 Python
使用Python爬取弹出窗口信息的实例
2020/03/14 Python
解决TensorFlow调用Keras库函数存在的问题
2020/07/06 Python
Python绘图实现台风路径可视化代码实例
2020/10/23 Python
HTML5注册表单的自动聚焦与占位文本示例代码
2013/07/19 HTML / CSS
世界上最大的罕见唱片、CD和音乐纪念品网上商店:991.com
2018/05/03 全球购物
办公室主任职责范本
2014/03/07 职场文书
2015年试用期工作总结范文
2015/05/28 职场文书
朋友离别感言
2015/08/04 职场文书
2016年校长新年寄语
2015/08/17 职场文书
会计做账心得体会
2016/01/22 职场文书
500字作文之周记
2019/12/13 职场文书
golang 实现两个结构体复制字段
2021/04/28 Golang
vue+echarts实现多条折线图
2022/03/21 Vue.js