2017-02-21 8 views
0

В настоящее время я работаю над скриптом, который проверяет все ссылки на страницу и выделяет любые неработающие ссылки. Синхронно это не было главной задачей, но я только начал работать с Asynch, поэтому любая помощь с моим кодом была бы высоко оценена.Выполнение async forEach() '

var size = 0; 
var itemsProcessed = 0; 
    console.log("Size: " + size); 

function linkCheck() { 
var body = document.querySelectorAll("*"); 
var checker = Array.from($(body).filter("a")); 
size = (Object.keys(checker).length); 

    console.log("Size: " + size); 
var list; 

checker.forEach(function (anchor) { 
    var link = $(anchor).attr("href"); 
    itemsProcessed++; 
    console.log("Items: " + itemsProcessed); 
    if (itemsProcessed == size) { 
     colorUp(list); 
    } 
    var req = new XMLHttpRequest(); 
    req.open('HEAD', $(checker).attr("href"), true); 
    itemsProcessed++; 
    try { 
     req.send(null); 
    } catch (e) { 
     console.log("ERROR"); 
     return true; 
    } 
    console.log(req.status); 
    var data = (req.status !== 200); 
    if (data) { 
     //console.log("Added to List") 
      list += data; 
    } 
    console.log(link, data); 
}); 
} 

function colorUp(list) { 
console.log("DONE"); 
$(list).css({ 
    "border": "3px solid #ffb700", 
    "background": "repeating-linear-gradient(135deg, #FFE0B2, #FFE0B2 5px, #ffffff 5px, #ffffff 10px)" 
}); 
} 


linkCheck(); 

В настоящее время у меня возникают проблемы ожидания для Foreach, чтобы закончить, но если у вас есть какие-либо предложения, или все, что я могу сделать, чтобы сделать эту проблему более ясной, не стесняйтесь оставить пост!

Спасибо ребята

+0

Используйте 'document.querySelectorAll ('a'); ' или '$ ('a')' для получения всех якорей. Также решите, собираетесь ли вы использовать jQuery или нет. Если да, используйте его для всего, и вы будете намного счастливее. Также обратите внимание, что ajax ('XMLHttpRequuest') является асинхронным, поэтому' req.status' не обязательно будет правильным, когда вы его проверяете. –

+0

Просто потому, что я незнаком с этим, как я могу заставить его ждать, пока req.status не будет загружен, прежде чем я его проверю? Кроме того, как я должен сделать forEach частью асинхронным до вызова colorUp()? Благодарим за отзыв Майка. – Gwinert

+1

Вы хотите провести некоторое исследование обещаний и функцию под названием 'Promise.all'. Если вы используете метод jQuery '$ .ajax', это немного проще. В противном случае вам нужно будет выполнить работу XMLHttpRequest с обещаниями, что немаловажно. Возможно, вы, вероятно, найдете библиотеку, которая сделает это за вас. В основном, исследования, исследования, исследования :). –

ответ

0

Если вам нужно ждать несколько запросов, чтобы запустить один за другим, и сделать что-то после того, как они закончат, вы должны использовать метод reduce массива.

checker.reduce((promise, anchor) => { 
    return promise.then(() => $.ajax({type: "HEAD", url: $(anchor).attr("href")})); 
}, $.Deferred().resolve()).then(responseFromLastRequest => { 
    // Do your stuff here  
}); 

Или, если вы не заботитесь о порядке запросов, вы можете запустить их одновременно:

$.when.apply($, checker.map(anchor => { 
    return $.ajax({type: "HEAD", url: $(anchor).attr("href")}); 
})).then(() => { 
    // Do your stuff here 
}); 
0

Как уже было сказано, работа с XMLHttpRequest не весело. Вот полный пример использования jQuery. Несмотря на то, что исследование об обещаниях - это, конечно, хорошая идея, потому что сначала это может быть лучше для начинающего.

function linkCheck() { 
    var itemsProcessed = 0; 

    var $checker = $('a'); 
    var size = $checker.length; 
    console.log("Size: " + size); 

    var $list = $(); 

    $checker.each(function (anchor) { 
     var link = $(anchor).attr("href"); 
     itemsProcessed++; 
     $.ajax(link, { 
      type: 'HEAD', 
      success: function (response, status, xhr) { 
       var data = (req.status !== 200); 
       if (data) { 
        $list.pushStack([anchor]); 
       } 
       console.log(link, data); 
      }, 
      error: function (xhr, err) { 
       console.log("ERROR"); 
      }, 
      complete: function() { 
       console.log(req.status); 
       console.log("Items: " + itemsProcessed); 
       if (itemsProcessed == size) { 
        colorUp(); 
       } 
      } 
     }); 
    }); 
} 

function colorUp() { 

    console.log("DONE"); 
    $(list).css({ 
     "border": "3px solid #ffb700", 
     "background": "repeating-linear-gradient(135deg, #FFE0B2, #FFE0B2 5px, #ffffff 5px, #ffffff 10px)" 
    }); 
} 


linkCheck(); 

$.ajax(url, settings) функция принимает в качестве второго параметра объект, который направляет «ожидает ответа» процесс. Он определяет набор функций, которые должны выполняться асинхронно в более поздний момент времени после завершения функции linkCheck().

После ответа от сервера приходит, либо функция указана для success или одного указанного в собственность error выполняется, и в обоих случаях, после того, что функция complete запускается на выполнение.

Главное, что нужно помнить: если вы определите любую функцию send, исходная функция продолжит выполнение, не дожидаясь ответа. Если вы хотите что-то сделать, когда ответ появится, вы должны определить его в закрытии.

Смежные вопросы