图片 17

webpack使用理解,致我们终将组件化的Web

致大家必定组件化的Web

2015/11/25 · HTML5 · 1
评论 ·
组件化

原稿出处:
AlloyTeam   

那篇小说将从八年前的三回能力争论起来。争论的聚集就是下图的八个目录分层结构。笔者说按模块划分好,他说您傻逼啊,当然是按资源划分。

图片 1 《=》图片 2

”按模块划分“目录结构,把这段日子模块下的具有逻辑和能源都放一块了,那对于多少人独立开辟和护卫个人模块不是很行吗?当然了,那争辨的结果是自我婴孩地改回主流的”按能源划分“的目录结构。因为,没有完成JS模块化和能源模块化,仅仅物理地点上的模块划分是未曾意思的,只会扩大营造的资本而已。

固然她说得好有道理小编无话可说,可是自身心不甘,等待她这几天端组件化成熟了,再来世界一战!

而前几日正是自个儿频频正义的日子!只是那时格外跟你撕逼的人不在。

模块化的供应满足不了供给

模块经常指能够单独拆分且通用的代码单元。由于JavaScript语言自个儿并未内置的模块机制(ES6有了!!卡塔 尔(英语:State of Qatar),大家常常会动用CMD或ADM创建起模块机制。以往许多微微大型一点的档次,都会使用requirejs或然seajs来完结JS的模块化。五个人分工合营开辟,其个别定义重视和揭破接口,维护成效模块间独立性,对于项目标花费功能和品种早先时期扩充和珍贵,都以是有比比较大的相助意义。

但,麻烦大家某些略读一下底下的代码

JavaScript

require([
‘Tmpl!../tmpl/list.html’,’lib/qqapi’,’module/position’,’module/refresh’,’module/page’,’module/net’
], function(listTmpl, QQapi, Position, Refresh, Page, NET){ var foo =
”, bar = []; QQapi.report(); Position.getLocaiton(function(data){
//… }); var init = function(){ bind();
NET.get(‘/cgi-bin/xxx/xxx’,function(data){ renderA(data.banner);
renderB(data.list); }); }; var processData = function(){ }; var bind =
function(){ }; var renderA = function(){ }; var renderB =
function(data){ listTmpl.render(‘#listContent’,processData(data)); };
var refresh = function(){ Page.refresh(); }; // app start init(); });

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
require([
    ‘Tmpl!../tmpl/list.html’,’lib/qqapi’,’module/position’,’module/refresh’,’module/page’,’module/net’
], function(listTmpl, QQapi, Position, Refresh, Page, NET){
    var foo = ”,
        bar = [];
    QQapi.report();
    Position.getLocaiton(function(data){
        //…
    });
    var init = function(){
        bind();
        NET.get(‘/cgi-bin/xxx/xxx’,function(data){
            renderA(data.banner);
            renderB(data.list);
        });
    };
    var processData = function(){
    };
    var bind = function(){
    };
    var renderA = function(){
    };
    var renderB = function(data){
        listTmpl.render(‘#listContent’,processData(data));
    };
    var refresh = function(){
        Page.refresh();
    };
    // app start
    init();
});

上边是活龙活现有个别页面包车型客车主js,已经封装了像Position,NET,Refresh等功效模块,但页面包车型大巴主逻辑仍为”面向进程“的代码结构。所谓面向进度,是指依据页面包车型客车渲染进程来编排代码结构。像:init
-> getData -> processData -> bindevent -> report -> xxx

方法之间线性跳转,你差相当的少也能体会那样代码缺欠。随着页面逻辑更是复杂,那条”进程线“也会更为长,何况进一步绕。加之贫乏专门的学问约束,别的品种成员根据各自供给,在”进度线“加插各自逻辑,最后这些页面包车型大巴逻辑变得难以保证。

图片 3

支出供给严谨,生怕影响“进程线”前边正常逻辑。并且每二次加插或矫正都是bug泛滥,无不令付加物有关职员意气风发律心有余悸。

 页面结构模块化

基于上边的面向进度的难点,行当内也可以有众多施工方案,而我们协会也总括出意气风发套成熟的解决方案:Abstractjs,页面结构模块化。大家得以把我们的页面想象为叁个乐高机器人,要求差异零构件组装,如下图,假若页面划分为tabContainer,listContainer和imgsContainer多个模块。最后把那几个模块add到最后的pageModel里面,最终利用rock方法让页面运行起来。

图片 4
(原经过线示例图卡塔尔

图片 5
(页面结构化示例图卡塔尔

上面是伪代码的贯彻

JavaScript

require([
‘Tmpl!../tmpl/list.html’,’Tmpl!../tmpl/imgs.html’,’lib/qqapi’,’module/refresh’,’module/page’
], function(listTmpl, imgsTmpl, QQapi, Refresh, Page ){ var
tabContainer = new RenderModel({ renderContainer: ‘#tabWrap’, data: {},
renderTmpl: “<li soda-repeat=’item in
data.tabs’>{{item}}</li>”, event: function(){ // tab’s event }
}); var listContainer = new ScrollModel({ scrollEl: $.os.ios ?
$(‘#Page’) : window, renderContainer: ‘#listWrap’, renderTmpl:
listTmpl, cgiName: ‘/cgi-bin/index-list?num=1’, processData:
function(data) { //… }, event: function(){ // listElement’s event },
error: function(data) { Page.show(‘数据重回万分[‘ + data.retcode +
‘]’); } }); var imgsContainer = new renderModel({ renderContainer:
‘#imgsWrap’, renderTmpl: listTmpl, cgiName: ‘/cgi-bin/getPics’,
processData: function(data) { //… }, event: function(){ //
imgsElement’s event }, complete: function(data) { QQapi.report(); } });
var page = new PageModel();
page.add([tabContainer,listContainer,imgsContainer]); page.rock(); });

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
require([
    ‘Tmpl!../tmpl/list.html’,’Tmpl!../tmpl/imgs.html’,’lib/qqapi’,’module/refresh’,’module/page’
], function(listTmpl, imgsTmpl, QQapi, Refresh, Page ){
 
    var tabContainer = new RenderModel({
        renderContainer: ‘#tabWrap’,
        data: {},
        renderTmpl: "<li soda-repeat=’item in data.tabs’>{{item}}</li>",
        event: function(){
            // tab’s event
        }
    });
 
    var listContainer = new ScrollModel({
        scrollEl: $.os.ios ? $(‘#Page’) : window,
        renderContainer: ‘#listWrap’,
        renderTmpl: listTmpl,
        cgiName: ‘/cgi-bin/index-list?num=1’,
        processData: function(data) {
            //…
        },
        event: function(){
            // listElement’s event
        },
        error: function(data) {
            Page.show(‘数据返回异常[‘ + data.retcode + ‘]’);
        }
    });
 
    var imgsContainer = new renderModel({
        renderContainer: ‘#imgsWrap’,
        renderTmpl: listTmpl,
        cgiName: ‘/cgi-bin/getPics’,
        processData: function(data) {
            //…
        },
        event: function(){
            // imgsElement’s event
        },
        complete: function(data) {
           QQapi.report();
        }
    });
 
    var page = new PageModel();
    page.add([tabContainer,listContainer,imgsContainer]);
    page.rock();
 
});

大家把这么些常用的伸手CGI,管理数据,事件绑定,上报,容错处理等后生可畏鳞萃比栉逻辑方式,以页面块为单位封装成三个Model模块。

如此的三个空洞层Model,大家得以清楚地看看该页面块,伏乞的CGI是何许,绑定了何等风浪,做了什么上报,出错怎么管理。新增的代码就相应放置在相应的模块上相应的景况方法(preload,process,event,complete…卡塔尔国,杜绝了往年的无准则乱增代码的行文。况兼,依照不一致职业逻辑封装不一样类别的Model,如列表滚动的ScrollModel,滑块功用的SliderModel等等,可以拓展中度封装,聚集优化。

现在依靠Model的页面结构开辟,已经满含一点”组件化“的意味。每一个Model都蕴含各自的多寡,模板,逻辑。已经算是三个完完全全的效用单元。但离开真正的WebComponent依旧有大器晚成段间隔,起码满意不断笔者的”理想目录结构“。

 WebComponents 标准

大家回忆一下应用五个datapicker的jquery的插件,所急需的步奏:

  1. 引进插件js

  2. 引进插件所需的css(借使有卡塔尔国

  3. copy 组件的所需的html片段

  4. 增加代码触发组件运维

一时的“组件”基本上只能到达是某些功效单元上的成团。他的能源都以松散地分散在三种能源文件中,何况组件效能域暴光在全局意义域下,匮乏内聚性相当轻巧就能够跟别的零部件发生冲突,如最简易的css命名冲突。对于这种“组件”,还不及上边的页面结构模块化。

于是乎W3C按耐不住了,拟订多少个WebComponents标准,为组件化的前景指导了明路。

下边以较为轻松的点子介绍这份正经,力求大家能够非常快通晓实现组件化的开始和结果。(对那风流倜傥部分叩问的同校,能够跳过这一小节卡塔尔国

1. <template>模板手艺

模板那东西哈工大学家最熟稔可是了,2018年见的超多的模板质量战争artTemplate,juicer,tmpl,underscoretemplate等等。而现行反革命又有mustachejs无逻辑模板引擎等新入选手。然则大家有没有想过,这么底子的力量,原生HTML5是不帮衬的(T_T)。

而后天WebComponent就要提供原生的模版才干

XHTML

<template id=”datapcikerTmpl”>
<div>笔者是原生的沙盘</div> </template>

1
2
3
<template id="datapcikerTmpl">
<div>我是原生的模板</div>
</template>

template标签钦赐义了myTmpl的模版,供给选取的时候将要innerHTML= document.querySelector('#myTmpl').content;可以看见那么些原生的模板够原始,模板占位符等成效都尚未,对于动态数据渲染模板本事只好自力更新。

2. ShadowDom 封装组件独立的内部结构

ShadowDom能够清楚为大器晚成份有独立成效域的html片段。那一个html片段的CSS境况和主文书档案隔开的,各自保持内部的独立性。也正是ShadowDom的单身性格,使得组件化成为了说不佳。

JavaScript

var wrap = document.querySelector(‘#wrap’); var shadow =
wrap.createShadowRoot(); shadow.innerHTML = ‘<p>you can not see me
</p>’

1
2
3
var wrap = document.querySelector(‘#wrap’);
var shadow = wrap.createShadowRoot();
shadow.innerHTML = ‘<p>you can not see me </p>’

在切切实实dom节点上选用createShadowRoot方法就能够生成其ShadowDom。就疑似在整份Html的室内面,新建了三个shadow的屋企。房间外的人都不了然房间内有怎么样,保持shadowDom的独立性。

3. 自定义原生标签

首先接触Angularjs的directive指令作用,设定好组件的逻辑后,一个<Datepicker
/>就能够引进整个组件。如此狂炫丽炸碉堡天的功效,实在让人大得人心,跃地三尺。

JavaScript

var tmpl = document.querySelector(‘#datapickerTmpl’); var
datapickerProto = Object.create(HTMLElement.prototype); //
设置把大家模板内容大家的shadowDom datapickerProto.createdCallback =
function() { var root = this.createShadowRoot();
root.appendChild(document.importNode(tmpl.content, true)); }; var
datapicker = docuemnt.registerElement(‘datapicker’,{ prototype:
datapickerProto });

1
2
3
4
5
6
7
8
9
10
11
12
var tmpl = document.querySelector(‘#datapickerTmpl’);
var datapickerProto = Object.create(HTMLElement.prototype);
 
// 设置把我们模板内容我们的shadowDom
datapickerProto.createdCallback = function() {
    var root = this.createShadowRoot();
    root.appendChild(document.importNode(tmpl.content, true));
};
 
var datapicker = docuemnt.registerElement(‘datapicker’,{
    prototype: datapickerProto
});

Object.create形式继续HTMLElement.prototype,获得三个新的prototype。当解析器发掘大家在文书档案中标识它将检查是或不是二个名字为createdCallback的艺术。纵然找到这些主意它将即时运行它,所以大家把克隆模板的剧情来创建的ShadowDom。

最后,registerElement的主意传递大家的prototype来注册自定义标签。

地点的代码初叶略显复杂了,把后边多少个工夫“模板”“shadowDom”结合,产生组件的中间逻辑。最后通过registerElement的法子注册组件。之后方可快乐地<datapicker></datapicker>的施用。

4. imports化解组件间的正视性

XHTML

<link rel=”import” href=”datapciker.html”>

1
<link rel="import" href="datapciker.html">

其意气风发类php最常用的html导入作用,HTML原生也能支撑了。

WebComponents标准内容差十分少到那边,是的,小编那边未有何样德姆o,也并未有执行经验分享。由于webComponents新特性,基本重三了高版本的Chrome支持外,别的浏览器的辅助度甚少。尽管有polymer扶持拉动webcompoents的仓库储存在,然则polymer自己的渴求版本也是十一分高(IE10+卡塔 尔(英语:State of Qatar)。所以明天的台柱并非他。

咱俩大约来回看一下WebCompoents的四部分机能:

1 .<template>定义组件的HTML模板本事

  1. Shadow Dom封装组件的内部结构,并且保持其独立性

  2. Custom Element 对外提供组件的价签,达成自定义标签

  3. import化解组件结合和注重加载

 组件化实施方案

合法的正规看完了,大家考虑一下。风流浪漫份真正成熟可信的组件化方案,需求有所的力量。

“财富高内聚”—— 组件财富内部高内聚,组件财富由笔者加载调节

“功用域独立”—— 内部结构密封,不与大局或其余构件产生潜濡默化

“自定义标签”—— 定义组件的利用格局

“可相互结合”—— 组件正在有力之处,组件间组装整合

“接口标准化”—— 组件接口有统黄金时代标准,只怕是生命周期的管住

村办感觉,模板本领是根底技术,跟是还是不是组件化未有强联系,所以并未有建议一个大点。

既是是推行,现阶段WebComponent的支撑度还不成熟,不能够看做方案的花招。而除此以外生机勃勃套以高品质设想Dom为切入点的机件框架React,在facebook的造势下,社区赢得了大力发展。别的一名骨干Webpack,肩负解决组件能源内聚,同一时候跟React特别契合产生补充。

所以【Webpack】+【React】将会是那套方案的核心技艺。

不了然您以往是“又是react+webpack”感觉深负众望图片 6,还是“太好了是react+webpack”不用再学三次新框架的喜悦图片 7。无论怎样下边包车型客车内容不会让您深负众望的。

生龙活虎,组件生命周期

图片 8

React天生正是强制性组件化的,所以可以从根本性上消除面向进度代码所推动的分神。React组件本身有生命周期方法,能够满足“接口标准化”技巧点。何况跟“页面结构模块化”的所封装分离的多少个主意能挨个对应。其余react的jsx自带模板效能,把html页面片直接写在render方法内,组件内聚性越发紧密。

由于React编写的JSX是会先生成虚构Dom的,必要机缘才真的插入到Dom树。使用React必供给明了组件的生命周期,其生命周期多少个情景:

Mount: 插入Dom

Update: 更新Dom

Unmount: 拔出Dom

mount那单词翻译扩充,嵌入等。小编倒是提议“插入”越来越好掌握。插入!拔出!插入!拔出!默念三遍,懂了没?别少看黄段子的技巧,

图片 9

组件状态正是: 插入-> 更新 ->拔出。

接下来各种组件状态会有二种管理函数,大器晚成前风度翩翩后,will函数和did函数。

componentWillMount()  思忖插入前

componentDidlMount()  插入后

componentWillUpdate() 计划更新前

componentDidUpdate()  更新后

componentWillUnmount() 准备拔出前

因为拔出后基本都以贤者形态(小编说的是组件卡塔尔国,所以并未DidUnmount那个办法。

其余React别的一个为主:数据模型props和state,对应着也可以有自个状态方法

getInitialState()     获取发轫化state。

getDefaultProps() 获取默许props。对于那四个从没父组件传递的props,通过该方法设置暗中同意的props

componentWillReceiveProps()  已插入的构件收到新的props时调用

再有四个区别常常景况的管理函数,用于优化管理

shouldComponentUpdate():剖断组件是或不是需求update调用

拉长最主要的render方法,React本人带的办法刚刚巧13个。对于初读书人的话是相比较难以消食。但实在getInitialStatecomponentDidMountrender八个情景方法都能产生超越50%构件,不必惧怕。

回去组件化的核心。

一个页面结构模块化的零件,能独立包装整个组件的进程线

图片 10

我们换算成React生命周期方法:

图片 11

 

零构件的情况方法流中,有两点需求独特表明:

1,贰回渲染:

是因为React的虚构Dom性情,组件的render函数不需协和触发,依照props和state的更动自个通过差距算法,得出最优的渲染。

恳请CGI日常都以异步,所以必然带来贰遍渲染。只是空数据渲染的时候,有相当的大概率会被React优化掉。当数码回来,通过setState,触发二回render

 

2,componentWiillMount与componentDidMount的差别

和大多数React的科目作品不平等,ajax央浼笔者建议在WillMount的艺术内实行,实际不是组件早先化成功今后的DidMount。那样能在“空数据渲染”阶段早先供给数据,尽早地减少一遍渲染的时间。

willMount只会实行一遍,非常切合做init的事情。

didMount也只会实践一回,並且那时真实的Dom已经形成,特别相符事件绑定和complete类的逻辑。

 

 二,JSX超丑,可是组件内聚的严重性!

WebComponents的科班之风流罗曼蒂克,需求模板技术。本是以为是大家耳濡目染的模版手艺,但React中的JSX那样的奇人还是令人谈空说有。React尚未火起来的时候,大家就早就在新浪上狠狠地嘲弄了“JSX写的代码那TM的丑”。这实际只是德姆o阶段JSX,等到实战的大型项目中的JSX,满含多情状超级多据多事件的时候,你会意识………….JSX写的代码仍然好丑。

图片 12
(尽管用sublime-babel等插件高亮,逻辑和渲染耦合一齐,阅读性依然略差卡塔尔

缘何大家会认为丑?因为大家早已经对“视图-样式-逻辑”分离的做法潜濡默化。

依赖维护性和可读性,以至质量,我们都不提出直接在Dom上边绑定事件只怕直接写style属性。大家会在JS写事件代理,在CSS上写上classname,html上的就是明显的Dom结构。大家很好地掩护着MVC的设计格局,一切安好。直到JSX把他们都夹杂在合作,所守护的本事栈受到入侵,难免有着抗拒。

 

唯独从组件化的目标来看,这种高内聚的做法未尝不可。

下边包车型大巴代码,以前的“逻辑视图分离”形式,大家须求去找相应的js文件,相应的event函数体内,找到td-info的class所绑定的风浪。

比较之下起JSX的万丈内聚,所有的事件逻辑正是在自身jsx文件内,绑定的就是自己的showInfo方法。组件化的风味能顿时呈现出来。

(注意:尽管写法上大家好疑似HTML的内联事件微处理机,可是在React底层并从未实际赋值近似onClick属性,内层仍旧利用相像事件代理的不二秘技,高效地保险着事件微机卡塔 尔(阿拉伯语:قطر‎

再来看豆蔻梢头段style的jsx。其实jsx未有对体制有硬性规定,大家一齐可依据以前的定义class的逻辑。任何生机勃勃段样式都应该用class来定义。在jsx你也统统能够这么做。然而由于组件的独立性,作者提议部分独有“二次性”的体裁直接行使style赋值越来越好。收缩冗余的class。

XHTML

<div className=”list” style={{background: “#ddd”}}> {list_html}
</div>

1
2
3
<div className="list" style={{background: "#ddd"}}>
   {list_html}
</div>

想必JSX内部有担任繁杂的逻辑样式,可JSX的自定义标签工夫,组件的黑盒性立马能体会出来,是或不是瞬美好了大多。

JavaScript

render: function(){ return ( <div> <Menus
bannerNums={this.state.list.length}></Menus> <TableList
data={this.state.list}></TableList> </div> ); }

1
2
3
4
5
6
7
8
render: function(){
    return (
      <div>
         <Menus bannerNums={this.state.list.length}></Menus>
         <TableList data={this.state.list}></TableList>
      </div>
   );
}

虽说JSX本质上是为着虚构Dom而准备的,但这种逻辑和视图中度合风度翩翩对于组件化未尝不是风度翩翩件善事。

 

上学完React这几个组件化框架后,看看组件化技巧点的成功景况

“能源高内聚”—— (33%卡塔尔  html与js内聚

“成效域独立”—— (50%卡塔尔国  js的成效域独立

“自定义标签”—— (百分百卡塔 尔(阿拉伯语:قطر‎jsx

“可交互作用结合”—— (十分之五卡塔尔国  可整合,但缺少有效的加载方式

“接口标准化”—— (百分百卡塔尔国组件生命周期方法

 

Webpack 财富组件化

对此组件化的能源独立性,平日的模块加载工具和营造流程视乎变得吃力。组件化的构建筑工程程化,不再是前边我们分布的,css合二,js合三,而是体验在组件间的依附于加载关系。webpack刚好合乎须求点,一方面增加补充组件化本领点,另一方帮衬大家完善组件化的完整营造情形。

率先要说圣元点是,webpack是二个模块加载打包工具,用于管理你的模块能源信任打包难点。那跟我们耳闻则诵的requirejs模块加载工具,和grunt/gulp营造筑工程具的定义,多多少稀少个别出入又有个别雷同。

图片 13

率先webpak对于CommonJS与速龙同一时间扶持,知足大家模块/组件的加载情势。

JavaScript

require(“module”); require(“../file.js”); exports.doStuff = function()
{}; module.exports = someValue;

1
2
3
4
require("module");
require("../file.js");
exports.doStuff = function() {};
module.exports = someValue;

JavaScript

define(“mymodule”, [“dep1”, “dep2”], function(d1, d2) { return
someExportedValue; });

1
2
3
define("mymodule", ["dep1", "dep2"], function(d1, d2) {
    return someExportedValue;
});

本来最精锐的,最出色的,当然是模块打包功效。那正是这一意义,补充了组件化财富重视,以至完整工程化的力量

依附webpack的计划性意见,全数财富都是“模块”,webpack内部落到实处了风度翩翩套财富加运载飞机制,能够把想css,图片等财富等有借助关系的“模块”加载。那跟大家应用requirejs这种只有管理js大大差别。而那套加运载飞机制,通过二个个loader来达成。

 

JavaScript

// webpack.config.js module.exports = { entry: { entry: ‘./index.jsx’,
}, output: { path: __dirname, filename: ‘[name].min.js’ }, module:
{ loaders: [ {test: /.css$/, loader: ‘style!css’ }, {test:
/.(jsx|js)?$/, loader: ‘jsx?harmony’, exclude: /node_modules/},
{test: /.(png|jpg|jpeg)$/, loader: ‘url-loader?limit=10240’} ] } };

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
// webpack.config.js
module.exports = {
    entry: {
     entry: ‘./index.jsx’,
    },
    output: {
        path: __dirname,
        filename: ‘[name].min.js’
    },
    module: {
        loaders: [
            {test: /.css$/, loader: ‘style!css’ },
            {test: /.(jsx|js)?$/, loader: ‘jsx?harmony’, exclude: /node_modules/},
            {test: /.(png|jpg|jpeg)$/, loader: ‘url-loader?limit=10240’}
        ]
    }
};

上面生机勃勃份轻便的webpack配置文件,在意loaders的配置,数组内二个object配置为黄金时代种模块财富的加运载飞机制。test的正则为协作文件法则,loader的为相称到文件将由什么加载器管理,多个计算机之间用相隔,管理顺序从右到左。

 

style!css,css文件通过css-loader(管理css卡塔 尔(阿拉伯语:قطر‎,再到style-loader(inline到html卡塔尔的加工管理流。

jsx文件通过jsx-loader编写翻译,‘?’开启加载参数,harmony扶助ES6的语法。

图形财富通过url-loader加载器,配置参数limit,调节少于10KB的图形将会base64化。

 财富文件如何被require?

JavaScript

// 加载组件本身css require(‘./slider.css’); // 加载组件信任的模块 var
Clip = require(‘./clipitem.js’); // 加载图片财富 var spinnerImg =
require(‘./loading.png’);

1
2
3
4
5
6
// 加载组件自身css
require(‘./slider.css’);
// 加载组件依赖的模块
var Clip = require(‘./clipitem.js’);
// 加载图片资源
var spinnerImg = require(‘./loading.png’);

在webpack的js文件中大家除了require大家经常的js文件,css和png等静态文件也足以被require进来。大家透过webpack命令,编写翻译之后,看看输出结果如何:

JavaScript

webpackJsonp([0], { /* 0 */ /***/ function(module, exports,
__webpack_require__) { // 加载组件本人css
__webpack_require__(1); // 加载组件注重的模块 var Clip =
__webpack_require__(5); // 加载图片财富 var spinnerImg =
__webpack_require__(6); /***/ }, /* 1 */ /***/
function(module, exports, __webpack_require__) { /***/ }, /* 2
*/ /***/ function(module, exports, __webpack_require__) {
exports = module.exports = __webpack_require__(3)();
exports.push([module.id, “.slider-wrap{rn position: relative;rn
width: 100%;rn margin: 50px;rn background:
#fff;rn}rnrn.slider-wrap li{rn text-align:
center;rn line-height: 20px;rn}”, “”]); /***/ }, /* 3 */
/***/ function(module, exports) { /***/ }, /* 4 */ /***/
function(module, exports, __webpack_require__) { /***/ }, /* 5
*/ /***/ function(module, exports) { console.log(‘hello, here is
clipitem.js’) ; /***/ }, /* 6 */ /***/ function(module, exports)
{ module.exports = “data:image/png;base64,iVBORw0KGg……” /***/ }
]);

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
webpackJsonp([0], {
/* 0 */
/***/ function(module, exports, __webpack_require__) {
          // 加载组件自身css
          __webpack_require__(1);
          // 加载组件依赖的模块
          var Clip = __webpack_require__(5);
          // 加载图片资源
          var spinnerImg = __webpack_require__(6);
/***/ },
/* 1 */
/***/ function(module, exports, __webpack_require__) {
 
/***/ },
/* 2 */
/***/ function(module, exports, __webpack_require__) {
          exports = module.exports = __webpack_require__(3)();
          exports.push([module.id, ".slider-wrap{rn position: relative;rn width: 100%;rn margin: 50px;rn background: #fff;rn}rnrn.slider-wrap li{rn text-align: center;rn line-height: 20px;rn}", ""]);
 
/***/ },
/* 3 */
/***/ function(module, exports) {
 
/***/ },
 
/* 4 */
/***/ function(module, exports, __webpack_require__) {
/***/ },
 
/* 5 */
/***/ function(module, exports) {
          console.log(‘hello, here is clipitem.js’) ;
/***/ },
/* 6 */
/***/ function(module, exports) {
          module.exports = "data:image/png;base64,iVBORw0KGg……"
/***/ }
]);

webpack编写翻译之后,输出文件视乎乱糟糟的,但实际每二个财富都被封装在贰个函数体内,並且以编号的情势标识(注释卡塔 尔(阿拉伯语:قطر‎。这几个模块,由webpack的__webpack_require__当中方法加载。入口文件为编号0的函数index.js,可以观察__webpack_require__加载其余编号的模块。

css文件在数码1,由于使用css-loader和style-loader,编号1-4都以管理css。此中编号2我们得以看我们的css的string体。最后会以内联的法子插入到html中。

图表文件在编号6,能够看出exports出base64化的图纸。

 组件生机勃勃体输出

JavaScript

// 加载组件自己css require(‘./slider.css’); // 加载组件注重的模块 var
React = require(‘react’); var Clip = require(‘../ui/clipitem.jsx’); //
加载图片能源 var spinnerImg = require(‘./loading.png’); var Slider =
React.createClass({ getInitialState: function() { // … },
componentDidMount: function(){ // … }, render: function() { return (
<div> <Clip data={this.props.imgs} /> <img
className=”loading” src={spinnerImg} /> </div> ); } });
module.exports = Slider;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
// 加载组件自身css
require(‘./slider.css’);
// 加载组件依赖的模块
var React = require(‘react’);
var Clip = require(‘../ui/clipitem.jsx’);
// 加载图片资源
var spinnerImg = require(‘./loading.png’);
var Slider = React.createClass({
    getInitialState: function() {
        // …
    },
    componentDidMount: function(){
        // …
    },
    render: function() {
        return (
            <div>
               <Clip data={this.props.imgs} />
               <img className="loading" src={spinnerImg} />
            </div>
        );
    }
});
module.exports = Slider;

假诺说,react使到html和js合为风度翩翩体。

那么丰裕webpack,两个结合一齐的话。js,css,png(base64),html
全部web财富都能合成二个JS文件。那正是那套方案的主旨所在:零器件独立风度翩翩体化。要是要引用三个零件,仅仅require('./slider.js') 就可以实现。

 

到场webpack的模块加载器之后,我们组件的加载问题,内聚难题也都立业成家地缓慢解决掉

“能源高内聚”—— (百分之百卡塔尔 所有能源能够一js出口

“可相互结合”—— (百分之百卡塔尔  可整合可依附加载

 

 CSS模块化施行

很兴奋,你能阅读到此地。如今大家的组件达成度特别的高,能源内聚,易于组合,功效域独立互不污染。。。。等等图片 14,视乎CSS模块的实现度有欠缺。

那么前段时间组件达成度来看,CSS作用域其实是全局性的,并不是组件内部独立。下一步,大家要做得就是什么样让我们组件内部的CSS功效域独立。

此刻大概有人马上跳出,大喊一句“德玛西亚!”,哦不,应该是“用sass啊傻逼!”。不过项目组件化之后,组件的内部封装已经很好了,其里面dom结商谈css趋势轻易,独立,以致是破破烂烂的。LESS和SASS的黄金年代体式样式框架的规划,他的嵌套,变量,include,函数等丰富的效率对于全体大型项目标样式管理特别实用。但对于三个成效单意气风发组件内部样式,视乎就变的多少冲突。“无法为了框架而框架,合适才是最棒的”。视乎原生的css技艺已经满足组件的体制须要,唯独就是上边的css效率域难题。

 

此间笔者付出考虑的方案:
classname随意写,保持原生的办法。编写翻译阶段,依照组件在档案的次序路径的唯生机勃勃性,由【组件classname+组件唯风姿罗曼蒂克渠道】打成md5,生成全局唯生龙活虎性classname。正当自家要写一个loader完毕自己的主见的时候,开采歪果仁已经早在先走一步了。。。。

此地具体方案参谋作者后边博客的译文:

事先大家研讨过JS的模块。今后因此Webpack被加载的CSS能源叫做“CSS模块”?小编认为仍有毛病的。今后style-loader插件的兑现精气神上只是创制link[rel=stylesheet]要素插入到document中。这种行为和平常引入JS模块特别例外。引进另三个JS模块是调用它所提供的接口,但引进一个CSS却并不“调用”CSS。所以引入CSS本人对于JS程序来讲并海市蜃楼“模块化”意义,纯粹只是表明了生龙活虎种能源信任——即该器件所要完毕的功效还要求一些asset。

由此,那位歪果仁还增加了“CSS模块化”的定义,除了下边的我们必要有个别效能域外,还可能有众多功力,这里不详述。具体参照他事他说加以考察原版的书文 

丰盛赞的有些,正是cssmodules已经被css-loader收纳。所以我们没有必要依据额外的loader,基本的css-loader开启参数modules就可以

JavaScript

//webpack.config.js … module: { loaders: [ {test: /.css$/, loader:
‘style!css?modules&localIdentName=[local]__[name]_[hash:base64:5]’
}, ] } ….

1
2
3
4
5
6
7
8
//webpack.config.js
…  
    module: {
        loaders: [
            {test: /.css$/, loader: ‘style!css?modules&localIdentName=[local]__[name]_[hash:base64:5]’ },
        ]  
    }
….

modules参数代表开启css-modules作用,loaclIdentName为设置大家编写翻译后的css名字,为了有助于debug,大家把classname(local卡塔尔和组件名字(name卡塔尔输出。当然能够在最后输出的本子为了节省提交,仅仅使用hash值就能够。其它在react中的用法大概如下。

JavaScript

var styles = require(‘./banner.css’); var Banner = new
React.createClass({ … render: function(){ return ( <div> <div
className={styles.classA}></div> </div> ) } });

1
2
3
4
5
6
7
8
9
10
11
var styles = require(‘./banner.css’);
var Banner = new React.createClass({
    …
    render: function(){
        return (
            <div>
                <div className={styles.classA}></div>
            </div>
        )
    }
});

终极这里关于出于对CSS一些酌量,

关于css-modules的别样作用,笔者并不寻思利用。在其间分享【我们鞠躬尽瘁地让CSS变得复杂】中聊起:

咱俩项目中山大学部的CSS都不会像boostrap那样要求变量来安装,身为一线开拓者的大家差相当少能够心得到:设计员们改版UI,相对不是粗略的换个色或改个间隔,而是改头换面的崭新UI,那纯属不是二个变量所能消除的”维护性“。

相反项目实战进度中,真正要缓慢解决的是:在本子迭代进度中那么些淘汰掉的过期CSS,多量地堆集在项目在那之中。大家像极了家中的欧巴酱不舍得放弃没用的事物,因为那可是咱们接收sass或less编写出具备中度的可维护性的,肯定有复用的一天。

那么些聚成堆的晚点CSS(or
sass卡塔尔之间又有局部信任,意气风发部分超时失效了,大器晚成都部队分又被新的体制复用了,招致没人敢动那多少个历史样式。结果现网项目迭代还带着一大波四年前没用的体制文件。

组件化之后,css的布局相像被更改了。可能postcss才是您将来手上最切合的工具,而不在是sass。

 

到此地,大家总算把组件化最终叁个主题材料也解决了。

“功效域独立”—— (百分百卡塔 尔(阿拉伯语:قطر‎ 就像是shadowDom功能域独立

 

到那边,大家得以开生龙活虎瓶82年的百事可乐,好好庆祝一下。不是啊?

图片 15

 

 组件化之路还在世襲

webpack和react还应该有无数新极其首要的特征和功用,介于本文仅仅围绕着组件化的为主导,未有各类解说。别的,配搭gulp/grunt补充webpack创设技巧,webpack的codeSplitting,react的机件通信难点,开拓与生育意况安排等等,都是全体大型项目方案的所必需的,限于篇幅问题。能够等等作者更新下篇,或大家能够自动查阅。

可是,必须要再安利一下react-hotloader神器。热加载的开支形式相对是下一代前端开辟必备。严酷说,假如未有了热加载,小编会很坚决地甩掉那套方案,纵然那套方案再怎么完美,作者都讨厌react供给5~6s的编写翻译时间。但是hotloader能够在自己不刷新页面包车型大巴地方下,动态纠正代码,而且不单单是样式,连逻辑也是即时生效。

图片 16

如上在form表单内。使用热加载,表单无需再行填写,修正submit的逻辑马上看到成效。那样的支付功能真不是抓牢仅仅三个水平。必需安利一下。

 

也许你意识,使用组件化方案未来,整个才具栈都被更新了生龙活虎番。学习花销也不菲,况且能够预言到,基于组件化的前端还有大概会过多欠缺的难点,举例质量优化方案供给再一次思忖,以致最主题的构件可复用性不自然高。后边相当短后生可畏段时间,供给我们不住磨砺与优化,研究最优的前端组件化之道。

起码我们得以想像,不再顾忌自身写的代码跟有个别什么人哪个人冲突,不再为找某段逻辑在多少个文本和办法间穿梭,不再copy一片片逻辑然后改改。大家每回编写都是可选择,可组合,独立且内聚的组件。而各样页面将会由四个个嵌套组合的零件,相互独立却相互影响。

 

对此那样的前端现在,有所指望,不是很可以吗

由来,感激您的翻阅。

1 赞 6 收藏 1
评论

图片 17

黄金时代、什么是webpack:webpack是大器晚成款模块加载兼打包工具,它能够将js、jsx、coffee、样式sass、less,图片等作为模块来利用和管理。
二、优势:1、以commonJS的款式来书写脚本,对英特尔、CMD的扶助也很康健,方便旧项目标迁徙。2、能被模块化的无休止是JS了。3、能替代部分grunt/gulp的干活,例如打包,压缩混淆,图片转base64等。3、扩大性强,插件机制完善,援救React热拔插(react-hot-loader卡塔尔
三、安装和布置:
1、安装:直接利用npm来进展安装
$ npm install webpack -g
将依据写入package.json包
$ npm init
$ npm install webpack –save-dev
2、配置:
每种门类必需安排三个webpack.config.js,功用就像gulpfile.js/Gruntfile.js,三个布置项,告诉webpack要做什么样。
示例:
var webpack = require(‘webpack’);
var commonsPlugin = new
webpack.optimize.CommonsChunkPlugin(‘common.js’);
module.exports = {
//插件项
plugins: [commonsPlugin],
//页面入口文件配置
entry: {
index : ‘./src/js/page/index.js’
},
//入口文件输出配置
output: {
path: ‘dist/js/page’,
filename: ‘[name].js’
},
module: {
//加载器配置
loaders: [
{ test: /.css$/, loader: ‘style-loader!css-loader’ },
{ test: /.js$/, loader: ‘jsx-loader?harmony’ },
{ test: /.scss$/, loader: ‘style!css!sass?sourceMap’},
{ test: /.(png|jpg)$/, loader: ‘url-loader?limit=8192’}
]
},
//此外应用方案安顿
resolve: {
root: ‘E:/github/flux-example/src’, //相对路径
extensions: [”, ‘.js’, ‘.json’, ‘.scss’],
alias: {
AppStore : ‘js/stores/AppStores.js’,
ActionType : ‘js/actions/ActionType.js’,
AppAction : ‘js/actions/AppAction.js’
}
}
};
(1)plugins是插件项,这里运用了二个CommonsChunkPlugin的插件,它用来提取多个入口文件的公家脚本有的,然后生成三个common.js来方便多页面之间的复用。
(2)entry是页面包车型客车进口文件配置,output是应和的输出项配置
{
entry: {
page1: “./page1”,
//帮助数组方式,将加载数组中的所有模块,但以最终二个模块作为出口
page2: [“./entry1”, “./entry2”]
},
output: {
path: “dist/js/page”,
filename: “[name].bundle.js”
}
}
该代码会扭转三个page1.bundle.js和page2.bundle.js,并寄存在./dist/js/page文件夹下。
(3)module.loaders,告知webpack每大器晚成种文件都急需哪些加载器来拍卖
module: {
//加载器配置
loaders: [
//.css 文件使用 style-loader 和 css-loader 来拍卖
{ test: /.css$/, loader: ‘style-loader!css-loader’ },
//.js 文件使用 jsx-loader 来编译处理
{ test: /.js$/, loader: ‘jsx-loader?harmony’ },
//.scss 文件使用 style-loader、css-loader 和 sass-loader 来编写翻译处理
{ test: /.scss$/, loader: ‘style!css!sass?sourceMap’},
//图片文件使用 url-loader 来拍卖,小于8kb的直白转为base64
{ test: /.(png|jpg)$/, loader: ‘url-loader?limit=8192’}
]
}
-loader能够不写,七个loader之间用“!”连接起来。全体的加载器都亟需经过npm来加载。
举个例子最后三个url-loader,它会将样式中援用到的图样转为模块来拍卖。使用前行行安装:
$ npm install url-loader -save-dev
安排音信的参数:“?limit=8192”表示将装有小于8kb的图纸都转为base64格局(超越8kb的才使用url-loader来映射到文件,不然转为data
url方式)
(4)resolve配置,
resolve: {
//查找module的话从这里开端查找
root: ‘E:/github/flux-example/src’, //相对路径
//自动扩张文件后缀名,意味着大家require模块能够大致不写后缀名
extensions: [”, ‘.js’, ‘.json’, ‘.scss’],
//模块外号定义,方便后续直接援用小名,无须多写长长的地址
alias: {
AppStore : ‘js/stores/AppStores.js’,//后续直接 require(‘AppStore’)
就能够
ActionType : ‘js/actions/ActionType.js’,
AppAction : ‘js/actions/AppAction.js’
}
}
四、运营webpack,间接实行:
$ webpack –display-error-details
末尾的参数
“-display-error-details”推荐加上,方便出错开上下班时间能领悟到更详实的音讯。其余重要参数:
$ webpack –config XXX.js
//使用另豆蔻梢头份配置文件(比如webpack.config2.js卡塔 尔(阿拉伯语:قطر‎来打包
$ webpack –watch //监听变动并自动打包
$ webpack -p //压缩混淆脚本,那几个这些可怜关键!
$ webpack -d //生成map映射文件,告知哪些模块被最后包装到何地了
-p是很首要的参数,曾经三个未压缩的 700kb 的公文,压缩后直接减低到180kb(主假设体制那块一句就攻陷生机勃勃行脚本,以致未压缩脚本变得非常的大卡塔 尔(阿拉伯语:قطر‎。
五、模块引进:
1、在HTML页面引进:引进webpack最终生成的剧本就可以:
<!DOCTYPE html>
<html>
<head lang=”en”>
<meta charset=”UTF-8″>
<title>demo</title>
</head>
<body>
<script src=”dist/js/page/common.js”></script>
<script src=”dist/js/page/index.js”></script>
</body>
</html>
能够看出大家连样式都毫不引进,终归脚本实行时会动态生成style并标签打到head里。
2、JS引入:各脚本模块可以应用common.js来书写,并能够间接引进未经编写翻译的模块,比方:jsx,coffee,sass,只要在webpack.config.js中配置好了相应的加载器就行。
编写翻译页面包车型客车输入文件:
require(‘../../css/reset.scss’); //加载开始化样式
require(‘../../css/allComponent.scss’); //加载组件样式
var React = require(‘react’);
var AppWrap = require(‘../component/AppWrap’); //加载组件
var createRedux = require(‘redux’).createRedux;
var Provider = require(‘redux/react’).Provider;
var stores = require(‘AppStore’);
var redux = createRedux(stores);
var App = React.createClass({
render: function() {
return (
<Provider redux={redux}>
{function() { return <AppWrap />; }}
</Provider>
);
}
});
React.render(
<App />, document.body
);

这里须求在output模块里面安装publicPath不然CSS背景图片等输出有标题

其他:
1、shimming :
在 AMD/CMD
中,我们须求对不切合标准的模块(例如一些平素回到全局变量的插件卡塔尔国实行shim 管理,那个时候大家必要选用 exports-loader 来增派:
{ test: require.resolve(“./src/js/tool/swipe.js”), loader:
“exports?swipe”}
从此在剧本中要求引用该模块的时候,这么轻易地来行使就能够了:
require(‘./tool/swipe.js’);
swipe();
2、自定义公共模块提取:
在小说开头我们采纳了 CommonsChunkPlugin
插件来提取四个页面之间的国有模块,并将该模块打包为 common.js 。
但有的时候大家期望能越发性格化一些,大家得以这样安顿:
var CommonsChunkPlugin =
require(“webpack/lib/optimize/CommonsChunkPlugin”);
module.exports = {
entry: {
p1: “./page1”,
p2: “./page2”,
p3: “./page3”,
ap1: “./admin/page1”,
ap2: “./admin/page2”
},
output: {
filename: “[name].js”
},
plugins: [
new CommonsChunkPlugin(“admin-commons.js”, [“ap1”, “ap2”]),
new CommonsChunkPlugin(“commons.js”, [“p1”, “p2”,
“admin-commons.js”])
]
};
// <script>s required:
// page1.html: commons.js, p1.js
// page2.html: commons.js, p2.js
// page3.html: p3.js
// admin-page1.html: commons.js, admin-commons.js, ap1.js
// admin-page2.html: commons.js, admin-commons.js, ap2.js
3、独立包装样式:
神跡恐怕希望项指标体裁能毫无被打包到脚本中,而是独立出来作为.css,然后在页面中以标签引入。这个时候大家需要extract-text-webpack-plugin 来帮助:
var webpack = require(‘webpack’);
var commonsPlugin = new
webpack.optimize.CommonsChunkPlugin(‘common.js’);
var ExtractTextPlugin = require(“extract-text-webpack-plugin”);
module.exports = {
plugins: [commonsPlugin, new ExtractTextPlugin(“[name].css”)],
entry: {
//…省略此外配置
最终 webpack 施行后会乖乖地把体制文件提抽取来:
4、使用CDN远程文件:
突发性大家希望有个别模块走CDN并以<script>的款式挂载到页面上来加载,但又希望能在
webpack 的模块中利用上。
这会儿大家得以在布置文件里使用 externals 属性来扶助:
{
externals: {
// require(“jquery”) 是援引自外界模块的
// 对应全局变量 jQuery
“jquery”: “jQuery”
}
}
亟需小心的是,得有限协助 CDN 文件必得在 webpack 打包文件引进在此之前先引进。
我们倒也能够利用 script.js 在本子中来加载大家的模块:
var $script = require(“scriptjs”);
$script(“//ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js”,
function() {
$(‘body’).html(‘It works!’)
});
5、与grunt/gulp相结合:
gulp.task(“webpack”, function(callback) {
// run webpack
webpack({
// configuration
}, function(err, stats) {
if(err) throw new gutil.PluginError(“webpack”, err);
gutil.log(“[webpack]”, stats.toString({
// output options
}));
callback();
});
});
本来我们只须要把安插写到 webpack({ … }) 中去就可以,无须再写
webpack.config.js 了。

{ “scripts”: { “build”: “webpack”, “dev”: “webpack-dev-server –devtool
eval –progress –colors –hot –content-base build” }}

*纸包不住火模块使用案例

在package.json 设置它的scripts npm run build===webpack(这里是运作打包卡塔尔国

*引进模块

npm i webpack-dev-server –save
npm run dev
在http://localhost:8080监听文件纠正
“dev”: “webpack-dev-server –devtool eval –progress –colors –hot
–content-base build”

是模块和财富的转变器,它本人是二个函数,选拔源文件作为参数,再次来到转变的结果。那样,大家就能够透过
require 来加载任何项目标模块或文件,举个例子CoffeeScriptJSX
LESS图片

var MyModule = require(‘./MyModule.js’);//commonjs

document.getElementById(“box”).innerHTML=index.main();

entry: {
page1: “./page1”,//单个文件方式援救数组格局,将加载数组中的全部模块,但以最终叁个模块作为出口
page2: [“./entry1”, “./entry2”]
},//数组情势 假若利用上边你的写法 无法用上边的这种
output: {
path: “dist/js/page”,
filename: “[name].bundle.js”
}

webpack require 一切
require(“./content.js”); // 添加content.js

import “../css/main.css”;//ES6引入格局

webpack-dev-server

*loader理解

module.exports = {

path: ‘./dist’,

path: ‘./dist’,

二个放在package.json 的dependencies , 八个位居devDependencies里面

};

  • 在 localhost:8080 创建二个 Web 服务器
    –devtool eval
  • 为您的代码成立源地址。当有另境外报纸错的时候能够让您尤其正确地牢固到文件和行号
    –progress
  • 展现合併代码进程
    –colors
  • Yay,命令行中展现颜色!
    –content-base build
  • 针对设置的输出目录

};

*安装

*npm install –save 与 npm install –save-dev 的区别

**

import MyModule from ‘./modules/MyModule.js’;//es6

//那是在另多个文书
var index=require(“./content.js”); // 添加content.js

*安顿文件

扩展:

entry: {

    page1:["./js/entry.js","./js/double.js"]

},

output: {

安装css-loader : npm install css-loader style-loader
require(“style!css!
../css/main.css”)//加载CSS style!css!是声称那几个模块是CSS
style!css!能够不写 在loaders里面配备音讯就可以

npm i webpack-dev-server –save

若是须要浏览器自动刷新你必要在布署中加进三个入口点。
webpack.config.js
**entry: [ ‘webpack/hot/dev-server’,
‘webpack-dev-server/client?http://localhost:8080’,
path.resolve(__dirname, ‘app/main.js’) ],

npm i react-dom –save

var index={//那是增多content.js
main:function(){
var html=”1111111″;
return html;
}
}
module.exports=index;

*目录

var path = require(‘path’);

webpack.config.js 以下是基本配置
单个入口文件
var path = require(‘path’);

export default Girls;//ES6

npm install react –save

    publicPath: './dist/',

    filename: "bundle.js"

},

module: {

    loaders: [

        { test: /.css$/, loader: "style!css" }

    ]

}

页面要引进打包后的门道的JS文件

*注意事项

手动打包: webpack 源文件路线 打包路径(webpack ./entry.js
./bundle.js卡塔尔//这里是未曾配置webpack.config.js
$ webpack –watch //监听变动并机关打包 监视webpack.config.js 的改观$
webpack -p //压缩混淆脚本,那么些可怜可怜关键!

module.exports = “It works from content.js.”;//nodejs中的揭破方式

    publicPath: './dist/',

    filename: "bundle.js"

},

module: {

    loaders: [

        { test: /.css$/, loader: "style!css" }

    ]

}
entry: "./js/entry.js",

output: {

index.html
js / 你的js文件
dist / 你打包的文书(也正是你JS目录下的文本打包后的公文卡塔 尔(英语:State of Qatar)
手动打包方法

npm install babel-loader babel-core babel-preset-es2015
babel-preset-react –save-dev

*加载CSS

module: { //加载器配置 loaders: [ { test: /.css$/, loader:
‘style-loader!css-loader’ }, { test: /.js$/, loader:
‘jsx-loader?harmony’ }, { test: /.scss$/, loader:
‘style!css!sass?sourceMap’}, { test: /.(png|jpg)$/, loader:
‘url-loader?limit=8192’} ] },

npm install webpack –save-dev

加载器配置

webpack-dev-server 自动监听(当时还无法自行刷新浏览器卡塔 尔(英语:State of Qatar)ctrl+C退出服务

多个输入文件

module.exports = {

跻身到您的等级次序将webpack安装到项指标依靠中,那样就能够动用处目本地版本的webpack
npm install webpack@1.12.x–save-dev(这种格式是安装钦点版本)

*揭露模块

发表评论