How to loop for asynchronous acquisition? The loop variable cannot be determined?

requirements: use Github V3 version of API to get the number of items of a user"s star.

and user"s api does not provide the number of star separately, but provides such an interface
" starred_url ":" https://api.github.com/users/tj/starred{/owner}{/repo}"

"

check . Github api uses paging technology. If you use the above default interface, you can only return up to 30 items. Therefore, you need to use parameters to obtain: https://api.github.com/users/tj/starred?page=1&per_page=100 Magi perturbed page can be up to 100.

that means I need to GET multiple interfaces like this until the acquired interface returns [] :
axios.get (`/ users/$ {app.userName} / starred?page=$ {iPP} & per_page= 100`)

The

loop is executed synchronously, and the GET request is obtained asynchronously. However, my loop variables are related to the data obtained asynchronously! So how do you write the loop code?
here is the code I wrote with recursion, but very slowly. This is demo , you can type tj to try, very slow.

let starredLists = []
                    
!function getStarred(index){
    axios.get(`/users/${app.userName}/starred?page=${indexPP}&per_page=100`)
        .then(function(response){
            starredLists.push(...response.data)
            console.log(starredLists.length + "   " + index)
            if(response.data.length == 100)
                getStarred(index);
            if(response.data.length != 100)
                app.stars = starredLists.length;
        })
}(1)

do you have to loop? use recursive requests


you can use Promise.all

//get user's starred repos   
//get user's starred repos   
let starredLists = [],
    rq = [];
    
axios.defaults.baseURL = 'https://api.github.com';

for(let i = 1;i < 10; iPP){
    rq.push(axios.get(`/users/tj/starred?page=${i}&per_page=100`)
        .then(function (response) {
            if(response.data.length == 0)
                break;
            starredLists.push(...response.data)
            console.log('starredLists.length: '+ starredLists.length)
        }));
}

Promise.all(rq).then(() => {
    // 
    app.stars = starredLists.length 
}).finally(() => {
    //   then  catch 
    // 
    if(!app.stars) {
        app.stars = starredLists.length 
    }   
}); 

uses recursion to solve the problem that loop variables cannot be determined;
also makes batch requests with Promise.all () for performance. It takes about 10 seconds to get 10 interfaces in 3 groups (take tj's star as an example)

//get user's starred repos   
let starredLists = [];
let promiseTen = [], 
    promiseOne;

!function getStarred(index) {
    //for--
    for (let i = 0; i < 10; iPP) {
        promiseOne = axios.get(`/users/${app.userName}/starred?page=${indexPP}&per_page=100`)
            .then(function (response) {
                starredLists.push(...response.data)
            })
        promiseTen.push(promiseOne)
    }
    Promise.all(promiseTen).then(() => {
        if(starredLists.length % 100 == 0)      //
            getStarred(index)                       
        else 
            app.stars = starredLists.length        
    })
}(1)
MySQL Query : SELECT * FROM `codeshelper`.`v9_news` WHERE status=99 AND catid='6' ORDER BY rand() LIMIT 5
MySQL Error : Disk full (/tmp/#sql-temptable-64f5-1c11f66-32dc6.MAI); waiting for someone to free some space... (errno: 28 "No space left on device")
MySQL Errno : 1021
Message : Disk full (/tmp/#sql-temptable-64f5-1c11f66-32dc6.MAI); waiting for someone to free some space... (errno: 28 "No space left on device")
Need Help?