vue3,父组件通过props传递异步数据,子组件接收不到问题
vue
vuejs/vue: 是一个用于构建用户界面的 JavaScript 框架,具有简洁的语法和丰富的组件库,可以用于开发单页面应用程序和多页面应用程序。
项目地址:https://gitcode.com/gh_mirrors/vu/vue
·
原因
在父子组件传值时会遇到传的值是异步请求的数据,从而可能导致一些问题。父组件中发起请求拿到数据,将数据传给子组件,子组件onMounted生命周期却接收不到值(或者说只接收了父组件定义的初始值)。
主要是因为父子组件的生命周期:
加载渲染数据过程
vue2:父组件 beforeCreate -->父组件 created -->父组件 beforeMount -->子组件 beforeCreate -->子组件 created --子组件 beforeMount -->子组件 mounted -->父组件 mounted
vue3:子组件 onMounted -->父组件 onMounted
父组件:
<template>
<div id="app">
<Formation :current-project="currentProject" :origin-list="originList"></Formation>
</div>
</template>
<script lang="ts">
import Formation from "./view/Formation.vue";
import { onMounted } from "vue";
let currentProject=ref<any>()
// 用定时器模拟发请求异步获取后端接口的数据
setTimeout(() => {
currentProject = {
d_config:""
bd_live_time:0
bd_pos_status:0
command_format:""
create_time:1713492217292
describe:"dfdgb"
};
}, 200);
onMounted(() => {
console.log("父", currentProject);
});
</script>
子组件:
<template>
<div>
<h2>{{currentProject.describe}}</h2>
</div>
</template>
<script lang="ts">
import { onMounted} from "vue";
const props = defineProps({
currentProject: {
type: Object,
},
originList: {
type: Array<any>,
default() {
return [];
},
},
});
onMounted(() => {
console.log("子", props.currentProject);
});
</script>
结果:
![]()
方案一 使用v-if控制子组件渲染的时机
思路很简单,就是初始还没获取到异步数据的时候,不让组件渲染,等拿到的时候再渲染组件。通过v-if控制子组件渲染,等拿到数据的时子组件就会渲染。可以认为是改变了父子组件的生命周期。但是这种方式有一个小问题,就是最终效果会显得子组件有些延迟才出现效果。因为异步数据是从后端的接口获取的,如果接口时间长一些的话,最终效果渲染也会慢一点。
父组件:
<template>
<div id="app">
<Formation v-if="isGetData" :current-project="currentProject" :origin-list="originList" ></Formation>
</div>
</template>
<script lang="ts">
import Formation from "./view/Formation.vue";
import {ref, onMounted } from "vue";
let currentProject=ref<any>()
let isGetData=ref(false)
// 用定时器模拟发请求异步获取后端接口的数据
setTimeout(() => {
currentProject = {
d_config:""
bd_live_time:0
bd_pos_status:0
command_format:""
create_time:1713492217292
describe:"dfdgb"
};
isGetData.value=true
}, 200);
onMounted(() => {
console.log("父", currentProject);
});
</script>
结果:

方案二 子组件使用watch监听父组件传递过来的数据
在子组件中监听父元素传过来的参数
子组件:
<template>
<div>
<h2>{{currentProject.describe}}</h2>
</div>
</template>
<script lang="ts">
import { onMounted,watch} from "vue";
const props = defineProps({
currentProject: {
type: Object,
},
originList: {
type: Array<any>,
default() {
return [];
},
},
});
watch(
() => props.currentProject,
(val, old) => {
console.log(val);//正常接收
}
);
</script>
vuejs/vue: 是一个用于构建用户界面的 JavaScript 框架,具有简洁的语法和丰富的组件库,可以用于开发单页面应用程序和多页面应用程序。
最近提交(Master分支:4 个月前 )
9e887079
[skip ci] 1 年前
73486cb5
* chore: fix link broken
Signed-off-by: snoppy <michaleli@foxmail.com>
* Update packages/template-compiler/README.md [skip ci]
---------
Signed-off-by: snoppy <michaleli@foxmail.com>
Co-authored-by: Eduardo San Martin Morote <posva@users.noreply.github.com> 1 年前
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐


所有评论(0)