如何防止在执行另一个函数之前触发函数

How can i prevent a function to be fired before the execution of an other

提问人:Fefe 提问时间:10/10/2023 最后编辑:Fefe 更新时间:10/10/2023 访问量:40

问:

我使用一个函数从 XMLhttpRequest 中提取数据,此数据被推送到主异步函数之外的变量数组,Everthing 适用于这部分,但是当我调用此函数时,即使我之前放置了 await,也会在函数完成运行之前触发之后的事件,从而产生一个空数组,因为触发的事件是调用路由函数的重定向 (ctx.response.redirect),该检索数组变量...换句话说,我使用外部变量数组将数据从一个路由函数传递到另一个路由函数,但是应该获取变量数组的路由函数在数组填充之前被触发。我怎样才能使这段代码在运行下面的事件之前等待函数完成

代码如下:

Route 函数,我从 XMLhttprequest 中提取数据并将其推送到外部变量数组

const validateSHipping = async(ctx:any)=>{
        const body = await ctx.request.body({type: 'form-data'});
        const product =  await body.value.read();
        if(!ctx.request.hasBody){
            ctx.response.status = 400;
             ctx.response.body ={
                 success: false,
                 msg: 'No data'}
          
        }else{
            try{
    
    
                
               let shipFunction = async(inData:any,inMethod:string,inUrl:string,inArray:boolean,serviceName:string)=>{
    
                
                    var xhr = new XMLHttpRequest();
                    xhr.withCredentials = true;
                    
                    xhr.addEventListener("readystatechange", function () {
                       
                        if (this.readyState === 4) {
                            
                            var response = xhr.responseText;
                            var jsonResponse = JSON.parse(response);
                            
                            if(inArray == true){  
                         
                            }else if(inArray == false){
                                
                               if(inUrl === `https://api.laposte.fr/controladresse/v2/adresses?q=${okapiAdress}`){
                                    console.log('-- okapiAdress ---');
                                    const jsonResponseLength = jsonResponse.length;
                                    for(let i = 0; i < jsonResponseLength; i++){
                                        adressesFound.push(jsonResponse[i].adresse);
                                    }  
                                   
                                }
                                
                            }
      
                                
                        }
                    
                    });

                    xhr.open(inMethod,inUrl);
    
                    if(serviceName ==='Okapi'){
                        xhr.setRequestHeader("Content-Type", "application/json");
                        xhr.setRequestHeader("X-Okapi-Key", "ZLd3/5PZpfN4bwSQ8qiwVK25ZqC61XHCtZmuV33dpWnTO0/uOplAL+PpNTjYeMi0");  
                    }

                    if(inMethod === "GET"){
                        xhr.send();
                    }else if(inMethod === "POST"){
                        xhr.send(inData);
                    }
                    
                
                }
    
                
               await shipFunction(null,"GET",`https://api.laposte.fr/controladresse/v2/adresses?q=${okapiAdress}`,false,"Okapi");
                    
                    
               ctx.cookies.set('adressValidation','true');
               ctx.response.redirect('/OBV/panier'); // Redirection 
    
  
            }catch(err){
                ctx.response.status = 200;
                ctx.response.body = {
                    success: false,
                    msg: err.toString()
                };
            }
        }
    }
    

这是我检索这个数组的路由函数,上面有外部变量:


let adressesFound:any = [];

const getPanier = async(ctx:any) => {

        try{
    
            
            const adressValidation = await ctx.cookies.get('adressValidation');
            
            
                console.log('adressesFound : ' + adressesFound); // Retrieved variable array

                if(adressValidation === 'true'){ 
                    console.log(' -- WrittenAdress = true ');
                    console.log(' -- adressValidationCookie : ' + adressValidation);
                    ctx.render('./OBV/panier/Panier.ejs',{labels: labelProduitsArray,quantity: quantityProduitsArray,prices: prixProduitsArray,Voyant: true, UserIdPanier: userId, deletePanier: false, adressesFound: adressesFound, writtenAdress: 'true'});
                   }else{
                    console.log(' -- WrittenAdress = false ');
                    console.log(' -- adressValidationCookie : ' + adressValidation);
                    ctx.render('./OBV/panier/Panier.ejs',{labels: labelProduitsArray,quantity: quantityProduitsArray,prices: prixProduitsArray,Voyant: true, UserIdPanier: userId, deletePanier: false, adressesFound: null, writtenAdress: 'false'}); 
                   }
           
                   
            
            ctx.cookies.set('activePage','panier');
            ctx.cookies.delete('adressValidation');
        }catch(err){
    
            ctx.response.status = 200;
            ctx.response.body = {
                    success: false,
                    msg: err.toString()
                }
        }
        
    
    }

最后,这是我得到的日志,我们可以看到重定向是在 shipEngine 函数完成运行之前触发的

第一个日志结果

当我重新加载页面或使用相同的 URL(相同的效果)执行 GET 请求时,路由函数 getPanier 再次运行,现在我从数组变量中获取一些数据,证明在变量数组有时间填充之前触发重定向(我想):

手动重新加载页面后的第二个日志结果

我怎样才能避免这种行为,我自然而然地想到了承诺,但我该如何实现它?为什么 await 不在这里工作?

async-await promise xmlhttprequest deno oak

评论

0赞 Bergi 10/10/2023
在请求返回之前,您不会等待请求(履行返回的承诺)。你到底为什么要使用 XHR 而不是现代 ,它与你可以轻松实现的承诺一起工作?shipFunctionfetchawait
0赞 Fefe 10/10/2023
那么我必须更改什么才能使用此工作流完成请求? ;对于 XHR 使用,我不知道这很棘手,一开始我发现它更方便,但我肯定会更改为 fetch
1赞 Fefe 10/11/2023
好的,所以使用 fetch 方法在 3-4 行中恢复了我现在的所有代码,并解决了我遇到的异步问题,我现在可以轻松检索我想要的数据,我不知道为什么我错过了这个方法,这很大!谢谢Bergi

答: 暂无答案