- ВКонтакте
- РћРТвЂВВВВВВВВнокласснРСвЂВВВВВВВВРєРСвЂВВВВВВВВ
- РњРѕР№ Р В Р’В Р РЋРЎв„ўР В Р’В Р РЋРІР‚ВВВВВВВВРЎР‚
- Viber
- Skype
- Telegram
React Native - отображение данных полученных по API вызывает ошибку
Доброе утро!
Прошу помощи - глобально не понимаю проблемы в своём коде, только изучаю React Native.
Имеется вот такой код экрана
import React, {useEffect, useState} from 'react';
import { View, Text, Image, StyleSheet, TouchableOpacity, ScrollView, Alert } from 'react-native';
import { useNavigation} from '@react-navigation/native';
import AsyncStorage from '@react-native-async-storage/async-storage'
import NavigationButtons from "../Components/NavigationButtons";
//Объект данных
type ScreenData = {
user:{
user_id: string;
user_name: string;
},
balances: {
balance: {
balance: string;
currency: string;
},
frozen: {
balance: string;
currency: string;
},
available: {
balance: string;
currency: string;
}
}
}
//Базовый шаблон экрана
const BalanceScreen = () => {
const navigation = useNavigation();
const [androidKey, setAndroidKey] = useState();
const [screenData, setScreenData] = useState<ScreenData>([]);
//Проверка хранилища на наличие ключа
//Подгрузка ключа
const loadKeyData = async () => {
try
{
const value = await AsyncStorage.getItem('android_app_connect_key');
if(value !== null)
{
setAndroidKey(value);
}
}
catch (e)
{
//error
}
};
loadKeyData();
const loadBalanceData = async () => {
try
{
if(androidTraderKey == null || androidTraderKey == '' || androidTraderKey == false)
{
return;
}
const response = await fetch('here_external_url', {
method: 'POST',
headers: {
Accept: 'application/json',
'Content-Type': 'application/json',
},
body: JSON.stringify({
android_app_connect_key: androidKey
}),
});
const json = await response.json();
setScreenData(json);
}
catch (error)
{
//error
}
finally
{
//finally
}
};
loadBalanceData();
return (
<View style={styles.screen_wrapper}>
<ScrollView
style={styles.screen_view}
>
<View style={styles.user_data_head}>
<Text style={styles.user_data_head_title}>{screenData.user.user_name} #{screenData.user.user_id}</Text>
</View>
</ScrollView>
<NavigationButtons />
</View>
);
};
export default BalanceScreen
const styles = StyleSheet.create({
screen_wrapper: {
width: "100%",
flex: 1,
backgroundColor: '#16171B',
},
screen_view: {
padding: 16,
},
screen_title: {
fontFamily: 'Inter-SemiBold',
fontSize: 16,
color: "#ffffff",
padding: 16,
},
user_data_head:{
width: "100%",
flex: 1,
justifyContent: 'flex-start',
alignItems: 'flex-start',
backgroundColor: '#1E1F28',
borderRadius: 4,
marginBottom: 4,
},
user_data_head_title:{
fontFamily: 'Inter-Bold',
fontSize: 16,
color: "#ffffff",
padding: 16,
},
user_data_balance_block:{
width: "100%",
flex: 1,
flexDirection: 'column',
justifyContent: 'flex-start',
alignItems: 'flex-start',
backgroundColor: '#1E1F28',
borderRadius: 4,
padding: 16,
marginBottom: 4,
},
user_data_balance_block_title:{
fontFamily: 'Inter-Regular',
fontSize: 14,
color: "#60667C",
},
user_data_balance_block_text:{
fontFamily: 'Inter-SemiBold',
fontSize: 16,
color: "#ffffff",
}
});
Но в итоге получаю ошибку
Cannot read property 'user_name' of undefined
Ответ АПИ при этом корректный
{
"user": {
"user_id": 844,
"user_name": "testuser"
},
"balances": {
"balance": {
"currency": "rub",
"balance": 569.87
},
"frozen": {
"currency": "rub",
"balance": 0
},
"available": {
"currency": "rub",
"balance": 569.87
}
}
}
Предполагаю, что ошибка возникает из-за отсутствия данных от АПИ в момент отрисовки/рендера экрана, но как победить проблему - ума не приложу.
UPD в useState добавил значения по-умолчанию
const [screenData, setScreenData] = useState<ScreenData>(
{
user: {
user_name: 'none',
user_id: 'none',
},
balances: {
balance:
{
balance: '0',
currency: 'rub',
},
frozen:
{
balance: '0',
currency: 'rub',
},
available:
{
balance: '0',
currency: 'rub',
}
}
}
);
и завязал всё это на useEffect
useEffect(() => {
loadBalanceData();
}, [androidKey])
То есть, теперь пока не прогрузится androidKey
запрос к АПИ не уходит.
Выглядит разумно и вроде как верно, мастера-js, что скажете?