设置初始状态以避免错误的最佳方法是什么:"无法读取未定义的属性"?

时间:2017-02-10 11:28:33

标签: javascript reactjs redux

我从服务器获取一些用户数据。 此数据用于设置React组件的初始状态。 此初始状态必须具有包含嵌套对象的对象initialValues。

避免错误:"无法读取未定义"的属性,由以下原因引起:

  1. 初始渲染的ajax调用延迟;
  2. 从服务器获取的UserData对象中可能存在空值(并非每个用户都需要有一个地址,汽车信息......);

    如果其值为null,则检查每个UserData属性,然后为其分配值。

  3. 下面是mapStateToProps函数和我创建的对象:

    function mapStateToProps(state) {
    const data = state.userData.userData;
    return {
        userName: `${data.firstname || "User Name"} ${data.surname || ""}`,
        ajaxCallLink: (data._links == undefined) ? "" : data._links.self.href,
        initialValues: {
            firstname: data.firstname || "",
            surname: data.surname || "",
            jobTitle: data.jobTitle || "",
            dob: data.dob || "",
            pps: data.pps || "",
            phone: data.phone || "",
            email: data.email || "",
            address: {
                addressLine1: (data.address == undefined) ? "" : (data.address.addressLine1 || ""),
                addressLine2: (data.address == undefined) ? "" : (data.address.addressLine2 || ""),
                addressLine3: (data.address == undefined) ? "" : (data.address.addressLine3 || ""),
                addressLine4: (data.address == undefined) ? "" : (data.address.addressLine4 || ""),
            },
            car: {
                make: (data.car == undefined) ? "" : (data.car.make || ""),
                model: (data.car == undefined) ? "" : (data.car.model || ""),
                engineSize: (data.car == undefined) ? "" : (data.car.engineSize || ""),
            },
            bankAccount: {
                accountType: (data.bankAccount == undefined) ? "" : (data.bankAccount.accountType || ""),
                accountNumber: (data.bankAccount == undefined) ? "" : (data.bankAccount.accountNumber || ""),
                sortCode: (data.bankAccount == undefined) ? "" : (data.bankAccount.sortCode || ""),
                bank: (data.bankAccount == undefined) ? "" : (data.bankAccount.bank || ""),
                paymentAdvice: (data.bankAccount == undefined) ? "" : (data.bankAccount.paymentAdvice || ""),
                iban: (data.bankAccount == undefined) ? "" : (data.bankAccount.iban || ""),
                bic: (data.bankAccount == undefined) ? "" : (data.bankAccount.bic || ""),
                address: {
                    addressLine1: (data.bankAccount == undefined || data.bankAccount.address.addressLine1 == undefined) ? "" : (data.bankAccount.address.addressLine1 || ""),
                    addressLine2: (data.bankAccount == undefined || data.bankAccount.address.addressLine2 == undefined) ? "" : (data.bankAccount.address.addressLine2 || ""),
                    addressLine3: (data.bankAccount == undefined || data.bankAccount.address.addressLine3 == undefined) ? "" : (data.bankAccount.address.addressLine3 || ""),
                    addressLine4: (data.bankAccount == undefined || data.bankAccount.address.addressLine4 == undefined) ? "" : (data.bankAccount.address.addressLine4 || ""),
                },
            }
        }
    };
    }
    

    这个initialValues对象正在完成它的工作,应用程序运行正常。 但是,我觉得我做错了什么。 有没有更好的方法来替换未定义的值,只是不为每个单独的组件写,如巨大的 initialValues对象,具有如此多的条件值赋值?

2 个答案:

答案 0 :(得分:1)

将初始值放在具有相同结构的分离对象中:

this.defaultData = {
    ajaxCallLink:  "" 
    initialValues: {
        firstname: "",
        lastname: "",
 //.....

}

然后使用Object.assign扩展您的对象,使用默认值:

 const data = state.userData.userData;
 return  Object.assign(this.defaultData, data)

但是,由于数据对象的深度大于1,因此您需要deep assign而不是Object.assign

答案 1 :(得分:0)

我们也可以

// within mapStateToProps
return {
    initialValues: data.initialValues
}

然后处理未定义的内联,例如

const { initialValues } = this.props; 
const bankAccountIban = initialValues.bankAccount && initialValues.bankAccount.iban;

缺点是您必须为每个道具都做,但是如果不需要使用所有道具,例如只需要iban,这是一个好方法。 / p>