vue原始碼分析四 從入口檔案開始

2021-09-09 07:09:38 字數 3361 閱讀 1238

在 web 應用下,我們來分析 runtime + compiler 構建出來的 vue.js

根據package.json,執行npm run dev命令

//target引數就是package.json中執行的命令,這裡就是web-full-dev

if (process.env.target) else

從上述**,配合alias.js這樣入口檔案我們就找到了,就是src/platforms/web/entry-runtime-with-compiler.js。

import vue from './runtime/index'
import vue from 'core/index'
這個地方的檔案路徑沒有./什麼的,是因為在用rollup打包的時候,有這麼乙個別名的配置const aliases = require(』./alias』)

core: resolve(『src/core』),

import vue from './instance/index'
import  from './init'

import from './state'

import from './render'

import from './events'

import from './lifecycle'

import from '../util/index'

function vue (options)

、、this._init(options)

} = function (options?: object) {},即this._init()

initmixin(vue)

//$set、$delete、$watch

statemixin(vue)

//$on、$once、$off、$emit

eventsmixin(vue)

//_update、$forceupdate、$destroy

lifecyclemixin(vue)

//$nexttick、_render、以及多個內部呼叫的方法

rendermixin(vue)

export default vue

到這裡,我們知道它實際上就是乙個用 function 實現的類,我們只能通過 new vue 去例項化它。

我們往後看這裡有很多***mixin的函式呼叫,並把 vue 當引數傳入,它們的功能都是給 vue 的 prototype 上擴充套件一些方法(這裡具體的細節會在之後的文章介紹,這裡不展開)。

vue 按功能把這些擴充套件分散到多個模組中去實現,而不是在乙個模組裡實現所有,這種方式是用 class 難以實現的。

這麼做的好處是非常方便**的維護和管理,這種程式設計技巧也非常值得我們去學習。

vue.js 在整個初始化過程中,除了給它的原型 prototype 上擴充套件方法,還會給vue 這個物件本身擴充套件全域性的靜態方法

我們按照剛才所提到的檔案引入順序一步步來看。src/core/instance/index.js執行之後,是src/core/index.js檔案

//在 vue 建構函式上掛載靜態屬性和方法

initglobalapi(vue)

//用於判斷是不是服務端渲染

object.defineproperty(vue.prototype, '$isserver', )

vue.version = '__version__'

vue 在經過 initglobalapi 之後,會變成這樣:

// src/core/index.js / src/core/global-api/index.js

vue.config

vue.util = util

vue.set = set

vue.delete = del

vue.nexttick = util.nexttick

vue.options = ,

directives: {},

filters: {},

_base: vue

}vue.use

vue.mixin

vue.cid = 0

vue.extend

vue.component = function(){}

vue.directive = function(){}

vue.filter = function(){}

vue.prototype.$isserver

vue.version = '__version__'

稍微複雜一點的就是 vue.options。

覆蓋 vue.config 的屬性,將其設定為平台特有的一些方法

vue.options.directives 和 vue.options.components 安裝平台特有的指令和元件

在 vue.prototype 上定義patch和 $mount

// 安裝平台特定的utils

vue.config.isunknownelement = isunknownelement

vue.config.isreservedtag = isreservedtag

vue.config.gettagnamespace = gettagnamespace

vue.config.mustuseprop = mustuseprop

// 安裝平台特定的 指令 和 元件

vue.options = ,

directives: ,

filters: {},

_base: vue

}vue.prototype.__patch__

vue.prototype.$mount

這裡大家要注意的是 vue.options 的變化

vue本質上就是乙個用 function 實現的 class,然後它的原型 prototype 以及它本身都擴充套件了一系列的方法和屬性。

入口檔案開始,分析Vue原始碼實現

網上現有的vue原始碼解析文章一搜一大批,但是為什麼我還要去做這樣的事情呢?因為覺得 紙上得來終覺淺,絕知此事要躬行。然後平時的專案也主要是vue,在使用vue的過程中,也對其一些約定產生了一些疑問,可能官網上只會建議你這麼做,但是核心實現我們可能並不知道。比如 其次,很久沒有更新內容了,之前對vu...

入口檔案開始,分析Vue原始碼實現

網上現有的vue原始碼解析文章一搜一大批,但是為什麼我還要去做這樣的事情呢?因為覺得紙上得來終覺淺,絕知此事要躬行。然後平時的專案也主要是vue,在使用vue的過程中,也對其一些約定產生了一些疑問,可能官網上只會建議你這麼做,但是核心實現我們可能並不知道。比如 其次,很久沒有更新內容了,之前對vue...

Dubbo原始碼 從HelloWorld開始

dubbo,相信做後端的同學應該都用過,或者有所耳聞。沒錯,我就是那個有所耳聞中的一員。公司在好幾年前實現了一套自己的rpc框架,所以也就沒有機會使用市面上琳琅滿目的rpc框架產品。之所以想好好看看dubbo,有以下幾個原因 dubbo是alibaba開源的分布式服務框架,它最大的特點是按照分層的方...