Как позвонить в несколько запросов отдыха с Axios - PullRequest
0 голосов
/ 17 мая 2018

Я новичок в React JS. Я прочитал несколько примеров того, как создать клиентский отдых в Reactjs.
мои вопросы - я получаю все курсы и затем хочу для каждого курса вызвать другую службу HTTP. Мой код ниже.

export default class Courses extends Component{

    constructor(props) {
        super(props);
        this.state = {courses: []};
    }

    componentDidMount() {
        axios.get('http://localhost:8065/api/course/all')
        .then(response => {
            const courseList = response.data.map(c => {
                return {
                  id: c.id,
                  name: c.name,
                  previewBase64:c.previewBase64,
                  authors:
                     axios.get('http://localhost:8065/api/course/getAuthorsByCourseId/'+c.id+"/")
                    .then(res => {
                        const profiles = res.data.map(p => {
                            return {
                              name: p.name                       
                            };
                          })
                    })
                };
              })
              console.log(courseList);
              const newState = Object.assign({}, this.state, {
                courses: courseList
              });
              // store the new state object in the component's state
              this.setState(newState);
        }); 
    };
    render(){
        return(
            <CourseList courses={this.state.courses}/>
        )
    }
}

my CourseList.jsx:

const courseList = (props) => (
    <Grid>
    <Row>
        {
            props.courses.map((course, i)=>{
                return  (
                <Col key ={i} lg={2} sm={8} xs={12} md={6}>
                    <div className="course-block">
                         <p>{course.name}</p>
                         <p>AUTHOR NAME WILL BE HERE </p>
                    </div>

                </Col>)
                }) 
            }                             
    </Row>
</Grid>
);

export default courseList;

Этот код работает, но я получаю "обещание" для таких авторов. {id: 7, name: "HTML", previewBase64: "", авторы: Promise}

Ответы [ 3 ]

0 голосов
/ 17 мая 2018

Вы можете попробовать это ниже, используйте это как ссылку https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/async_function

async componentWillMount() {
        let data = await axios.get('http://localhost:8065/api/course/all').then(response => {
            return response
        })
        const courseList = data.map(c => {
            return {
                id: c.id,
                name: c.name,
                previewBase64: c.previewBase64,
                authors: await axios.get('http://localhost:8065/api/course/getAuthorsByCourseId/' + c.id + "/")
                    .then(res => {
                        const profiles = res.data.map(p => {
                            return {
                                name: p.name
                            };
                        })
                    })
            };
        })
        console.log(courseList);
        const newState = Object.assign({}, this.state, {
            courses: courseList
        });
        // store the new state object in the component's state
        this.setState(newState);
    }
0 голосов
/ 17 мая 2018

Вы можете попробовать рефакторинг таким образом, в любом случае лучше иметь только один API, который возвращает как курсы, так и авторов

componentDidMount() {
    axios.get('http://localhost:8065/api/course/all')
    .then(response => {

      const promises = response.data.map(c => {
        axios.get('http://localhost:8065/api/course/getAuthorsByCourseId/'+c.id+"/")
        .then(res => { //for each course get the authors
            return res.data.map(p => {
                return {
                  name: p.name                       
                };
              });
        })
        .then(profiles => ({ id: c.id, profiles })); //keep a reference with the course
      });

      axios.all(promises, (allProfiles) => { //wait for all getAuthorsByCourseId are resolved
        const profileMap = allProfiles.reduce((map, profiles)=> {
          return map[profiles.id] = profiles.profiles;
        }, {}); // from array to map
        const courseList = response.data.map(c => {
          return {
            id: c.id,
            name: c.name,
            previewBase64:c.previewBase64,
            authors: profileMap[c.id],
          };
        }); //build the courseList with all data resolved
        const newState = Object.assign({}, this.state, {
          courses: courseList
        });
        // store the new state object in the component's state
        this.setState(newState);       
      });
    }); 
};
0 голосов
/ 17 мая 2018

Вам нужно Promise.all или axios.all

const baseURL = 'http://localhost:8065/api/course/getAuthorsByCourseId/';

const p = Promise.all(response.data.map(({ id }) => axios.get(`${baseURL}${id}`)));

p.then(result => {
  console.log(result);
}).catch(e => {
  throw e;
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...