Vue.js Vue:创建的钩子中出现错误:";TypeError:无法将未定义或null转换为object";

Vue.js Vue:创建的钩子中出现错误:";TypeError:无法将未定义或null转换为object";,vue.js,vue-component,Vue.js,Vue Component,因此,当我尝试在浏览器中运行父组件“Dashboard”时。子组件“ChartUsage”在我的控制台中抛出一个错误:[Vue warn]:创建的钩子中的错误:“TypeError:无法将未定义或null转换为object”当我尝试调试时,我看到prop:userSubmitsProp只返回一个空数组。所以这也很奇怪。但我不明白为什么。有人能帮我吗 发送prop:userSubmitsProp: <template> <div class="dashboard">

因此,当我尝试在浏览器中运行父组件“Dashboard”时。子组件“ChartUsage”在我的控制台中抛出一个错误:
[Vue warn]:创建的钩子中的错误:“TypeError:无法将未定义或null转换为object”
当我尝试调试时,我看到prop:userSubmitsProp只返回一个空数组。所以这也很奇怪。但我不明白为什么。有人能帮我吗

发送prop:userSubmitsProp:

<template>
  <div class="dashboard">
    <cards :userDataProp="currentUserData"/>
    <chartusage :userSubmitsProp="previousSubmits" />
  </div>
</template>

<script>
import db from '@/firebase/init'
import firebase from 'firebase'
import moment from 'moment'
import Chartusage from '@/components/dashboard/ChartUsage'
import Cards from '@/components/dashboard/Cards'

export default {
  name: 'Dashboard',
  components: {
    Chartusage,
    Cards
  },
  data () {
    return {
      currentUserData: {},
      previousSubmits: []
    }
  },
  created () {
    let user = firebase.auth().currentUser

    // find the user record
    db.collection('users').where('user_id', '==', user.uid).get()
      .then(snapshot => {
        snapshot.forEach((doc) => {
          let userData = doc.data()
          userData.timestamp = moment(doc.data().timestamp).format('lll')
          this.currentUserData = userData
        })
      })
      .then(() => {
        // fetch the user previous submits from the firestore
        db.collection('submits').where('user', '==', this.currentUserData.alias).get()
          .then(snapshot => {
            snapshot.forEach(doc => {
              let submit = doc.data()
              submit.id = doc.id
              submit.timestamp = moment(doc.data().timestamp).format('lll')
              this.previousSubmits.push(submit)

              // sort previousSubmits array by date
              this.previousSubmits.sort((a, b) => {
                a = new Date(a.timestamp)
                b = new Date(b.timestamp)
                return b - a
              })
              console.log(this.previousSubmits)
            })
          })
      })
  }
}
</script>

<style>
</style>

从“@/firebase/init”导入数据库
从“firebase”导入firebase
从“时刻”导入时刻
从“@/components/dashboard/Chartusage”导入Chartusage
从“@/components/dashboard/Cards”导入卡
导出默认值{
名称:“仪表板”,
组成部分:{
图表用法,
卡
},
数据(){
返回{
currentUserData:{},
先前提交:[]
}
},
创建(){
让user=firebase.auth().currentUser
//查找用户记录
db.collection('users').where('user_id','=',user.uid).get()
。然后(快照=>{
snapshot.forEach((doc)=>{
让userData=doc.data()
userData.timestamp=时刻(doc.data().timestamp).format('lll')
this.currentUserData=用户数据
})
})
.然后(()=>{
//从firestore获取用户以前提交的内容
db.collection('submits')。其中('user','=',this.currentUserData.alias)。get()
。然后(快照=>{
snapshot.forEach(doc=>{
让提交=doc.data()
submit.id=doc.id
submit.timestamp=时刻(doc.data().timestamp).format('lll'))
this.previousSubmits.push(提交)
//按日期对数组排序
this.previousSubmits.sort((a,b)=>{
a=新日期(a.时间戳)
b=新日期(b.时间戳)
返回b-a
})
console.log(this.previousSubmits)
})
})
})
}
}
接收userSubmitsProp道具以生成图表的子组件:

