我正在尝试访问以下api端点的special_abilities
数组:http://www.dnd5eapi.co/api/monsters/1
这是我的容器组件:
import React, { Component } from 'react'
import { Link } from 'react-router';
import MonsterSpecialAbilities from '../components/MonsterSpecialAbilities'
class MonstersContainer extends Component {
constructor(props) {
super(props)
this.state = {
monster: {},
number: Math.floor((Math.random())*325)
}
this.handleRandomClick = this.handleRandomClick.bind(this)
}
componentDidMount() {
fetch(`http://www.dnd5eapi.co/api/monsters/${this.state.number}`)
.then(response => response.json())
.then(responseData => {
this.setState({ monster: responseData })
})
}
render() {
let spec_abilities;
spec_abilities = this.state.monster.special_abilities.map((ab) => {
return(
<MonsterSpecialAbilities
desc={ab.desc}
/>
)
})
return(
<div>
{this.state.monster.name}
{spec_abilities}
</div>
)
}
}
export default MonstersContainer
现在.map
函数会破坏我的组件,我收到控制台错误:Uncaught TypeError: this.state.monster.special_abilities.map is not a function
。我尝试访问this.state.monster.special_abilities[0]
来尝试访问该数组,但这会返回null
,这让我相信它是一个无效的数组。
我尝试创建一个州名monster_special_ability
并按以下方式手动设置数组:
componentDidMount() {
fetch(`http://www.dnd5eapi.co/api/monsters/${this.state.number}`)
.then(response => response.json())
.then(responseData => {
this.setState({ monster: responseData })
this.setState({ monster_special_abilities: responseData.special_abilities })
})
}
我已经尝试将调试器放入setState
函数,并在控制台中输入responseData.special_abilities
返回我想要的数组,但是在设置状态后,似乎该数组不可用(它变成原型:对象)
答案 0 :(得分:0)
将您的怪物更改为初始状态下的null
,并将渲染更改为:
render() {
if (!this.state.monster) {
return <div> Loading monster...</div>;
}
const spec_abilities = this.state.monster.special_abilities.map(ab =>
<MonsterSpecialAbilities desc={ab.desc} />
)
return (
<div>
{this.state.monster.name}
{spec_abilities}
</div>
)
}
如果您需要将monster
作为对象,则可以检查是否已设置special_abilities
,monster
答案 1 :(得分:0)
在反应组件中使用fetch时的常见做法是使用加载状态。最初将其设置为false,一旦解析了fetch,将其设置为true。如果加载状态为true,则只渲染组件。因此,您的最终代码应如下所示:
class MonstersContainer extends Component {
constructor(props) {
super(props)
this.state = {
isDataLoaded: false,
monster: {},
number: Math.floor((Math.random())*325)
}
this.handleRandomClick = this.handleRandomClick.bind(this)
}
componentDidMount() {
fetch(`http://www.dnd5eapi.co/api/monsters/${this.state.number}`)
.then(response => response.json())
.then(responseData => {
this.setState({
isDataLoaded: true,
monster: responseData
})
}).catch(e => console.log(e));
}
render() {
const { isDataLoaded, monster } = this.state;
const monsterProps = { isDataLoaded, monster };
return <Monsters {...monsterProps} />
}
}
function MonsterSpecialAbilities(desc) {
return <div>desc</div>
}
function Monsters(props) {
const {isDataLoaded, monster} = props;
let spec_abilities;
if (isDataLoaded && monster.special_abilities) {
spec_abilities = monster.special_abilities.map((ab) =>
<MonsterSpecialAbilities
desc={ab.desc}
/>
);
}
return (isDataLoaded && spec_abilities && monster.name) ? (
<div>
{monster.name}
{spec_abilities}
</div>
): <div>loading monster data...</div>;
}
&#13;
在jsbin上查看。
请注意,提取可能会失败,您还需要对其执行某些操作。您可以添加另一个名为errorMessage
的状态,该状态显示错误消息。在您的情况下,请确保您的主机在http而不是https上运行,因为使用https获取时获取网址不起作用。