MongoDB created collection shows in NodeJS but not in CLI? - node.js

I am trying to create a capped collection in MongoDB using NodeJS driver.
db.createCollection(req.body.name,options,function onCreateCollection(mongoErr,mongoCollection){
if(mongoErr){
...
}else{
console.log( mongoCollection.collectionName );
...
}
});
The collection name prints on the console but show collections does not list it. I tried a hyphenated name this-is-a-collection.
Why is that?
Also, what are the limitations in naming a collection?

I don't know why your code doesn't work. But I just tried to create a collection with the hyphenated name this-is-a-collection with this simple script, it worked.
var MongoClient = require('mongodb').MongoClient;
var url = 'mongodb://localhost:27017/db';
MongoClient.connect(url, function(err, db) {
console.log("Connected correctly to server");
db.createCollection('this-is-a-collection', { capped : true, size : 10000 } ,function onCreateCollection(err,mongoCollection){
if(err){
console.log(err);
} else {
console.log(mongoCollection.collectionName);
}
db.close();
});
});
And in the CLI :
MBP:mongo sapher$ mongo
MongoDB shell version: 3.0.5
connecting to: test
....
> use db
switched to db db
> show collections
system.indexes
this-is-a-collection
You can follow this link to get more info on MongoDB naming restrictions.
For naming convention, I personnaly use snake case like remote_users. I think this is the most elegant way to name a collection. Naming isn't that important as long as you stay consistent.

As it turns out, on older version of the driver 1.4.x, creating a capped collection without specifying the size option doesn't result in an error. It even returns a success response. On the newer version, 2.0.x, it does result in an error.
For a capped collection, size is needed while max is optional. The docs are slightly ambiguous as they do not state that you need a size to create a capped collection.

Related

List Collection Names in MongoDB using Monk

In my Node.js (Express) app that uses Monk, I need to render a list of all collections in the MongoDB database.
Is there a way to get the list of collections in the database using Monk?
This wil basicaly do that, but it takes some digging into the underlying driver to do so:
var db = require('monk')('localhost/test');
db.on("open",function() {
console.log(
db.driver._native.command(
{ "listCollections": 1 },
function(err,result) {
console.log( result.cursor.firstBatch.map(function(el) {
return el.name;
}))
}
)
);
});
The driver command is of course "listCollections" and those are the basic hoops you need to jump through to get there

Inserting document into Mongodb with NodeJs returns document but it is not in collection

I have a weird issue where I have a test to see prove that you cannot create a new user if a user with the same name/email exists, however it always seems to fail. However when I look at the first step which adds a user to the database with the details expected, it inserts and calls back with the document:
[ { Username: 'AccountUser',
Email: 'some#email.com',
CreatedDate: Mon Sep 22 2014 12:52:48 GMT+0100 (GMT Summer Time),
_id: 54200d90d0a34ffc1565df13 } ]
So if I do a console.log of the documents returned from insert thats what I get which is ok, and the _id has been set by mongo which is correct, so I know the call succeeded, and there was no errors.
However if I then go and view the database (MongoVUE) that collection is empty, so I am a bit baffled as to why this is happening.
I am using pooled mongodb connections (i.e setting up during app setup then using app.set("database_connection", database);. So I am a bit baffled as to why this is happening?
Here is some example code, which is part of larger code but basically is contained within promises:
// Point of connection creation
var mongoClient = mongodb.MongoClient;
var connectionCallback = function (err, database) {
if (err) { reject(err); }
resolve(database);
};
try
{ mongoClient.connect(connectionString, connectionCallback); }
catch(exception)
{ reject(exception); }
// Point of usage
var usersCollection = connection.collection("users");
usersCollection.insert(userDocument, function(err, docs) {
if(err) {
reject(err);
return;
}
console.log(docs);
resolve(docs[0]);
});
So I create the connection and pass back the database for use elsewhere, then at the point of inserting I get the connection, get the collection and then insert into it, and log the documents added, which is what is in the above log output.
Also finally running:
Windows 8.1
Node 0.11.13
npm mongodb latest
MongoDB 2.6.1
Not the answer I was hoping for, but I restarted the computer (rare occurrence) and the issue no longer occurs. I have no idea what was causing it and I am still slightly worried incase it happens again, but for now I am up and running again.

Why aren't these MongoDB document changes saved?

This code is intended to make changes in bulk to all the documents in a MongoDB collection. However there is no change at all to the documents in the collection after running this code. What is wrong with it?
var mongoose = require('mongoose'),
async = require('async'),
Person = require('../../model/Person');
mongoose.connect('mongodb://localhost/people-questions');
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'connection error:'));
Person.find(function (err, people) {
if (err) return console.error(err);
//download bio info
async.each(people, function(person, callback) {
person.birthdateYear = '01';
person.save();
callback();
});
mongoose.connection.close();
});
I have verified that there are no changes made by leaving a mongo cli instance open in Terminal and running db.people.find(); to see the field is not updated at all, and also queries such as db.people.find({ "_id" : ObjectId("5379e6e21fe1e8e2fc364d17")});, referencing specific IDs to verify that my Javascript code is indeed connected to the right database and is using the right collection (that ID came from a previous script using identical connection details to print out document IDs).
Also, I am using Mongoose. The Mongoose Schema was updated to include extra fields like birthdateYear after the original documents were created, but from the googling and Mongo Docs reading that I've done already it appears as though Schema changes shouldn't require any special work - you can set attributes against documents with the updated schema right away (should be able to anyway).
The reason the updates are not persisted is that the connection to MongoDB is closed before the save() callbacks have a chance to complete. By ensuring all the save() callbacks complete before closing the connection, the data is saved.
person.save is an async function
try something like
person.save (function(err){
if(err) console.log(err);
callback();
});