<template>
  <div class="check-usage">
    <div class="row">
      <div class="col s12">
        <div class="chart">
          <chartjs-line
            :fill="true"
            :datalabel="'My household usage'"
            :labels="labels"
            :data="dataset"
            :bordercolor="'#1976D2'"
            :backgroundcolor="'rgba(25,118,210, 0.5)'"
            :pointborderwidth="mywidth"
            :pointbordercolor="mypointbordercolor"
            :pointhoverborderwidth="hoverwidth"
            :pointhoverbackgroundcolor="hoverbackgroundcolor"
            :pointhoverbordercolor="hoverbordercolor"
            :bind="true">
          </chartjs-line>
          </div>
      </div>
  </div>
  </div>
</template>

<script>
export default {
  name: 'Chartusage',
  props: {
    userSubmitsProp: {
      type: Array,
      required: true
    }
  },
  data () {
    return {
      submits: this.userSubmitsProp,
      // chart data
      labels: [],
      dataset: [],
      // hover point
      mywidth: 3,
      mypointbordercolor: '#1976D2',
      hoverwidth: 3,
      hoverbackgroundcolor: '#636b6f',
      hoverbordercolor: '#ffd663'
    }
  },
  methods: {
    addChartLabels () {
      debugger
      for (let submit of Object.values(this.submits)) {
        this.labels.push(submit.timestamp)
      }
    },
    addChartdataset () {
      for (let submit of Object.values(this.usersubmits)) {
        this.dataset.push(submit.usage)
      }
    }
  },
  created () {
    this.addChartLabels()
    this.addChartdataset()
  }
}
</script>

<style>
.check-usage {
  margin: 20px 20px 30px 20px;
  box-shadow: 0 4px 70px -18px #707070;
  padding: 10px;
}

.chart {
  padding: 10px;
}
</style>

导出默认值{
名称:'Chartusage',
道具:{
userSubmitsProp:{
类型:数组,
必填项:true
}
},
数据(){
返回{
提交:this.userSubmitsProp,
//图表数据
标签:[],
数据集:[],
//悬停点
我的宽度:3,
mypointbordercolor:“#1976D2”,
悬停宽度:3,
hoverbackgroundcolor:“#636b6f”,
悬停边框颜色:“#ffd663”
}
},
方法:{
添加图表标签(){
调试器
for(让提交Object.values(this.submits)){
this.labels.push(submit.timestamp)
}
},
addChartdataset(){
for(让提交Object.values(this.usersubmits)){
this.dataset.push(submit.usage)
}
}
},
创建(){
这是addChartLabels()
this.addChartdataset()
}
}
.检查使用情况{
利润率:20px 20px 30px 20px;
盒影:0 4px70px-18px#707070;
填充:10px;
}
.图表{
填充:10px;
}

因此,仪表板组件中的
是一个空数组:

export default {
  name: 'Dashboard',
  data () {
    return {
      currentUserData: {},
      previousSubmits: []
    }
  },
Object.values(this.submits)
这就是作为
userSubmitsProp
传递给chartusage组件的内容:

    <chartusage :userSubmitsProp="previousSubmits" />
然后代码尝试调用空数组上的
对象。值

export default {
  name: 'Dashboard',
  data () {
    return {
      currentUserData: {},
      previousSubmits: []
    }
  },
Object.values(this.submits)
顺便说一句,为组件提供属性的惯用方法是使用破折号而不是camelCase:

    <chartusage :user-submits-prop="previousSubmits" />


谢谢你的回答Stephan!但在dashboard组件的反创建周期中,previousSubmits数组不是填充了Firestore数据吗?或者在填充之前,是否在创建的循环之前将previousSubmits数组传递给道具?谢谢你的提示。从现在起,我将对属性使用camelcase:)而不是在创建组件时。只有在HTTP请求承诺解决之后,我才开始这么做。我怎样才能解决这个问题?设置一个超时,以便它有时间等待数据?我建议花一点时间阅读web上的一些Vue教程。您采用的整个方法似乎与典型的Vue开发相反。我认为如果您坚持使用更常见的体系结构,您可能会更成功。Vue官方网站上甚至有几个示例(例如)。感谢您的帮助!我会听从你的建议。