JSON.stringify not working in my map method in template literals

593 Views Asked by At

I am trying to map through some data and display the values from the objects I am mapping through, but it keeps return "[object Object]", usually I just wrap it in JSON.stringify but that isn't working here, what am I doing wrong? Here's my code:

const ListingItem = (props: any) => {

  const MOVIE_POSTER_API_URL = "https://image.tmdb.org/t/p/w92/";
  const [openMovieDbData, setOpenMovieDbData] = useState<Array<any>>([]);
  const [openMovieDbRatings, setOpenMovieDbRatings] = useState([]);

  useEffect((): any => {
    axios.get(`http://www.omdbapi.com/?t=${props.movie.title}&y=${props.movie.release_date && props.movie.release_date.substr(0, 4)}&apikey=${process.env.REACT_APP_OPEN_MOVIE_API_KEY}`)
    .then(response => {
      setOpenMovieDbData(response.data);
      setOpenMovieDbRatings(response.data.Ratings);
    })
    .catch((error) => console.log('Open Movie DB HTTP GET Request Error response:', error))
  }, [])

  return (
    <ListItem key={props.movie.id}>
      {props.movie.backdrop_path ?
        <ListItemAvatar>
          <Avatar src={MOVIE_POSTER_API_URL + props.movie.backdrop_path} />
        </ListItemAvatar> :
        <ListItemIcon>
          <Avatar>
            <LocalMoviesIcon />
          </Avatar>
        </ListItemIcon>
      }
      <ListItemText
        primary={props.movie.title}
        secondary={`${props.movie.overview} Released in ${props.movie.release_date ? props.movie.release_date.substr(0, 4) : 'N/A'}
                    ${openMovieDbRatings ? openMovieDbRatings.map((rating: any) => <div>{JSON.stringify(rating.Source)}: {JSON.stringify(rating.Value)}</div>) : 'No Reviews'}
                    Rated: ${openMovieDbData['Rated'] ? openMovieDbData['Rated'] : 'N/A'}
                    `
                  }
      />
    </ListItem>
  )
}

This is an example of what will get returned, in place of [object Object] should be the object values I am trying to access: example of what is returned

Example of response data:

{
    "Title": "Braveheart",
    "Year": "1995",
    "Rated": "R",
    "Released": "24 May 1995",
    "Runtime": "178 min",
    "Genre": "Biography, Drama, History, War",
    "Director": "Mel Gibson",
    "Writer": "Randall Wallace",
    "Actors": "James Robinson, Sean Lawlor, Sandy Nelson, James Cosmo",
    "Plot": "Scottish warrior William Wallace leads his countrymen in a rebellion to free his homeland from the tyranny of King Edward I of England.",
    "Language": "English, French, Latin, Scottish Gaelic, Italian",
    "Country": "USA",
    "Awards": "Won 5 Oscars. Another 28 wins & 33 nominations.",
    "Poster": "https://m.media-amazon.com/images/M/MV5BMzkzMmU0YTYtOWM3My00YzBmLWI0YzctOGYyNTkwMWE5MTJkXkEyXkFqcGdeQXVyNzkwMjQ5NzM@._V1_SX300.jpg",
    "Ratings": [{
        "Source": "Internet Movie Database",
        "Value": "8.3/10"
    }, {
        "Source": "Rotten Tomatoes",
        "Value": "78%"
    }, {
        "Source": "Metacritic",
        "Value": "68/100"
    }],
    "Metascore": "68",
    "imdbRating": "8.3",
    "imdbVotes": "944,923",
    "imdbID": "tt0112573",
    "Type": "movie",
    "DVD": "N/A",
    "BoxOffice": "N/A",
    "Production": "Icon Entertainment International, Twentieth Century Fox, Ladd Company, Paramount Pictures, B.H. Finance C.V.",
    "Website": "N/A",
    "Response": "True"
}
1

There are 1 best solutions below

0
On BEST ANSWER

i think the issue is here,

secondary={`${props.movie.overview} Released in ${props.movie.release_date ? props.movie.release_date.substr(0, 4) : 'N/A'}
    ${openMovieDbRatings ? openMovieDbRatings.map((rating: any) => <div>{JSON.stringify(rating.Source)}: {JSON.stringify(rating.Value)}</div>) : 'No Reviews'}
    Rated: ${openMovieDbData['Rated'] ? openMovieDbData['Rated'] : 'N/A'}
`}

#1: (main)

${openMovieDbRatings
  ? openMovieDbRatings.map((rating: any) => 
    <div>{JSON.stringify(rating.Source)}: {JSON.stringify(rating.Value)}</div>
  )
  : 'No Reviews'}

You are mapping openMovieDbRatings and making em ReactElements (aka Objects) by wrapping those inside divs. But, Then u directly pass them to string. This is causing the [object object] thing

#2:

The Rating Object,

"Ratings": [{
        "Source": "Internet Movie Database",
        "Value": "8.3/10"
    }, {
        "Source": "Rotten Tomatoes",
        "Value": "78%"
    }, {
        "Source": "Metacritic",
        "Value": "68/100"
    }],

Here, The Rating Value & Source are strings. So, it unnecessary to JSON.stringify them,

<div>{JSON.stringify(rating.Source)}: {JSON.stringify(rating.Value)}</div>

My Solution,

<ListItemText
    primary={props.movie.title}
    secondary={
        <>
            {props.movie.overview} Released in{' '}
            {props.movie.release_date
                ? props.movie.release_date.substr(0, 4)
                : 'N/A'}{' '}
            {openMovieDbRatings
                ? openMovieDbRatings.map((rating: any) => (
                        <div>
                            {rating.Source}: {rating.Value}
                        </div>
                    ))
                : 'No Reviews'}
            Rated:{' '}
            {openMovieDbData['Rated'] ? openMovieDbData['Rated'] : 'N/A'}
        </>
    }
/>

Simply, use React.Fragments.