Getting "Error: Can't use $geoWithin with Array" from MongooseJS

When I execute the following kind of query with MongooseJS:
Place
.find({location:{$geoWithin:{$box:[[0, -40],[151.0983703,-33.8674744]]}}})
.exec(function(err, places) {
...
});
I get zero results and the following message returned in the err
[Error: Can't use $geoWithin with Array.]
Yet if I execute the exact same criteria directly against MongoDB, on the command line:
> db.places.find({location:{$geoWithin:{$box:[[0, -40],[151.0983703,-33.8674744]]}}})
I get the correct list of records shown in the output.
What am I doing wrong with the MongooseJS code?
Looks like $geoWithin wasn't implemented in the version of Mongoose that I'm using.
My solution for the time being is to use the native mongodb library, until the stable build of Mongoose is updated with support for $geoWithin.
var mongodb = require('mongodb');
mongodb.MongoClient.connect(app.get('mongodb connection string'), function(err, db) {
if (err) throw err;
db.collection('places')
.find({location:{
$geoWithin:{
$box:[[Number(req.query.northEastLng), Number(req.query.northEastLat)],
[Number(req.query.southWestLng), Number(req.query.southWestLat)]]}}})
.toArray(function(err, results) {
if (!results)
results = [];
res.render('nearbyplaces', {
results: results
});
db.close();
});
});
This works fine.
(Note: if you really want to use Mongoose, you could download the latest unstable build from their Github page. I'd just prefer not to, because it would complicate deployment of my app. I want to be able to download everything with just npm install).

Update not working-NodeJs and MongoDB using MongoClient

I was going through the mongodb and nodejs course on MongoDBUniversity and one of the task involves finding the documents which has the highest recorded temperature for any state and then add a field "month_high" to it.I am able to find the documents for the state with the highest temperature but am unable to update it. The code is as below.
Can someone tell me what might I be doing wrong?
var MongoClient=require('mongodb').MongoClient;
MongoClient.connect('mongodb://localhost:27017/course',function(err,db){
var cursor=db.collection("weather").find();
cursor.sort({"State":1,"Temperature":-1});
var oldState,newState;
cursor.each(function(err,doc){
if(err)throw err;
if(doc==null){
return db.close();
}
newState=doc.State;
if(newState!=oldState){
var operator={'$set':{"month_high":true}};
var query={"_id":doc._id};
console.log(doc._id+" has temp "+doc.Temperature+" "+doc.State);
db.collection("weather").update(doc,operator,function(err,updated){
console.log("hi");//---->Never Logs
if(err)throw err;
// console.log(JSON.stringify(updated));
})
}
oldState=newState;
});
});
I'm not 100% sure, but given the syntax reported on the docs you might have to specify the options parameter even if not using it:
db.collection("weather").update(doc,operator, options, function(err,updated)
Also, the connection might get closed before the callbacks are called. Does it change anything if you remove the db.close() call?
Collection name is 'data'. In this homework 'weather' is database name.
See
https://education.mongodb.com/courses/10gen/M101JS/2013_October/courseware/CRUD/Homework_2.2/
> use weather
switched to db weather
> db.data.findOne()

Resources