jQuery-嵌套ajax调用并使用每个调用中的数据-Wikipedia API

时间:2018-08-13 21:49:43

标签: javascript jquery json asynchronous wikipedia-api

我在使用jQuery将ajax调用嵌套到Wikipedia api时遇到问题。 HTML很简单,只是一个输入表单和一个按钮:

$data2

该搜索按钮具有一个事件侦听器,该事件侦听器会触发从维基百科API抓取数据的函数:

<input id='search-input' type="text" class="form-control">
 <button id="search-button" type="button" class="btn btn-primary">Search</button>
<div id ='outputDiv'></div>

但是,... searchBtn.addEventListener('click', searchwiki); ... function searchwiki(){ let searchTermObjects =[] let term = inputfield.value; let titleUrl = search_term(term); createWikiObject(titleUrl).then(function(){ searchTermObjects.forEach(function(elem){ addExtrctToObj(elem) }) }).then(function(data){ append_result(searchTermObjects) }) } function createWikiObject(titleUrl){ return $.ajax({ type: "GET", url: titleUrl, dataType : 'jsonp', async: true, error : function(ermsg){ console.log('error in searching',ermsg) },}).then(function(data){ for(let i = 0; i < data[1].length; i ++){ searchTermObjects.push({ 'title': data[1][i].replace(/\s+/g, '_'), 'description': data[2][i], 'url': data[3][i], }) }; // this for loop should push each result as an object to an array named searchtTermObjects, and i am planning to use this array in the next ajax call to add another property named extract to each object in array } ); } function addExtrctToObj(obj){ console.log(obj) return $.ajax({ type: "GET", url: get_text(obj['title']), dataType : 'jsonp', async: true, error : function(ermsg){ console.log('error getting text',ermsg) } }).then(function (data){ let pageID = Object.keys(data.query.pages); if(data.query.pages[pageID].hasOwnProperty('extract')){ obj['extract'] = data.query.pages[pageID].extract; } // this function adds the extracted text for each article , // the searchTermObjects now looks something like: / [{'title':...,'url':...,'description':...,'extract':..},{...}] }) }; function append_result(termsObjectsArray){ // this function should loop through the searchtermobjects and append leading text for each object in the array to the Output div under the button for (let i = 0; i < termsObjectsArray.length; i++){ let newDiv = document.createElement('div'); 目前仅返回三个键,而没有看到提取键'

Object.keys(termsObjectsArray[i])

这里是我出错的地方-newDiv的inerHtml值未定义

        console.log(Object.keys(termsObjectsArray[i]))
        newDiv.classList.add('wiki-result');
        newDiv.innerHTML = termsObjectsArray[i]["extract"];

在我 outputDiv.appendChild(newDiv); } } // the api calls are formed with these functions: let base_url = "https://en.wikipedia.org/w/api.php"; function search_term(term) { let request_url = base_url + "?action=opensearch&search=" + term + "&format=json&callback=?"; return request_url; } function get_text(term){ let request_url = base_url + "?action=query&prop=extracts&exintro=&format=json&titles=" + term; // explaintex= returns plaintext, if ommited returns html return request_url; } 之后,我得到了我所需要的,带有对象的数组,这些对象具有正确名称的所有4个属性,但是我不明白为什么console.log(searchTermObjects)函数看不到'提取物键。

在控制台中记录的对象旁边是“ i”符号,上面写着“下面的值现在才被求值”,在那里,我有了我想要的-每个搜索结果都是带有标题,URL,描述,并提取密钥。

将此代码复制到您的IDE中,以查看是否可以帮助我找到解决方案。

1 个答案:

答案 0 :(得分:0)

我相信您遇到的问题是,您正在尝试返回Deferred对象,并且由于推迟而没有任何返回。

return $.ajax({
    type: "GET",
    url:  get_text(obj['title']),
    dataType : 'jsonp',
    async: true,
    error : function(ermsg){
        console.log('error getting text',ermsg)
    }
})

async的值为true,因此代码在请求完成之前继续运行,并且您将获得空值。

尝试设置async: false,看看是否有更好的响应。正如安德鲁·洛尔(Andrew Lohr)在评论中指出的那样,这不是解决问题的好方法,它只会告诉您是否是问题所在。

如果是,那么我建议不要将请求分解为多个功能。您应该只使用延迟方法将AJAX调用链接起来。它的结构如下:

$.ajax({ ... }).then(function(data){
    // ... do something with the data ...
    // Make your followup request.
    $.ajax({ ... }).then(function(data) {
        // ... finalize the response ...
    });
});

还可以考虑在ajax调用中使用context选项来传递回调方法,该方法一旦链完成就可以触发。