React- Render two different data arrays in a single card

Viewed 86

I have fetched card images and data into a object. But I am not to render image and data object. Please find below my rough implementation,

import React, { useState, useEffect, useCallback } from 'react';
import {Row, Col, Card} from 'react-bootstrap';
import axios from 'axios';
import {Container} from 'react-bootstrap';

export const App = () => {

  const [ users, getUsers ] = useState([]);

  const getUsersData = useCallback(async () => {
    const [image, userData] = await Promise.all([
      axios.get('https://...'),
      axios.get('https://...')
    ]);
    getUsers({ image: image.data, data: userData.data});
  },[])

  useEffect(() => {
    getUsersData()
  },[getUsersData]);

  return (
    <>
    <Container>
      <h1>User Details</h1>
      <Row>
          {/* {
            users?.image?.map(user => (
              <Card.Img src={user?.image} variant='top' />
            ))
          } */}
          {
            users?.data?.map(user => (
             <Col sm={12} md={6} lg={4} xl={3}>
              <Card className='my-3 p-3 rounded'>
                <Card.Body>
                  <Card.Title>
                    <strong>{user?.name}</strong>
                  </Card.Title>
                  <Card.Text as='h3'>{user?.details}</Card.Text>
                </Card.Body>
               </Card>
              </Col>
             ))
          }
      </Row>
    </Container>
    </>
  );
}

Users Object

How can I add image card in data card?

here image and data object needs to be mapped in same card. and size of image and data array is different so cannot combine objects into single object

2 Answers

I think your users state structure is not clear with your question but if it has structured like you share, this solution should work. Otherwise I would recommend you to add how users state looks like to your question

import React, { useState, useEffect, useCallback } from 'react';
import {Row, Col, Card} from 'react-bootstrap';
import axios from 'axios';
import {Container} from 'react-bootstrap';

export const App = () => {

  const [ users, getUsers ] = useState([]);

  const getUsersData = useCallback(async () => {
    const [image, userData] = await Promise.all([
      axios.get('https://...'),
      axios.get('https://...')
    ]);
    getUsers({ image: image.data, data: userData.data});
  },[])

  useEffect(() => {
    getUsersData()
  },[getUsersData]);

  return (
    <>
    <Container>
      <h1>User Details</h1>
      <Row> 
          {
            users?.map(user => (
             <Col sm={12} md={6} lg={4} xl={3}>
              <Card className='my-3 p-3 rounded'>
              <Card.Img src={user?.image?.image} variant='top' />
                <Card.Body>
                  <Card.Title>
                    <strong>{user?.data?.name}</strong>
                  </Card.Title>
                  <Card.Text as='h3'>{user?.data?.details}</Card.Text>
                </Card.Body>
               </Card>
              </Col>
             ))
          }
      </Row>
    </Container>
    </>
  );
}

You have initialized the state with an empty array. It means that the state can take only the array value. That's ok. But at the time of setting it, you are setting an object to the state. You must either initialize the state with a null value or update the state with the previous state value. I'll go with initializing the state with a null value.

const [ users, getUsers ] = useState(null);

Your return React element would be like this

<Container>
  <h1>User Details</h1>
  <Row>
     {users && users.data.map((user) => ( //update
      <Col sm={12} md={6} lg={4} xl={3}>
        <Card className="my-3 p-3 rounded">
          <Card.Body>
            <Card.Title>
              <strong>{user.name}</strong>
            </Card.Title>
            <Card.Text as="h3">{user.details}</Card.Text>
          </Card.Body>
        </Card>
      </Col>
    ))}
  </Row>
</Container>
Related