Search code examples
node.jssails.jswaterlinesails-mongo

As I can use different models in the same controller action


I'm trying to send to the view, information from multiple models as follows:

var tareasGlob = "";
var directoresProy = "";
var usuariosGlob = "";
var proyectosGlob = "";

module.exports = {


'index' : function(req, res, next){

    // De esta forma se utlisaria la funcion de utilidad que cree en el archivo /api/services/utility.js
    // utility.sliceIt();


    Tarea.find().done(function(err, tareas){
        if(err){ return res.serverError(err); } 
        tareasGlob = tareas; 
    });
    console.log('tareas', tareasGlob);
    DirectorProy.find().done(function(err, directsproy){
        if(err){ return res.serverError(err); } 
        directoresProy = directsproy;
    });

    Usuario.find().done(function(err, usuarios){
        if(err){ return res.serverError(err); } 
        usuariosGlob = usuarios;
    });

    Proyecto.find().done(function(err, proyectos){
        if(err){ return res.serverError(err); } 
        proyectosGlob = proyectos;
    });



    res.view({
        'tareas'         : tareasGlob,
        'directoresproy' : directoresProy,
        'usuarios'       : usuariosGlob,
        'proyectos'      : proyectosGlob
    });

},

but then an error occurs because when I do the "res.view ()" are not yet assigned values ​​to variables and are shipped empty.

Thanks in advance for the help you can give me to correct the problem.


Solution

  • There are node packages available to help you with asynchronous coding problems like this one. Sails globalizes the async library, which would allow you to rewrite your code as:

    // All four of the functions inside `async.auto` will run in parallel,
    // and if successful their results will be passed to the "allDone"
    // function
    async.auto({
        tareas: function(cb) {
            Tarea.find().exec(cb);
        },
        directsproy: function(cb) {
            DirectorProy.find().exec(cb);
        },
        usuarios: function(cb) {
            Usuario.find().exec(cb);
        },
        proyectos: function(cb) {
            Proyecto.find().exec(cb);
        }
    }, function allDone(err, results) {
        // If any of the functions called the callback with an error,
        // allDone will immediately be called with the error as the
        // first argument
        if (err) {return res.serverError(err);}
    
        // Otherwise, `results` will be an object whose keys are the
        // same as those of the first argument (tareas, directsproy,
        // usuarios and proyectos, and whose values are the results
        // of their `find` queries.
        res.view(results);
    });
    

    You can also use async.auto to declare dependencies between the different functions, use async.forEach to do asynchronous looping over arrays, and all sorts of fun stuff.

    Full docs for async here.