Как вытащить опоры в компонент? - PullRequest
0 голосов
/ 21 января 2020

Я создаю простое приложение, которое создает «карточки» путем отображения рабочих заданий (первый API). Через этот API есть workersId, необходимый для извлечения рабочих данных из второго API.

Это мое приложение. js


  class App extends React.Component{
  constructor(props){
      super(props);

      this.state = {
          orders:[],
          workersData: []
      };
  }

  componentDidMount(){
    fetch('https://www.hatchways.io/api/assessment/work_orders')
      .then(res=> res.json())
      .then(({ orders }) => {
        this.setState({
          orders: orders
        }, () => {
          this.state.orders.map(order => {
            fetch(`https://www.hatchways.io/api/assessment/workers/${order.workerId}`)
              .then(response=> response.json())
              .then(workersData => {
                this.setState({
                  workersData: workersData
                })
              })
          })
        });
      })
      .catch(err => {
        console.log(err)
      });
  }

  render(){
    const { orders, workersData } = this.state;
      return(
       <CardList orders={ orders } workersData={ workersData } />
      );
  }
}

export default App;

Я несу 'orders' и 'workerData' добавляются в мой компонент 'CardList', так что я могу попытаться отобразить каждый фрагмент данных и поместить его в отдельные карты.

const CardList = props => {
    console.log(props) //<-- this contains the 'orders' and 'workersData'

    const workOrderJsx = props.orders.map( order => (
        <Col key={ order.id } md={6} >
            <Card order={order} />
        </Col>
    ))

    return (
        <ListGroup>
            <MDBContainer fluid={true} >
                <MDBRow>
                    {workOrderJsx}
                </MDBRow>
            </MDBContainer>
        </ListGroup>
    );
}

export default CardList;

Все это прекрасно работает, но проблема Я сталкиваюсь с тем, что, просматривая заказы, я получаю только карты с заказами на них. Как я также могу одновременно получать информацию о работниках, которая соответствует id в orders объекте?

const Card = props => {
    console.log(props) //<-- only order data

    let date = new Date( props.order.deadline * 1000 );
    const newTime = date.toLocaleString()

    return (
        <div className="card-container">
            <h1 className="order-name">{props.order.name}</h1>
            <p className="ml-5 mr-4">{props.order.description}</p>
            <div>
                <h5> Worker: {props.order.workerId} </h5> //<-- this is where I need the workers info to go
            </div>
            <p className="date">{newTime}</p>
        </div>
    )
}

export default Card;

Ответы [ 3 ]

0 голосов
/ 22 января 2020

Что вы могли бы сделать, так это найти работника, который соответствует порядку в вашей функции карты.

Я полагаю, что вашему коду нужно будет что-то посмотреть в этом направлении.

const CardList = props => {
  console.log(props) //<-- this contains the 'orders' and 'workersData'

  const findWorker = (id) => props.workersData.find(worker => worker.id === id);

  const workOrderJsx = props.orders.map(order => {
    const worker = findWorker(order.id);
    return (
      <Col key={order.id} md={6} >
        <Card order={order} worker={worker}/>
      </Col>
    )
  })

  return (
    <ListGroup>
      <MDBContainer fluid={true} >
        <MDBRow>
          {workOrderJsx}
        </MDBRow>
      </MDBContainer>
    </ListGroup>
  );
}

export default CardList;
0 голосов
/ 22 января 2020

Прежде всего ваши множественные запросы на получение workerData для каждого заказа всегда переопределяются новым ответом, что означает, что ваш workerData будет содержать данные только для последнего заказа. Таким образом, вы должны использовать Object там, где каждый workerData будет помещен против каждого заказа. Структура должна выглядеть следующим образом: { [orderWorkerId]: fetchedWorkerData}

Тогда в методе карты вы можете получить указанные workerData на основе order.workerId и передать их компоненту, где вы получите правильные данные для каждого заказа. Надеюсь, это поможет:)

Дополнительная информация:

В своем вызове API для извлечения workerData сделайте это следующим образом:

this.setState({workersData: { ...this.state.workersData, [order.workerId]: workersData }

Таким образом, вы можете сохранить все ваши workerData против order.workerId. После этого в вашем методе карт для заказов сделайте это следующим образом:

<Card order={order} workerData={props.workersData[order.workerId]} />

Таким образом вы получите связанные с данными workerData с вашим заказом в компоненте Card и можете использовать его как ты хочешь. :)

0 голосов
/ 22 января 2020

Похоже, вы перезаписываете данные работников в вашей карте при вызове выборки. Вы должны скопировать существующий workerData из предыдущих l oop итераций и объединить их с текущей итерацией workerData.

componentDidMount(){
    fetch('https://www.hatchways.io/api/assessment/work_orders')
      .then(res=> res.json())
      .then(({ orders }) => {
        this.setState({
          orders: orders
        }, () => {
          this.state.orders.map(order => {
            fetch(`https://www.hatchways.io/api/assessment/workers/${order.workerId}`)
              .then(response=> response.json())
              .then(workersData => {
                this.setState({
                  workersData: [...this.state.workersData, workersData]
                })
              })
          })
        });
      })
      .catch(err => {
        console.log(err)
      });
  }

Затем вы можете передать объект данных работников в компонент карты вместе с заказами. В компоненте карты вы можете искать информацию о работнике по идентификатору заказа в объекте workerData.

...