Open lbwa opened 5 years ago
在 vue-rotuer 源码中,vuejs 的插件开发是依赖通过插件 install 方法 动态 传入的 Vue 对象。这是为了避免单独 import Vue 将导致插件直接依赖 Vuejs,进而导致 package 包含 Vuejs,即插件体积增大。
vue-rotuer
vuejs
install
Vue
import Vue
Vuejs
package
// src/index.js import { install } from './install' export default class VueRouter { // ... } // 定义插件的 install 方法,在作为模块引入插件时,必须调用 Vue.use(VueRouter) 来向 install 方法动 // 态传入 Vue 对象,使得插件可以使用 Vue 对象 VueRouter.install = install // 全局环境自动调用 Vue.use(VueRouter) if (inBrowser && window.Vue) { window.Vue.use(VueRouter) }
通过在插件的 install 模块中建立一个缓存容器来缓存作为参数被传入的 Vue 对象。此时, Vue 是作为参数 动态 传入,并不是作为函数中的静态变量而存在。那么仅在调用 install 方法时, Vue 对象才会被传入。那么也就避免了在插件 install 函数中直接依赖 Vue 对象。同时也并不影响插件在被调用时对 Vue 对象的依赖。
// src/install.js // 缓存容器,export 之后可用于其他非 install.js 的模块调用 Vue 对象,如 src/history/base.js export let _Vue // 通过参数形式来避免 Vue 被 install 方法直接依赖,此举可避免插件 package 打包 Vue export function install (Vue) { if (install.installed && _Vue === Vue) return install.installed = true _Vue = Vue // ... }
纵观 vuejs 的插件开发原理,无论是在以后自己开发 vuejs 插件还是其他库,都可利用 将依赖转变为参数 的方式来避免 package 体积增大。即避免了模块对其他模块的直接依赖。这个思路个人认为比较适合插件开发,因为它的依赖动态引入原理极大地限制了插件的 dependcies。
dependcies
Vue-rotuer/index.js
Vue-router/install.js
Vuejs 技术揭秘
此举本质上与函数式编程中的 dependency injection 概念相同,它用于显式地指明函数的依赖变量。但 Vue.js 的插件机制重点 不仅仅 在于保持函数式编程中的函数 纯洁性,而是更加侧重于对于函数内部变量的解耦,即动态引入变量。
dependency injection
Vue.js
纯洁性
vue-router
在
vue-rotuer
源码中,vuejs
的插件开发是依赖通过插件install
方法 动态 传入的Vue
对象。这是为了避免单独import Vue
将导致插件直接依赖Vuejs
,进而导致package
包含Vuejs
,即插件体积增大。通过在插件的
install
模块中建立一个缓存容器来缓存作为参数被传入的Vue
对象。此时,Vue
是作为参数 动态 传入,并不是作为函数中的静态变量而存在。那么仅在调用install
方法时,Vue
对象才会被传入。那么也就避免了在插件install
函数中直接依赖Vue
对象。同时也并不影响插件在被调用时对Vue
对象的依赖。总结
纵观
vuejs
的插件开发原理,无论是在以后自己开发vuejs
插件还是其他库,都可利用 将依赖转变为参数 的方式来避免package
体积增大。即避免了模块对其他模块的直接依赖。这个思路个人认为比较适合插件开发,因为它的依赖动态引入原理极大地限制了插件的dependcies
。Reference
Vue-rotuer/index.js
Vue-router/install.js
Vuejs 技术揭秘