這是xue源碼學(xué)習(xí)記錄,如有錯(cuò)誤請(qǐng)指出,謝謝!相互學(xué)習(xí)相互進(jìn)步。
vue源碼目錄為vue ├── src #vue源碼 ├── flow #flow定義的數(shù)據(jù)類型庫(vue通過flow來檢測(cè)數(shù)據(jù)類型是否正確) ├── examples #demo ├── scripts #vue構(gòu)建命令 ├── ...
vue內(nèi)部代碼模塊比較清晰,這邊主要分析scripts內(nèi)部代碼,講解vue是如何進(jìn)行構(gòu)建的.
首先你必須要懂一些rollup,vue內(nèi)部是通過rollup來進(jìn)行構(gòu)建的,rollup是一款js的構(gòu)建工具,
將各個(gè)小模塊打包成一個(gè)總的模塊(只針對(duì)js文件,比較輕量,不會(huì)有css,img等壓縮,比較適合開發(fā)插件,
如果是ui組件庫的話,還是webpack構(gòu)建會(huì)比較好。)
rollup說明文檔:https://rollupjs.cn/
文件主要是scripts下的alias.js,config.js和build.js三個(gè)文件組成
alias主要就是提供文件對(duì)應(yīng)的路徑
const path = require("path") const resolve = p => path.resolve(__dirname, "../", p) // 以下是設(shè)置別名,與對(duì)應(yīng)的真實(shí)文件路徑 module.exports = { vue: resolve("src/platforms/web/entry-runtime-with-compiler"), compiler: resolve("src/compiler"), core: resolve("src/core"), shared: resolve("src/shared"), web: resolve("src/platforms/web"), weex: resolve("src/platforms/weex"), server: resolve("src/server"), entries: resolve("src/entries"), sfc: resolve("src/sfc"), test: resolve("src/test") // 這個(gè)是測(cè)試目錄是自己添加的 }
其中test是我自己加的,為了測(cè)試打包
configconfig是為了提供打包的基礎(chǔ)配置(即rollup打包配置文件格式),由于打包內(nèi)容比較多,
所以做成可配置的
const path = require("path") const buble = require("rollup-plugin-buble") // 提供modules名稱的 alias 和reslove 功能 const alias = require("rollup-plugin-alias") // 將CommonJS模塊轉(zhuǎn)換為 ES2015供Rollup 處理 const cjs = require("rollup-plugin-commonjs") // 變量替換,可以將動(dòng)態(tài)設(shè)置的變量提取出來在配置文件中設(shè)置 const replace = require("rollup-plugin-replace") // 幫助 Rollup 查找外部模塊,然后安裝 const node = require("rollup-plugin-node-resolve") const flow = require("rollup-plugin-flow-no-whitespace") const version = process.env.VERSION || require("../package.json").version // 下面是weex服務(wù)器端代碼,不需要管 // const weexVersion = process.env.WEEX_VERSION || require("../packages/weex-vue-framework/package.json").version // 這邊是打包完成后模塊外部首行注釋代碼 const banner = `/* * test-vue.js v${version} * (C) 2014-${new Date().getFullYear()} Enan You * @author zhengjie */ ` // 獲取文件夾路徑別名 const aliases = require("./alias") // 尋找路徑 const resolve = p => { const base = p.split("/")[0] if (aliases[base]) { return path.resolve(aliases[base], p.slice(base.length + 1)) } else { return path.resolve(__dirname, "../", p) } } // 設(shè)置打包參數(shù) // 這邊把原先vue打包文件去除,替換成知己的一個(gè)測(cè)試文件 const builds = { "test-cjs": { entry: resolve("test/main.js"), dest: resolve("dist/test-cjs.js"), format: "cjs", // csj格式 module.exports banner }, "test-es": { entry: resolve("test/main.js"), dest: resolve("dist/test-es.js"), format: "es", // es格式 export default banner }, "test-umd": { entry: resolve("test/main.js"), dest: resolve("dist/test-umd.js"), format: "umd", // 瀏覽器格式 return banner } } // 根據(jù)上面builds打包轉(zhuǎn)換成rollup打包格式 function getConfig(name) { const opts = builds[name] const config = { input: opts.entry, external: opts.external, plugins: [ replace({ __WEEX__: !!opts.weex, __WEEX_VERSION__: null, __VERSION__: version }), flow(), buble(), alias(Object.assign({}, aliases, opts.alias)) ].concat(opts.plugins || []), output: { file: opts.dest, format: opts.format, banner: opts.banner, name: opts.moduleName || "Vue" } } // 如果是開發(fā)模式 if (opts.env) { config.plugins.push(replace({ "process.env.NODE_ENV": JSON.stringify(opts.env) })) } // 增加屬性 Object.defineProperty(config, "_name", { enumerable: false, value: name }) return config } if (process.env.TARGET) { module.exports = getConfig(process.env.TARGET) } else { exports.getBuild = getConfig exports.getAllBuilds = () => Object.keys(builds).map(getConfig) }
其中里面的builds已被替換成我自己的測(cè)試文件,用于測(cè)試打敗es,模塊化和瀏覽器的不同格式。
buildbuild文件就是根據(jù)配置文件進(jìn)行打包,打包模式分為全部打包,或者是可配置打包,
如果運(yùn)行npm run build,將會(huì)打包所有的配置,
而運(yùn)行npm run build "參數(shù)", 則根據(jù)參數(shù)配置進(jìn)行打包
const fs = require("fs") const path = require("path") const zlib = require("zlib") const rollup = require("rollup") const uglify = require("uglify-js") // 檢測(cè)是否有dist文件 if (!fs.existsSync("dist")) { fs.mkdirSync("dist") } let builds = require("./config").getAllBuilds() // build后面輸入的參數(shù) if (process.argv[2]) { // 過濾出需要打包的數(shù)組 const filters = process.argv[2].split(",") builds = builds.filter(b => { return filters.some(f => b.output.file.indexOf(f) > -1 || b._name.indexOf(f) > -1) }) } else { // 這邊過濾出weex,不需要管 builds = builds.filter(b => { return b.output.file.indexOf("weex") === -1 }) } // 把需要打包的打包出來 build(builds) // 打包函數(shù) function build(builds) { let built = 0 const total = builds.length const next = () => { buildEntry(builds[built]).then(() => { built++ if (built < total) { next() } }).catch(logError) } next() } // 單個(gè)配置文件打包 function buildEntry(config) { const output = config.output const {file, banner} = output // 是否為壓縮文件 const isProd = /min.js$/.test(file) return rollup.rollup(config) .then(bundle => bundle.generate(output)) .then(({code}) => { // 壓縮我文件 if (isProd) { var minified = (banner ? banner + " " : "") + uglify.minify(code, { output: { ascii_only: true }, compress: { pure_funcs: ["makeMap"] } }).code return write(file, minified, true) } else { return write(file, code) } }) } function write(dest, code, zip) { return new Promise((resolve, reject) => { function report (extra) { console.log(blue(path.relative(process.cwd(), dest)) + " " + getSize(code) + (extra || "")) resolve() } fs.writeFile(dest, code, err => { if (err) return reject(err) if (zip) { zlib.gzip(code, (err, zipped) => { if (err) return reject(err) report(" (gzipped: " + getSize(zipped) + ")") }) } else { report() } }) }) } // 計(jì)算文件大小 function getSize (code) { return (code.length / 1024).toFixed(2) + "kb" } // 輸入錯(cuò)誤信息 function logError (e) { console.log(e) } function blue (str) { return "x1b[1mx1b[34m" + str + "x1b[39mx1b[22m" }測(cè)試文件
main.js
import foo from "./foo"; export default function () { console.log(foo) }
foo.js
export default "hello rollup"
通過npm run build打包測(cè)試,會(huì)在dist文件打包出test-cjs.js,test-es.js,test-umd.js
文件內(nèi)容如下:
test-cjs.js
/* * test-vue.js v1.0.0 * (C) 2014-2018 Enan You * @author zhengjie */ "use strict"; var foo = "hello rollup" function main () { console.log(foo); } module.exports = main;
test-es.js
/* * test-vue.js v1.0.0 * (C) 2014-2018 Enan You * @author zhengjie */ var foo = "hello rollup" function main () { console.log(foo); } export default main;
test-umd.js
/* * test-vue.js v1.0.0 * (C) 2014-2018 Enan You * @author zhengjie */ (function (global, factory) { typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define(factory) : (global.Vue = factory()); }(this, (function () { "use strict"; var foo = "hello rollup" function main () { console.log(foo); } return main; })));
這個(gè)構(gòu)建的過程不難,比起webpack的配置文件要容易懂很多
懂得了vue的構(gòu)建,接下來就可以開始vue源碼的學(xué)習(xí)了
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/98401.html
摘要:至此算是找到了源碼位置。至此進(jìn)入過渡的部分完畢。在動(dòng)畫結(jié)束后,調(diào)用了由組件生命周期傳入的方法,把這個(gè)元素的副本移出了文檔流。這篇并沒有去分析相關(guān)的內(nèi)容,推薦一篇講非常不錯(cuò)的文章,對(duì)構(gòu)造函數(shù)如何來的感興趣的同學(xué)可以看這里 Vue transition源碼分析 本來打算自己造一個(gè)transition的輪子,所以決定先看看源碼,理清思路。Vue的transition組件提供了一系列鉤子函數(shù),...
摘要:框架使用了作為類型檢查,來保證項(xiàng)目的可讀性和維護(hù)性。的主目錄下有的配置文件,還有目錄,指定了各種自定義類型。表示構(gòu)建出來的文件遵循規(guī)范。 Flow vue框架使用了Flow作為類型檢查,來保證項(xiàng)目的可讀性和維護(hù)性。vue.js的主目錄下有Flow的配置.flowconfig文件,還有flow目錄,指定了各種自定義類型。 在學(xué)習(xí)源碼前可以先看下Flow的語法 官方文檔 目錄結(jié)構(gòu) vue....
摘要:源碼目錄結(jié)構(gòu)打包相關(guān)的配置文件,其中最重要的是。主要是根據(jù)不同的入口,打包為不同的文件。這個(gè)目錄下的代碼邏輯會(huì)把文件內(nèi)容解析成一個(gè)的對(duì)象。 源碼目錄結(jié)構(gòu) VUE 2.6.10 ├── scripts # 打包相關(guān)的配置文件,其中最重要的是config.js。主要是根據(jù)不同的入口,打 包為不同的文件。 ├── dist # 打包之后文...
摘要:了解的構(gòu)建,可以從文件開始命令內(nèi)關(guān)于構(gòu)建的命令如下版本從命令看出是通過來進(jìn)行構(gòu)建的同樣的構(gòu)建工具更強(qiáng)大一些,可以處理圖片等但是只做的處理,相比之下更輕量所以更適合框架的打包總共有三個(gè)版本的構(gòu)建從版本的為起點(diǎn)來了解,版本的構(gòu)建 了解Vue的構(gòu)建,可以從package.json文件開始sprits命令內(nèi)關(guān)于構(gòu)建的命令如下 { ... build: node scri...
摘要:運(yùn)行時(shí)用來創(chuàng)建實(shí)例渲染并處理虛擬等的代碼。基本上就是除去編譯器的其它一切。版本可以通過標(biāo)簽直接用在瀏覽器中。為這些打包工具提供的默認(rèn)文件是只有運(yùn)行時(shí)的構(gòu)建。為瀏覽器提供的用于在現(xiàn)代瀏覽器中通過直接導(dǎo)入。 Vue版本:2.6.9 源碼結(jié)構(gòu)圖 ├─ .circleci // 包含CircleCI持續(xù)集成/持續(xù)部署工具的配置文件 ├─ .github ...
閱讀 2078·2021-11-23 10:13
閱讀 2788·2021-11-09 09:47
閱讀 2737·2021-09-22 15:08
閱讀 3312·2021-09-03 10:46
閱讀 2230·2019-08-30 15:54
閱讀 909·2019-08-28 18:09
閱讀 2429·2019-08-26 18:26
閱讀 2341·2019-08-26 13:48