Vue CLI中添加演员Axios请求后触发无限循环导致页面崩溃的问题排查
问题分析与解决方案
嘿,我来帮你揪出这个无限循环的元凶!你的代码里有两个核心问题导致了页面崩溃:
为什么会触发无限循环?
- 模板直接调用请求方法触发重复渲染:你在模板的
v-for里直接调用了ricercaAttori()方法。Vue的响应式系统中,每次组件重新渲染(比如数据更新、props变化)都会执行模板里的表达式。而ricercaAttori方法里修改了响应式数据arrayAttori,这又会触发组件重新渲染——于是就形成了「渲染→调用请求→修改数据→重新渲染→再次调用请求」的死循环,疯狂请求API直到页面崩溃。 - 异步请求的时序错误:你在axios请求外面直接写了
this.arrayAttori.length = 5,这时候请求还没返回,arrayAttori还是null,不仅会报错,而且就算请求完成后,这个截取操作也不会生效,因为异步回调是在这行代码之后执行的。
修复方案
我们需要把数据请求和模板渲染解耦,用合适的时机触发请求,再正确处理异步数据:
修改后的CardFilm.vue代码
<template> <div class="card p-4 col-2 text-center text-white bg-black"> <img v-show="filmData.poster_path != null" :src="'http://image.tmdb.org/t/p/w342/' + filmData.poster_path" :alt="filmData.title" /> <h3>{{ filmData.title }}</h3> <h5 v-show=" filmData.title.toLowerCase() != filmData.original_title.toLowerCase() " > {{ filmData.original_title }} </h5> <lang-flag class="flag" :iso="filmData.original_language" :squared="false" /> <h4>{{ filmData.vote_average }}</h4> <div> <div class="star" v-for="element in fullArrayStars()" :key="element"> ★ </div> <!-- 直接遍历响应式数组,不再调用请求方法 --> <div class="actor" v-for="element in arrayAttori" :key="element.id" > {{ element.name }} </div> </div> </div> </template> <script> import LangFlag from "vue-lang-code-flags"; import axios from "axios"; export default { name: "CardBool", data() { return { starf: "star", arrayStars: [], stars: Math.floor(this.filmData.vote_average / 2), arrayAttori: [], // 初始化为空数组,避免渲染报错 }; }, components: { LangFlag, }, props: { filmData: Object, }, // 监听filmData变化,触发演员数据请求(组件挂载时立即执行一次) watch: { filmData: { immediate: true, handler(newFilm) { this.fetchActors(newFilm.id); } } }, methods: { fullArrayStars() { return this.stars; }, // 单独封装演员数据请求方法 fetchActors(movieId) { axios .get( `https://api.themoviedb.org/3/movie/${movieId}/credits?api_key=9631e84004e35c8371fcb3c009af9551` ) .then((response) => { // 在异步回调里截取前5个演员,再赋值给响应式数组 this.arrayAttori = response.data.cast.slice(0, 5); }) .catch(err => { // 添加错误处理,避免请求失败导致的异常 console.error('获取演员数据失败:', err); this.arrayAttori = []; }); }, }, }; </script>
关键修改点说明
- 用watch监听props触发请求:通过
watch监听filmData的变化(包括组件挂载时的初始值),调用单独封装的fetchActors方法请求数据,彻底避免了模板里直接调用方法导致的重复渲染问题。 - 异步数据正确处理:在axios的
then回调里,用slice(0,5)截取前5个演员后再赋值给arrayAttori,确保数据返回后再处理和更新响应式状态。 - 模板直接遍历响应式数组:v-for直接遍历
arrayAttori,不再调用请求方法,从根源上切断了循环触发的链路。 - 初始化与错误处理:把
arrayAttori初始化为空数组,避免渲染时因为null报错;添加catch处理请求失败的情况,提升代码的健壮性。
内容的提问来源于stack exchange,提问作者Marzio Della Rocca
相关产品推荐
相关产品推荐

