Naguib 凪
Naguib 凪

Reputation: 25

Mongoose / NodeJS - String from db is retrieved but considered as not defined

Here's my problem now:

I query a findOne and populate on my DB in order to retrieve an array of string to use in my .EJS but the log says that the value is not defined but its give the value name : "stringName is not defined"

I must have missed something..

This is the User schema :

var UserSchema = new mongoose.Schema({
    username: {  type: String, required: true, index: {  
    unique: true } },
    email: {  type: String, required: true, index: {unique: true } },
    password: {  type: String, required: true },
    tables: [{ type: Schema.Types.ObjectId, ref: 'Table' }],
    resetPasswordToken: String,
    resetPasswordExpires: Date,
    uuid: String,                
});

This is the Table schema :

var TableSchema = Schema({
    name: { type: String, required: true, index: { unique: true }},
    logos: [{ type: Schema.Types.ObjectId, ref: 'Logo'}],
});

This is where I do the query and send the document to the .ejs page:

app.get('/dashboard/:uuid', function(req, res){
    if (req.user && userId != "")
    {
        var query = User.findOne({username:    req.user.username}).populate('tables').select('tables');

        query.exec(function (err, tables){
            if (err) return console.error(err);
            console.log (tables.tables[0].name); // Return the right string name
            res.render('./pages/dashboard.ejs', {username: req.user.username, tables: tables.tables});
        });
    }
    else
        res.redirect('/');
});

And this is the script in ejs that is supposed to render the table names in my page:

 <script>
     $(document).ready(function (){
         <% for(var i = 0; i < tables.length; i++) {%>
         var newTab = "<a href=\"/work\"><div class=\"square\" style=\"display: inline-block\"><span style=\"margin-top: 50%; text-align: center\">" + <%=tables[i].name%> + "</span></div></a>";
         $(newTab).appendTo('.jumbotron');
         <%}%>

    });
</script>

If you guys could enlighten up a bit my way that would be so great !

Upvotes: 1

Views: 300

Answers (1)

Medet Tleukabiluly
Medet Tleukabiluly

Reputation: 11950

Take a look at this implementation, this is how i would query schema, in firs example we reuse req.user (good), in second we make 2 database calls (bad). In your example you make 1 database call but not populating Logo field of table schema (bad).

app.get('/dashboard/:uuid', function(req, res){
    // first example
    // no need to query users, you already have tables field
    if (!req.user) // what is userId, why you check it
        // add `err` checks
        return res.redirect('/');

    TableSchema
        .find({ _id: { $in: req.user.tables } })
        .populate('logos', 'url'); // Logo schema fields
        .exec(function(err, result_tables){
           res.render('./pages/dashboard.ejs', {username: req.user.username, tables: result_tables});
    });

    // or second example
    // if you still for some reason cannot use req.user.tables field
    // but strongly recommend to use first one
    User.findById(req.user._id, 'tables') 
        .exec(function (err, user_tables){
            // add `err` checks
            TableSchema.populate(user_tables, { path: 'logos', model: 'Logo' }, function (err, result_tables){
                // add `err` checks
                res.render('./pages/dashboard.ejs', {username: req.user.username, tables: result_tables});
            });
    });
});

As per your comment

in chrome browser : " Uncaught ReferenceError: stringName is not defined " (stringName = what's in tables[0].name)

Try to use forEach operator

<script>
     $(document).ready(function (){
         <% tables.forEach(function(table){ %>
             var newTab = "<a ommited><%= table.name %></a>"; //notice: no `"`
             $(newTab).appendTo('.jumbotron');
         <% }) %>
    });
</script>

Upvotes: 1

Related Questions