我的useEffect有问题,我认为这是由于内部的异步函数造成的,但我不知道如何解决这个问题。让我解释一下:在我的useEffect中,由于AsyncStorage
,我有一个用于检索用户数据的函数,我希望在天气API请求中,我可以输入用户的城市作为参数,以便它在现场工作,但当我重新加载应用程序时,它会给我一条错误消息,如:currentUserData.user.city is undefined
这是代码:
const [loading, setLoading] = useState(false);
const [currentData, setCurrentData] = useState({});
const [currentUserData, setCurrentUserData] = useState({});
const navigation = useNavigation();
useEffect(() => {
setLoading(true);
const getUserData = async () => {
try {
const jsonValue = await AsyncStorage.getItem('user');
setCurrentUserData(JSON.parse(jsonValue));
const response = await axios.get(
`https://api.weatherapi.com/v1/current.json?key=${APIKEY}&q=${currentUserData.user.city}&aqi=no&lang=fr`,
);
setCurrentData(response.data.current.condition);
setLoading(false);
} catch (e) {
setLoading(false);
alert(e);
}
};
getUserData();
}, []);
if (loading) {
return (
<View style={{flex: 1, alignItems: 'center', justifyContent: 'center'}}>
<Text
style={{
fontSize: 80,
color: 'red',
}}>
Loading...
</Text>
</View>
);
} else {
return (
<View style={styles.container}>
<View style={styles.content}>
<View
style={{
flexDirection: 'row',
justifyContent: 'space-between',
alignItems: 'center',
marginTop: 50,
}}>
<View
style={{flexDirection: 'column', marginLeft: 20, marginTop: 20}}>
<Image
style={{width: 50, height: 50}}
source={{
uri: `https:${
Object.keys(currentUserData).length > 0
? currentData.icon
: ''
}`,
}}
/>
</View>
<Text style={styles.title}>
Bienvenue, {'n'}{' '}
<Text style={{fontWeight: 'bold'}}>
{Object.keys(currentUserData).length > 0
? currentUserData.user.first_name
: ''}
</Text>
</Text>
<TouchableWithoutFeedback
onPress={() => navigation.navigate('UserScreen')}>
<FontAwesomeIcon
style={{marginRight: 20, marginTop: 20}}
size={35}
icon={faUser}
/>
</TouchableWithoutFeedback>
</View>
</View>
</View>
);
}
}
请使用?
运算符访问currentUserData.user
。例如CCD_ 5。
因为初始状态是{}
,所以currentUserData.user
是undefined
,并且您的代码试图从undefined
中获取值。
并在您的API URL中使用。
首先请写一个控制台。并尝试使用以下代码。
`https://api.weatherapi.com/v1/current.json?key=${APIKEY}&q=${currentUserData? currentUserData?.user?.city || '' : ''}&aqi=no&lang=fr`
您的错误是在调用setCurrentUserData时就使用了状态变量。我们不能这样使用它。更新后的挂钩如下:
useEffect(() => {
setLoading(true);
const getUserData = async () => {
try {
const jsonValue = await AsyncStorage.getItem('user');
const parsedUserData = JSON.parse(jsonValue) || {};
setCurrentUserData(parsedUserData);
const response = await axios.get(
`https://api.weatherapi.com/v1/current.json?key=${APIKEY}&q=${parsedUserData?.user?.city}&aqi=no&lang=fr`,
);
setCurrentData(response.data.current.condition);
setLoading(false);
} catch (e) {
setLoading(false);
alert(e);
}
};
getUserData();
}, []);
我认为您可能会滥用React Hook,setCurrentUserData
异步更新状态,立即使用currentUserData.user.city
是完全错误的,因此您可以使用以下选项:
- 使用从AsyncStorage返回的数据
const jsonValue = await AsyncStorage.getItem('user');
const userData = JSON.parse(jsonValue)
setCurrentUserData(userData);
const response = await axios.get(
`https://api.weatherapi.com/v1/current.json?key=${APIKEY}&q=${currentUserData.user.city}&aqi=no&lang=fr`,
);
- 删除
setCurrentUserData(JSON.parse(jsonValue));
下面的所有逻辑,并将它们移到另一个使用currentUserData
作为依赖项的useEffect中
useEffect(() => {
if(currentUserData) {
// make api request here
const response = await axios.get(
`https://api.weatherapi.com/v1/current.json?key=${APIKEY}&q=${currentUserData.user.city}&aqi=no&lang=fr`,
);
// some logic here...
}
}, [currentUserData])