html Vue无法读取对象属性的未定义属性,只能在模板中读取

kmbjn2e3  于 2022-12-16  发布在  其他
关注(0)|答案(3)|浏览(216)

我在vue中创建了变量

data() {
        return {
            plans: [],
}

Plans后来被赋予了推送到它的对象。当我在js中打印该对象时,它给出{id: 'filler', name: 'Premium', priceId: 'filler', price: '10000'}。我也可以用console.log(this.plans[1]['name'])专门获得名称,它会正确地给出'Premium'。然而,在模板中,我试图用<h1>{{plans[0].name}}</h1>显示名称(我也尝试了['name']),它说Uncatch(在承诺中)TypeError:无法读取未定义的属性(阅读“name”)。但是,如果我只给予它<h1>{{plans[0]}}</h1>,它会正确显示整个对象。非常困惑我错过了什么,请让我知道如果需要任何更多的信息。
EDIT:阵列中填充了以下内容

async getPlans(){
        
        const db = getFirestore()
        const productsRef = collection(db, "products")
        const productsQuery = query(productsRef, where("active","==", true))
        const productsQuerySnap = await getDocs(productsQuery)
        // console.log(productsQuerySnap[0])
        // const temp = []
        for (let i = 0; i<2; i++){
            // const doc = i.docs
            console.log(productsQuerySnap.docs[i])
            const pricesRef = collection(db, "products", productsQuerySnap.docs[i].id, "prices")
            const pricesQuerySnap = await getDocs(pricesRef)
            const name = productsQuerySnap.docs[i]["_document"]["data"]["value"]["mapValue"]["fields"]["name"]["stringValue"]
            console.log(pricesQuerySnap.docs[0]["id"])
            const priceId = pricesQuerySnap.docs[0]["id"]
            const price = pricesQuerySnap.docs[0]["_document"]["data"]["value"]["mapValue"]["fields"]["unit_amount"]['integerValue']
            console.log({id: productsQuerySnap.docs[i].id, name: name, priceId: priceId, price: price})
            this.plans.push({id: productsQuerySnap.docs[i].id, name: name, priceId: priceId, price: price})
        }
        console.log(this.plans[0]['name'], "plans is running")
    

  },

它是装在

2g32fytz

2g32fytz1#

在访问模板中的数据之前,一定要确保数据是可用的。这些类型的错误 (无法读取..,的未定义属性) 大多是由于没有事先检查而发生的。
在您的示例中,在访问plans arrayplans' key (plans[0])之前,创建一个计算属性或直接在模板上应用一个条件,以检查它在DOM中是否可用,如下所示-
1.如果要在所有计划物料上循环-

<template>
  <div v-if="plans && plans.length">
     <template v-for="(item, index) in plans">
       <h1>{{ item.name }}</h1>
     </template>
  </div>
</template>

1.如果您只想显示一个项目-

<template>
  <div v-if="plans && plans.length && plans[0]">
    <h1>{{ plans[0].name }}</h1>
  </div>
</template>

推荐-

您可以为plans && plans.length创建一个计算属性,而不是直接在模板中编写plans && plans.length,并且可以在任何地方访问,而无需重复代码-

<template>
  <div v-if="isPlansAvailable">
     <template v-for="(item, index) in plans">
       <h1>{{ item.name }}</h1>
     </template>
  </div>
</template>

<script>
  export default {
    name: "ComponentName",
    
    data() {
      return {
        plans: [],
      }
    },
  
    computed: {
      isPlansAvailable() {
        return this.plans && this.plans.length;
      }
    },
    
    mounted() {
      // YOUR API METHOD
    },
  }
</script>
aamkag61

aamkag612#

data() {
        return {
            plans: Object,
}
inb24sb2

inb24sb23#

我不确定是否有利用方法和挂载的解决方案,但我通过使用setup()而不是方法和挂载来解决这个问题。我将ref的值设置为完整的对象数组,然后在安装结束时返回该值,所有内容都在模板中正确访问。

相关问题