Вопрос

This script is part of a chrome extension that will loop through a table, look for a match, and send a message back to a background script. Here is the script (content script):

function resolveMulti(city){
  counter = 1;
  results = "";
  resultsArray = $("iFrame").contents().find("#table tr[id*='row'] td:nth-child(13)");
  resultsArray.each(function(index){
    if($(this).html().toLowerCase() == city.toLowerCase()){
      results = "Found";
    }
    else if(counter == resultsArray.length){
      results = "No City Match Found";
    }
    counter++;
  });
  return results;
}

The function is returning prior to the $.each loop finishing. Since 'results' isn't defined until the $.each loop is evaluated, the browser raises an error that 'results' hasn't been defined. How can I return the correct results from this function?

Это было полезно?

Решение

First your questions, then some notes about several issues in that code.

The function is returning prior to the $.each loop finishing.

No, it isn't. It may be raising an exception, which is similar but different.

Since 'results' isn't defined until the $.each loop is evaluated, the browser raises an error that 'results' hasn't been defined. How can I return the correct results from this function?

By declaring the variable. You need a var results in the function:

function resolveMulti(city){
  var results; // <=========== Here
  counter = 1;
  resultsArray = $("iFrame").contents().find("#table tr[id*='row'] td:nth-child(13)");
  resultsArray.each(function(index){
    if($(this).html().toLowerCase() == city.toLowerCase()){
      results = "Found";
    }
    else if(counter == resultsArray.length){
      results = "No City Match Found";
    }
    counter++;
  });
  return results;
}

Without one, in loose mode you're falling prey to The Horror of Implicit Globals (in strict mode, it would be an error). But the Horror of Implicit Globals only works for setting; if it happens that there are no matches for that jQuery selector, you'll never set anything, and so never create the global, and your return will try to read the value of an undefined symbol, which will cause a ReferenceError even in loose mode.

It's hard to tell from the snippet shown, but you may well have other undeclared variables in there (counter and resultsArray) that you want to declare with var.

But there's another issue: Your results variable will have the result from the last iteration of the each loop, overwriting any value from a previous iteration. And if there are no matching elements at all, it will never have a value. I suspect you wanted something like this:

function resolveMulti(city){
  var results = "No City Match Found";
  var resultsArray = $("iFrame").contents().find("#table tr[id*='row'] td:nth-child(13)");
  resultsArray.each(function(index){
    if($(this).html().toLowerCase() == city.toLowerCase()){
      results = "Found";
      return false; // <== Stops the `each` loop
    }
  });
  return results;
}
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top