首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >在回调函数完成后从父控制器方法返回数据

在回调函数完成后从父控制器方法返回数据
EN

Stack Overflow用户
提问于 2020-04-28 23:03:35
回答 1查看 63关注 0票数 0

我知道有人问过类似的问题,我试着理解它们,并将其应用到我自己的问题上,但我还没有能够使任何事情生效。

下面的代码是Adonis.js控制器中的一个函数。

它应该获取一个搜索项,并使用Google search API (serpApi)来搜索该搜索项,然后返回一个URL数组。

但是,目前我只能让它链接‘console.log’,但是每当调用'googleSearch‘函数时,我都想返回一个链接数组。

代码语言:javascript
复制
     async googleSearch(searchTerm) {

        let client = new GSR.GoogleSearchResults("[MyApiKey]")

            var parameter = {
                q: `${searchTerm}`,
                hl: "en",
                gl: "us",
                google_domain: "google.com",
            };

            const callback = function(data) {
                let links = []; 
                for (let i = 0; i < data.organic_results.length; i++) {                       
                    links.push(data.organic_results[i].link)            
                }
              console.log(links)                                  
           }            

        client.json(parameter, callback)

        }

当我从回调函数中进行控制台日志时,我可以看到我需要的数据,但是,我希望在调用父函数时返回这些数据,而不是将其记录到控制台。

我知道问题出在异步/同步区域的某个地方,我试着想办法重新组织回调并改变事情的顺序,尽我所知,但我似乎不能让它工作。

下面是我试图实现的一个例子,显然它不起作用,但它可能有助于澄清一些事情。

代码语言:javascript
复制
    async googleSearch(searchTerm) {

        let results= []
        let client = new GSR.GoogleSearchResults("[MyApiKey]")

            var parameter = {
                q: `${searchTerm}`,
                hl: "en",
                gl: "us",
                google_domain: "google.com",
            };

            const callback = await function(data) {
                let links = []; 
                for (let i = 0; i < data.organic_results.length; i++) {                       
                    links.push(data.organic_results[i].link)            
                }
              results.push(links)                                
           }            

        client.json(parameter, callback)
       return results 
        }
EN

回答 1

Stack Overflow用户

发布于 2020-04-29 00:32:41

变体1。

试着改变“等到”的心态,最好把它想成“当你做完了告诉我”。

假设您的方法googleSearch有第二个参数,该参数将是您的父(调用)组件提供的函数。此函数将仅在当前回调中调用,而不是在console.log(链接)中调用。这样,调用组件不会等到接收到带有链接的结果,而是在链接准备就绪时,父组件将接收到对所提供函数的异步调用,它们将作为参数传递。因此,让我们将该函数称为“processLinks”。

代码语言:javascript
复制
googleSearch(searchTerm, processLinks) {

    let client = new GSR.GoogleSearchResults("[MyApiKey]")

        var parameter = {
            q: `${searchTerm}`,
            hl: "en",
            gl: "us",
            google_domain: "google.com",
        };

        const callback = function(data) {
            let links = []; 
            for (let i = 0; i < data.organic_results.length; i++) {                       
                links.push(data.organic_results[i].link)            
            }
          processLinks(links)                                  
       }            

    client.json(parameter, callback)

    }

然后父组件将调用类似如下的内容:

代码语言:javascript
复制
onSearchTermChange(searchTerm){
  childComponent.googleSearch(searchTerm, this.processLinks);
},
processLinks(links){
  // Do whatever needed with the links.
}

变体2。

上层解决方案是一种实现自己的承诺机制(不是很酷,只是为了帮助你理解原则)。因此,第二个变体不是添加一个processLinks函数作为参数,而是让googleSearch返回一个promise。Promise的构造函数接受resolve和reject方法作为lambda参数(它们将再次用作回调,但它们不是在父组件中声明为函数,而是作为Promise的一部分。您可以使用resolve将数据传递回父组件,并在出现错误时使用reject,父组件不应再等待结果。让我们用一个例子来尝试一下:

代码语言:javascript
复制
    googleSearch(searchTerm) {
      return new Promise ((resolve, reject) => {
         let client = new GSR.GoogleSearchResults("[MyApiKey]")

           var parameter = {
              q: `${searchTerm}`,
              hl: "en",
              gl: "us",
              google_domain: "google.com",
          };

          const callback = function(data) {
              let links = []; 
              for (let i = 0; i < data.organic_results.length; i++) {                       
                  links.push(data.organic_results[i].link)            
              }
              resolve(links)                                  
          }            

         client.json(parameter, callback) // TODO If this fails call reject(errorDetails);
      }); // The promise returned.     
    }

然后,父服务将使用返回的promise来指定解析promise时要执行的操作。这是通过调用'then‘并传递两个lambda来完成的(一个用于成功场景,一个用于错误处理)

代码语言:javascript
复制
onSearchTermChange(searchTerm){
  childComponent.googleSearch(searchTerm, this.processLinks).then((links) => {
      // Here we are when the child component invoked 'resolve(links)'
    }, (error) => {
      // Well in upper example I dont use the error handled (and should). You can add it for example if your call to client.json fails for some reason.
    });
},

我有没有向你解释过你需要什么,或者这两个变体实际上让你更困惑了?:)请让我知道。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61483434

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档