Home > Blockchain >  Value "undefined" when trying to consume an API REST in c# with React Native and Expo
Value "undefined" when trying to consume an API REST in c# with React Native and Expo

Time:11-02

I am making an Android application with the Expo framework. I am a beginner with React Native and I don't know why I get this "error". When I try to consume the Rest API I get that the values are "undefined". The Rest API is in C #, I don't know if it's how I made the API or it's trying to consume the API.

This would be my code in React Native with Expo:

import { StatusBar } from 'expo-status-bar';
import React from 'react';
console.reportErrorsAsExceptions = false;
import { StyleSheet, Text, View } from 'react-native';

export default class App extends React.Component {
  state={
    data:{'Medicines':'Cargando...'}
  }
  
  getJsonData = () =>{
    fetch('https://localhost:5001/api/Medicines/',
    {method:'GET'}).then((response)=>response.json())
    .then((responseJson)=>{
      console.log(responseJson);
      this.setState({
        data:responseJson
      })
    })
    .catch((error)=>{
      console.error(error)
    });
  }

  componentDidMount=()=>{
    this.getJsonData();
  }
  
  render(){
      return (
        <View style={styles.container}>
          <Text style={{margin:10, fontSize:16}}>{'ID: '  this.state.data['id']}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Name: '  this.state.data['name']}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Price: '  this.state.data['price']}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Mark: '  this.state.data['mark']}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Description: '  this.state.data['description']}</Text>
          <StatusBar style="auto" />
        </View>
      );
    }
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#fff',
    alignItems: 'center',
    justifyContent: 'center',
  },
});

This is what I get when using the expo web view (I use the expo web view as the Android view consumes too much resource from my PC), for what it's worth: enter image description here

CodePudding user response:

You define your state with a data object, later in the setState, you update it with an array of object.

so change your state definition:

state = {
  data: []
}

If you want to have a default value, you can initialize your state.data:

state = {
  data: [{id: 0, name: "", mark: "", description: "", ...}]
}

After a successful API call, your data will be:

state = {
  data = [
   {id: 0, name: 'Moderna', price: 0, ...},
   {id: 1, name: 'Patillas', price: 123.5, ...},
  ]
}

Now, in the return method you can loop throughout the data to show all the data or show the first item:

render(){

 console.log(this.state.data)

 const firstElement = this.state.data[0]

      return (
        <View style={styles.container}>
          <Text style={{margin:10, fontSize:16}}>{'ID: '  firstElement.id}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Name: '  firstElement.name}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Price: '  firstElement.price}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Mark: '  firstElement.mark}</Text>
          <Text style={{margin:10, fontSize:16}}>{'Description: '  firstElement.description}</Text>
          <StatusBar style="auto" />
        </View>
      );
    }

Note: you can put a console.log in the render method and before the return to see the data.

Update

If you want to loop throughout your data, you need to create another component (can be a functional component):

const ShowItem = ({id, name, price, mark, description}) => (
    <View style={styles.container} key={id}>
      <Text style={{margin:10, fontSize:16}}>{'ID: '  id}</Text>
      <Text style={{margin:10, fontSize:16}}>{'Name: '  name}</Text>
      <Text style={{margin:10, fontSize:16}}>{'Price: '  price}</Text>
      <Text style={{margin:10, fontSize:16}}>{'Mark: '  mark}</Text>
      <Text style={{margin:10, fontSize:16}}>{'Description: '  description} </Text>
      <StatusBar style="auto" />
    </View>
)

Note: Don't forget to pass the key

Now, use it on the App component:

render(){
  return(
    <View>
     {
       this.state.data.map(item => (
         <ShowItem 
            id={item.id}
            name={item.name} 
            price={item.price}
            mark={item.mark}
            description={item.description}
         /> 
       ))
     }
    </View>
  )
}

CodePudding user response:

You are getting a array in response and you are accessing the state as an object in UI. Change your code to this: this.state.data[0].id and similarly other fields as well.

  • Related