Vue组件通信provide和inject,注入
使用场景,祖先组件向下层所有组件注入,无论层级多深,子组件均能接收来自祖先组件。某个模块由根组件内统一管理子组件内的状态。
类型
provide:Object | () => Object
inject:Array<string> | { [key: string]: string | Symbol | Object }
基本使用
// 父级组件提供 'foo'
var Provider = {
provide: {
foo: 'bar'
},
// ...
}
// 子组件注入 'foo'
var Child = {
inject: ['foo'],
created () {
console.log(this.foo) // => "bar"
}
}
事实上没人用这么用provide和inject。provide的变量默认不是响应的。
但是开发中我们需要provide的变量为响应式,那么如何操作能让provide变为响应式呢?
官网提示:provide 和 inject 绑定并不是可响应的。这是刻意为之的。然而,如果你传入了一个可监听的对象,那么其对象的 property 还是可响应的。
// 父组件provide
data() {
return {
companyData:{}, // 响应式数据
workShopData:{}
};
},
...
provide(){
return {
getCompanyData:()=>this.companyData, //给子组件注入请求回的数据,按照官网要求的格式使数据变为响应式
getWorkShopData:()=>this.workShopData,
}
}
// 子组件inject注入
inject:['getCompanyData','getWorkShopData'], // 注入你需要的数据
...
computed:{
companyData(){
return this.getCompanyData() // 由于传递的时候是个函数,顾需使用computed计算取出值,此时数据已经完成响应式
}
},
场景及注意事项
- 使用场景,目前遇到的不多,听说和react的context还有angualr的依赖注入相似。祖先组件统一管理状态,无论层级多深,子孙组件将继承到。
- 其实provide和inject并不适合像vuex和pinna做状态管理,首先他是不可响应式的,其次本身提供的api写法并不是响应式的,说明开发者并不想要使用者用依赖注入来做状态管理,他只适合做单一的祖先组件统一向子组件传递值。或者简单点说,我有一个父组件需要向下面的子组件传递参数统一管理,此时就适合使用provide和inject。
- 网上抄了些观点,我觉得很好的解释了为什么需要依赖注入。
- 它是项目前端工程化的体现
- 它使本来复杂的页面简单化
- 可以轻松实现代码的复用
- 它可以避免开发者重复的造轮子
- 方便团队合作。给定引用的接口,使用者不用管内部实现。(我在项目中使用他管理特定的接口请求页面)
- 方便前端的调试