首页 > 解决方案 > 如何使用axios和react js访问函数外的数据

问题描述

当从 h1 标签调用 retriveStudentPhoto() 函数时。我无法获得价值回报。我该如何解决这个问题。提前致谢 。

                               {data.map((val, index) => (
                                    <tr>
                                        <td style={{ outline: 'none' }} data-heading="Photo">
                                          <h1{ retriveStudentPhoto(val.email) }</h1> /*call 
                                                                                             this function */ 
                                        </td>
                               ))}


   function retriveStudentPhoto (email)  {
          var photo = ""
          axios.get(`/user-info/${email}`)
          .then((result)=>{
          photo = result.data[0].profile_photo; 
        }).catch((error)=>error)
        return photo ;
     }

由于该函数在 map 内部,因此会多次调用,每次都会返回值。我使用了 useState 钩子,但没有根据需要得到结果。

请帮助我更多。提前致谢。

完整代码:

import React, { useEffect, useState } from 'react';
import { Button, Alert } from 'react-bootstrap';
import $ from 'jquery';
import axios from '../../config/axios';
import '../Attendance_Table/css/App.scss';
import { useAuth } from "../../contexts/AuthContext";
import { Link, useHistory } from 'react-router-dom';

function PeopleList({ match }) {
    const course_code = match.params.course_code;
    const { currentUser } = useAuth();
    const history = useHistory();
    const [msg, setMsg] = useState("");
    const [course_name, setcourse_name] = useState("");


    var breakOn = 'medium'
    let tableClass = 'table-container__table';
    if (breakOn === 'small') {
        tableClass += ' table-container__table--break-sm';
    } else if (breakOn === 'medium') {
        tableClass += ' table-container__table--break-md';
    } else if (breakOn === 'large') {
        tableClass += ' table-container__table--break-lg';
    }
    const headingColumns = ['Photo', 'Student ID', 'Name', 'Email']
    const headingColumns2 = ['Photo', 'Name', 'Email']
    const [data, setData] = useState([]);
    const [studentsPhoto, setStudentsPhoto] = useState([]);
    const [techInfo, setTechInfo] = useState([]);



    useEffect(() => {
        axios.get(`/course/info/${course_code}`).then((result) => {
            setcourse_name(result.data[0].course_name)
        })

        SearchHandle();


    }, [])
    let SearchHandle = () => {

        axios.get(`people/${course_code}`).then((result) => {
            setData(result.data)

            // teacher info retrieve 
            axios.get(`user-info/${result.data[0].tecEmail}`)
                .then((res) => {

                    setTechInfo(res.data[0]);

                })
            //close teacher retrieve

            let student_photo = [];
            let promises = [];
            for (let i = 0; i < result.data.length; i++) {
                promises.push(

                    axios.get(`/user-info/${result.data[i].email}`)
                        .then((res) => {
                            student_photo.push(res?.data[0]?.profile_photo)
                        })

                )

            }
            Promise.all(promises).then(() => {
                setStudentsPhoto(student_photo);
            })
        }).catch((err) => console.log(err))


    }




    function retriveStudentPhoto(email) {
        var photo = "";
        axios.get(`/user-info/${email}`)
            .then((result) => {
                var photo = result.data[0].profile_photo;

            }).catch((error) => error)

        return photo;
    }

    return (
        <div>
            {/* {msg ? ( */}
            <div>



                <div className="table-container" style={{ backgroundColor: 'white' }}>
                    <div className="table-container__title">
                        <h5>People -- {course_name}({course_code})</h5>
                    </div>
                    <h5 style={{ padding: '10px', fontFamily: 'roboto' }}>Teacher</h5>
                    <table style={{ outline: 'none', border: 'none' }} className={tableClass}>
                        <thead>
                            <tr>
                                {headingColumns2.map((col, index) => (
                                    <th data-heading={index} key={index}>{col}</th>

                                ))}

                            </tr>
                        </thead>
                        <tbody>



                            <tr>
                                <td style={{ outline: 'none' }} data-heading="Photo">
                                    {techInfo.profile_photo ? (
                                        <img style={{ borderRadius: '150px', height: '40px', width: '40px' }}
                                            src={techInfo.profile_photo} />
                                    ) : (
                                        <img style={{ borderRadius: '150px', height: '40px', width: '40px' }}
                                            src="https://lh3.googleusercontent.com/-XdUIqdMkCWA/AAAAAAAAAAI/AAAAAAAAAAA/4252rscbv5M/s75-c-fbw=1/photo.jpg" />

                                    )}

                                </td>

                                <td data-heading="Student Name">{techInfo.name} </td>
                                <td data-heading="Student Email"><span style={{ fontSize: '11.5px' }}>{techInfo.email}</span> </td>

                            </tr>

                        </tbody>
                    </table><br />




                    <br />
                    {data.length ? (
                        <table style={{ outline: 'none', border: 'none' }} className={tableClass}>
                            <thead>
                                <tr>
                                    {headingColumns.map((col, index) => (
                                        <th data-heading={index} key={index}>{col}</th>

                                    ))}

                                </tr>
                            </thead>
                            <tbody>

                                {data.map((val, index) => (
                                    <tr>
                                        <td style={{ outline: 'none' }} data-heading="Photo">

                                            <h1>{retriveStudentPhoto(val.email)}</h1>

                                        </td>
                                        <td style={{ outline: 'none' }} data-heading="Student ID">{val.student_id}</td>
                                        <td data-heading="Student Name">{val.student_name} </td>
                                        <td data-heading="Student Email"><span style={{ fontSize: '11.5px' }}>{val.email}</span> </td>

                                    </tr>
                                ))}
                            </tbody>
                        </table>
                    ) : (
                        <div>
                            <Alert className="md-4 w-100"  variant="danger">
                                No Student add to this course yet
                            </Alert>
                        </div>
                    )}
                    <br />
                    <div style={{ textAlign: 'center', paddingBottom: '5px' }}>
                        <Link to={`/attendance-sheet/${course_code}`}><span>Back to {course_code}</span></Link>
                    </div>
                </div>


            </div>
            {/* ) : ""} */}
        </div>

    );
}

export default PeopleList;

标签: reactjsaxios

解决方案


Render 是一个纯粹的同步函数。如果您需要进行异步调用,请在生命周期中执行此操作,在这种情况下,使用useEffect挂钩并将结果存储在要呈现的状态中。

迭代result.data数组并发出 GET 请求,当请求解决时发出功能状态更新以创建新data数组,使用迭代元素的索引注入新photo属性。

const SearchHandle = () => {
  axios.get(`people/${course_code}`)
    .then((result) => {
      setData(result.data);

      result.data.forEach(async (item, index) => {
        try {
          const result = await axios.get(`/user-info/${item.email}`);
          const photo = result.data[0].profile_photo;
          setData(data => data.map(
            (el, i) => i === index
              ? { ...el, photo }
              : el)
          )
        } catch(error) {
          // log error, etc...
        }
      });

      ...

}

在渲染中访问photo您在上面添加的新属性。

{data.map((val, index) => (
  <tr key={val.student_name}>
    <td style={{ outline: 'none' }} data-heading="Photo">
      <h1>{val.photo}</h1>
    </td>
    <td style={{ outline: 'none' }} data-heading="Student ID">{val.student_id}</td>
      <td data-heading="Student Name">{val.student_name} </td>
      <td data-heading="Student Email">
        <span style={{ fontSize: '11.5px' }}>{val.email}</span>
      </td>
    </tr>
  )
)}

推荐阅读