React原理探索- @providesModule 模块系统
@providesModule是什么
react抛出组件化的概念后,对于开发者而言,为了提高代码的可读性与结构性,通过文件目录结构去阐述组件嵌套关系无疑是一个很好的办法,但是目录级别的加深,同时让require的文件路径让人头疼。绝大多数公司会使用自己定制的alias工具,在脚手架入口配置文件中给相应的filePath赋予别名,pack时,进行统一替换。
#ykit.config
...
alias:{
'Common':'./src/util/index.js',
'Component':'src/components/index.js'
}
...
当然也可以在文件中写入唯一的标识位,pack时将该标识位与当前声明标识位的filePath建立联系,facebook提供的@providesModule的就是这一策略。使用方法如下:
#a.js
/**
* @providesModule Common
*/
export const isArray = () => {
...
}
export const isObject = () => {
...
}
#b.js
import { isArray } from 'Common'
isArray([])
如何实现@providesModule
fbjs-script/gulp:
shared/provides-module.js中提供了这样一段正则,用于匹配文件中是否有类似@providesModule的标识符
module.exports = {
regexp: /\r?\n \* \@providesModule (\S+)(?=\r?\n)/,
};
modules-map.js 中:
transform函数调用如上正则对读入文本进行解析,并将alias的别名与filePath建立映射关系
flush函数将前面拿到的映射表进行处理加上统一前缀,并导入到json文件中
function transform(file, enc, cb) {
if (file.isNull()) {
cb(null, file);
return;
}
if (file.isStream()) {
cb(new gutil.PluginError('module-map', 'Streaming not supported'));
return;
}
// Get the @providesModule piece of out the file and save that.
var matches = file.contents.toString().match(PM_REGEXP);
if (matches) {
var name = matches[1];
if (moduleMap.hasOwnProperty(name)) {
this.emit(
'error',
new gutil.PluginError(
PLUGIN_NAME,
'Duplicate module found: ' + name + ' at ' + file.path + ' and ' +
moduleMap[name]
)
);
}
moduleMap[name] = file.path;
}
this.push(file);
cb();
}
function flush(cb) {
// Keep it ABC order for better diffing.
var map = Object.keys(moduleMap).sort().reduce(function(prev, curr) {
// Rewrite path here since we don't need the full path anymore.
prev[curr] = prefix + path.basename(moduleMap[curr], '.js');
return prev;
}, {});
fs.writeFile(moduleMapFile, JSON.stringify(map, null, 2), 'utf-8', function() {
// avoid calling cb with fs.write callback data
cb();
});
}
最后导出如下json(以fbjs build为例)
{
"BrowserSupportCore": "fbjs/lib/BrowserSupportCore",
"CSSCore": "fbjs/lib/CSSCore",
"CircularBuffer": "fbjs/lib/CircularBuffer",
"DOMMouseMoveTracker": "fbjs/lib/DOMMouseMoveTracker",
"DataTransfer": "fbjs/lib/DataTransfer",
"Deferred": "fbjs/lib/Deferred",
"ErrorUtils": "fbjs/lib/ErrorUtils",
"EventListener": "fbjs/lib/EventListener",
"ExecutionEnvironment": "fbjs/lib/ExecutionEnvironment",
"Heap": "fbjs/lib/Heap",
"IntegerBufferSet": "fbjs/lib/IntegerBufferSet",
"Keys": "fbjs/lib/Keys",
"Locale": "fbjs/lib/Locale",
"Map": "fbjs/lib/Map",
"PhotosMimeType": "fbjs/lib/PhotosMimeType",
"PrefixIntervalTree": "fbjs/lib/PrefixIntervalTree",
"Promise": "fbjs/lib/Promise",
"PromiseMap": "fbjs/lib/PromiseMap",
}
而后该做什么大家也清楚了,要么node脚本去把文件里require 对应别名的进行路径替换,要么通过babel替换,当然,facebook是通过babel玩的
题外话
其实对于alias system目前提供的两种方法,各有利弊。fb提供的方法,使得使用上更加便利,但是由于alias遍地存在,声明冲突也变得家常便饭(当然可以通过统一前缀解决)。传统在脚手架配置文件中声明的方法,虽然能让你对alias的声明一目了然,但是使用上也繁琐很多
React原理探索- @providesModule 模块系统的更多相关文章
- 探索Java9 模块系统和反应流
Java9 新特性 ,Java 模块化,Java 反应流 Reactive,Jigsaw 模块系统 Java平台模块系统(JPMS)是Java9中的特性,它是Jigsaw项目的产物.简而言之,它以更简 ...
- vue原理探索--响应式系统
Vue.js 是一款 MVVM 框架,数据模型仅仅是普通的 JavaScript 对象,但是对这些对象进行操作时,却能影响对应视图,它的核心实现就是「响应式系统」. 首先看一下 Object.defi ...
- ABP文档笔记 - 模块系统 及 配置中心
ABP框架 - 模块系统 ABP框架 - 启动配置 Module System Startup Configuration ABP源码分析三:ABP Module ABP源码分析四:Configura ...
- webpack前言:前端模块系统的演进
前端开发和其他开发工作的主要区别,首先是前端是基于多语言.多层次的编码和组织工作,其次前端产品的交付是基于浏览器,这些资源是通过增量加载的方式运行到浏览器端,如何在开发环境组织好这些碎片化的代码和资源 ...
- Nodejs中的模块系统
一.模块化的定义 ①具有文件作用域 ②具有通信规则:加载和导出规则 二.CommonJS模块规范 1.nodejs中的模块系统,具有文件作用域,也具有通信规则,使用require方法加载模块,使用ex ...
- 极简 Node.js 入门 - 1.2 模块系统
极简 Node.js 入门系列教程:https://www.yuque.com/sunluyong/node 本文更佳阅读体验:https://www.yuque.com/sunluyong/node ...
- ABP(现代ASP.NET样板开发框架)系列之4、ABP模块系统
点这里进入ABP系列文章总目录 基于DDD的现代ASP.NET开发框架--ABP系列之4.ABP模块系统 ABP是“ASP.NET Boilerplate Project (ASP.NET样板项目)” ...
- ABP框架 - 模块系统
文档目录 本节内容: 简介 模块定义 生命周期方法 PreInitialize(预初始化) Initialize(初始化) PostInitialize(提交初始化) Shutdown(关闭) 模块依 ...
- Node.js 教程 04 - 模块系统
前言: Node.js的模块系统类似于C/C++的文件引用,可以声明对象,也可以定义类 创建对象. 大家这么理解,就简单了. 定义: 为了让Node.js的文件可以相互调用,Node.js提供了一个简 ...
随机推荐
- 2017ccpc哈尔滨区域赛H
n堆石子 每次只能拿一个石子从一堆移到另一堆 知道所有的堆的石子数目都能整除x(x>1) 问最小移动次数 枚举x的可能取值 即a[i]和的素因子即可 合因子的区间变化会比较大 然后求余 ...
- zookeeper基本讲解及基本命令和配置 (转)
一.ZooKeeper概述 ZooKeeper是一种为分布式应用所设计的高可用.高性能且一致的开源协调服务,是Google的Chubby一个开源实现,是Hadoop和Hbase的重要组件,它提供了一项 ...
- 使用Redis和jackson操作json中遇到的坑
前言(可以略过) 最近在开发一个智能电表的管理系统,与常规的面向业务的系统不同.智能电表特点是每30分钟会向服务器发一次请求,报道自己目前的电表情况.然后服务器根据电表情况统计此电表的电量使用情况,包 ...
- css实现视差滚动效果
今天逛京东金融的时候发现他家网站首页的滚动效果看着很有意思,于是就做了一个,demo链接http://1.liwenyang.applinzi.com/index.html 大多数的视差滚动效果都是使 ...
- jq实现上传头像并实时预览功能
效果 页面结构 <form action="" name="form0" id="form0"> <input type= ...
- [国嵌攻略][051][NandFlash原理解析]
扮演角色 相当于嵌入式设备的硬盘 NandFlash分类 1.SCL(single level cell):单层式存储 2.MLC(multi level cell):多层式存储 3.SCL在存储格上 ...
- async函数解析
转载请注明出处:async函数解析 async函数是基于Generator函数实现的,也就是说是Generator函数的语法糖.在之前的文章有介绍过Generator函数语法和异步应用,如果对其不了解 ...
- 怎么解决ERROR in Node Sass does not yet support your current environmen问题?
好久没有重新安装node.js,昨天和小伙伴们一起安装,由于自己是在网上自行下载的node,安装地比较顺利,但另外两个小伙伴用的共享文件夹里自带的node,却是屡次碰到问题,快被逼疯,在运行Vue时总 ...
- 修真院java后端工程师学习课程--任务1(day four)
今天学习的是spring框架,内容主要有: spring的概念,主要是做什么的: Spring是一个基于IOC和AOP的结构J2EE系统的框架 IOC 反转控制 是Spring的基础,Inversio ...
- Android 双卡获取当前使用流量在线卡的信息
最近接触了一个项目,需要获取在线流量卡的信息,下面的方式,可以获取大部分手机的正确手机卡信息. 一 获取获取IMEI public static String getDeviced(int solt ...