1 Frage: Wie übergebe ich eine Liste mit Objekten vom Server an FlatList?

Frage erstellt am Wed, May 8, 2019 12:00 AM

Ich versuche, eine FlatList zu erstellen, die ein Array mit Objekten enthält, die ein Array von einem Server haben, und ich kann es nicht zum Laufen bringen.

meine Fehlermeldung:

  

TypeError: Eigenschaft 'Data' von undefined kann nicht gelesen werden

Ich kann es mit meiner normalen Liste, die nicht von einem Server abgerufen wurde, zum Laufen bringen. Hier ist die Struktur aus meiner Arbeitsliste

[{"DATA":[{"filter_id":"44","filter_name":"filter 1"}, {"filter_id":"45","filter_name":"filter 2"},{"filter_id":"46","filter_name":"filter 3"},{"filter_id":"47","filter_name":"filter 4"},{"filter_id":"48","filter_name":"filter 5"}],"MESSAGE":"DATA FOUND","STATUS":200}]

Meine Serverliste hat dieselbe Struktur, aber unterschiedliche Werte für filter_name und filter_id

hier ist mein Code:

constructor(props){
    super(props); 
    this.state = {
    data: [],
    oldData: [{"DATA":[{"filter_id":"44","filter_name":"filter 1"},{"filter_id":"45","filter_name":"filter 2"},{"filter_id":"46","filter_name":"filter 3"},{"filter_id":"47","filter_name":"filter 4"},{"filter_id":"48","filter_name":"filter 5"}],"MESSAGE":"DATA FOUND","STATUS":200}],
    page:1,
    status: null,
    isLoading: false,
    }
}
getData = async () => {
const url = 'http://ollenorstrom.se/ollenorstrom.se/avoka/api/getFilter.php?page='+this.state.page+'&row_per_page=5';
fetch(url).then((response) => response.json())
.then((responseJson) => {
   this.setState({
    data:this.state.data.concat(responseJson),
    isLoading:false
   });
})
}
componentDidMount() {
  this.getData();
}
renderRow = ({item}) => {
  console.log('item', item);
  return (
   <View style={styles.item}>
    <Text>{item.filter_name}</Text>
   </View>
  )
}
render() {
   console.log('state', this.state.data[0]);
   console.log('oldstate', this.state.oldData[0]) // this 
   return (
    <View style={styles.container}>
     <FlatList 
      data={this.state.data[0].DATA}
      renderItem={this.renderRow} 
      keyExtractor={(item, index) => index.toString()}
      />
     </View>
  );
}

Expo: https://snack.expo.io/@thesvarta/tenacious-sandwich

    
0
1 Antworten                              1                         

Das Problem ist, dass beim erstmaligen Rendern der Komponente this.state.data nichts angezeigt wird, da gewartet werden muss, bis getData Daten zurückgibt. Aus diesem Grund können Sie zu Beginn nicht auf this.state.data[0].DATA zugreifen.

Die Lösung besteht darin, Ihre getData-Funktion ein wenig zu aktualisieren.

getData = async () => {
    const url = 'http://ollenorstrom.se/ollenorstrom.se/avoka/api/getFilter.php?page='+this.state.page+'&row_per_page=5';
    fetch(url).then((response) => response.json())
    .then((responseJson) => {
      // here we save the data, we want to access later. 
      console.log('responseJson', responseJson[0].DATA);
       this.setState({
        data:this.state.data.concat(responseJson[0].DATA),
        isLoading:false
       });
    })
  }

Jetzt werden Ihre Daten direkt in this.state.data gespeichert. Wir können jetzt Ihre render()-Funktion vereinfachen:

 <FlatList 
       data={this.state.data} // simplified, passing an empty array at the beginning is ok
       renderItem={this.renderRow} 
       keyExtractor={(item, index) => index.toString()}
      />

Arbeitsbeispiel:

https://snack.expo.io/HJ--GFlnN

    
1
2019-05-08 16: 23: 10Z
Quelle platziert Hier