Sua
break
instrução não está dentro do corpo de um loop. Em vez disso, está dentro do corpo de uma função, ou seja, o findOne
ligue de volta. Para ver isso mais claramente, pode ser útil usar temporariamente uma função nomeada como seu manipulador de retorno de chamada:var cb = function(err, data){
if (data.id){
uniqueNumber++;
}
else {
saveLandmark(newUnique);
break; // not inside a loop!
}
};
db.collection('landmarks').findOne({'id':uniqueIDer}, function(err, data){
//if ID exists already
if (data.id){
var uniqueNumber = 1;
while (1) {
var uniqueNum_string = uniqueNumber.toString();
var newUnique = data.id + uniqueNum_string;
db.collection('landmarks').findOne({'id':newUnique}, cb);
}
}
else {
saveLandmark(uniqueIDer);
}
});
Está bem claro agora que o
break
no corpo da função de retorno de chamada não está dentro de um loop! Eu também fiz as coisas quebrarem de outras maneiras porque o uniqueNumber
e newUnique
os valores não estão mais no escopo, mas esse é um problema diferente. :) O importante a se ver aqui é que uma função introduz um limite "rígido" em seu código que pode ser difícil de ver baseado puramente na sintaxe da linguagem. Essa é uma das razões pelas quais esse estilo de programação de retorno de chamada pode ser tão difícil de acertar. Na verdade, é muito mais difícil fazer isso do que sua tentativa original no código implicaria. Você precisará ter uma maneira de passar um sinal de sucesso através de camadas possivelmente arbitrárias de retornos de chamada ao chamar repetidamente
findOne
e analisar o resultado (de forma assíncrona). Você pode obter ajuda com isso usando o excelente
async
biblioteca, por exemplo https://github.com/caolan/async#whilst
.