2016-08-12 2 views
0

Я форма с несколькими раскрывающихся списков, которые должны быть заполнены значениями из базы данных MongoDB, в моем коде файла маршрут кажется что-то вроде этого:Multiple Mongoose запросов перед визуализацией вид

Make.find({},function(err,allMakes){ 
     if(err){ 
      console.log("error while trying to get all makes from the database"); 
     }else{ 
      makes = allMakes; 
} 

Color.find({},function(err,allColors){ 
     if(err){ 
      console.log("error while trying to get all colors from the database"); 
     }else{ 
      colors = allColors; 
} 

Я 8 случаи, когда мне нужно запросить БД затем поместить результат в локальном переменной для того, чтобы передать его, чтобы сделать функцию как пары, как это:

res.render("viewname",{makes:makes,colors:colors....etc}); 

проблемой является, что в моем файле представления я получаю не определен для Params ,

любые решения для асинхронного кода nodejs ?!

+0

Можете ли вы сказать мне, что фактическая проблема есть, что вы ищете? –

+0

@GandalftheWhite проблема заключалась в том, что значения, которые должны быть отправлены в качестве параметров для метода рендеринга, не присваиваются ожидаемому значению, в порядке слов метод визуализации выполняется, прежде чем методы вызовут инициирование параметров. – Abdallah

ответ

0

Я полагаю, что две функции находятся в одной и той же (родительской) функции. Вы не можете назвать два метода, как это, и ожидать, что результаты будут получены в то же время, когда они вам понадобятся. Вы можете черепитчатые такие методы, как:

Make.find({},function(err,allMakes){ 
    if(err){ 
     console.log("error while trying to get all makes from the database"); 
    }else{ 
     makes = allMakes; 

    Color.find({},function(err,allColors){ 
     if(err){ 
      console.log("error while trying to get all colors from the database"); 
     }else{ 
      colors = allColors; 
      methodForRender(makes, colors); 
    } 
} 

methodForRender может быть функцией обратного вызова, в которой вы будете возвращаться марок и цветов, или просто функцию. Но я предпочитаю обратный вызов, потому что лучше иметь такие методы в файле модели и визуализировать представления один в файле маршрута.

1

Вызовы MongoDB являются асинхронными, что означает, что значения make, colors и т. Д. Не установлены перед res.render ("viewname"); вызывается. Вам нужно вложить свои асинхронные вызовы, использовать Promise.all или в идеале использовать библиотеку, например async, для параллельной работы ваших вызовов БД, а затем вызвать res.render только после того, как все обратные вызовы БД задали значения, которые должны быть переданы вид.

Например, если вы вложенности ваши звонки:

Make.find({}, function(err,allMakes) { 
    if (err) { 
     console.log("error while trying to get all makes from the database"); 
    } else { 
     makes = allMakes; 
    } 

    Color.find({}, function(err,allColors) { 
     if (err) { 
      console.log("error while trying to get all colors from the database"); 
     } else { 
      colors = allColors; 
     } 

     res.render("viewname",{makes:makes,colors:colors....etc}); 
    } 
} 
+0

И, возможно, добавьте небольшую обработку ошибок, так как make и цвета не будут определены, если ошибка вернется к истине. – mtjhax

1

Спасибо всем, кто пытался помочь ответить на этот вопрос.

Я нашел решение, решение с использованием nodejs модуль под названием асинхронной

http://caolan.github.io/async/docs.html#.series

рабочий код выглядит следующим образом:

router.get("/new",function(req,res){ 

    // get vehicles makes available in the DB 
    var makes; 
    var colors; 
    var categories; 
    var usages; 
    var registrationCenters; 
    var fuelTypes; 
    var insuranceCompanies; 
    var insuranceCoverages; 

    async.series([function(callback){ 
     Make.find({},function(err,allMakes){ 
      if(err) return callback(err); 
      makes = allMakes; 
      callback(null,allMakes); 
     }) 
    },function(callback){ 
     Color.find({},function(err,allColors){ 
      if(err) return callback(err); 
      colors = allColors; 
      callback(null,allColors); 
     }) 
    },function(callback){ 
     Category.find({},function(err,allCates){ 
      if(err) return callback(err); 
      categories = allCates; 
      callback(null,allCates); 
     }) 
    },function(callback){ 
     Usage.find({},function(err,allUsages){ 
      if(err) return callback(err); 
      usages = allUsages; 
      callback(null,allUsages); 
     }) 
    },function(callback){ 
     RegistraionCenter.find({},function(err,allCenters){ 
      if(err) return callback(err); 
      registrationCenters = allCenters; 
      console.log(allCenters); 
      callback(null,allCenters); 
     }) 
    },function(callback){ 
     FuelType.find({},function(err,allTypes){ 
      if(err) return callback(err); 
      fuelTypes = allTypes; 

      callback(null,allTypes); 
     }) 
    }, 
    function(callback){ 
     InsuranceCompanies.find({},function(err,allCompanies){ 
      if(err) return callback(err); 
      insuranceCompanies = allCompanies; 
      callback(null,allCompanies); 
     }) 
    },function(callback){ 
     InsuranceCoverages.find({},function(err,allCoverages){ 
      if(err) return callback(err); 

      insuranceCoverages = allCoverages; 
      callback(null,allCoverages); 
     }) 
    } 
    ],function(err){ 
     res.render("vehicles/new",{makes:makes,colors:colors,categories:categories,usages:usages, 
      registrationCenters:registrationCenters,fueltypes:fuelTypes,InsuranceCompanies:insuranceCompanies,insuranceCoverages:insuranceCoverages} 
     ); 
    }); 


}); 
Смежные вопросы