Admin = function (db,
topology,
promiseLibrary) {
if(!(this instanceof Admin)) return new Admin(db, topology);
// Internal state
this.s = {
db: db
, topology: topology
, promiseLibrary: promiseLibrary
}
}n/a
function Binary(buffer,
subType) {
if(!(this instanceof Binary)) return new Binary(buffer, subType);
this._bsontype = 'Binary';
if(buffer instanceof Number) {
this.sub_type = buffer;
this.position = 0;
} else {
this.sub_type = subType == null ? BSON_BINARY_SUBTYPE_DEFAULT : subType;
this.position = 0;
}
if(buffer != null && !(buffer instanceof Number)) {
// Only accept Buffer, Uint8Array or Arrays
if(typeof buffer == 'string') {
// Different ways of writing the length of the string for the different types
if(typeof Buffer != 'undefined') {
this.buffer = new Buffer(buffer);
} else if(typeof Uint8Array != 'undefined' || (Object.prototype.toString.call(buffer) == '[object Array]')) {
this.buffer = writeStringToArray(buffer);
} else {
throw new Error("only String, Buffer, Uint8Array or Array accepted");
}
} else {
this.buffer = buffer;
}
this.position = buffer.length;
} else {
if(typeof Buffer != 'undefined') {
this.buffer = new Buffer(Binary.BUFFER_SIZE);
} else if(typeof Uint8Array != 'undefined'){
this.buffer = new Uint8Array(new ArrayBuffer(Binary.BUFFER_SIZE));
} else {
this.buffer = new Array(Binary.BUFFER_SIZE);
}
// Set position to start of buffer
this.position = 0;
}
}n/a
Chunk = function (file,
mongoObject,
writeConcern) {
if(!(this instanceof Chunk)) return new Chunk(file, mongoObject);
this.file = file;
var mongoObjectFinal = mongoObject == null ? {} : mongoObject;
this.writeConcern = writeConcern || {w:1};
this.objectId = mongoObjectFinal._id == null ? new ObjectID() : mongoObjectFinal._id;
this.chunkNumber = mongoObjectFinal.n == null ? 0 : mongoObjectFinal.n;
this.data = new Binary();
if(typeof mongoObjectFinal.data == "string") {
var buffer = new Buffer(mongoObjectFinal.data.length);
buffer.write(mongoObjectFinal.data, 0, mongoObjectFinal.data.length, 'binary');
this.data = new Binary(buffer);
} else if(Array.isArray(mongoObjectFinal.data)) {
buffer = new Buffer(mongoObjectFinal.data.length);
var data = mongoObjectFinal.data.join('');
buffer.write(data, 0, data.length, 'binary');
this.data = new Binary(buffer);
} else if(mongoObjectFinal.data && mongoObjectFinal.data._bsontype === 'Binary') {
this.data = mongoObjectFinal.data;
} else if(!Buffer.isBuffer(mongoObjectFinal.data) && !(mongoObjectFinal.data == null)){
throw Error("Illegal chunk format");
}
// Update position
this.internalPosition = 0;
}n/a
function Code(code,
scope) {
if(!(this instanceof Code)) return new Code(code, scope);
this._bsontype = 'Code';
this.code = code;
this.scope = scope;
}n/a
Collection = function (db,
topology,
dbName,
name,
pkFactory,
options) {
checkCollectionName(name);
// Unpack variables
var internalHint = null;
var slaveOk = options == null || options.slaveOk == null ? db.slaveOk : options.slaveOk;
var serializeFunctions = options == null || options.serializeFunctions == null ? db.s.options.serializeFunctions : options.ser\
ializeFunctions;
var raw = options == null || options.raw == null ? db.s.options.raw : options.raw;
var promoteLongs = options == null || options.promoteLongs == null ? db.s.options.promoteLongs : options.promoteLongs;
var promoteValues = options == null || options.promoteValues == null ? db.s.options.promoteValues : options.promoteValues;
var promoteBuffers = options == null || options.promoteBuffers == null ? db.s.options.promoteBuffers : options.promoteBuffers;
var readPreference = null;
var collectionHint = null;
var namespace = f("%s.%s", dbName, name);
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Assign the right collection level readPreference
if(options && options.readPreference) {
readPreference = options.readPreference;
} else if(db.options.readPreference) {
readPreference = db.options.readPreference;
}
// Set custom primary key factory if provided
pkFactory = pkFactory == null
? ObjectID
: pkFactory;
// Internal state
this.s = {
// Set custom primary key factory if provided
pkFactory: pkFactory
// Db
, db: db
// Topology
, topology: topology
// dbName
, dbName: dbName
// Options
, options: options
// Namespace
, namespace: namespace
// Read preference
, readPreference: readPreference
// SlaveOK
, slaveOk: slaveOk
// Serialize functions
, serializeFunctions: serializeFunctions
// Raw
, raw: raw
// promoteLongs
, promoteLongs: promoteLongs
// promoteValues
, promoteValues: promoteValues
// promoteBuffers
, promoteBuffers: promoteBuffers
// internalHint
, internalHint: internalHint
// collectionHint
, collectionHint: collectionHint
// Name
, name: name
// Promise library
, promiseLibrary: promiseLibrary
// Read Concern
, readConcern: options.readConcern
}
}n/a
CoreConnection = function (messageHandler,
options) {
// Add event listener
EventEmitter.call(this);
// Set empty if no options passed
this.options = options || {};
// Identification information
this.id = _id++;
// Logger instance
this.logger = Logger('Connection', options);
// No bson parser passed in
if(!options.bson) throw new Error("must pass in valid bson parser");
// Get bson parser
this.bson = options.bson;
// Grouping tag used for debugging purposes
this.tag = options.tag;
// Message handler
this.messageHandler = messageHandler;
// Max BSON message size
this.maxBsonMessageSize = options.maxBsonMessageSize || (1024 * 1024 * 16 * 4);
// Debug information
if(this.logger.isDebug()) this.logger.debug(f('creating connection %s with options [%s]', this.id, JSON.stringify(debugOptions\
(debugFields, options))));
// Default options
this.port = options.port || 27017;
this.host = options.host || 'localhost';
this.keepAlive = typeof options.keepAlive == 'boolean' ? options.keepAlive : true;
this.keepAliveInitialDelay = options.keepAliveInitialDelay || 0;
this.noDelay = typeof options.noDelay == 'boolean' ? options.noDelay : true;
this.connectionTimeout = options.connectionTimeout || 0;
this.socketTimeout = options.socketTimeout || 0;
// If connection was destroyed
this.destroyed = false;
// Check if we have a domain socket
this.domainSocket = this.host.indexOf('\/') != -1;
// Serialize commands using function
this.singleBufferSerializtion = typeof options.singleBufferSerializtion == 'boolean' ? options.singleBufferSerializtion : true\
;
this.serializationFunction = this.singleBufferSerializtion ? 'toBinUnified' : 'toBin';
// SSL options
this.ca = options.ca || null;
this.cert = options.cert || null;
this.key = options.key || null;
this.passphrase = options.passphrase || null;
this.ssl = typeof options.ssl == 'boolean' ? options.ssl : false;
this.rejectUnauthorized = typeof options.rejectUnauthorized == 'boolean' ? options.rejectUnauthorized : true;
this.checkServerIdentity = typeof options.checkServerIdentity == 'boolean'
|| typeof options.checkServerIdentity == 'function' ? options.checkServerIdentity : true;
// If ssl not enabled
if(!this.ssl) this.rejectUnauthorized = false;
// Response options
this.responseOptions = {
promoteLongs: typeof options.promoteLongs == 'boolean' ? options.promoteLongs : true,
promoteValues: typeof options.promoteValues == 'boolean' ? options.promoteValues : true,
promoteBuffers: typeof options.promoteBuffers == 'boolean' ? options.promoteBuffers: false
}
// Flushing
this.flushing = false;
this.queue = [];
// Internal state
this.connection = null;
this.writeStream = null;
// Create hash method
var hash = crypto.createHash('sha1');
hash.update(f('%s:%s', this.host, this.port));
// Create a hash name
this.hashedName = hash.digest('hex');
// All operations in flight on the connection
this.workItems = [];
}n/a
CoreServer = function (options) {
options = options || {};
// Add event listener
EventEmitter.call(this);
// Server instance id
this.id = id++;
// Internal state
this.s = {
// Options
options: options,
// Logger
logger: Logger('Server', options),
// Factory overrides
Cursor: options.cursorFactory || BasicCursor,
// BSON instance
bson: options.bson || new BSON([BSON.Binary, BSON.Code, BSON.DBRef, BSON.Decimal128,
BSON.Double, BSON.Int32, BSON.Long, BSON.Map, BSON.MaxKey, BSON.MinKey,
BSON.ObjectId, BSON.BSONRegExp, BSON.Symbol, BSON.Timestamp]),
// Pool
pool: null,
// Disconnect handler
disconnectHandler: options.disconnectHandler,
// Monitor thread (keeps the connection alive)
monitoring: typeof options.monitoring == 'boolean' ? options.monitoring : true,
// Is the server in a topology
inTopology: typeof options.inTopology == 'boolean' ? options.inTopology : false,
// Monitoring timeout
monitoringInterval: typeof options.monitoringInterval == 'number'
? options.monitoringInterval
: 5000,
// Topology id
topologyId: -1
}
// Curent ismaster
this.ismaster = null;
// Current ping time
this.lastIsMasterMS = -1;
// The monitoringProcessId
this.monitoringProcessId = null;
// Initial connection
this.initalConnect = true;
// Wire protocol handler, default to oldest known protocol handler
// this gets changed when the first ismaster is called.
this.wireProtocolHandler = new PreTwoSixWireProtocolSupport();
// Default type
this._type = 'server';
// Set the client info
this.clientInfo = createClientInfo(options);
// Max Stalleness values
// last time we updated the ismaster state
this.lastUpdateTime = 0;
// Last write time
this.lastWriteDate = 0;
// Stalleness
this.staleness = 0;
}n/a
Cursor = function (bson,
ns,
cmd,
options,
topology,
topologyOptions) {
CoreCursor.apply(this, Array.prototype.slice.call(arguments, 0));
var self = this;
var state = Cursor.INIT;
var streamOptions = {};
// Tailable cursor options
var numberOfRetries = options.numberOfRetries || 5;
var tailableRetryInterval = options.tailableRetryInterval || 500;
var currentNumberOfRetries = numberOfRetries;
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Set up
Readable.call(this, {objectMode: true});
// Internal cursor state
this.s = {
// Tailable cursor options
numberOfRetries: numberOfRetries
, tailableRetryInterval: tailableRetryInterval
, currentNumberOfRetries: currentNumberOfRetries
// State
, state: state
// Stream options
, streamOptions: streamOptions
// BSON
, bson: bson
// Namespace
, ns: ns
// Command
, cmd: cmd
// Options
, options: options
// Topology
, topology: topology
// Topology options
, topologyOptions: topologyOptions
// Promise library
, promiseLibrary: promiseLibrary
// Current doc
, currentDoc: null
}
// Translate correctly
if(self.s.options.noCursorTimeout == true) {
self.addCursorFlag('noCursorTimeout', true);
}
// Set the sort value
this.sortValue = self.s.cmd.sort;
}n/a
function DBRef(namespace,
oid,
db) {
if(!(this instanceof DBRef)) return new DBRef(namespace, oid, db);
this._bsontype = 'DBRef';
this.namespace = namespace;
this.oid = oid;
this.db = db;
}n/a
Db = function (databaseName,
topology,
options) {
options = options || {};
if(!(this instanceof Db)) return new Db(databaseName, topology, options);
EventEmitter.call(this);
var self = this;
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Filter the options
options = filterOptions(options, legalOptionNames);
// Ensure we put the promiseLib in the options
options.promiseLibrary = promiseLibrary;
// var self = this; // Internal state of the db object
this.s = {
// Database name
databaseName: databaseName
// DbCache
, dbCache: {}
// Children db's
, children: []
// Topology
, topology: topology
// Options
, options: options
// Logger instance
, logger: Logger('Db', options)
// Get the bson parser
, bson: topology ? topology.bson : null
// Authsource if any
, authSource: options.authSource
// Unpack read preference
, readPreference: options.readPreference
// Set buffermaxEntries
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : -1
// Parent db (if chained)
, parentDb: options.parentDb || null
// Set up the primary key factory or fallback to ObjectID
, pkFactory: options.pkFactory || ObjectID
// Get native parser
, nativeParser: options.nativeParser || options.native_parser
// Promise library
, promiseLibrary: promiseLibrary
// No listener
, noListener: typeof options.noListener == 'boolean' ? options.noListener : false
// ReadConcern
, readConcern: options.readConcern
}
// Ensure we have a valid db name
validateDatabaseName(self.s.databaseName);
// Add a read Only property
getSingleProperty(this, 'serverConfig', self.s.topology);
getSingleProperty(this, 'bufferMaxEntries', self.s.bufferMaxEntries);
getSingleProperty(this, 'databaseName', self.s.databaseName);
// This is a child db, do not register any listeners
if(options.parentDb) return;
if(this.s.noListener) return;
// Add listeners
topology.on('error', createListener(self, 'error', self));
topology.on('timeout', createListener(self, 'timeout', self));
topology.on('close', createListener(self, 'close', self));
topology.on('parseError', createListener(self, 'parseError', self));
topology.once('open', createListener(self, 'open', self));
topology.once('fullsetup', createListener(self, 'fullsetup', self));
topology.once('all', createListener(self, 'all', self));
topology.on('reconnect', createListener(self, 'reconnect', self));
}n/a
Decimal128 = function (bytes) {
this._bsontype = 'Decimal128';
this.bytes = bytes;
}n/a
function Double(value) {
if(!(this instanceof Double)) return new Double(value);
this._bsontype = 'Double';
this.value = value;
}n/a
function GridFSBucket(db,
options) {
Emitter.apply(this);
this.setMaxListeners(0);
if (options && typeof options === 'object') {
options = shallowClone(options);
var keys = Object.keys(DEFAULT_GRIDFS_BUCKET_OPTIONS);
for (var i = 0; i < keys.length; ++i) {
if (!options[keys[i]]) {
options[keys[i]] = DEFAULT_GRIDFS_BUCKET_OPTIONS[keys[i]];
}
}
} else {
options = DEFAULT_GRIDFS_BUCKET_OPTIONS;
}
this.s = {
db: db,
options: options,
_chunksCollection: db.collection(options.bucketName + '.chunks'),
_filesCollection: db.collection(options.bucketName + '.files'),
checkedIndexes: false,
calledOpenUploadStream: false,
promiseLibrary: db.s.promiseLibrary ||
(typeof global.Promise == 'function' ? global.Promise : require('es6-promise').Promise)
};
}n/a
function GridStore(db,
id,
filename,
mode,
options) {
if(!(this instanceof GridStore)) return new GridStore(db, id, filename, mode, options);
this.db = db;
// Handle options
if(typeof options === 'undefined') options = {};
// Handle mode
if(typeof mode === 'undefined') {
mode = filename;
filename = undefined;
} else if(typeof mode == 'object') {
options = mode;
mode = filename;
filename = undefined;
}
if(id && id._bsontype == 'ObjectID') {
this.referenceBy = REFERENCE_BY_ID;
this.fileId = id;
this.filename = filename;
} else if(typeof filename == 'undefined') {
this.referenceBy = REFERENCE_BY_FILENAME;
this.filename = id;
if (mode.indexOf('w') != null) {
this.fileId = new ObjectID();
}
} else {
this.referenceBy = REFERENCE_BY_ID;
this.fileId = id;
this.filename = filename;
}
// Set up the rest
this.mode = mode == null ? "r" : mode;
this.options = options || {};
// Opened
this.isOpen = false;
// Set the root if overridden
this.root = this.options['root'] == null ? GridStore.DEFAULT_ROOT_COLLECTION : this.options['root'];
this.position = 0;
this.readPreference = this.options.readPreference || db.options.readPreference || ReadPreference.PRIMARY;
this.writeConcern = _getWriteConcern(db, this.options);
// Set default chunk size
this.internalChunkSize = this.options['chunkSize'] == null ? Chunk.DEFAULT_CHUNK_SIZE : this.options['chunkSize'];
// Get the promiseLibrary
var promiseLibrary = this.options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Set the promiseLibrary
this.promiseLibrary = promiseLibrary;
Object.defineProperty(this, "chunkSize", { enumerable: true
, get: function () {
return this.internalChunkSize;
}
, set: function(value) {
if(!(this.mode[0] == "w" && this.position == 0 && this.uploadDate == null)) {
this.internalChunkSize = this.internalChunkSize;
} else {
this.internalChunkSize = value;
}
}
});
Object.defineProperty(this, "md5", { enumerable: true
, get: function () {
return this.internalMd5;
}
});
Object.defineProperty(this, "chunkNumber", { enumerable: true
, get: function () {
return this.currentChunk && this.currentChunk.chunkNumber ? this.currentChunk.chunkNumber : null;
}
});
}n/a
Int32 = function (value) {
if(!(this instanceof Int32)) return new Int32(value);
this._bsontype = 'Int32';
this.value = value;
}n/a
Logger = function (className,
options) {
if(!(this instanceof Logger)) return new Logger(className, options);
options = options || {};
// Current reference
this.className = className;
// Current logger
if(options.logger) {
currentLogger = options.logger;
} else if(currentLogger == null) {
currentLogger = console.log;
}
// Set level of logging, default is error
if(options.loggerLevel) {
level = options.loggerLevel || 'error';
}
// Add all class names
if(filteredClasses[this.className] == null) classFilters[this.className] = true;
}n/a
function Long(low,
high) {
if(!(this instanceof Long)) return new Long(low, high);
this._bsontype = 'Long';
/**
* @type {number}
* @ignore
*/
this.low_ = low | 0; // force into 32 signed bits.
/**
* @type {number}
* @ignore
*/
this.high_ = high | 0; // force into 32 signed bits.
}n/a
function Map() { [native code] }n/a
function MaxKey() {
if(!(this instanceof MaxKey)) return new MaxKey();
this._bsontype = 'MaxKey';
}n/a
function MinKey() {
if(!(this instanceof MinKey)) return new MinKey();
this._bsontype = 'MinKey';
}n/a
function MongoClient() {
/**
* The callback format for results
* @callback MongoClient~connectCallback
* @param {MongoError} error An error instance representing the error during the execution.
* @param {Db} db The connected database.
*/
/**
* Connect to MongoDB using a url as documented at
*
* docs.mongodb.org/manual/reference/connection-string/
*
* Note that for replicasets the replicaSet query parameter is required in the 2.0 driver
*
* @method
* @param {string} url The connection URI string
* @param {object} [options=null] Optional settings.
* @param {boolean} [options.uri_decode_auth=false] Uri decode the user name and password for authentication
* @param {object} [options.db=null] A hash of options to set on the db object, see **Db constructor**
* @param {object} [options.server=null] A hash of options to set on the server objects, see **Server** constructor**
* @param {object} [options.replSet=null] A hash of options to set on the replSet object, see **ReplSet** constructor**
* @param {object} [options.mongos=null] A hash of options to set on the mongos object, see **Mongos** constructor**
* @param {object} [options.promiseLibrary=null] A Promise library class the application wishes to use such as Bluebird, must \
be ES6 compatible
* @param {MongoClient~connectCallback} [callback] The command result callback
* @return {Promise} returns Promise if no callback passed
*/
this.connect = MongoClient.connect;
}n/a
function MongoError(message) {
this.name = 'MongoError';
this.message = message;
Error.captureStackTrace(this, MongoError);
}n/a
Mongos = function (servers,
options) {
if(!(this instanceof Mongos)) return new Mongos(servers, options);
options = options || {};
var self = this;
// Filter the options
options = filterOptions(options, legalOptionNames);
// Ensure all the instances are Server
for(var i = 0; i < servers.length; i++) {
if(!(servers[i] instanceof Server)) {
throw MongoError.create({message: "all seed list instances must be of the Server type", driver:true});
}
}
// Stored options
var storeOptions = {
force: false
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : MAX_JS_INT
}
// Shared global store
var store = options.store || new Store(self, storeOptions);
// Set up event emitter
EventEmitter.call(this);
// Build seed list
var seedlist = servers.map(function(x) {
return {host: x.host, port: x.port}
});
// Get the reconnect option
var reconnect = typeof options.auto_reconnect == 'boolean' ? options.auto_reconnect : true;
reconnect = typeof options.autoReconnect == 'boolean' ? options.autoReconnect : reconnect;
// Clone options
var clonedOptions = mergeOptions({}, {
disconnectHandler: store,
cursorFactory: Cursor,
reconnect: reconnect,
emitError: typeof options.emitError == 'boolean' ? options.emitError : true,
size: typeof options.poolSize == 'number' ? options.poolSize : 5
});
// Translate any SSL options and other connectivity options
clonedOptions = translateOptions(clonedOptions, options);
// Socket options
var socketOptions = options.socketOptions && Object.keys(options.socketOptions).length > 0
? options.socketOptions : options;
// Translate all the options to the mongodb-core ones
clonedOptions = translateOptions(clonedOptions, socketOptions);
if(typeof clonedOptions.keepAlive == 'number') {
clonedOptions.keepAliveInitialDelay = clonedOptions.keepAlive;
clonedOptions.keepAlive = clonedOptions.keepAlive > 0;
}
// Build default client information
this.clientInfo = {
driver: {
name: "nodejs",
version: driverVersion
},
os: {
type: type,
name: name,
architecture: architecture,
version: release
},
platform: nodejsversion
}
// Build default client information
clonedOptions.clientInfo = this.clientInfo;
// Do we have an application specific string
if(options.appname) {
clonedOptions.clientInfo.application = { name: options.appname };
}
// Create the Mongos
var mongos = new CMongos(seedlist, clonedOptions)
// Server capabilities
var sCapabilities = null;
// Internal state
this.s = {
// Create the Mongos
mongos: mongos
// Server capabilities
, sCapabilities: sCapabilities
// Debug turned on
, debug: clonedOptions.debug
// Store option defaults
, storeOptions: storeOptions
// Cloned options
, clonedOptions: clonedOptions
// Actual store of callbacks
, store: store
// Options
, options: options
}
}n/a
function ObjectID(id) {
// Duck-typing to support ObjectId from different npm packages
if(id instanceof ObjectID) return id;
if(!(this instanceof ObjectID)) return new ObjectID(id);
this._bsontype = 'ObjectID';
var __id = null;
var valid = ObjectID.isValid(id);
// Throw an error if it's not a valid setup
if(!valid && id != null){
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
} else if(valid && typeof id == 'string' && id.length == 24) {
return ObjectID.createFromHexString(id);
} else if(id == null || typeof id == 'number') {
// convert to 12 byte binary string
this.id = this.generate(id);
} else if(id != null && id.length === 12) {
// assume 12 byte string
this.id = id;
} else if(id != null && id.toHexString) {
// Duck-typing to support ObjectId from different npm packages
return id;
} else {
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
}
if(ObjectID.cacheHexString) this.__id = this.toHexString();
}n/a
function ObjectID(id) {
// Duck-typing to support ObjectId from different npm packages
if(id instanceof ObjectID) return id;
if(!(this instanceof ObjectID)) return new ObjectID(id);
this._bsontype = 'ObjectID';
var __id = null;
var valid = ObjectID.isValid(id);
// Throw an error if it's not a valid setup
if(!valid && id != null){
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
} else if(valid && typeof id == 'string' && id.length == 24) {
return ObjectID.createFromHexString(id);
} else if(id == null || typeof id == 'number') {
// convert to 12 byte binary string
this.id = this.generate(id);
} else if(id != null && id.length === 12) {
// assume 12 byte string
this.id = id;
} else if(id != null && id.toHexString) {
// Duck-typing to support ObjectId from different npm packages
return id;
} else {
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
}
if(ObjectID.cacheHexString) this.__id = this.toHexString();
}n/a
ReadPreference = function (mode,
tags,
options) {
if(!(this instanceof ReadPreference)) {
return new ReadPreference(mode, tags, options);
}
this._type = 'ReadPreference';
this.mode = mode;
this.tags = tags;
this.options = options;
// If no tags were passed in
if(tags && typeof tags == 'object' && !Array.isArray(tags)) {
if(tags.maxStalenessSeconds) {
this.options = tags;
this.tags = null;
}
}
// Add the maxStalenessSeconds value to the read Preference
if(this.options && this.options.maxStalenessSeconds) {
this.maxStalenessSeconds = this.options.maxStalenessSeconds;
}
}n/a
ReplSet = function (servers,
options) {
if(!(this instanceof ReplSet)) return new ReplSet(servers, options);
options = options || {};
var self = this;
// Set up event emitter
EventEmitter.call(this);
// Filter the options
options = filterOptions(options, legalOptionNames);
// Ensure all the instances are Server
for(var i = 0; i < servers.length; i++) {
if(!(servers[i] instanceof Server)) {
throw MongoError.create({message: "all seed list instances must be of the Server type", driver:true});
}
}
// Stored options
var storeOptions = {
force: false
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : MAX_JS_INT
}
// Shared global store
var store = options.store || new Store(self, storeOptions);
// Build seed list
var seedlist = servers.map(function(x) {
return {host: x.host, port: x.port}
});
// Clone options
var clonedOptions = mergeOptions({}, {
disconnectHandler: store,
cursorFactory: Cursor,
reconnect: false,
emitError: typeof options.emitError == 'boolean' ? options.emitError : true,
size: typeof options.poolSize == 'number' ? options.poolSize : 5
});
// Translate any SSL options and other connectivity options
clonedOptions = translateOptions(clonedOptions, options);
// Socket options
var socketOptions = options.socketOptions && Object.keys(options.socketOptions).length > 0
? options.socketOptions : options;
// Translate all the options to the mongodb-core ones
clonedOptions = translateOptions(clonedOptions, socketOptions);
if(typeof clonedOptions.keepAlive == 'number') {
clonedOptions.keepAliveInitialDelay = clonedOptions.keepAlive;
clonedOptions.keepAlive = clonedOptions.keepAlive > 0;
}
// Client info
this.clientInfo = {
driver: {
name: "nodejs",
version: driverVersion
},
os: {
type: type,
name: name,
architecture: architecture,
version: release
},
platform: nodejsversion
}
// Build default client information
clonedOptions.clientInfo = this.clientInfo;
// Do we have an application specific string
if(options.appname) {
clonedOptions.clientInfo.application = { name: options.appname };
}
// Create the ReplSet
var replset = new CReplSet(seedlist, clonedOptions);
// Listen to reconnect event
replset.on('reconnect', function() {
self.emit('reconnect');
store.execute();
});
// Internal state
this.s = {
// Replicaset
replset: replset
// Server capabilities
, sCapabilities: null
// Debug tag
, tag: options.tag
// Store options
, storeOptions: storeOptions
// Cloned options
, clonedOptions: clonedOptions
// Store
, store: store
// Options
, options: options
}
// Debug
if(clonedOptions.debug) {
// Last ismaster
Object.defineProperty(this, 'replset', {
enumerable:true, get: function() { return replset; }
});
}
}n/a
Server = function (host,
port,
options) {
options = options || {};
if(!(this instanceof Server)) return new Server(host, port, options);
EventEmitter.call(this);
var self = this;
// Filter the options
options = filterOptions(options, legalOptionNames);
// Stored options
var storeOptions = {
force: false
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : MAX_JS_INT
}
// Shared global store
var store = options.store || new Store(self, storeOptions);
// Detect if we have a socket connection
if(host.indexOf('\/') != -1) {
if(port != null && typeof port == 'object') {
options = port;
port = null;
}
} else if(port == null) {
throw MongoError.create({message: 'port must be specified', driver:true});
}
// Get the reconnect option
var reconnect = typeof options.auto_reconnect == 'boolean' ? options.auto_reconnect : true;
reconnect = typeof options.autoReconnect == 'boolean' ? options.autoReconnect : reconnect;
// Clone options
var clonedOptions = mergeOptions({}, {
host: host, port: port, disconnectHandler: store,
cursorFactory: Cursor,
reconnect: reconnect,
emitError: typeof options.emitError == 'boolean' ? options.emitError : true,
size: typeof options.poolSize == 'number' ? options.poolSize : 5
});
// Translate any SSL options and other connectivity options
clonedOptions = translateOptions(clonedOptions, options);
// Socket options
var socketOptions = options.socketOptions && Object.keys(options.socketOptions).length > 0
? options.socketOptions : options;
// Translate all the options to the mongodb-core ones
clonedOptions = translateOptions(clonedOptions, socketOptions);
if(typeof clonedOptions.keepAlive == 'number') {
clonedOptions.keepAliveInitialDelay = clonedOptions.keepAlive;
clonedOptions.keepAlive = clonedOptions.keepAlive > 0;
}
// Build default client information
this.clientInfo = {
driver: {
name: "nodejs",
version: driverVersion
},
os: {
type: type,
name: name,
architecture: architecture,
version: release
},
platform: nodejsversion
}
// Build default client information
clonedOptions.clientInfo = this.clientInfo;
// Do we have an application specific string
if(options.appname) {
clonedOptions.clientInfo.application = { name: options.appname };
}
// Create an instance of a server instance from mongodb-core
var server = new CServer(clonedOptions);
// Define the internal properties
this.s = {
// Create an instance of a server instance from mongodb-core
server: server
// Server capabilities
, sCapabilities: null
// Cloned options
, clonedOptions: clonedOptions
// Reconnect
, reconnect: clonedOptions.reconnect
// Emit error
, emitError: clonedOptions.emitError
// Pool size
, poolSize: clonedOptions.size
// Store Options
, storeOptions: storeOptions
// Store
, store: store
// Host
, host: host
// Port
, port: port
// Options
, options: options
}
}n/a
function Symbol(value) {
if(!(this instanceof Symbol)) return new Symbol(value);
this._bsontype = 'Symbol';
this.value = value;
}n/a
function Timestamp(low,
high) {
if(!(this instanceof Timestamp)) return new Timestamp(low, high);
this._bsontype = 'Timestamp';
/**
* @type {number}
* @ignore
*/
this.low_ = low | 0; // force into 32 signed bits.
/**
* @type {number}
* @ignore
*/
this.high_ = high | 0; // force into 32 signed bits.
}n/a
connect = function (url,
options,
callback) {
var args = Array.prototype.slice.call(arguments, 1);
callback = typeof args[args.length - 1] == 'function' ? args.pop() : null;
options = args.length ? args.shift() : null;
options = options || {};
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Return a promise
if(typeof callback != 'function') {
return new promiseLibrary(function(resolve, reject) {
connect(url, options, function(err, db) {
if(err) return reject(err);
resolve(db);
});
});
}
// Fallback to callback based connect
connect(url, options, callback);
}...
```js
var MongoClient = require('mongodb').MongoClient
, assert = require('assert');
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
...instrument = function (options,
callback) {
if(typeof options == 'function') callback = options, options = {};
return new Instrumentation(core, options, callback);
}n/a
Admin = function (db,
topology,
promiseLibrary) {
if(!(this instanceof Admin)) return new Admin(db, topology);
// Internal state
this.s = {
db: db
, topology: topology
, promiseLibrary: promiseLibrary
}
}n/a
addUser = function (username,
password,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() : {};
options = options || {};
// Get the options
options = writeConcern(options, self.s.db)
// Set the db name to admin
options.dbName = 'admin';
// Execute using callback
if(typeof callback == 'function')
return self.s.db.addUser(username, password, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.addUser(username, password, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
authenticate = function (username,
password,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options);
options.authdb = 'admin';
// Execute using callback
if(typeof callback == 'function') return this.s.db.authenticate(username, password, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.authenticate(username, password, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
buildInfo = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return this.serverInfo(callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.serverInfo(function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
command = function (command,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() : {};
// Execute using callback
if(typeof callback == 'function') return this.s.db.executeDbAdminCommand(command, options, function(err, doc) {
return callback != null ? callback(err, doc) : null;
});
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.executeDbAdminCommand(command, options, function(err, doc) {
if(err) return reject(err);
resolve(doc);
});
});
}n/a
listDatabases = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return self.s.db.executeDbAdminCommand({listDatabases:1}, {}, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.executeDbAdminCommand({listDatabases:1}, {}, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
logout = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return this.s.db.logout({dbName: 'admin'}, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.logout({dbName: 'admin'}, function(err) {
if(err) return reject(err);
resolve(true);
});
});
}n/a
ping = function (options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
// Execute using callback
if(typeof callback == 'function') return this.s.db.executeDbAdminCommand({ping: 1}, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.executeDbAdminCommand({ping: 1}, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
profilingInfo = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return profilingInfo(self, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
profilingInfo(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
profilingLevel = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return profilingLevel(self, callback)
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
profilingLevel(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
removeUser = function (username,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() : {};
options = options || {};
// Get the options
options = writeConcern(options, self.s.db)
// Set the db name
options.dbName = 'admin';
// Execute using callback
if(typeof callback == 'function')
return self.s.db.removeUser(username, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.removeUser(username, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
replSetGetStatus = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return replSetGetStatus(self, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
replSetGetStatus(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
serverInfo = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return this.s.db.executeDbAdminCommand({buildinfo:1}, function(err, doc) {
if(err != null) return callback(err, null);
callback(null, doc);
});
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.executeDbAdminCommand({buildinfo:1}, function(err, doc) {
if(err) return reject(err);
resolve(doc);
});
});
}n/a
serverStatus = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return serverStatus(self, callback)
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
serverStatus(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
setProfilingLevel = function (level,
callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return setProfilingLevel(self, level, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
setProfilingLevel(self, level, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
validateCollection = function (collectionName,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() : {};
options = options || {};
// Execute using callback
if(typeof callback == 'function')
return validateCollection(self, collectionName, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
validateCollection(self, collectionName, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
function Binary(buffer,
subType) {
if(!(this instanceof Binary)) return new Binary(buffer, subType);
this._bsontype = 'Binary';
if(buffer instanceof Number) {
this.sub_type = buffer;
this.position = 0;
} else {
this.sub_type = subType == null ? BSON_BINARY_SUBTYPE_DEFAULT : subType;
this.position = 0;
}
if(buffer != null && !(buffer instanceof Number)) {
// Only accept Buffer, Uint8Array or Arrays
if(typeof buffer == 'string') {
// Different ways of writing the length of the string for the different types
if(typeof Buffer != 'undefined') {
this.buffer = new Buffer(buffer);
} else if(typeof Uint8Array != 'undefined' || (Object.prototype.toString.call(buffer) == '[object Array]')) {
this.buffer = writeStringToArray(buffer);
} else {
throw new Error("only String, Buffer, Uint8Array or Array accepted");
}
} else {
this.buffer = buffer;
}
this.position = buffer.length;
} else {
if(typeof Buffer != 'undefined') {
this.buffer = new Buffer(Binary.BUFFER_SIZE);
} else if(typeof Uint8Array != 'undefined'){
this.buffer = new Uint8Array(new ArrayBuffer(Binary.BUFFER_SIZE));
} else {
this.buffer = new Array(Binary.BUFFER_SIZE);
}
// Set position to start of buffer
this.position = 0;
}
}n/a
function length() {
return this.position;
}n/a
function put(byte_value) {
// If it's a string and a has more than one character throw an error
if(byte_value['length'] != null && typeof byte_value != 'number' && byte_value.length != 1) throw new Error("only accepts sing\
le character String, Uint8Array or Array");
if(typeof byte_value != 'number' && byte_value < 0 || byte_value > 255) throw new Error("only accepts number in a valid unsign\
ed byte range 0-255");
// Decode the byte value once
var decoded_byte = null;
if(typeof byte_value == 'string') {
decoded_byte = byte_value.charCodeAt(0);
} else if(byte_value['length'] != null) {
decoded_byte = byte_value[0];
} else {
decoded_byte = byte_value;
}
if(this.buffer.length > this.position) {
this.buffer[this.position++] = decoded_byte;
} else {
if(typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer)) {
// Create additional overflow buffer
var buffer = new Buffer(Binary.BUFFER_SIZE + this.buffer.length);
// Combine the two buffers together
this.buffer.copy(buffer, 0, 0, this.buffer.length);
this.buffer = buffer;
this.buffer[this.position++] = decoded_byte;
} else {
var buffer = null;
// Create a new buffer (typed or normal array)
if(Object.prototype.toString.call(this.buffer) == '[object Uint8Array]') {
buffer = new Uint8Array(new ArrayBuffer(Binary.BUFFER_SIZE + this.buffer.length));
} else {
buffer = new Array(Binary.BUFFER_SIZE + this.buffer.length);
}
// We need to copy all the content to the new array
for(var i = 0; i < this.buffer.length; i++) {
buffer[i] = this.buffer[i];
}
// Reassign the buffer
this.buffer = buffer;
// Write the byte
this.buffer[this.position++] = decoded_byte;
}
}
}n/a
function read(position,
length) {
length = length && length > 0
? length
: this.position;
// Let's return the data based on the type we have
if(this.buffer['slice']) {
return this.buffer.slice(position, position + length);
} else {
// Create a buffer to keep the result
var buffer = typeof Uint8Array != 'undefined' ? new Uint8Array(new ArrayBuffer(length)) : new Array(length);
for(var i = 0; i < length; i++) {
buffer[i] = this.buffer[position++];
}
}
// Return the buffer
return buffer;
}n/a
toJSON = function () {
return this.buffer != null ? this.buffer.toString('base64') : '';
}n/a
toString = function (format) {
return this.buffer != null ? this.buffer.slice(0, this.position).toString(format) : '';
}n/a
function value(asRaw) {
asRaw = asRaw == null ? false : asRaw;
// Optimize to serialize for the situation where the data == size of buffer
if(asRaw && typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer) && this.buffer.length == this.position)
return this.buffer;
// If it's a node.js buffer object
if(typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer)) {
return asRaw ? this.buffer.slice(0, this.position) : this.buffer.toString('binary', 0, this.position);
} else {
if(asRaw) {
// we support the slice command use it
if(this.buffer['slice'] != null) {
return this.buffer.slice(0, this.position);
} else {
// Create a new buffer to copy content to
var newBuffer = Object.prototype.toString.call(this.buffer) == '[object Uint8Array]' ? new Uint8Array(new ArrayBuffer(th\
is.position)) : new Array(this.position);
// Copy content
for(var i = 0; i < this.position; i++) {
newBuffer[i] = this.buffer[i];
}
// Return the buffer
return newBuffer;
}
} else {
return convertArraytoUtf8BinaryString(this.buffer, 0, this.position);
}
}
}n/a
function write(string,
offset) {
offset = typeof offset == 'number' ? offset : this.position;
// If the buffer is to small let's extend the buffer
if(this.buffer.length < offset + string.length) {
var buffer = null;
// If we are in node.js
if(typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer)) {
buffer = new Buffer(this.buffer.length + string.length);
this.buffer.copy(buffer, 0, 0, this.buffer.length);
} else if(Object.prototype.toString.call(this.buffer) == '[object Uint8Array]') {
// Create a new buffer
buffer = new Uint8Array(new ArrayBuffer(this.buffer.length + string.length))
// Copy the content
for(var i = 0; i < this.position; i++) {
buffer[i] = this.buffer[i];
}
}
// Assign the new buffer
this.buffer = buffer;
}
if(typeof Buffer != 'undefined' && Buffer.isBuffer(string) && Buffer.isBuffer(this.buffer)) {
string.copy(this.buffer, offset, 0, string.length);
this.position = (offset + string.length) > this.position ? (offset + string.length) : this.position;
// offset = string.length
} else if(typeof Buffer != 'undefined' && typeof string == 'string' && Buffer.isBuffer(this.buffer)) {
this.buffer.write(string, offset, 'binary');
this.position = (offset + string.length) > this.position ? (offset + string.length) : this.position;
// offset = string.length;
} else if(Object.prototype.toString.call(string) == '[object Uint8Array]'
|| Object.prototype.toString.call(string) == '[object Array]' && typeof string != 'string') {
for(var i = 0; i < string.length; i++) {
this.buffer[offset++] = string[i];
}
this.position = offset > this.position ? offset : this.position;
} else if(typeof string == 'string') {
for(var i = 0; i < string.length; i++) {
this.buffer[offset++] = string.charCodeAt(i);
}
this.position = offset > this.position ? offset : this.position;
}
}n/a
Chunk = function (file,
mongoObject,
writeConcern) {
if(!(this instanceof Chunk)) return new Chunk(file, mongoObject);
this.file = file;
var mongoObjectFinal = mongoObject == null ? {} : mongoObject;
this.writeConcern = writeConcern || {w:1};
this.objectId = mongoObjectFinal._id == null ? new ObjectID() : mongoObjectFinal._id;
this.chunkNumber = mongoObjectFinal.n == null ? 0 : mongoObjectFinal.n;
this.data = new Binary();
if(typeof mongoObjectFinal.data == "string") {
var buffer = new Buffer(mongoObjectFinal.data.length);
buffer.write(mongoObjectFinal.data, 0, mongoObjectFinal.data.length, 'binary');
this.data = new Binary(buffer);
} else if(Array.isArray(mongoObjectFinal.data)) {
buffer = new Buffer(mongoObjectFinal.data.length);
var data = mongoObjectFinal.data.join('');
buffer.write(data, 0, data.length, 'binary');
this.data = new Binary(buffer);
} else if(mongoObjectFinal.data && mongoObjectFinal.data._bsontype === 'Binary') {
this.data = mongoObjectFinal.data;
} else if(!Buffer.isBuffer(mongoObjectFinal.data) && !(mongoObjectFinal.data == null)){
throw Error("Illegal chunk format");
}
// Update position
this.internalPosition = 0;
}n/a
buildMongoObject = function (callback) {
var mongoObject = {
'files_id': this.file.fileId,
'n': this.chunkNumber,
'data': this.data};
// If we are saving using a specific ObjectId
if(this.objectId != null) mongoObject._id = this.objectId;
callback(mongoObject);
}n/a
eof = function () {
return this.internalPosition == this.length() ? true : false;
}n/a
getc = function () {
return this.read(1);
}n/a
length = function () {
return this.data.length();
}n/a
read = function (length) {
// Default to full read if no index defined
length = length == null || length == 0 ? this.length() : length;
if(this.length() - this.internalPosition + 1 >= length) {
var data = this.data.read(this.internalPosition, length);
this.internalPosition = this.internalPosition + length;
return data;
} else {
return '';
}
}n/a
readSlice = function (length) {
if ((this.length() - this.internalPosition) >= length) {
var data = null;
if (this.data.buffer != null) { //Pure BSON
data = this.data.buffer.slice(this.internalPosition, this.internalPosition + length);
} else { //Native BSON
data = new Buffer(length);
length = this.data.readInto(data, this.internalPosition);
}
this.internalPosition = this.internalPosition + length;
return data;
} else {
return null;
}
}n/a
rewind = function () {
this.internalPosition = 0;
this.data = new Binary();
}n/a
save = function (options,
callback) {
var self = this;
if(typeof options == 'function') {
callback = options;
options = {};
}
self.file.chunkCollection(function(err, collection) {
if(err) return callback(err);
// Merge the options
var writeOptions = { upsert: true };
for(var name in options) writeOptions[name] = options[name];
for(name in self.writeConcern) writeOptions[name] = self.writeConcern[name];
if(self.data.length() > 0) {
self.buildMongoObject(function(mongoObject) {
var options = {forceServerObjectId:true};
for(var name in self.writeConcern) {
options[name] = self.writeConcern[name];
}
collection.replaceOne({'_id':self.objectId}, mongoObject, writeOptions, function(err) {
callback(err, self);
});
});
} else {
callback(null, self);
}
// });
});
}n/a
write = function (data,
callback) {
this.data.write(data, this.internalPosition, data.length, 'binary');
this.internalPosition = this.data.length();
if(callback != null) return callback(null, this);
return this;
}n/a
function Code(code,
scope) {
if(!(this instanceof Code)) return new Code(code, scope);
this._bsontype = 'Code';
this.code = code;
this.scope = scope;
}n/a
toJSON = function () {
return {scope:this.scope, code:this.code};
}n/a
Collection = function (db,
topology,
dbName,
name,
pkFactory,
options) {
checkCollectionName(name);
// Unpack variables
var internalHint = null;
var slaveOk = options == null || options.slaveOk == null ? db.slaveOk : options.slaveOk;
var serializeFunctions = options == null || options.serializeFunctions == null ? db.s.options.serializeFunctions : options.ser\
ializeFunctions;
var raw = options == null || options.raw == null ? db.s.options.raw : options.raw;
var promoteLongs = options == null || options.promoteLongs == null ? db.s.options.promoteLongs : options.promoteLongs;
var promoteValues = options == null || options.promoteValues == null ? db.s.options.promoteValues : options.promoteValues;
var promoteBuffers = options == null || options.promoteBuffers == null ? db.s.options.promoteBuffers : options.promoteBuffers;
var readPreference = null;
var collectionHint = null;
var namespace = f("%s.%s", dbName, name);
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Assign the right collection level readPreference
if(options && options.readPreference) {
readPreference = options.readPreference;
} else if(db.options.readPreference) {
readPreference = db.options.readPreference;
}
// Set custom primary key factory if provided
pkFactory = pkFactory == null
? ObjectID
: pkFactory;
// Internal state
this.s = {
// Set custom primary key factory if provided
pkFactory: pkFactory
// Db
, db: db
// Topology
, topology: topology
// dbName
, dbName: dbName
// Options
, options: options
// Namespace
, namespace: namespace
// Read preference
, readPreference: readPreference
// SlaveOK
, slaveOk: slaveOk
// Serialize functions
, serializeFunctions: serializeFunctions
// Raw
, raw: raw
// promoteLongs
, promoteLongs: promoteLongs
// promoteValues
, promoteValues: promoteValues
// promoteBuffers
, promoteBuffers: promoteBuffers
// internalHint
, internalHint: internalHint
// collectionHint
, collectionHint: collectionHint
// Name
, name: name
// Promise library
, promiseLibrary: promiseLibrary
// Read Concern
, readConcern: options.readConcern
}
}n/a
aggregate = function (pipeline,
options,
callback) {
var self = this;
if(Array.isArray(pipeline)) {
// Set up callback if one is provided
if(typeof options == 'function') {
callback = options;
options = {};
}
// If we have no options or callback we are doing
// a cursor based aggregation
if(options == null && callback == null) {
options = {};
}
} else {
// Aggregation pipeline passed as arguments on the method
var args = Array.prototype.slice.call(arguments, 0);
// Get the callback
callback = args.pop();
// Get the possible options object
var opts = args[args.length - 1];
// If it contains any of the admissible options pop it of the args
options = opts && (opts.readPreference
|| opts.explain || opts.cursor || opts.out
|| opts.maxTimeMS || opts.allowDiskUse) ? args.pop() : {};
// Left over arguments is the pipeline
pipeline = args;
}
// Ignore readConcern option
var ignoreReadConcern = false;
// Build the command
var command = { aggregate : this.s.name, pipeline : pipeline};
// If out was specified
if(typeof options.out == 'string') {
pipeline.push({$out: options.out});
// Ignore read concern
ignoreReadConcern = true;
} else if(pipeline.length > 0 && pipeline[pipeline.length - 1]['$out']) {
ignoreReadConcern = true;
}
// Decorate command with writeConcern if out has been specified
if(pipeline.length > 0 && pipeline[pipeline.length - 1]['$out']) {
decorateWithWriteConcern(command, self, options);
}
// Have we specified collation
decorateWithCollation(command, self, options);
// If we have bypassDocumentValidation set
if(typeof options.bypassDocumentValidation == 'boolean') {
command.bypassDocumentValidation = options.bypassDocumentValidation;
}
// Do we have a readConcern specified
if(!ignoreReadConcern && this.s.readConcern) {
command.readConcern = this.s.readConcern;
}
// If we have allowDiskUse defined
if(options.allowDiskUse) command.allowDiskUse = options.allowDiskUse;
if(typeof options.maxTimeMS == 'number') command.maxTimeMS = options.maxTimeMS;
options = shallowClone(options);
// Ensure we have the right read preference inheritance
options = getReadPreference(this, options, this.s.db, this);
// If explain has been specified add it
if(options.explain) command.explain = options.explain;
// Validate that cursor options is valid
if(options.cursor != null && typeof options.cursor != 'object') {
throw toError('cursor options must be an object');
}
// promiseLibrary
options.promiseLibrary = this.s.promiseLibrary;
// Set the AggregationCursor constructor
options.cursorFactory = AggregationCursor;
if(typeof callback != 'function') {
if(!this.s.topology.capabilities()) {
throw new MongoError('cannot connect to server');
}
if(this.s.topology.capabilities().hasAggregationCursor) {
options.cursor = options.cursor || { batchSize : 1000 };
command.cursor = options.cursor;
}
// Allow disk usage command
if(typeof options.allowDiskUse == 'boolean') command.allowDiskUse = options.allowDiskUse;
if(typeof options.maxTimeMS == 'number') command.maxTimeMS = options.maxTimeMS;
// Execute the cursor
return this.s.topology.cursor(this.s.namespace, command, options);
}
// We do not allow cursor
if(options.cursor) {
return this.s.topology.cursor(this.s.namespace, command, options);
}
// Execute the command
this.s.db.command(command, options, function(err, result) {
if(err) {
handleCallback(callback, err);
} else if(result['err'] || result['errmsg']) {
handleCallback(callback, toError(result));
} else if(typeof result == 'object' && result['serverPipeline']) {
handleCallback(callback, null, result['serverPipeline']);
} else if(typeof result == 'object' && result['stages']) {
handleCallback(callback, null, result['stages']);
} else {
handleCallback(callback, null, result.result);
}
});
}n/a
bulkWrite = function (operations,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {ordered:true};
if(!Array.isArray(operations)) {
throw MongoError.create({message: "operations must be an array of documents", driver:true });
}
// Execute using callback
if(typeof callback == 'function') return bulkWrite(self, operations, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
bulkWrite(self, operations, options, function(err, r) {
if(err && r == null) return reject(err);
resolve(r);
});
});
}n/a
count = function (query,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
var queryOption = args.length ? args.shift() || {} : {};
var optionsOption = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return count(self, queryOption, optionsOption, callback);
// Check if query is empty
query = query || {};
options = options || {};
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
count(self, query, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
createIndex = function (fieldOrSpec,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() || {} : {};
options = typeof callback === 'function' ? options : callback;
options = options == null ? {} : options;
// Execute using callback
if(typeof callback == 'function') return createIndex(self, fieldOrSpec, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
createIndex(self, fieldOrSpec, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
createIndexes = function (indexSpecs,
callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return createIndexes(self, indexSpecs, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
createIndexes(self, indexSpecs, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
deleteMany = function (filter,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options);
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return deleteMany(self, filter, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
deleteMany(self, filter, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
deleteOne = function (filter,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options);
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return deleteOne(self, filter, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
deleteOne(self, filter, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}...
Next lets delete the document where the field **a** equals to **3**.
```js
var deleteDocument = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Insert some documents
collection.deleteOne({ a : 3 }, function(err, result) {
assert.equal(err, null);
assert.equal(1, result.result.n);
console.log("Removed the document with the field a equal to 3");
callback(result);
});
}
```
...distinct = function (key,
query,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
var queryOption = args.length ? args.shift() || {} : {};
var optionsOption = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return distinct(self, key, queryOption, optionsOption, callback);
// Ensure the query and options are set
query = query || {};
options = options || {};
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
distinct(self, key, query, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
drop = function (options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Execute using callback
if(typeof callback == 'function') return self.s.db.dropCollection(self.s.name, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.db.dropCollection(self.s.name, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
dropAllIndexes = function (options,
callback) {
var self = this;
// Do we have options
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Execute using callback
if(typeof callback == 'function') return dropIndexes(self, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
dropIndexes(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
dropIndex = function (indexName,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() || {} : {};
// Run only against primary
options.readPreference = ReadPreference.PRIMARY;
// Execute using callback
if(typeof callback == 'function') return dropIndex(self, indexName, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
dropIndex(self, indexName, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
dropIndexes = function (options,
callback) {
var self = this;
// Do we have options
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Execute using callback
if(typeof callback == 'function') return dropIndexes(self, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
dropIndexes(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
ensureIndex = function (fieldOrSpec,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Execute using callback
if(typeof callback == 'function') return ensureIndex(self, fieldOrSpec, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
ensureIndex(self, fieldOrSpec, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
find = function () {
var options
, args = Array.prototype.slice.call(arguments, 0)
, has_callback = typeof args[args.length - 1] === 'function'
, has_weird_callback = typeof args[0] === 'function'
, callback = has_callback ? args.pop() : (has_weird_callback ? args.shift() : null)
, len = args.length
, selector = len >= 1 ? args[0] : {}
, fields = len >= 2 ? args[1] : undefined;
if(len === 1 && has_weird_callback) {
// backwards compat for callback?, options case
selector = {};
options = args[0];
}
if(len === 2 && fields !== undefined && !Array.isArray(fields)) {
var fieldKeys = Object.keys(fields);
var is_option = false;
for(var i = 0; i < fieldKeys.length; i++) {
if(testForFields[fieldKeys[i]] != null) {
is_option = true;
break;
}
}
if(is_option) {
options = fields;
fields = undefined;
} else {
options = {};
}
} else if(len === 2 && Array.isArray(fields) && !Array.isArray(fields[0])) {
var newFields = {};
// Rewrite the array
for(i = 0; i < fields.length; i++) {
newFields[fields[i]] = 1;
}
// Set the fields
fields = newFields;
}
if(3 === len) {
options = args[2];
}
// Ensure selector is not null
selector = selector == null ? {} : selector;
// Validate correctness off the selector
var object = selector;
if(Buffer.isBuffer(object)) {
var object_size = object[0] | object[1] << 8 | object[2] << 16 | object[3] << 24;
if(object_size != object.length) {
var error = new Error("query selector raw message size does not match message header size [" + object.length + "] != [" + \
object_size + "]");
error.name = 'MongoError';
throw error;
}
}
// Validate correctness of the field selector
object = fields;
if(Buffer.isBuffer(object)) {
object_size = object[0] | object[1] << 8 | object[2] << 16 | object[3] << 24;
if(object_size != object.length) {
error = new Error("query fields raw message size does not match message header size [" + object.length + "] != [" + object\
_size + "]");
error.name = 'MongoError';
throw error;
}
}
// Check special case where we are using an objectId
if(selector != null && selector._bsontype == 'ObjectID') {
selector = {_id:selector};
}
// If it's a serialized fields field we need to just let it through
// user be warned it better be good
if(options && options.fields && !(Buffer.isBuffer(options.fields))) {
fields = {};
if(Array.isArray(options.fields)) {
if(!options.fields.length) {
fields['_id'] = 1;
} else {
var l = options.fields.length;
for (i = 0; i < l; i++) {
fields[options.fields[i]] = 1;
}
}
} else {
fields = options.fields;
}
}
if (!options) options = {};
var newOptions = {};
// Make a shallow copy of options
for (var key in options) {
newOptions[key] = options[key];
}
// Unpack options
newOptions.skip = len > 3 ? args[2] : options.skip ? options.skip : 0;
newOptions.limit = len > 3 ? args[3] : options.limit ? options.limit : 0;
newOptions.raw = options.raw != null && typeof options.raw === 'boolean' ? options.raw : this.s.raw;
newOptions.hint = options.hint != null ? normalizeHintField(options.hint) : this.s.collectionHint;
newOptions.timeout = len == 5 ? args[4] : typeof options.timeout === 'undefined' ? undefined : options.timeout;
// // If we have overridden slaveOk otherwise use the default db setting
newOptions.slaveOk = options.slaveOk != null ? options.slaveOk : this.s.db.slaveOk;
// Add read preference if needed
newOptions = getReadPreference(this, newOptions, this.s.db, this);
// Set slave ok to true if read preference different from primary
if(newOptions.readPreference != null
&& (newOptions.readPreference != 'primary' || newOptions.readPreference.mode != 'primary')) {
newOptions.slaveOk = true;
}
// Ensure the query is an object
if(selector != null && typeof selector != 'object') { ......
We will finish up the Quickstart CRUD methods by performing a simple query that returns all the documents matching the query.
```js
var findDocuments = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Find some documents
collection.find({}).toArray(function(err, docs) {
assert.equal(err, null);
assert.equal(2, docs.length);
console.log("Found the following records");
console.dir(docs);
callback(docs);
});
}
...findAndModify = function (query,
sort,
doc,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
sort = args.length ? args.shift() || [] : [];
doc = args.length ? args.shift() : null;
options = args.length ? args.shift() || {} : {};
// Clone options
options = shallowClone(options);
// Force read preference primary
options.readPreference = ReadPreference.PRIMARY;
// Execute using callback
if(typeof callback == 'function') return findAndModify(self, query, sort, doc, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
options = options || {};
findAndModify(self, query, sort, doc, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
findAndRemove = function (query,
sort,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
sort = args.length ? args.shift() || [] : [];
options = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return findAndRemove(self, query, sort, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
findAndRemove(self, query, sort, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
findOne = function () {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
var callback = args.pop();
if(typeof callback != 'function') args.push(callback);
// Execute using callback
if(typeof callback == 'function') return findOne(self, args, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
findOne(self, args, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
findOneAndDelete = function (filter,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Basic validation
if(filter == null || typeof filter != 'object') throw toError('filter parameter must be an object');
// Execute using callback
if(typeof callback == 'function') return findOneAndDelete(self, filter, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
options = options || {};
findOneAndDelete(self, filter, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
findOneAndReplace = function (filter,
replacement,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Basic validation
if(filter == null || typeof filter != 'object') throw toError('filter parameter must be an object');
if(replacement == null || typeof replacement != 'object') throw toError('replacement parameter must be an object');
// Execute using callback
if(typeof callback == 'function') return findOneAndReplace(self, filter, replacement, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
options = options || {};
findOneAndReplace(self, filter, replacement, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
findOneAndUpdate = function (filter,
update,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Basic validation
if(filter == null || typeof filter != 'object') throw toError('filter parameter must be an object');
if(update == null || typeof update != 'object') throw toError('update parameter must be an object');
// Execute using callback
if(typeof callback == 'function') return findOneAndUpdate(self, filter, update, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
options = options || {};
findOneAndUpdate(self, filter, update, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
geoHaystackSearch = function (x,
y,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
// Fetch all commands
options = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return geoHaystackSearch(self, x, y, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
geoHaystackSearch(self, x, y, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
geoNear = function (x,
y,
options,
callback) {
var self = this;
var point = typeof(x) == 'object' && x
, args = Array.prototype.slice.call(arguments, point?1:2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
// Fetch all commands
options = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return geoNear(self, x, y, point, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
geoNear(self, x, y, point, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
group = function (keys,
condition,
initial,
reduce,
finalize,
command,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 3);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
// Fetch all commands
reduce = args.length ? args.shift() : null;
finalize = args.length ? args.shift() : null;
command = args.length ? args.shift() : null;
options = args.length ? args.shift() || {} : {};
// Make sure we are backward compatible
if(!(typeof finalize == 'function')) {
command = finalize;
finalize = null;
}
if (!Array.isArray(keys) && keys instanceof Object && typeof(keys) !== 'function' && !(keys._bsontype == 'Code')) {
keys = Object.keys(keys);
}
if(typeof reduce === 'function') {
reduce = reduce.toString();
}
if(typeof finalize === 'function') {
finalize = finalize.toString();
}
// Set up the command as default
command = command == null ? true : command;
// Execute using callback
if(typeof callback == 'function') return group(self, keys, condition, initial, reduce, finalize, command, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
group(self, keys, condition, initial, reduce, finalize, command, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
indexExists = function (indexes,
callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return indexExists(self, indexes, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
indexExists(self, indexes, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
indexInformation = function (options,
callback) {
var self = this;
// Unpack calls
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return indexInformation(self, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
indexInformation(self, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
indexes = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return indexes(self, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
indexes(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
initializeOrderedBulkOp = function (options) {
options = options || {};
options.promiseLibrary = this.s.promiseLibrary;
return ordered(this.s.topology, this, options);
}n/a
initializeUnorderedBulkOp = function (options) {
options = options || {};
options.promiseLibrary = this.s.promiseLibrary;
return unordered(this.s.topology, this, options);
}n/a
insert = function (docs,
options,
callback) {
if(typeof options == 'function') callback = options, options = {};
options = options || {ordered:false};
docs = !Array.isArray(docs) ? [docs] : docs;
if(options.keepGoing == true) {
options.ordered = false;
}
return this.insertMany(docs, options, callback);
}n/a
insertMany = function (docs,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {ordered:true};
if(!Array.isArray(docs) && typeof callback == 'function') {
return callback(MongoError.create({message: 'docs parameter must be an array of documents', driver:true }));
} else if(!Array.isArray(docs)) {
return new this.s.promiseLibrary(function(resolve, reject) {
reject(MongoError.create({message: 'docs parameter must be an array of documents', driver:true }));
});
}
// Get the write concern options
if(typeof options.checkKeys != 'boolean') {
options.checkKeys = true;
}
// If keep going set unordered
options['serializeFunctions'] = options['serializeFunctions'] || self.s.serializeFunctions;
// Set up the force server object id
var forceServerObjectId = typeof options.forceServerObjectId == 'boolean'
? options.forceServerObjectId : self.s.db.options.forceServerObjectId;
// Do we want to force the server to assign the _id key
if(forceServerObjectId !== true) {
// Add _id if not specified
for(var i = 0; i < docs.length; i++) {
if(docs[i]._id == null) docs[i]._id = self.s.pkFactory.createPk();
}
}
// Generate the bulk write operations
var operations = [{
insertMany: docs
}];
// Execute using callback
if(typeof callback == 'function') return bulkWrite(self, operations, options, function(err, r) {
if(err) return callback(err, r);
callback(null, mapInserManyResults(docs, r));
});
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
bulkWrite(self, operations, options, function(err, r) {
if(err) return reject(err);
resolve(mapInserManyResults(docs, r));
});
});
}...
Let's create a function that will insert some documents for us.
```js
var insertDocuments = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Insert some documents
collection.insertMany([
{a : 1}, {a : 2}, {a : 3}
], function(err, result) {
assert.equal(err, null);
assert.equal(3, result.result.n);
assert.equal(3, result.ops.length);
console.log("Inserted 3 documents into the document collection");
callback(result);
...insertOne = function (doc,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
if(Array.isArray(doc) && typeof callback == 'function') {
return callback(MongoError.create({message: 'doc parameter must be an object', driver:true }));
} else if(Array.isArray(doc)) {
return new this.s.promiseLibrary(function(resolve, reject) {
reject(MongoError.create({message: 'doc parameter must be an object', driver:true }));
});
}
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return insertOne(self, doc, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
insertOne(self, doc, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
isCapped = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return isCapped(self, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
isCapped(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
listIndexes = function (options) {
options = options || {};
// Clone the options
options = shallowClone(options);
// Determine the read preference in the options.
options = getReadPreference(this, options, this.s.db, this);
// Set the CommandCursor constructor
options.cursorFactory = CommandCursor;
// Set the promiseLibrary
options.promiseLibrary = this.s.promiseLibrary;
if(!this.s.topology.capabilities()) {
throw new MongoError('cannot connect to server');
}
// We have a list collections command
if(this.s.topology.capabilities().hasListIndexesCommand) {
// Cursor options
var cursor = options.batchSize ? {batchSize: options.batchSize} : {}
// Build the command
var command = { listIndexes: this.s.name, cursor: cursor };
// Execute the cursor
cursor = this.s.topology.cursor(f('%s.$cmd', this.s.dbName), command, options);
// Do we have a readPreference, apply it
if(options.readPreference) cursor.setReadPreference(options.readPreference);
// Return the cursor
return cursor;
}
// Get the namespace
var ns = f('%s.system.indexes', this.s.dbName);
// Get the query
cursor = this.s.topology.cursor(ns, {find: ns, query: {ns: this.s.namespace}}, options);
// Do we have a readPreference, apply it
if(options.readPreference) cursor.setReadPreference(options.readPreference);
// Set the passed in batch size if one was provided
if(options.batchSize) cursor = cursor.batchSize(options.batchSize);
// Return the cursor
return cursor;
}n/a
mapReduce = function (map,
reduce,
options,
callback) {
var self = this;
if('function' === typeof options) callback = options, options = {};
// Out must allways be defined (make sure we don't break weirdly on pre 1.8+ servers)
if(null == options.out) {
throw new Error("the out option parameter must be defined, see mongodb docs for possible values");
}
if('function' === typeof map) {
map = map.toString();
}
if('function' === typeof reduce) {
reduce = reduce.toString();
}
if('function' === typeof options.finalize) {
options.finalize = options.finalize.toString();
}
// Execute using callback
if(typeof callback == 'function') return mapReduce(self, map, reduce, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
mapReduce(self, map, reduce, options, function(err, r, r1) {
if(err) return reject(err);
if(!r1) return resolve(r);
resolve({results: r, stats: r1});
});
});
}n/a
options = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') return options(self, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
options(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
parallelCollectionScan = function (options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {numCursors: 1};
// Set number of cursors to 1
options.numCursors = options.numCursors || 1;
options.batchSize = options.batchSize || 1000;
options = shallowClone(options);
// Ensure we have the right read preference inheritance
options = getReadPreference(this, options, this.s.db, this);
// Add a promiseLibrary
options.promiseLibrary = this.s.promiseLibrary;
// Execute using callback
if(typeof callback == 'function') return parallelCollectionScan(self, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
parallelCollectionScan(self, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
reIndex = function (options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Execute using callback
if(typeof callback == 'function') return reIndex(self, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
reIndex(self, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
remove = function (selector,
options,
callback) {
var self = this;
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return removeDocuments(self, selector, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
removeDocuments(self, selector, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
removeMany = function (filter,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options);
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return deleteMany(self, filter, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
deleteMany(self, filter, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
removeOne = function (filter,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options);
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return deleteOne(self, filter, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
deleteOne(self, filter, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
rename = function (newName,
opt,
callback) {
var self = this;
if(typeof opt == 'function') callback = opt, opt = {};
opt = assign({}, opt, {readPreference: ReadPreference.PRIMARY});
// Execute using callback
if(typeof callback == 'function') return rename(self, newName, opt, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
rename(self, newName, opt, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
replaceOne = function (filter,
doc,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options)
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return replaceOne(self, filter, doc, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
replaceOne(self, filter, doc, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
save = function (doc,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return save(self, doc, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
save(self, doc, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
stats = function (options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
// Fetch all commands
options = args.length ? args.shift() || {} : {};
// Execute using callback
if(typeof callback == 'function') return stats(self, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
stats(self, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
update = function (selector,
document,
options,
callback) {
var self = this;
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return updateDocuments(self, selector, document, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
updateDocuments(self, selector, document, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
updateMany = function (filter,
update,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options)
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return updateMany(self, filter, update, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
updateMany(self, filter, update, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
updateOne = function (filter,
update,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = shallowClone(options)
// Add ignoreUndfined
if(this.s.options.ignoreUndefined) {
options = shallowClone(options);
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute using callback
if(typeof callback == 'function') return updateOne(self, filter, update, options, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
updateOne(self, filter, update, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}...
Let's look at how to do a simple document update by adding a new field **b** to the document that has the field **a** set t\
o **2**.
```js
var updateDocument = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Update document where a is 2, set b equal to 1
collection.updateOne({ a : 2 }
, { $set: { b : 1 } }, function(err, result) {
assert.equal(err, null);
assert.equal(1, result.result.n);
console.log("Updated the document with the field a equal to 2");
callback(result);
});
}
...CoreConnection = function (messageHandler,
options) {
// Add event listener
EventEmitter.call(this);
// Set empty if no options passed
this.options = options || {};
// Identification information
this.id = _id++;
// Logger instance
this.logger = Logger('Connection', options);
// No bson parser passed in
if(!options.bson) throw new Error("must pass in valid bson parser");
// Get bson parser
this.bson = options.bson;
// Grouping tag used for debugging purposes
this.tag = options.tag;
// Message handler
this.messageHandler = messageHandler;
// Max BSON message size
this.maxBsonMessageSize = options.maxBsonMessageSize || (1024 * 1024 * 16 * 4);
// Debug information
if(this.logger.isDebug()) this.logger.debug(f('creating connection %s with options [%s]', this.id, JSON.stringify(debugOptions\
(debugFields, options))));
// Default options
this.port = options.port || 27017;
this.host = options.host || 'localhost';
this.keepAlive = typeof options.keepAlive == 'boolean' ? options.keepAlive : true;
this.keepAliveInitialDelay = options.keepAliveInitialDelay || 0;
this.noDelay = typeof options.noDelay == 'boolean' ? options.noDelay : true;
this.connectionTimeout = options.connectionTimeout || 0;
this.socketTimeout = options.socketTimeout || 0;
// If connection was destroyed
this.destroyed = false;
// Check if we have a domain socket
this.domainSocket = this.host.indexOf('\/') != -1;
// Serialize commands using function
this.singleBufferSerializtion = typeof options.singleBufferSerializtion == 'boolean' ? options.singleBufferSerializtion : true\
;
this.serializationFunction = this.singleBufferSerializtion ? 'toBinUnified' : 'toBin';
// SSL options
this.ca = options.ca || null;
this.cert = options.cert || null;
this.key = options.key || null;
this.passphrase = options.passphrase || null;
this.ssl = typeof options.ssl == 'boolean' ? options.ssl : false;
this.rejectUnauthorized = typeof options.rejectUnauthorized == 'boolean' ? options.rejectUnauthorized : true;
this.checkServerIdentity = typeof options.checkServerIdentity == 'boolean'
|| typeof options.checkServerIdentity == 'function' ? options.checkServerIdentity : true;
// If ssl not enabled
if(!this.ssl) this.rejectUnauthorized = false;
// Response options
this.responseOptions = {
promoteLongs: typeof options.promoteLongs == 'boolean' ? options.promoteLongs : true,
promoteValues: typeof options.promoteValues == 'boolean' ? options.promoteValues : true,
promoteBuffers: typeof options.promoteBuffers == 'boolean' ? options.promoteBuffers: false
}
// Flushing
this.flushing = false;
this.queue = [];
// Internal state
this.connection = null;
this.writeStream = null;
// Create hash method
var hash = crypto.createHash('sha1');
hash.update(f('%s:%s', this.host, this.port));
// Create a hash name
this.hashedName = hash.digest('hex');
// All operations in flight on the connection
this.workItems = [];
}n/a
connections = function () {
return connections;
}n/a
disableConnectionAccounting = function () {
connectionAccounting = false;
}n/a
enableConnectionAccounting = function () {
connectionAccounting = true;
connections = {};
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
connect = function (_options) {
var self = this;
_options = _options || {};
// Set the connections
if(connectionAccounting) addConnection(this.id, this);
// Check if we are overriding the promoteLongs
if(typeof _options.promoteLongs == 'boolean') {
self.responseOptions.promoteLongs = _options.promoteLongs;
self.responseOptions.promoteValues = _options.promoteValues;
self.responseOptions.promoteBuffers = _options.promoteBuffers;
}
// Create new connection instance
self.connection = self.domainSocket
? net.createConnection(self.host)
: net.createConnection(self.port, self.host);
// Set the options for the connection
self.connection.setKeepAlive(self.keepAlive, self.keepAliveInitialDelay);
self.connection.setTimeout(self.connectionTimeout);
self.connection.setNoDelay(self.noDelay);
// If we have ssl enabled
if(self.ssl) {
var sslOptions = {
socket: self.connection
, rejectUnauthorized: self.rejectUnauthorized
}
// Merge in options
merge(sslOptions, this.options);
merge(sslOptions, _options);
// Set options for ssl
if(self.ca) sslOptions.ca = self.ca;
if(self.cert) sslOptions.cert = self.cert;
if(self.key) sslOptions.key = self.key;
if(self.passphrase) sslOptions.passphrase = self.passphrase;
// Override checkServerIdentity behavior
if(self.checkServerIdentity == false) {
// Skip the identiy check by retuning undefined as per node documents
// https://nodejs.org/api/tls.html#tls_tls_connect_options_callback
sslOptions.checkServerIdentity = function() {
return undefined;
}
} else if(typeof self.checkServerIdentity == 'function') {
sslOptions.checkServerIdentity = self.checkServerIdentity;
}
// Set default sni servername to be the same as host
if(sslOptions.servername == null) {
sslOptions.servername = self.host;
}
// Attempt SSL connection
self.connection = tls.connect(self.port, self.host, sslOptions, function() {
// Error on auth or skip
if(self.connection.authorizationError && self.rejectUnauthorized) {
return self.emit("error", self.connection.authorizationError, self, {ssl:true});
}
// Set socket timeout instead of connection timeout
self.connection.setTimeout(self.socketTimeout);
// We are done emit connect
self.emit('connect', self);
});
self.connection.setTimeout(self.connectionTimeout);
} else {
self.connection.on('connect', function() {
// Set socket timeout instead of connection timeout
self.connection.setTimeout(self.socketTimeout);
// Emit connect event
self.emit('connect', self);
});
}
// Add handlers for events
self.connection.once('error', errorHandler(self));
self.connection.once('timeout', timeoutHandler(self));
self.connection.once('close', closeHandler(self));
self.connection.on('data', dataHandler(self));
}...
```js
var MongoClient = require('mongodb').MongoClient
, assert = require('assert');
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
...destroy = function () {
// Set the connections
if(connectionAccounting) deleteConnection(this.id);
if(this.connection) {
this.connection.end();
this.connection.destroy();
}
this.destroyed = true;
}n/a
isConnected = function () {
if(this.destroyed) return false;
return !this.connection.destroyed && this.connection.writable;
}n/a
resetSocketTimeout = function () {
if(this.connection) {
this.connection.setTimeout(this.socketTimeout);
}
}n/a
setSocketTimeout = function (value) {
if(this.connection) {
this.connection.setTimeout(value);
}
}n/a
toJSON = function () {
return {id: this.id, host: this.host, port: this.port};
}n/a
toString = function () {
return "" + this.id;
}n/a
unref = function () {
if (this.connection) this.connection.unref();
else {
var self = this;
this.once('connect', function() {
self.connection.unref();
});
}
}n/a
write = function (buffer) {
var i;
// Debug Log
if(this.logger.isDebug()) {
if(!Array.isArray(buffer)) {
this.logger.debug(f('writing buffer [%s] to %s:%s', buffer.toString('hex'), this.host, this.port));
} else {
for(i = 0; i < buffer.length; i++)
this.logger.debug(f('writing buffer [%s] to %s:%s', buffer[i].toString('hex'), this.host, this.port));
}
}
// Write out the command
if(!Array.isArray(buffer)) return this.connection.write(buffer, 'binary');
// Iterate over all buffers and write them in order to the socket
for(i = 0; i < buffer.length; i++) this.connection.write(buffer[i], 'binary');
}n/a
CoreServer = function (options) {
options = options || {};
// Add event listener
EventEmitter.call(this);
// Server instance id
this.id = id++;
// Internal state
this.s = {
// Options
options: options,
// Logger
logger: Logger('Server', options),
// Factory overrides
Cursor: options.cursorFactory || BasicCursor,
// BSON instance
bson: options.bson || new BSON([BSON.Binary, BSON.Code, BSON.DBRef, BSON.Decimal128,
BSON.Double, BSON.Int32, BSON.Long, BSON.Map, BSON.MaxKey, BSON.MinKey,
BSON.ObjectId, BSON.BSONRegExp, BSON.Symbol, BSON.Timestamp]),
// Pool
pool: null,
// Disconnect handler
disconnectHandler: options.disconnectHandler,
// Monitor thread (keeps the connection alive)
monitoring: typeof options.monitoring == 'boolean' ? options.monitoring : true,
// Is the server in a topology
inTopology: typeof options.inTopology == 'boolean' ? options.inTopology : false,
// Monitoring timeout
monitoringInterval: typeof options.monitoringInterval == 'number'
? options.monitoringInterval
: 5000,
// Topology id
topologyId: -1
}
// Curent ismaster
this.ismaster = null;
// Current ping time
this.lastIsMasterMS = -1;
// The monitoringProcessId
this.monitoringProcessId = null;
// Initial connection
this.initalConnect = true;
// Wire protocol handler, default to oldest known protocol handler
// this gets changed when the first ismaster is called.
this.wireProtocolHandler = new PreTwoSixWireProtocolSupport();
// Default type
this._type = 'server';
// Set the client info
this.clientInfo = createClientInfo(options);
// Max Stalleness values
// last time we updated the ismaster state
this.lastUpdateTime = 0;
// Last write time
this.lastWriteDate = 0;
// Stalleness
this.staleness = 0;
}n/a
disableServerAccounting = function () {
serverAccounting = false;
}n/a
enableServerAccounting = function () {
serverAccounting = true;
servers = {};
}n/a
servers = function () {
return servers;
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
auth = function (mechanism,
db) {
var self = this;
// If we have the default mechanism we pick mechanism based on the wire
// protocol max version. If it's >= 3 then scram-sha1 otherwise mongodb-cr
if(mechanism == 'default' && self.ismaster && self.ismaster.maxWireVersion >= 3) {
mechanism = 'scram-sha-1';
} else if(mechanism == 'default') {
mechanism = 'mongocr';
}
// Slice all the arguments off
var args = Array.prototype.slice.call(arguments, 0);
// Set the mechanism
args[0] = mechanism;
// Get the callback
var callback = args[args.length - 1];
// If we are not connected or have a disconnectHandler specified
if(disconnectHandler(self, 'auth', db, args, {}, callback)) {
return;
}
// Do not authenticate if we are an arbiter
if(this.lastIsMaster() && this.lastIsMaster().arbiterOnly) {
return callback(null, true);
}
// Apply the arguments to the pool
self.s.pool.auth.apply(self.s.pool, args);
}n/a
command = function (ns,
cmd,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {}, options = options || {};
var result = basicReadValidations(self, options);
if(result) return callback(result);
// Debug log
if(self.s.logger.isDebug()) self.s.logger.debug(f('executing command [%s] against %s', JSON.stringify({
ns: ns, cmd: cmd, options: debugOptions(debugFields, options)
}), self.name));
// If we are not connected or have a disconnectHandler specified
if(disconnectHandler(self, 'command', ns, cmd, options, callback)) return;
// Check if we have collation support
if(this.ismaster && this.ismaster.maxWireVersion < 5 && cmd.collation) {
return callback(new MongoError(f('server %s does not support collation', this.name)));
}
// Query options
var queryOptions = {
numberToSkip: 0,
numberToReturn: -1,
checkKeys: typeof options.checkKeys == 'boolean' ? options.checkKeys: false,
serializeFunctions: typeof options.serializeFunctions == 'boolean' ? options.serializeFunctions : false,
ignoreUndefined: typeof options.ignoreUndefined == 'boolean' ? options.ignoreUndefined : false
};
// Create a query instance
var query = new Query(self.s.bson, ns, cmd, queryOptions);
// Set slave OK of the query
query.slaveOk = options.readPreference ? options.readPreference.slaveOk() : false;
// Write options
var writeOptions = {
raw: typeof options.raw == 'boolean' ? options.raw : false,
promoteLongs: typeof options.promoteLongs == 'boolean' ? options.promoteLongs : true,
promoteValues: typeof options.promoteValues == 'boolean' ? options.promoteValues : true,
promoteBuffers: typeof options.promoteBuffers == 'boolean' ? options.promoteBuffers : false,
command: true,
monitoring: typeof options.monitoring == 'boolean' ? options.monitoring : false,
fullResult: typeof options.fullResult == 'boolean' ? options.fullResult : false,
requestId: query.requestId,
socketTimeout: typeof options.socketTimeout == 'number' ? options.socketTimeout : null,
};
// Write the operation to the pool
self.s.pool.write(query, writeOptions, callback);
}n/a
connect = function (options) {
var self = this;
options = options || {};
// Set the connections
if(serverAccounting) servers[this.id] = this;
// Do not allow connect to be called on anything that's not disconnected
if(self.s.pool && !self.s.pool.isDisconnected() && !self.s.pool.isDestroyed()) {
throw MongoError.create(f('server instance in invalid state %s', self.s.state));
}
// Create a pool
self.s.pool = new Pool(assign(self.s.options, options, {bson: this.s.bson}));
// Set up listeners
self.s.pool.on('close', eventHandler(self, 'close'));
self.s.pool.on('error', eventHandler(self, 'error'));
self.s.pool.on('timeout', eventHandler(self, 'timeout'));
self.s.pool.on('parseError', eventHandler(self, 'parseError'));
self.s.pool.on('connect', eventHandler(self, 'connect'));
self.s.pool.on('reconnect', eventHandler(self, 'reconnect'));
self.s.pool.on('reconnectFailed', eventHandler(self, 'reconnectFailed'));
// Emit toplogy opening event if not in topology
if(!self.s.inTopology) {
this.emit('topologyOpening', { topologyId: self.id });
}
// Emit opening server event
self.emit('serverOpening', {
topologyId: self.s.topologyId != -1 ? self.s.topologyId : self.id,
address: self.name
});
// Connect with optional auth settings
if(options.auth) {
self.s.pool.connect.apply(self.s.pool, options.auth);
} else {
self.s.pool.connect();
}
}...
```js
var MongoClient = require('mongodb').MongoClient
, assert = require('assert');
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
...connections = function () {
return this.s.pool.allConnections();
}n/a
cursor = function (ns,
cmd,
cursorOptions) {
var s = this.s;
cursorOptions = cursorOptions || {};
// Set up final cursor type
var FinalCursor = cursorOptions.cursorFactory || s.Cursor;
// Return the cursor
return new FinalCursor(s.bson, ns, cmd, cursorOptions, this, s.options);
}n/a
destroy = function (options) {
options = options || {};
var self = this;
// Set the connections
if(serverAccounting) delete servers[this.id];
// Destroy the monitoring process if any
if(this.monitoringProcessId) {
clearTimeout(this.monitoringProcessId);
}
// Emit close event
if(options.emitClose) {
self.emit('close', self);
}
// Emit destroy event
if(options.emitDestroy) {
self.emit('destroy', self);
}
// Remove all listeners
listeners.forEach(function(event) {
self.s.pool.removeAllListeners(event);
});
// Emit opening server event
if(self.listeners('serverClosed').length > 0) self.emit('serverClosed', {
topologyId: self.s.topologyId != -1 ? self.s.topologyId : self.id, address: self.name
});
// Emit toplogy opening event if not in topology
if(self.listeners('topologyClosed').length > 0 && !self.s.inTopology) {
self.emit('topologyClosed', { topologyId: self.id });
}
if(self.s.logger.isDebug()) {
self.s.logger.debug(f('destroy called on server %s', self.name));
}
// Destroy the pool
this.s.pool.destroy(options.force);
}n/a
equals = function (server) {
if(typeof server == 'string') return this.name == server;
if(server.name) return this.name == server.name;
return false;
}n/a
getConnection = function () {
return this.s.pool.get();
}n/a
getDescription = function () {
var ismaster = this.ismaster || {};
var description = {
type: sdam.getTopologyType(this),
address: this.name,
};
// Add fields if available
if(ismaster.hosts) description.hosts = ismaster.hosts;
if(ismaster.arbiters) description.arbiters = ismaster.arbiters;
if(ismaster.passives) description.passives = ismaster.passives;
if(ismaster.setName) description.setName = ismaster.setName;
return description;
}n/a
getServer = function () {
return this;
}n/a
insert = function (ns,
ops,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {}, options = options || {};
var result = basicWriteValidations(self, options);
if(result) return callback(result);
// If we are not connected or have a disconnectHandler specified
if(disconnectHandler(self, 'insert', ns, ops, options, callback)) return;
// Setup the docs as an array
ops = Array.isArray(ops) ? ops : [ops];
// Execute write
return self.wireProtocolHandler.insert(self.s.pool, self.ismaster, ns, self.s.bson, ops, options, callback);
}n/a
isConnected = function () {
if(!this.s.pool) return false;
return this.s.pool.isConnected();
}n/a
isDestroyed = function () {
if(!this.s.pool) return false;
return this.s.pool.isDestroyed();
}n/a
lastIsMaster = function () {
return this.ismaster;
}n/a
logout = function (dbName,
callback) {
this.s.pool.logout(dbName, callback);
}n/a
remove = function (ns,
ops,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {}, options = options || {};
var result = basicWriteValidations(self, options);
if(result) return callback(result);
// If we are not connected or have a disconnectHandler specified
if(disconnectHandler(self, 'remove', ns, ops, options, callback)) return;
// Check if we have collation support
if(this.ismaster && this.ismaster.maxWireVersion < 5 && options.collation) {
return callback(new MongoError(f('server %s does not support collation', this.name)));
}
// Setup the docs as an array
ops = Array.isArray(ops) ? ops : [ops];
// Execute write
return self.wireProtocolHandler.remove(self.s.pool, self.ismaster, ns, self.s.bson, ops, options, callback);
}n/a
unref = function () {
this.s.pool.unref();
}n/a
update = function (ns,
ops,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {}, options = options || {};
var result = basicWriteValidations(self, options);
if(result) return callback(result);
// If we are not connected or have a disconnectHandler specified
if(disconnectHandler(self, 'update', ns, ops, options, callback)) return;
// Check if we have collation support
if(this.ismaster && this.ismaster.maxWireVersion < 5 && options.collation) {
return callback(new MongoError(f('server %s does not support collation', this.name)));
}
// Setup the docs as an array
ops = Array.isArray(ops) ? ops : [ops];
// Execute write
return self.wireProtocolHandler.update(self.s.pool, self.ismaster, ns, self.s.bson, ops, options, callback);
}n/a
Cursor = function (bson,
ns,
cmd,
options,
topology,
topologyOptions) {
CoreCursor.apply(this, Array.prototype.slice.call(arguments, 0));
var self = this;
var state = Cursor.INIT;
var streamOptions = {};
// Tailable cursor options
var numberOfRetries = options.numberOfRetries || 5;
var tailableRetryInterval = options.tailableRetryInterval || 500;
var currentNumberOfRetries = numberOfRetries;
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Set up
Readable.call(this, {objectMode: true});
// Internal cursor state
this.s = {
// Tailable cursor options
numberOfRetries: numberOfRetries
, tailableRetryInterval: tailableRetryInterval
, currentNumberOfRetries: currentNumberOfRetries
// State
, state: state
// Stream options
, streamOptions: streamOptions
// BSON
, bson: bson
// Namespace
, ns: ns
// Command
, cmd: cmd
// Options
, options: options
// Topology
, topology: topology
// Topology options
, topologyOptions: topologyOptions
// Promise library
, promiseLibrary: promiseLibrary
// Current doc
, currentDoc: null
}
// Translate correctly
if(self.s.options.noCursorTimeout == true) {
self.addCursorFlag('noCursorTimeout', true);
}
// Set the sort value
this.sortValue = self.s.cmd.sort;
}n/a
function Readable(options) {
if (!(this instanceof Readable))
return new Readable(options);
this._readableState = new ReadableState(options, this);
// legacy
this.readable = true;
if (options && typeof options.read === 'function')
this._read = options.read;
Stream.call(this);
}n/a
addCursorFlag = function (flag,
value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
if(flags.indexOf(flag) == -1) throw MongoError.create({message: f("flag %s not a supported flag %s", flag, flags), driver:true\
});
if(typeof value != 'boolean') throw MongoError.create({message: f("flag %s must be a boolean value", flag), driver:true});
this.s.cmd[flag] = value;
return this;
}n/a
addQueryModifier = function (name,
value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
if(name[0] != '$') throw MongoError.create({message: f("%s is not a valid query modifier"), driver:true});
// Strip of the $
var field = name.substr(1);
// Set on the command
this.s.cmd[field] = value;
// Deal with the special case for sort
if(field == 'orderby') this.s.cmd.sort = this.s.cmd[field];
return this;
}n/a
batchSize = function (value) {
if(this.s.options.tailable) throw MongoError.create({message: "Tailable cursor doesn't support batchSize", driver:true});
if(this.s.state == Cursor.CLOSED || this.isDead()) throw MongoError.create({message: "Cursor is closed", driver:true});
if(typeof value != 'number') throw MongoError.create({message: "batchSize requires an integer", driver:true});
this.s.cmd.batchSize = value;
this.setCursorBatchSize(value);
return this;
}n/a
bufferedCount = function () {
return this.cursorState.documents.length - this.cursorState.cursorIndex;
}n/a
clone = function () {
return this.topology.cursor(this.ns, this.cmd, this.options);
}n/a
close = function (callback) {
this.s.state = Cursor.CLOSED;
// Kill the cursor
this.kill();
// Emit the close event for the cursor
this.emit('close');
// Callback if provided
if(typeof callback == 'function') return handleCallback(callback, null, this);
// Return a Promise
return new this.s.promiseLibrary(function(resolve) {
resolve();
});
}...
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
Given that you booted up the **mongod** process earlier the application should connect successfully and print **Connected correc\
tly to server** to the console.
Let's Add some code to show the different CRUD operations available.
...collation = function (value) {
this.s.cmd.collation = value;
return this;
}n/a
comment = function (value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.comment = value;
return this;
}n/a
count = function (applySkipLimit,
opts,
callback) {
var self = this;
if(self.s.cmd.query == null) throw MongoError.create({message: "count can only be used with find command", driver:true});
if(typeof opts == 'function') callback = opts, opts = {};
opts = opts || {};
// Execute using callback
if(typeof callback == 'function') return count(self, applySkipLimit, opts, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
count(self, applySkipLimit, opts, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
cursorBatchSize = function () {
return this.cursorState.batchSize;
}n/a
cursorLimit = function () {
return this.cursorState.limit;
}n/a
cursorSkip = function () {
return this.cursorState.skip;
}n/a
destroy = function (err) {
if(err) this.emit('error', err);
this.pause();
this.close();
}n/a
each = function (callback) {
// Rewind cursor state
this.rewind();
// Set current cursor to INIT
this.s.state = Cursor.INIT;
// Run the query
_each(this, callback);
}n/a
explain = function (callback) {
var self = this;
this.s.cmd.explain = true;
// Do we have a readConcern
if(this.s.cmd.readConcern) {
delete this.s.cmd['readConcern'];
}
// Execute using callback
if(typeof callback == 'function') return this._next(callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
self._next(function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
filter = function (filter) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.query = filter;
return this;
}n/a
forEach = function (iterator,
callback) {
this.each(function(err, doc){
if(err) { callback(err); return false; }
if(doc != null) { iterator(doc); return true; }
if(doc == null && callback) {
var internalCallback = callback;
callback = null;
internalCallback(null);
return false;
}
});
}n/a
hasNext = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') {
if(self.s.currentDoc){
return callback(null, true);
} else {
return nextObject(self, function(err, doc) {
if(!doc) return callback(null, false);
self.s.currentDoc = doc;
callback(null, true);
});
}
}
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
if(self.s.currentDoc){
resolve(true);
} else {
nextObject(self, function(err, doc) {
if(self.s.state == Cursor.CLOSED || self.isDead()) return resolve(false);
if(err) return reject(err);
if(!doc) return resolve(false);
self.s.currentDoc = doc;
resolve(true);
});
}
});
}n/a
hint = function (hint) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.hint = hint;
return this;
}n/a
isClosed = function () {
return this.isDead();
}n/a
isDead = function () {
return this.cursorState.dead == true;
}n/a
isKilled = function () {
return this.cursorState.killed == true;
}n/a
isNotified = function () {
return this.cursorState.notified == true;
}n/a
kill = function (callback) {
this._killcursor(callback);
}n/a
limit = function (value) {
if(this.s.options.tailable) throw MongoError.create({message: "Tailable cursor doesn't support limit", driver:true});
if(this.s.state == Cursor.OPEN || this.s.state == Cursor.CLOSED || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
if(typeof value != 'number') throw MongoError.create({message: "limit requires an integer", driver:true});
this.s.cmd.limit = value;
// this.cursorLimit = value;
this.setCursorLimit(value);
return this;
}n/a
map = function (transform) {
this.cursorState.transforms = { doc: transform };
return this;
}n/a
max = function (max) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.max = max;
return this;
}n/a
maxAwaitTimeMS = function (value) {
if(typeof value != 'number') throw MongoError.create({message: "maxAwaitTimeMS must be a number", driver:true});
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.maxAwaitTimeMS = value;
return this;
}n/a
maxScan = function (maxScan) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.maxScan = maxScan;
return this;
}n/a
maxTimeMS = function (value) {
if(typeof value != 'number') throw MongoError.create({message: "maxTimeMS must be a number", driver:true});
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.maxTimeMS = value;
return this;
}n/a
maxTimeMs = function (value) {
if(typeof value != 'number') throw MongoError.create({message: "maxTimeMS must be a number", driver:true});
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.maxTimeMS = value;
return this;
}n/a
min = function (min) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.min = min;
return this;
}n/a
next = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') {
// Return the currentDoc if someone called hasNext first
if(self.s.currentDoc) {
var doc = self.s.currentDoc;
self.s.currentDoc = null;
return callback(null, doc);
}
// Return the next object
return nextObject(self, callback)
}
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
// Return the currentDoc if someone called hasNext first
if(self.s.currentDoc) {
var doc = self.s.currentDoc;
self.s.currentDoc = null;
return resolve(doc);
}
nextObject(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
nextObject = function (callback) {
var self = this;
// Execute using callback
if(typeof callback == 'function') {
// Return the currentDoc if someone called hasNext first
if(self.s.currentDoc) {
var doc = self.s.currentDoc;
self.s.currentDoc = null;
return callback(null, doc);
}
// Return the next object
return nextObject(self, callback)
}
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
// Return the currentDoc if someone called hasNext first
if(self.s.currentDoc) {
var doc = self.s.currentDoc;
self.s.currentDoc = null;
return resolve(doc);
}
nextObject(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
project = function (value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.fields = value;
return this;
}n/a
readBufferedDocuments = function (number) {
var unreadDocumentsLength = this.cursorState.documents.length - this.cursorState.cursorIndex;
var length = number < unreadDocumentsLength ? number : unreadDocumentsLength;
var elements = this.cursorState.documents.slice(this.cursorState.cursorIndex, this.cursorState.cursorIndex + length);
// Transform the doc with passed in transformation method if provided
if(this.cursorState.transforms && typeof this.cursorState.transforms.doc == 'function') {
// Transform all the elements
for(var i = 0; i < elements.length; i++) {
elements[i] = this.cursorState.transforms.doc(elements[i]);
}
}
// Ensure we do not return any more documents than the limit imposed
// Just return the number of elements up to the limit
if(this.cursorState.limit > 0 && (this.cursorState.currentLimit + elements.length) > this.cursorState.limit) {
elements = elements.slice(0, (this.cursorState.limit - this.cursorState.currentLimit));
this.kill();
}
// Adjust current limit
this.cursorState.currentLimit = this.cursorState.currentLimit + elements.length;
this.cursorState.cursorIndex = this.cursorState.cursorIndex + elements.length;
// Return elements
return elements;
}n/a
returnKey = function (value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.returnKey = value;
return this;
}n/a
rewind = function () {
if(this.cursorState.init) {
if(!this.cursorState.dead) {
this.kill();
}
this.cursorState.currentLimit = 0;
this.cursorState.init = false;
this.cursorState.dead = false;
this.cursorState.killed = false;
this.cursorState.notified = false;
this.cursorState.documents = [];
this.cursorState.cursorId = null;
this.cursorState.cursorIndex = 0;
}
}n/a
setCursorBatchSize = function (value) {
this.cursorState.batchSize = value;
}n/a
setCursorLimit = function (value) {
this.cursorState.limit = value;
}n/a
setCursorOption = function (field,
value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
if(fields.indexOf(field) == -1) throw MongoError.create({message: f("option %s not a supported option %s", field, fields), dri\
ver:true });
this.s[field] = value;
if(field == 'numberOfRetries')
this.s.currentNumberOfRetries = value;
return this;
}n/a
setCursorSkip = function (value) {
this.cursorState.skip = value;
}n/a
setReadPreference = function (r) {
if(this.s.state != Cursor.INIT) throw MongoError.create({message: 'cannot change cursor readPreference after cursor has been a\
ccessed', driver:true});
if(r instanceof ReadPreference) {
this.s.options.readPreference = new CoreReadPreference(r.mode, r.tags, {maxStalenessSeconds: r.maxStalenessSeconds});
} else if(typeof r == 'string'){
this.s.options.readPreference = new CoreReadPreference(r);
} else if(r instanceof CoreReadPreference) {
this.s.options.readPreference = r;
}
return this;
}n/a
showRecordId = function (value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.showDiskLoc = value;
return this;
}n/a
skip = function (value) {
if(this.s.options.tailable) throw MongoError.create({message: "Tailable cursor doesn't support skip", driver:true});
if(this.s.state == Cursor.OPEN || this.s.state == Cursor.CLOSED || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
if(typeof value != 'number') throw MongoError.create({message: "skip requires an integer", driver:true});
this.s.cmd.skip = value;
this.setCursorSkip(value);
return this;
}n/a
snapshot = function (value) {
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
this.s.cmd.snapshot = value;
return this;
}n/a
sort = function (keyOrList,
direction) {
if(this.s.options.tailable) throw MongoError.create({message: "Tailable cursor doesn't support sorting", driver:true});
if(this.s.state == Cursor.CLOSED || this.s.state == Cursor.OPEN || this.isDead()) throw MongoError.create({message: "Cursor is\
closed", driver:true});
var order = keyOrList;
// We have an array of arrays, we need to preserve the order of the sort
// so we will us a Map
if(Array.isArray(order) && Array.isArray(order[0])) {
order = new Map(order.map(function(x) {
var value = [x[0], null];
if(x[1] == 'asc') {
value[1] = 1;
} else if(x[1] == 'desc') {
value[1] = -1;
} else if(x[1] == 1 || x[1] == -1) {
value[1] = x[1];
} else {
throw new MongoError("Illegal sort clause, must be of the form [['field1', '(ascending|descending)'], ['field2', '(ascen\
ding|descending)']]");
}
return value;
}));
}
if(direction != null) {
order = [[keyOrList, direction]];
}
this.s.cmd.sort = order;
this.sortValue = order;
return this;
}n/a
stream = function (options) {
this.s.streamOptions = options || {};
return this;
}n/a
toArray = function (callback) {
var self = this;
if(self.s.options.tailable) throw MongoError.create({message: 'Tailable cursor cannot be converted to array', driver:true});
// Execute using callback
if(typeof callback == 'function') return toArray(self, callback);
// Return a Promise
return new this.s.promiseLibrary(function(resolve, reject) {
toArray(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}...
We will finish up the Quickstart CRUD methods by performing a simple query that returns all the documents matching the query.
```js
var findDocuments = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Find some documents
collection.find({}).toArray(function(err, docs) {
assert.equal(err, null);
assert.equal(2, docs.length);
console.log("Found the following records");
console.dir(docs);
callback(docs);
});
}
...function DBRef(namespace,
oid,
db) {
if(!(this instanceof DBRef)) return new DBRef(namespace, oid, db);
this._bsontype = 'DBRef';
this.namespace = namespace;
this.oid = oid;
this.db = db;
}n/a
toJSON = function () {
return {
'$ref':this.namespace,
'$id':this.oid,
'$db':this.db == null ? '' : this.db
};
}n/a
Db = function (databaseName,
topology,
options) {
options = options || {};
if(!(this instanceof Db)) return new Db(databaseName, topology, options);
EventEmitter.call(this);
var self = this;
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Filter the options
options = filterOptions(options, legalOptionNames);
// Ensure we put the promiseLib in the options
options.promiseLibrary = promiseLibrary;
// var self = this; // Internal state of the db object
this.s = {
// Database name
databaseName: databaseName
// DbCache
, dbCache: {}
// Children db's
, children: []
// Topology
, topology: topology
// Options
, options: options
// Logger instance
, logger: Logger('Db', options)
// Get the bson parser
, bson: topology ? topology.bson : null
// Authsource if any
, authSource: options.authSource
// Unpack read preference
, readPreference: options.readPreference
// Set buffermaxEntries
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : -1
// Parent db (if chained)
, parentDb: options.parentDb || null
// Set up the primary key factory or fallback to ObjectID
, pkFactory: options.pkFactory || ObjectID
// Get native parser
, nativeParser: options.nativeParser || options.native_parser
// Promise library
, promiseLibrary: promiseLibrary
// No listener
, noListener: typeof options.noListener == 'boolean' ? options.noListener : false
// ReadConcern
, readConcern: options.readConcern
}
// Ensure we have a valid db name
validateDatabaseName(self.s.databaseName);
// Add a read Only property
getSingleProperty(this, 'serverConfig', self.s.topology);
getSingleProperty(this, 'bufferMaxEntries', self.s.bufferMaxEntries);
getSingleProperty(this, 'databaseName', self.s.databaseName);
// This is a child db, do not register any listeners
if(options.parentDb) return;
if(this.s.noListener) return;
// Add listeners
topology.on('error', createListener(self, 'error', self));
topology.on('timeout', createListener(self, 'timeout', self));
topology.on('close', createListener(self, 'close', self));
topology.on('parseError', createListener(self, 'parseError', self));
topology.once('open', createListener(self, 'open', self));
topology.once('fullsetup', createListener(self, 'fullsetup', self));
topology.once('all', createListener(self, 'all', self));
topology.on('reconnect', createListener(self, 'reconnect', self));
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
addChild = function (db) {
if(this.s.parentDb) return this.s.parentDb.addChild(db);
this.s.children.push(db);
}n/a
addUser = function (username,
password,
options,
callback) {
// Unpack the parameters
var self = this;
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() || {} : {};
// If we have a callback fallback
if(typeof callback == 'function') return addUser(self, username, password, options, callback);
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
addUser(self, username, password, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
admin = function () {
return new Admin(this, this.s.topology, this.s.promiseLibrary);
}n/a
authenticate = function (username,
password,
options,
callback) {
if(typeof options == 'function') callback = options, options = {};
var self = this;
// Shallow copy the options
options = shallowClone(options);
// Set default mechanism
if(!options.authMechanism) {
options.authMechanism = 'DEFAULT';
} else if(options.authMechanism != 'GSSAPI'
&& options.authMechanism != 'DEFAULT'
&& options.authMechanism != 'MONGODB-CR'
&& options.authMechanism != 'MONGODB-X509'
&& options.authMechanism != 'SCRAM-SHA-1'
&& options.authMechanism != 'PLAIN') {
return handleCallback(callback, MongoError.create({message: "only DEFAULT, GSSAPI, PLAIN, MONGODB-X509, SCRAM-SHA-1 or MON\
GODB-CR is supported by authMechanism", driver:true}));
}
// If we have a callback fallback
if(typeof callback == 'function') return authenticate(self, username, password, options, function(err, r) {
// Support failed auth method
if(err && err.message && err.message.indexOf('saslStart') != -1) err.code = 59;
// Reject error
if(err) return callback(err, r);
callback(null, r);
});
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
authenticate(self, username, password, options, function(err, r) {
// Support failed auth method
if(err && err.message && err.message.indexOf('saslStart') != -1) err.code = 59;
// Reject error
if(err) return reject(err);
resolve(r);
});
});
}n/a
close = function (force,
callback) {
if(typeof force == 'function') callback = force, force = false;
this.s.topology.close(force);
var self = this;
// Fire close event if any listeners
if(this.listeners('close').length > 0) {
this.emit('close');
// If it's the top level db emit close on all children
if(this.parentDb == null) {
// Fire close on all children
for(var i = 0; i < this.s.children.length; i++) {
this.s.children[i].emit('close');
}
}
// Remove listeners after emit
self.removeAllListeners('close');
}
// Close parent db if set
if(this.s.parentDb) this.s.parentDb.close();
// Callback after next event loop tick
if(typeof callback == 'function') return process.nextTick(function() {
handleCallback(callback, null);
})
// Return dummy promise
return new this.s.promiseLibrary(function(resolve) {
resolve();
});
}...
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
Given that you booted up the **mongod** process earlier the application should connect successfully and print **Connected correc\
tly to server** to the console.
Let's Add some code to show the different CRUD operations available.
...collection = function (name,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
options = shallowClone(options);
// Set the promise library
options.promiseLibrary = this.s.promiseLibrary;
// If we have not set a collection level readConcern set the db level one
options.readConcern = options.readConcern || this.s.readConcern;
// Do we have ignoreUndefined set
if(this.s.options.ignoreUndefined) {
options.ignoreUndefined = this.s.options.ignoreUndefined;
}
// Execute
if(options == null || !options.strict) {
try {
var collection = new Collection(this, this.s.topology, this.s.databaseName, name, this.s.pkFactory, options);
if(callback) callback(null, collection);
return collection;
} catch(err) {
if(callback) return callback(err);
throw err;
}
}
// Strict mode
if(typeof callback != 'function') {
throw toError(f("A callback is required in strict mode. While getting collection %s.", name));
}
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) {
return callback(new MongoError('topology was destroyed'));
}
// Strict mode
this.listCollections({name:name}).toArray(function(err, collections) {
if(err != null) return handleCallback(callback, err, null);
if(collections.length == 0) return handleCallback(callback, toError(f("Collection %s does not exist. Currently in strict mod\
e.", name)), null);
try {
return handleCallback(callback, null, new Collection(self, self.s.topology, self.s.databaseName, name, self.s.pkFactory, o\
ptions));
} catch(err) {
return handleCallback(callback, err, null);
}
});
}...
Inserting a Document
--------------------
Let's create a function that will insert some documents for us.
```js
var insertDocuments = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Insert some documents
collection.insertMany([
{a : 1}, {a : 2}, {a : 3}
], function(err, result) {
assert.equal(err, null);
assert.equal(3, result.result.n);
assert.equal(3, result.ops.length);
...collections = function (callback) {
var self = this;
// Return the callback
if(typeof callback == 'function') return collections(self, callback);
// Return the promise
return new self.s.promiseLibrary(function(resolve, reject) {
collections(self, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
command = function (command,
options,
callback) {
var self = this;
// Change the callback
if(typeof options == 'function') callback = options, options = {};
// Clone the options
options = shallowClone(options);
// Do we have a callback
if(typeof callback == 'function') return executeCommand(self, command, options, callback);
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
executeCommand(self, command, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
createCollection = function (name,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
name = args.length ? args.shift() : null;
options = args.length ? args.shift() || {} : {};
// Do we have a promisesLibrary
options.promiseLibrary = options.promiseLibrary || this.s.promiseLibrary;
// Check if the callback is in fact a string
if(typeof callback == 'string') name = callback;
// Execute the fallback callback
if(typeof callback == 'function') return createCollection(self, name, options, callback);
return new this.s.promiseLibrary(function(resolve, reject) {
createCollection(self, name, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
createIndex = function (name,
fieldOrSpec,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() || {} : {};
options = typeof callback === 'function' ? options : callback;
options = options == null ? {} : options;
// Shallow clone the options
options = shallowClone(options);
// Run only against primary
options.readPreference = ReadPreference.PRIMARY;
// If we have a callback fallback
if(typeof callback == 'function') return createIndex(self, name, fieldOrSpec, options, callback);
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
createIndex(self, name, fieldOrSpec, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
db = function (dbName,
options) {
options = options || {};
// Copy the options and add out internal override of the not shared flag
var finalOptions = assign({}, this.options, options);
// Do we have the db in the cache already
if(this.s.dbCache[dbName] && finalOptions.returnNonCachedInstance !== true) {
return this.s.dbCache[dbName];
}
// Add current db as parentDb
if(finalOptions.noListener == null || finalOptions.noListener == false) {
finalOptions.parentDb = this;
}
// Add promiseLibrary
finalOptions.promiseLibrary = this.s.promiseLibrary;
// Return the db object
var db = new Db(dbName, this.s.topology, finalOptions)
// Add as child
if(finalOptions.noListener == null || finalOptions.noListener == false) {
this.addChild(db);
}
// Add the db to the cache
this.s.dbCache[dbName] = db;
// Return the database
return db;
}n/a
dropCollection = function (name,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Command to execute
var cmd = {'drop':name}
// Decorate with write concern
decorateWithWriteConcern(cmd, self, options);
// options
options = assign({}, this.s.options, {readPreference: ReadPreference.PRIMARY});
// Check if the callback is in fact a string
if(typeof callback == 'function') return this.command(cmd, options, function(err, result) {
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) return callback(new MongoError('topology was destroyed'));
if(err) return handleCallback(callback, err);
if(result.ok) return handleCallback(callback, null, true);
handleCallback(callback, null, false);
});
// Clone the options
options = shallowClone(self.s.options);
// Set readPreference PRIMARY
options.readPreference = ReadPreference.PRIMARY;
// Execute the command
return new this.s.promiseLibrary(function(resolve, reject) {
// Execute command
self.command(cmd, options, function(err, result) {
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) return reject(new MongoError('topology was destroyed'));
if(err) return reject(err);
if(result.ok) return resolve(true);
resolve(false);
});
});
}n/a
dropDatabase = function (options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Drop database command
var cmd = {'dropDatabase':1};
// Decorate with write concern
decorateWithWriteConcern(cmd, self, options);
// Ensure primary only
options = assign({}, this.s.options, {readPreference: ReadPreference.PRIMARY});
// Check if the callback is in fact a string
if(typeof callback == 'function') return this.command(cmd, options, function(err, result) {
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) return callback(new MongoError('topology was destroyed'));
if(callback == null) return;
if(err) return handleCallback(callback, err, null);
handleCallback(callback, null, result.ok ? true : false);
});
// Execute the command
return new this.s.promiseLibrary(function(resolve, reject) {
// Execute command
self.command(cmd, options, function(err, result) {
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) return reject(new MongoError('topology was destroyed'));
if(err) return reject(err);
if(result.ok) return resolve(true);
resolve(false);
});
});
}n/a
ensureIndex = function (name,
fieldOrSpec,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// If we have a callback fallback
if(typeof callback == 'function') return ensureIndex(self, name, fieldOrSpec, options, callback);
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
ensureIndex(self, name, fieldOrSpec, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
eval = function (code,
parameters,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
parameters = args.length ? args.shift() : parameters;
options = args.length ? args.shift() || {} : {};
// Check if the callback is in fact a string
if(typeof callback == 'function') return evaluate(self, code, parameters, options, callback);
// Execute the command
return new this.s.promiseLibrary(function(resolve, reject) {
evaluate(self, code, parameters, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
executeDbAdminCommand = function (selector,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Return the callback
if(typeof callback == 'function') {
// Convert read preference
if(options.readPreference) {
options.readPreference = convertReadPreference(options.readPreference)
}
return self.s.topology.command('admin.$cmd', selector, options, function(err, result) {
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) return callback(new MongoError('topology was destroyed'));
if(err) return handleCallback(callback, err);
handleCallback(callback, null, result.result);
});
}
// Return promise
return new self.s.promiseLibrary(function(resolve, reject) {
self.s.topology.command('admin.$cmd', selector, options, function(err, result) {
// Did the user destroy the topology
if(self.serverConfig && self.serverConfig.isDestroyed()) return reject(new MongoError('topology was destroyed'));
if(err) return reject(err);
resolve(result.result);
});
});
}n/a
indexInformation = function (name,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// If we have a callback fallback
if(typeof callback == 'function') return indexInformation(self, name, options, callback);
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
indexInformation(self, name, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
listCollections = function (filter,
options) {
filter = filter || {};
options = options || {};
// Shallow clone the object
options = shallowClone(options);
// Set the promise library
options.promiseLibrary = this.s.promiseLibrary;
// Ensure valid readPreference
if(options.readPreference) {
options.readPreference = convertReadPreference(options.readPreference);
}
// We have a list collections command
if(this.serverConfig.capabilities().hasListCollectionsCommand) {
// Cursor options
var cursor = options.batchSize ? {batchSize: options.batchSize} : {}
// Build the command
var command = { listCollections : true, filter: filter, cursor: cursor };
// Set the AggregationCursor constructor
options.cursorFactory = CommandCursor;
// Create the cursor
cursor = this.s.topology.cursor(f('%s.$cmd', this.s.databaseName), command, options);
// Do we have a readPreference, apply it
if(options.readPreference) {
cursor.setReadPreference(options.readPreference);
}
// Return the cursor
return cursor;
}
// We cannot use the listCollectionsCommand
if(!this.serverConfig.capabilities().hasListCollectionsCommand) {
// If we have legacy mode and have not provided a full db name filter it
if(typeof filter.name == 'string' && !(new RegExp('^' + this.databaseName + '\\.').test(filter.name))) {
filter = shallowClone(filter);
filter.name = f('%s.%s', this.s.databaseName, filter.name);
}
}
// No filter, filter by current database
if(filter == null) {
filter.name = f('/%s/', this.s.databaseName);
}
// Rewrite the filter to use $and to filter out indexes
if(filter.name) {
filter = {$and: [{name: filter.name}, {name:/^((?!\$).)*$/}]};
} else {
filter = {name:/^((?!\$).)*$/};
}
// Return options
var _options = {transforms: listCollectionsTranforms(this.s.databaseName)}
// Get the cursor
cursor = this.collection(Db.SYSTEM_NAMESPACE_COLLECTION).find(filter, _options);
// Do we have a readPreference, apply it
if(options.readPreference) cursor.setReadPreference(options.readPreference);
// Set the passed in batch size if one was provided
if(options.batchSize) cursor = cursor.batchSize(options.batchSize);
// We have a fallback mode using legacy systems collections
return cursor;
}n/a
logout = function (options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Establish the correct database name
var dbName = this.s.authSource ? this.s.authSource : this.s.databaseName;
dbName = options.dbName ? options.dbName : dbName;
// If we have a callback
if(typeof callback == 'function') {
return self.s.topology.logout(dbName, function(err) {
if(err) return callback(err);
callback(null, true);
});
}
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.s.topology.logout(dbName, function(err) {
if(err) return reject(err);
resolve(true);
});
});
}n/a
open = function (callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return open(self, callback);
// Return promise
return new self.s.promiseLibrary(function(resolve, reject) {
open(self, function(err, db) {
if(err) return reject(err);
resolve(db);
})
});
}n/a
removeUser = function (username,
options,
callback) {
// Unpack the parameters
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() || {} : {};
// If we have a callback fallback
if(typeof callback == 'function') return removeUser(self, username, options, callback);
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
removeUser(self, username, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
renameCollection = function (fromCollection,
toCollection,
options,
callback) {
var self = this;
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Add return new collection
options.new_collection = true;
// Check if the callback is in fact a string
if(typeof callback == 'function') {
return this.collection(fromCollection).rename(toCollection, options, callback);
}
// Return a promise
return new this.s.promiseLibrary(function(resolve, reject) {
self.collection(fromCollection).rename(toCollection, options, function(err, r) {
if(err) return reject(err);
resolve(r);
});
});
}n/a
stats = function (options,
callback) {
if(typeof options == 'function') callback = options, options = {};
options = options || {};
// Build command object
var commandObject = { dbStats:true };
// Check if we have the scale value
if(options['scale'] != null) commandObject['scale'] = options['scale'];
// If we have a readPreference set
if(options.readPreference == null && this.s.readPreference) {
options.readPreference = this.s.readPreference;
}
// Execute the command
return this.command(commandObject, options, callback);
}n/a
unref = function () {
this.s.topology.unref();
}n/a
Decimal128 = function (bytes) {
this._bsontype = 'Decimal128';
this.bytes = bytes;
}n/a
fromString = function (string) {
// Parse state tracking
var isNegative = false;
var sawRadix = false;
var foundNonZero = false;
// Total number of significant digits (no leading or trailing zero)
var significantDigits = 0;
// Total number of significand digits read
var nDigitsRead = 0;
// Total number of digits (no leading zeros)
var nDigits = 0;
// The number of the digits after radix
var radixPosition = 0;
// The index of the first non-zero in *str*
var firstNonZero = 0;
// Digits Array
var digits = [0];
// The number of digits in digits
var nDigitsStored = 0;
// Insertion pointer for digits
var digitsInsert = 0;
// The index of the first non-zero digit
var firstDigit = 0;
// The index of the last digit
var lastDigit = 0;
// Exponent
var exponent = 0;
// loop index over array
var i = 0;
// The high 17 digits of the significand
var significandHigh = [0, 0];
// The low 17 digits of the significand
var significandLow = [0, 0];
// The biased exponent
var biasedExponent = 0;
// Read index
var index = 0;
// Trim the string
string = string.trim();
// Results
var stringMatch = string.match(PARSE_STRING_REGEXP);
var infMatch = string.match(PARSE_INF_REGEXP);
var nanMatch = string.match(PARSE_NAN_REGEXP);
// Validate the string
if(!stringMatch
&& ! infMatch
&& ! nanMatch || string.length == 0) {
throw new Error("" + string + " not a valid Decimal128 string");
}
// Check if we have an illegal exponent format
if(stringMatch && stringMatch[4] && stringMatch[2] === undefined) {
throw new Error("" + string + " not a valid Decimal128 string");
}
// Get the negative or positive sign
if(string[index] == '+' || string[index] == '-') {
isNegative = string[index++] == '-';
}
// Check if user passed Infinity or NaN
if(!isDigit(string[index]) && string[index] != '.') {
if(string[index] == 'i' || string[index] == 'I') {
return new Decimal128(new Buffer(isNegative ? INF_NEGATIVE_BUFFER : INF_POSITIVE_BUFFER));
} else if(string[index] == 'N') {
return new Decimal128(new Buffer(NAN_BUFFER));
}
}
// Read all the digits
while(isDigit(string[index]) || string[index] == '.') {
if(string[index] == '.') {
if(sawRadix) {
return new Decimal128(new Buffer(NAN_BUFFER));
}
sawRadix = true;
index = index + 1;
continue;
}
if(nDigitsStored < 34) {
if(string[index] != '0' || foundNonZero) {
if(!foundNonZero) {
firstNonZero = nDigitsRead;
}
foundNonZero = true;
// Only store 34 digits
digits[digitsInsert++] = parseInt(string[index], 10);
nDigitsStored = nDigitsStored + 1;
}
}
if(foundNonZero) {
nDigits = nDigits + 1;
}
if(sawRadix) {
radixPosition = radixPosition + 1;
}
nDigitsRead = nDigitsRead + 1;
index = index + 1;
}
if(sawRadix && !nDigitsRead) {
throw new Error("" + string + " not a valid Decimal128 string");
}
// Read exponent if exists
if(string[index] == 'e' || string[index] == 'E') {
// Read exponent digits
var match = string.substr(++index).match(EXPONENT_REGEX);
// No digits read
if(!match || !match[2]) {
return new Decimal128(new Buffer(NAN_BUFFER));
}
// Get exponent
exponent = parseInt(match[0], 10);
// Adjust the index
index = index + match[0].length;
}
// Return not a number
if(string[index]) {
return new Decimal128(new Buffer(NAN_BUFFER));
}
// Done reading input
// Find first non-zero digit in digits
firstDigit = 0;
if(!nDigitsStored) {
firstDigit = 0;
lastDigit = 0;
digits[0] = 0;
nDigits = 1;
nDigitsStored = 1;
significantDigits = 0;
} else {
lastDigit = nDigitsStored - 1;
significantDigits = nDigits;
if(exponent != 0 && significantDigits != 1) {
while(string[firstNonZero + significantDigits - 1] == '0') {
significantDigits = significantDigits - 1;
}
}
}
// Normalization of ...n/a
toJSON = function () {
return { "$numberDecimal": this.toString() };
}n/a
toString = function () {
// Note: bits in this routine are referred to starting at 0,
// from the sign bit, towards the coefficient.
// bits 0 - 31
var high;
// bits 32 - 63
var midh;
// bits 64 - 95
var midl;
// bits 96 - 127
var low;
// bits 1 - 5
var combination;
// decoded biased exponent (14 bits)
var biased_exponent;
// the number of significand digits
var significand_digits = 0;
// the base-10 digits in the significand
var significand = new Array(36);
for(var i = 0; i < significand.length; i++) significand[i] = 0;
// read pointer into significand
var index = 0;
// unbiased exponent
var exponent;
// the exponent if scientific notation is used
var scientific_exponent;
// true if the number is zero
var is_zero = false;
// the most signifcant significand bits (50-46)
var significand_msb;
// temporary storage for significand decoding
var significand128 = {parts: new Array(4)};
// indexing variables
var i;
var j, k;
// Output string
var string = [];
// Unpack index
var index = 0;
// Buffer reference
var buffer = this.bytes;
// Unpack the low 64bits into a long
low = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
midl = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
// Unpack the high 64bits into a long
midh = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
high = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
// Unpack index
var index = 0;
// Create the state of the decimal
var dec = {
low: new Long(low, midl),
high: new Long(midh, high) };
if(dec.high.lessThan(Long.ZERO)) {
string.push('-');
}
// Decode combination field and exponent
combination = (high >> 26) & COMBINATION_MASK;
if((combination >> 3) == 3) {
// Check for 'special' values
if(combination == COMBINATION_INFINITY) {
return string.join('') + "Infinity";
} else if(combination == COMBINATION_NAN) {
return "NaN";
} else {
biased_exponent = (high >> 15) & EXPONENT_MASK;
significand_msb = 0x08 + ((high >> 14) & 0x01);
}
} else {
significand_msb = (high >> 14) & 0x07;
biased_exponent = (high >> 17) & EXPONENT_MASK;
}
exponent = biased_exponent - EXPONENT_BIAS;
// Create string of significand digits
// Convert the 114-bit binary number represented by
// (significand_high, significand_low) to at most 34 decimal
// digits through modulo and division.
significand128.parts[0] = (high & 0x3fff) + ((significand_msb & 0xf) << 14);
significand128.parts[1] = midh;
significand128.parts[2] = midl;
significand128.parts[3] = low;
if(significand128.parts[0] == 0 && significand128.parts[1] == 0
&& significand128.parts[2] == 0 && significand128.parts[3] == 0) {
is_zero = true;
} else {
for(var k = 3; k >= 0; k--) {
var least_digits = 0;
// Peform the divide
var result = divideu128(significand128);
significand128 = result.quotient;
least_digits = result.rem.low_;
// We now have the 9 least significant digits (in base 2).
// Convert and output to string.
if(!least_digits) continue;
for(var j = 8; j >= 0; j--) {
// significand[k * 9 + j] = Math.round(least_digits % 10);
significand[k * 9 + j] = least_digits % 10;
// least_digits = Math.round(least_digits / 10);
least_digits = Math.floor(least_digits / 10);
}
}
}
// Output format options:
// Scientific - [-]d.dddE(+/-)dd or [-]dE(+/-)dd
// Regular - ddd.ddd
if(is_zero) {
significand_digits = 1;
significand[index] = 0;
} else {
significand_digits = 36;
var i = 0;
while(!significand[index]) {
i++;
significand_digits = significand_digits - 1;
index = index + 1;
}
}
scientific_exponent = significand_digits - 1 + exponent;
// The scientific exponent checks are dictated by the string conversion
// ...n/a
function Double(value) {
if(!(this instanceof Double)) return new Double(value);
this._bsontype = 'Double';
this.value = value;
}n/a
toJSON = function () {
return this.value;
}n/a
valueOf = function () {
return this.value;
}n/a
function GridFSBucket(db,
options) {
Emitter.apply(this);
this.setMaxListeners(0);
if (options && typeof options === 'object') {
options = shallowClone(options);
var keys = Object.keys(DEFAULT_GRIDFS_BUCKET_OPTIONS);
for (var i = 0; i < keys.length; ++i) {
if (!options[keys[i]]) {
options[keys[i]] = DEFAULT_GRIDFS_BUCKET_OPTIONS[keys[i]];
}
}
} else {
options = DEFAULT_GRIDFS_BUCKET_OPTIONS;
}
this.s = {
db: db,
options: options,
_chunksCollection: db.collection(options.bucketName + '.chunks'),
_filesCollection: db.collection(options.bucketName + '.files'),
checkedIndexes: false,
calledOpenUploadStream: false,
promiseLibrary: db.s.promiseLibrary ||
(typeof global.Promise == 'function' ? global.Promise : require('es6-promise').Promise)
};
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
delete = function (id,
callback) {
if (typeof callback === 'function') {
return _delete(this, id, callback);
}
var _this = this;
return new this.s.promiseLibrary(function(resolve, reject) {
_delete(_this, id, function(error, res) {
if (error) {
reject(error);
} else {
resolve(res);
}
});
});
}n/a
drop = function (callback) {
if (typeof callback === 'function') {
return _drop(this, callback);
}
var _this = this;
return new this.s.promiseLibrary(function(resolve, reject) {
_drop(_this, function(error, res) {
if (error) {
reject(error);
} else {
resolve(res);
}
});
});
}n/a
find = function (filter,
options) {
filter = filter || {};
options = options || {};
var cursor = this.s._filesCollection.find(filter);
if (options.batchSize != null) {
cursor.batchSize(options.batchSize);
}
if (options.limit != null) {
cursor.limit(options.limit);
}
if (options.maxTimeMS != null) {
cursor.maxTimeMS(options.maxTimeMS);
}
if (options.noCursorTimeout != null) {
cursor.addCursorFlag('noCursorTimeout', options.noCursorTimeout);
}
if (options.skip != null) {
cursor.skip(options.skip);
}
if (options.sort != null) {
cursor.sort(options.sort);
}
return cursor;
}...
We will finish up the Quickstart CRUD methods by performing a simple query that returns all the documents matching the query.
```js
var findDocuments = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Find some documents
collection.find({}).toArray(function(err, docs) {
assert.equal(err, null);
assert.equal(2, docs.length);
console.log("Found the following records");
console.dir(docs);
callback(docs);
});
}
...openDownloadStream = function (id,
options) {
var filter = { _id: id };
options = {
start: options && options.start,
end: options && options.end
};
return new GridFSBucketReadStream(this.s._chunksCollection,
this.s._filesCollection, this.s.options.readPreference, filter, options);
}n/a
openDownloadStreamByName = function (filename,
options) {
var sort = { uploadDate: -1 };
var skip = null;
if (options && options.revision != null) {
if (options.revision >= 0) {
sort = { uploadDate: 1 };
skip = options.revision;
} else {
skip = -options.revision - 1;
}
}
var filter = { filename: filename };
options = {
sort: sort,
skip: skip,
start: options && options.start,
end: options && options.end
};
return new GridFSBucketReadStream(this.s._chunksCollection,
this.s._filesCollection, this.s.options.readPreference, filter, options);
}n/a
openUploadStream = function (filename,
options) {
if (options) {
options = shallowClone(options);
} else {
options = {};
}
if (!options.chunkSizeBytes) {
options.chunkSizeBytes = this.s.options.chunkSizeBytes;
}
return new GridFSBucketWriteStream(this, filename, options);
}n/a
openUploadStreamWithId = function (id,
filename,
options) {
if (options) {
options = shallowClone(options);
} else {
options = {};
}
if (!options.chunkSizeBytes) {
options.chunkSizeBytes = this.s.options.chunkSizeBytes;
}
options.id = id;
return new GridFSBucketWriteStream(this, filename, options);
}n/a
rename = function (id,
filename,
callback) {
if (typeof callback === 'function') {
return _rename(this, id, filename, callback);
}
var _this = this;
return new this.s.promiseLibrary(function(resolve, reject) {
_rename(_this, id, filename, function(error, res) {
if (error) {
reject(error);
} else {
resolve(res);
}
});
});
}n/a
function GridStore(db,
id,
filename,
mode,
options) {
if(!(this instanceof GridStore)) return new GridStore(db, id, filename, mode, options);
this.db = db;
// Handle options
if(typeof options === 'undefined') options = {};
// Handle mode
if(typeof mode === 'undefined') {
mode = filename;
filename = undefined;
} else if(typeof mode == 'object') {
options = mode;
mode = filename;
filename = undefined;
}
if(id && id._bsontype == 'ObjectID') {
this.referenceBy = REFERENCE_BY_ID;
this.fileId = id;
this.filename = filename;
} else if(typeof filename == 'undefined') {
this.referenceBy = REFERENCE_BY_FILENAME;
this.filename = id;
if (mode.indexOf('w') != null) {
this.fileId = new ObjectID();
}
} else {
this.referenceBy = REFERENCE_BY_ID;
this.fileId = id;
this.filename = filename;
}
// Set up the rest
this.mode = mode == null ? "r" : mode;
this.options = options || {};
// Opened
this.isOpen = false;
// Set the root if overridden
this.root = this.options['root'] == null ? GridStore.DEFAULT_ROOT_COLLECTION : this.options['root'];
this.position = 0;
this.readPreference = this.options.readPreference || db.options.readPreference || ReadPreference.PRIMARY;
this.writeConcern = _getWriteConcern(db, this.options);
// Set default chunk size
this.internalChunkSize = this.options['chunkSize'] == null ? Chunk.DEFAULT_CHUNK_SIZE : this.options['chunkSize'];
// Get the promiseLibrary
var promiseLibrary = this.options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// Set the promiseLibrary
this.promiseLibrary = promiseLibrary;
Object.defineProperty(this, "chunkSize", { enumerable: true
, get: function () {
return this.internalChunkSize;
}
, set: function(value) {
if(!(this.mode[0] == "w" && this.position == 0 && this.uploadDate == null)) {
this.internalChunkSize = this.internalChunkSize;
} else {
this.internalChunkSize = value;
}
}
});
Object.defineProperty(this, "md5", { enumerable: true
, get: function () {
return this.internalMd5;
}
});
Object.defineProperty(this, "chunkNumber", { enumerable: true
, get: function () {
return this.currentChunk && this.currentChunk.chunkNumber ? this.currentChunk.chunkNumber : null;
}
});
}n/a
exist = function (db,
fileIdObject,
rootCollection,
options,
callback) {
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
rootCollection = args.length ? args.shift() : null;
options = args.length ? args.shift() : {};
options = options || {};
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// We provided a callback leg
if(typeof callback == 'function') return exists(db, fileIdObject, rootCollection, options, callback);
// Return promise
return new promiseLibrary(function(resolve, reject) {
exists(db, fileIdObject, rootCollection, options, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
list = function (db,
rootCollection,
options,
callback) {
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
rootCollection = args.length ? args.shift() : null;
options = args.length ? args.shift() : {};
options = options || {};
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// We provided a callback leg
if(typeof callback == 'function') return list(db, rootCollection, options, callback);
// Return promise
return new promiseLibrary(function(resolve, reject) {
list(db, rootCollection, options, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
read = function (db,
name,
length,
offset,
options,
callback) {
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
length = args.length ? args.shift() : null;
offset = args.length ? args.shift() : null;
options = args.length ? args.shift() : null;
options = options || {};
// Get the promiseLibrary
var promiseLibrary = options ? options.promiseLibrary : null;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// We provided a callback leg
if(typeof callback == 'function') return readStatic(db, name, length, offset, options, callback);
// Return promise
return new promiseLibrary(function(resolve, reject) {
readStatic(db, name, length, offset, options, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
readlines = function (db,
name,
separator,
options,
callback) {
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
separator = args.length ? args.shift() : null;
options = args.length ? args.shift() : null;
options = options || {};
// Get the promiseLibrary
var promiseLibrary = options ? options.promiseLibrary : null;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// We provided a callback leg
if(typeof callback == 'function') return readlinesStatic(db, name, separator, options, callback);
// Return promise
return new promiseLibrary(function(resolve, reject) {
readlinesStatic(db, name, separator, options, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
unlink = function (db,
names,
options,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 2);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
options = args.length ? args.shift() : {};
options = options || {};
// Get the promiseLibrary
var promiseLibrary = options.promiseLibrary;
// No promise library selected fall back
if(!promiseLibrary) {
promiseLibrary = typeof global.Promise == 'function' ?
global.Promise : require('es6-promise').Promise;
}
// We provided a callback leg
if(typeof callback == 'function') return unlinkStatic(self, db, names, options, callback);
// Return promise
return new promiseLibrary(function(resolve, reject) {
unlinkStatic(self, db, names, options, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
chunkCollection = function (callback) {
if(typeof callback == 'function')
return this.db.collection((this.root + ".chunks"), callback);
return this.db.collection((this.root + ".chunks"));
}n/a
close = function (callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return close(self, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
close(self, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}...
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
Given that you booted up the **mongod** process earlier the application should connect successfully and print **Connected correc\
tly to server** to the console.
Let's Add some code to show the different CRUD operations available.
...collection = function (callback) {
if(typeof callback == 'function')
this.db.collection(this.root + ".files", callback);
return this.db.collection(this.root + ".files");
}...
Inserting a Document
--------------------
Let's create a function that will insert some documents for us.
```js
var insertDocuments = function(db, callback) {
// Get the documents collection
var collection = db.collection('documents');
// Insert some documents
collection.insertMany([
{a : 1}, {a : 2}, {a : 3}
], function(err, result) {
assert.equal(err, null);
assert.equal(3, result.result.n);
assert.equal(3, result.ops.length);
...function destroy() {
// close and do not emit any more events. queued data is not sent.
if(!this.writable) return;
this.readable = false;
if(this.writable) {
this.writable = false;
this._q.length = 0;
this.emit('close');
}
}n/a
eof = function () {
return this.position == this.length ? true : false;
}n/a
getc = function (callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return eof(self, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
eof(self, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
open = function (callback) {
var self = this;
if( this.mode != "w" && this.mode != "w+" && this.mode != "r"){
throw MongoError.create({message: "Illegal mode " + this.mode, driver:true});
}
// We provided a callback leg
if(typeof callback == 'function') return open(self, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
open(self, function(err, store) {
if(err) return reject(err);
resolve(store);
})
});
}n/a
puts = function (string,
callback) {
var self = this;
var finalString = string.match(/\n$/) == null ? string + "\n" : string;
// We provided a callback leg
if(typeof callback == 'function') return this.write(finalString, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
self.write(finalString, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
read = function (length,
buffer,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
length = args.length ? args.shift() : null;
buffer = args.length ? args.shift() : null;
// We provided a callback leg
if(typeof callback == 'function') return read(self, length, buffer, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
read(self, length, buffer, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
readlines = function (separator,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 0);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
separator = args.length ? args.shift() : "\n";
separator = separator || "\n";
// We provided a callback leg
if(typeof callback == 'function') return readlines(self, separator, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
readlines(self, separator, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
rewind = function (callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return rewind(self, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
rewind(self, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
seek = function (position,
seekLocation,
callback) {
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
callback = args.pop();
if(typeof callback != 'function') args.push(callback);
seekLocation = args.length ? args.shift() : null;
// We provided a callback leg
if(typeof callback == 'function') return seek(self, position, seekLocation, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
seek(self, position, seekLocation, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
stream = function () {
return new GridStoreStream(this);
}n/a
tell = function (callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return callback(null, this.position);
// Return promise
return new self.promiseLibrary(function(resolve) {
resolve(self.position);
});
}n/a
unlink = function (callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return unlink(self, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
unlink(self, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
function write(data,
close,
callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return _writeNormal(this, data, close, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
_writeNormal(self, data, close, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
writeFile = function (file,
callback) {
var self = this;
// We provided a callback leg
if(typeof callback == 'function') return writeFile(self, file, callback);
// Return promise
return new self.promiseLibrary(function(resolve, reject) {
writeFile(self, file, function(err, r) {
if(err) return reject(err);
resolve(r);
})
});
}n/a
Int32 = function (value) {
if(!(this instanceof Int32)) return new Int32(value);
this._bsontype = 'Int32';
this.value = value;
}n/a
toJSON = function () {
return this.value;
}n/a
valueOf = function () {
return this.value;
}n/a
Logger = function (className,
options) {
if(!(this instanceof Logger)) return new Logger(className, options);
options = options || {};
// Current reference
this.className = className;
// Current logger
if(options.logger) {
currentLogger = options.logger;
} else if(currentLogger == null) {
currentLogger = console.log;
}
// Set level of logging, default is error
if(options.loggerLevel) {
level = options.loggerLevel || 'error';
}
// Add all class names
if(filteredClasses[this.className] == null) classFilters[this.className] = true;
}n/a
currentLogger = function () {
return currentLogger;
}n/a
filter = function (type,
values) {
if(type == 'class' && Array.isArray(values)) {
filteredClasses = {};
values.forEach(function(x) {
filteredClasses[x] = true;
});
}
}n/a
reset = function () {
level = 'error';
filteredClasses = {};
}n/a
setCurrentLogger = function (logger) {
if(typeof logger != 'function') throw new MongoError("current logger must be a function");
currentLogger = logger;
}n/a
setLevel = function (_level) {
if(_level != 'info' && _level != 'error' && _level != 'debug' && _level != 'warn') {
throw new Error(f("%s is an illegal logging level", _level));
}
level = _level;
}n/a
debug = function (message,
object) {
if(this.isDebug()
&& ((Object.keys(filteredClasses).length > 0 && filteredClasses[this.className])
|| (Object.keys(filteredClasses).length == 0 && classFilters[this.className]))) {
var dateTime = new Date().getTime();
var msg = f("[%s-%s:%s] %s %s", 'DEBUG', this.className, pid, dateTime, message);
var state = {
type: 'debug', message: message, className: this.className, pid: pid, date: dateTime
};
if(object) state.meta = object;
currentLogger(msg, state);
}
}n/a
error = function (message,
object) {
if(this.isError()
&& ((Object.keys(filteredClasses).length > 0 && filteredClasses[this.className])
|| (Object.keys(filteredClasses).length == 0 && classFilters[this.className]))) {
var dateTime = new Date().getTime();
var msg = f("[%s-%s:%s] %s %s", 'ERROR', this.className, pid, dateTime, message);
var state = {
type: 'error', message: message, className: this.className, pid: pid, date: dateTime
};
if(object) state.meta = object;
currentLogger(msg, state);
}
}n/a
info = function (message,
object) {
if(this.isInfo()
&& ((Object.keys(filteredClasses).length > 0 && filteredClasses[this.className])
|| (Object.keys(filteredClasses).length == 0 && classFilters[this.className]))) {
var dateTime = new Date().getTime();
var msg = f("[%s-%s:%s] %s %s", 'INFO', this.className, pid, dateTime, message);
var state = {
type: 'info', message: message, className: this.className, pid: pid, date: dateTime
};
if(object) state.meta = object;
currentLogger(msg, state);
}
}n/a
isDebug = function () {
return level == 'debug';
}n/a
isError = function () {
return level == 'error' || level == 'info' || level == 'debug';
}n/a
isInfo = function () {
return level == 'info' || level == 'debug';
}n/a
isWarn = function () {
return level == 'error' || level == 'warn' || level == 'info' || level == 'debug';
}n/a
warn = function (message,
object) {
if(this.isWarn()
&& ((Object.keys(filteredClasses).length > 0 && filteredClasses[this.className])
|| (Object.keys(filteredClasses).length == 0 && classFilters[this.className]))) {
var dateTime = new Date().getTime();
var msg = f("[%s-%s:%s] %s %s", 'WARN', this.className, pid, dateTime, message);
var state = {
type: 'warn', message: message, className: this.className, pid: pid, date: dateTime
};
if(object) state.meta = object;
currentLogger(msg, state);
}
}n/a
function Long(low,
high) {
if(!(this instanceof Long)) return new Long(low, high);
this._bsontype = 'Long';
/**
* @type {number}
* @ignore
*/
this.low_ = low | 0; // force into 32 signed bits.
/**
* @type {number}
* @ignore
*/
this.high_ = high | 0; // force into 32 signed bits.
}n/a
fromBits = function (lowBits,
highBits) {
return new Long(lowBits, highBits);
}n/a
fromInt = function (value) {
if (-128 <= value && value < 128) {
var cachedObj = Long.INT_CACHE_[value];
if (cachedObj) {
return cachedObj;
}
}
var obj = new Long(value | 0, value < 0 ? -1 : 0);
if (-128 <= value && value < 128) {
Long.INT_CACHE_[value] = obj;
}
return obj;
}n/a
fromNumber = function (value) {
if (isNaN(value) || !isFinite(value)) {
return Long.ZERO;
} else if (value <= -Long.TWO_PWR_63_DBL_) {
return Long.MIN_VALUE;
} else if (value + 1 >= Long.TWO_PWR_63_DBL_) {
return Long.MAX_VALUE;
} else if (value < 0) {
return Long.fromNumber(-value).negate();
} else {
return new Long(
(value % Long.TWO_PWR_32_DBL_) | 0,
(value / Long.TWO_PWR_32_DBL_) | 0);
}
}n/a
fromString = function (str,
opt_radix) {
if (str.length == 0) {
throw Error('number format error: empty string');
}
var radix = opt_radix || 10;
if (radix < 2 || 36 < radix) {
throw Error('radix out of range: ' + radix);
}
if (str.charAt(0) == '-') {
return Long.fromString(str.substring(1), radix).negate();
} else if (str.indexOf('-') >= 0) {
throw Error('number format error: interior "-" character: ' + str);
}
// Do several (8) digits each time through the loop, so as to
// minimize the calls to the very expensive emulated div.
var radixToPower = Long.fromNumber(Math.pow(radix, 8));
var result = Long.ZERO;
for (var i = 0; i < str.length; i += 8) {
var size = Math.min(8, str.length - i);
var value = parseInt(str.substring(i, i + size), radix);
if (size < 8) {
var power = Long.fromNumber(Math.pow(radix, size));
result = result.multiply(power).add(Long.fromNumber(value));
} else {
result = result.multiply(radixToPower);
result = result.add(Long.fromNumber(value));
}
}
return result;
}n/a
add = function (other) {
// Divide each number into 4 chunks of 16 bits, and then sum the chunks.
var a48 = this.high_ >>> 16;
var a32 = this.high_ & 0xFFFF;
var a16 = this.low_ >>> 16;
var a00 = this.low_ & 0xFFFF;
var b48 = other.high_ >>> 16;
var b32 = other.high_ & 0xFFFF;
var b16 = other.low_ >>> 16;
var b00 = other.low_ & 0xFFFF;
var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
c00 += a00 + b00;
c16 += c00 >>> 16;
c00 &= 0xFFFF;
c16 += a16 + b16;
c32 += c16 >>> 16;
c16 &= 0xFFFF;
c32 += a32 + b32;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c48 += a48 + b48;
c48 &= 0xFFFF;
return Long.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
}n/a
and = function (other) {
return Long.fromBits(this.low_ & other.low_, this.high_ & other.high_);
}n/a
compare = function (other) {
if (this.equals(other)) {
return 0;
}
var thisNeg = this.isNegative();
var otherNeg = other.isNegative();
if (thisNeg && !otherNeg) {
return -1;
}
if (!thisNeg && otherNeg) {
return 1;
}
// at this point, the signs are the same, so subtraction will not overflow
if (this.subtract(other).isNegative()) {
return -1;
} else {
return 1;
}
}n/a
div = function (other) {
if (other.isZero()) {
throw Error('division by zero');
} else if (this.isZero()) {
return Long.ZERO;
}
if (this.equals(Long.MIN_VALUE)) {
if (other.equals(Long.ONE) ||
other.equals(Long.NEG_ONE)) {
return Long.MIN_VALUE; // recall that -MIN_VALUE == MIN_VALUE
} else if (other.equals(Long.MIN_VALUE)) {
return Long.ONE;
} else {
// At this point, we have |other| >= 2, so |this/other| < |MIN_VALUE|.
var halfThis = this.shiftRight(1);
var approx = halfThis.div(other).shiftLeft(1);
if (approx.equals(Long.ZERO)) {
return other.isNegative() ? Long.ONE : Long.NEG_ONE;
} else {
var rem = this.subtract(other.multiply(approx));
var result = approx.add(rem.div(other));
return result;
}
}
} else if (other.equals(Long.MIN_VALUE)) {
return Long.ZERO;
}
if (this.isNegative()) {
if (other.isNegative()) {
return this.negate().div(other.negate());
} else {
return this.negate().div(other).negate();
}
} else if (other.isNegative()) {
return this.div(other.negate()).negate();
}
// Repeat the following until the remainder is less than other: find a
// floating-point that approximates remainder / other *from below*, add this
// into the result, and subtract it from the remainder. It is critical that
// the approximate value is less than or equal to the real value so that the
// remainder never becomes negative.
var res = Long.ZERO;
var rem = this;
while (rem.greaterThanOrEqual(other)) {
// Approximate the result of division. This may be a little greater or
// smaller than the actual value.
var approx = Math.max(1, Math.floor(rem.toNumber() / other.toNumber()));
// We will tweak the approximate result by changing it in the 48-th digit or
// the smallest non-fractional digit, whichever is larger.
var log2 = Math.ceil(Math.log(approx) / Math.LN2);
var delta = (log2 <= 48) ? 1 : Math.pow(2, log2 - 48);
// Decrease the approximation until it is smaller than the remainder. Note
// that if it is too large, the product overflows and is negative.
var approxRes = Long.fromNumber(approx);
var approxRem = approxRes.multiply(other);
while (approxRem.isNegative() || approxRem.greaterThan(rem)) {
approx -= delta;
approxRes = Long.fromNumber(approx);
approxRem = approxRes.multiply(other);
}
// We know the answer can't be zero... and actually, zero would cause
// infinite recursion since we would make no progress.
if (approxRes.isZero()) {
approxRes = Long.ONE;
}
res = res.add(approxRes);
rem = rem.subtract(approxRem);
}
return res;
}n/a
equals = function (other) {
return (this.high_ == other.high_) && (this.low_ == other.low_);
}n/a
getHighBits = function () {
return this.high_;
}n/a
getLowBits = function () {
return this.low_;
}n/a
getLowBitsUnsigned = function () {
return (this.low_ >= 0) ?
this.low_ : Long.TWO_PWR_32_DBL_ + this.low_;
}n/a
getNumBitsAbs = function () {
if (this.isNegative()) {
if (this.equals(Long.MIN_VALUE)) {
return 64;
} else {
return this.negate().getNumBitsAbs();
}
} else {
var val = this.high_ != 0 ? this.high_ : this.low_;
for (var bit = 31; bit > 0; bit--) {
if ((val & (1 << bit)) != 0) {
break;
}
}
return this.high_ != 0 ? bit + 33 : bit + 1;
}
}n/a
greaterThan = function (other) {
return this.compare(other) > 0;
}n/a
greaterThanOrEqual = function (other) {
return this.compare(other) >= 0;
}n/a
isNegative = function () {
return this.high_ < 0;
}n/a
isOdd = function () {
return (this.low_ & 1) == 1;
}n/a
isZero = function () {
return this.high_ == 0 && this.low_ == 0;
}n/a
lessThan = function (other) {
return this.compare(other) < 0;
}n/a
lessThanOrEqual = function (other) {
return this.compare(other) <= 0;
}n/a
modulo = function (other) {
return this.subtract(this.div(other).multiply(other));
}n/a
multiply = function (other) {
if (this.isZero()) {
return Long.ZERO;
} else if (other.isZero()) {
return Long.ZERO;
}
if (this.equals(Long.MIN_VALUE)) {
return other.isOdd() ? Long.MIN_VALUE : Long.ZERO;
} else if (other.equals(Long.MIN_VALUE)) {
return this.isOdd() ? Long.MIN_VALUE : Long.ZERO;
}
if (this.isNegative()) {
if (other.isNegative()) {
return this.negate().multiply(other.negate());
} else {
return this.negate().multiply(other).negate();
}
} else if (other.isNegative()) {
return this.multiply(other.negate()).negate();
}
// If both Longs are small, use float multiplication
if (this.lessThan(Long.TWO_PWR_24_) &&
other.lessThan(Long.TWO_PWR_24_)) {
return Long.fromNumber(this.toNumber() * other.toNumber());
}
// Divide each Long into 4 chunks of 16 bits, and then add up 4x4 products.
// We can skip products that would overflow.
var a48 = this.high_ >>> 16;
var a32 = this.high_ & 0xFFFF;
var a16 = this.low_ >>> 16;
var a00 = this.low_ & 0xFFFF;
var b48 = other.high_ >>> 16;
var b32 = other.high_ & 0xFFFF;
var b16 = other.low_ >>> 16;
var b00 = other.low_ & 0xFFFF;
var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
c00 += a00 * b00;
c16 += c00 >>> 16;
c00 &= 0xFFFF;
c16 += a16 * b00;
c32 += c16 >>> 16;
c16 &= 0xFFFF;
c16 += a00 * b16;
c32 += c16 >>> 16;
c16 &= 0xFFFF;
c32 += a32 * b00;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c32 += a16 * b16;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c32 += a00 * b32;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c48 += a48 * b00 + a32 * b16 + a16 * b32 + a00 * b48;
c48 &= 0xFFFF;
return Long.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
}n/a
negate = function () {
if (this.equals(Long.MIN_VALUE)) {
return Long.MIN_VALUE;
} else {
return this.not().add(Long.ONE);
}
}n/a
not = function () {
return Long.fromBits(~this.low_, ~this.high_);
}n/a
notEquals = function (other) {
return (this.high_ != other.high_) || (this.low_ != other.low_);
}n/a
or = function (other) {
return Long.fromBits(this.low_ | other.low_, this.high_ | other.high_);
}n/a
shiftLeft = function (numBits) {
numBits &= 63;
if (numBits == 0) {
return this;
} else {
var low = this.low_;
if (numBits < 32) {
var high = this.high_;
return Long.fromBits(
low << numBits,
(high << numBits) | (low >>> (32 - numBits)));
} else {
return Long.fromBits(0, low << (numBits - 32));
}
}
}n/a
shiftRight = function (numBits) {
numBits &= 63;
if (numBits == 0) {
return this;
} else {
var high = this.high_;
if (numBits < 32) {
var low = this.low_;
return Long.fromBits(
(low >>> numBits) | (high << (32 - numBits)),
high >> numBits);
} else {
return Long.fromBits(
high >> (numBits - 32),
high >= 0 ? 0 : -1);
}
}
}n/a
shiftRightUnsigned = function (numBits) {
numBits &= 63;
if (numBits == 0) {
return this;
} else {
var high = this.high_;
if (numBits < 32) {
var low = this.low_;
return Long.fromBits(
(low >>> numBits) | (high << (32 - numBits)),
high >>> numBits);
} else if (numBits == 32) {
return Long.fromBits(high, 0);
} else {
return Long.fromBits(high >>> (numBits - 32), 0);
}
}
}n/a
subtract = function (other) {
return this.add(other.negate());
}n/a
toInt = function () {
return this.low_;
}n/a
toJSON = function () {
return this.toString();
}n/a
toNumber = function () {
return this.high_ * Long.TWO_PWR_32_DBL_ +
this.getLowBitsUnsigned();
}n/a
toString = function (opt_radix) {
var radix = opt_radix || 10;
if (radix < 2 || 36 < radix) {
throw Error('radix out of range: ' + radix);
}
if (this.isZero()) {
return '0';
}
if (this.isNegative()) {
if (this.equals(Long.MIN_VALUE)) {
// We need to change the Long value before it can be negated, so we remove
// the bottom-most digit in this base and then recurse to do the rest.
var radixLong = Long.fromNumber(radix);
var div = this.div(radixLong);
var rem = div.multiply(radixLong).subtract(this);
return div.toString(radix) + rem.toInt().toString(radix);
} else {
return '-' + this.negate().toString(radix);
}
}
// Do several (6) digits each time through the loop, so as to
// minimize the calls to the very expensive emulated div.
var radixToPower = Long.fromNumber(Math.pow(radix, 6));
var rem = this;
var result = '';
while (true) {
var remDiv = rem.div(radixToPower);
var intval = rem.subtract(remDiv.multiply(radixToPower)).toInt();
var digits = intval.toString(radix);
rem = remDiv;
if (rem.isZero()) {
return digits + result;
} else {
while (digits.length < 6) {
digits = '0' + digits;
}
result = '' + digits + result;
}
}
}n/a
xor = function (other) {
return Long.fromBits(this.low_ ^ other.low_, this.high_ ^ other.high_);
}n/a
Mongos = function (servers,
options) {
if(!(this instanceof Mongos)) return new Mongos(servers, options);
options = options || {};
var self = this;
// Filter the options
options = filterOptions(options, legalOptionNames);
// Ensure all the instances are Server
for(var i = 0; i < servers.length; i++) {
if(!(servers[i] instanceof Server)) {
throw MongoError.create({message: "all seed list instances must be of the Server type", driver:true});
}
}
// Stored options
var storeOptions = {
force: false
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : MAX_JS_INT
}
// Shared global store
var store = options.store || new Store(self, storeOptions);
// Set up event emitter
EventEmitter.call(this);
// Build seed list
var seedlist = servers.map(function(x) {
return {host: x.host, port: x.port}
});
// Get the reconnect option
var reconnect = typeof options.auto_reconnect == 'boolean' ? options.auto_reconnect : true;
reconnect = typeof options.autoReconnect == 'boolean' ? options.autoReconnect : reconnect;
// Clone options
var clonedOptions = mergeOptions({}, {
disconnectHandler: store,
cursorFactory: Cursor,
reconnect: reconnect,
emitError: typeof options.emitError == 'boolean' ? options.emitError : true,
size: typeof options.poolSize == 'number' ? options.poolSize : 5
});
// Translate any SSL options and other connectivity options
clonedOptions = translateOptions(clonedOptions, options);
// Socket options
var socketOptions = options.socketOptions && Object.keys(options.socketOptions).length > 0
? options.socketOptions : options;
// Translate all the options to the mongodb-core ones
clonedOptions = translateOptions(clonedOptions, socketOptions);
if(typeof clonedOptions.keepAlive == 'number') {
clonedOptions.keepAliveInitialDelay = clonedOptions.keepAlive;
clonedOptions.keepAlive = clonedOptions.keepAlive > 0;
}
// Build default client information
this.clientInfo = {
driver: {
name: "nodejs",
version: driverVersion
},
os: {
type: type,
name: name,
architecture: architecture,
version: release
},
platform: nodejsversion
}
// Build default client information
clonedOptions.clientInfo = this.clientInfo;
// Do we have an application specific string
if(options.appname) {
clonedOptions.clientInfo.application = { name: options.appname };
}
// Create the Mongos
var mongos = new CMongos(seedlist, clonedOptions)
// Server capabilities
var sCapabilities = null;
// Internal state
this.s = {
// Create the Mongos
mongos: mongos
// Server capabilities
, sCapabilities: sCapabilities
// Debug turned on
, debug: clonedOptions.debug
// Store option defaults
, storeOptions: storeOptions
// Cloned options
, clonedOptions: clonedOptions
// Actual store of callbacks
, store: store
// Options
, options: options
}
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
auth = function () {
var args = Array.prototype.slice.call(arguments, 0);
this.s.mongos.auth.apply(this.s.mongos, args);
}n/a
capabilities = function () {
if(this.s.sCapabilities) return this.s.sCapabilities;
if(this.s.mongos.lastIsMaster() == null) return null;
this.s.sCapabilities = new ServerCapabilities(this.s.mongos.lastIsMaster());
return this.s.sCapabilities;
}n/a
close = function (forceClosed) {
this.s.mongos.destroy();
// We need to wash out all stored processes
if(forceClosed == true) {
this.s.storeOptions.force = forceClosed;
this.s.store.flush();
}
}...
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
Given that you booted up the **mongod** process earlier the application should connect successfully and print **Connected correc\
tly to server** to the console.
Let's Add some code to show the different CRUD operations available.
...command = function (ns,
cmd,
options,
callback) {
this.s.mongos.command(ns, cmd, options, callback);
}n/a
connect = function (db,
_options,
callback) {
var self = this;
if('function' === typeof _options) callback = _options, _options = {};
if(_options == null) _options = {};
if(!('function' === typeof callback)) callback = null;
self.s.options = _options;
// Update bufferMaxEntries
self.s.storeOptions.bufferMaxEntries = db.bufferMaxEntries;
// Error handler
var connectErrorHandler = function() {
return function(err) {
// Remove all event handlers
var events = ['timeout', 'error', 'close'];
events.forEach(function(e) {
self.removeListener(e, connectErrorHandler);
});
self.s.mongos.removeListener('connect', connectErrorHandler);
// Try to callback
try {
callback(err);
} catch(err) {
process.nextTick(function() { throw err; })
}
}
}
// Actual handler
var errorHandler = function(event) {
return function(err) {
if(event != 'error') {
self.emit(event, err);
}
}
}
// Error handler
var reconnectHandler = function() {
self.emit('reconnect');
self.s.store.execute();
}
// relay the event
var relay = function(event) {
return function(t, server) {
self.emit(event, t, server);
}
}
// Connect handler
var connectHandler = function() {
// Clear out all the current handlers left over
["timeout", "error", "close", 'serverOpening', 'serverDescriptionChanged', 'serverHeartbeatStarted',
'serverHeartbeatSucceeded', 'serverHeartbeatFailed', 'serverClosed', 'topologyOpening',
'topologyClosed', 'topologyDescriptionChanged'].forEach(function(e) {
self.s.mongos.removeAllListeners(e);
});
// Set up listeners
self.s.mongos.once('timeout', errorHandler('timeout'));
self.s.mongos.once('error', errorHandler('error'));
self.s.mongos.once('close', errorHandler('close'));
// Set up SDAM listeners
self.s.mongos.on('serverDescriptionChanged', relay('serverDescriptionChanged'));
self.s.mongos.on('serverHeartbeatStarted', relay('serverHeartbeatStarted'));
self.s.mongos.on('serverHeartbeatSucceeded', relay('serverHeartbeatSucceeded'));
self.s.mongos.on('serverHeartbeatFailed', relay('serverHeartbeatFailed'));
self.s.mongos.on('serverOpening', relay('serverOpening'));
self.s.mongos.on('serverClosed', relay('serverClosed'));
self.s.mongos.on('topologyOpening', relay('topologyOpening'));
self.s.mongos.on('topologyClosed', relay('topologyClosed'));
self.s.mongos.on('topologyDescriptionChanged', relay('topologyDescriptionChanged'));
// Set up serverConfig listeners
self.s.mongos.on('fullsetup', relay('fullsetup'));
// Emit open event
self.emit('open', null, self);
// Return correctly
try {
callback(null, self);
} catch(err) {
process.nextTick(function() { throw err; })
}
}
// Set up listeners
self.s.mongos.once('timeout', connectErrorHandler('timeout'));
self.s.mongos.once('error', connectErrorHandler('error'));
self.s.mongos.once('close', connectErrorHandler('close'));
self.s.mongos.once('connect', connectHandler);
// Join and leave events
self.s.mongos.on('joined', relay('joined'));
self.s.mongos.on('left', relay('left'));
// Reconnect server
self.s.mongos.on('reconnect', reconnectHandler);
// Start connection
self.s.mongos.connect(_options);
}...
```js
var MongoClient = require('mongodb').MongoClient
, assert = require('assert');
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
...connections = function () {
return this.s.mongos.connections();
}n/a
cursor = function (ns,
cmd,
options) {
options.disconnectHandler = this.s.store;
return this.s.mongos.cursor(ns, cmd, options);
}n/a
insert = function (ns,
ops,
options,
callback) {
this.s.mongos.insert(ns, ops, options, function(e, m) {
callback(e, m)
});
}n/a
isConnected = function () {
return this.s.mongos.isConnected();
}n/a
isDestroyed = function () {
return this.s.mongos.isDestroyed();
}n/a
lastIsMaster = function () {
return this.s.mongos.lastIsMaster();
}n/a
logout = function () {
var args = Array.prototype.slice.call(arguments, 0);
this.s.mongos.logout.apply(this.s.mongos, args);
}n/a
remove = function (ns,
ops,
options,
callback) {
this.s.mongos.remove(ns, ops, options, callback);
}n/a
update = function (ns,
ops,
options,
callback) {
this.s.mongos.update(ns, ops, options, callback);
}n/a
function ObjectID(id) {
// Duck-typing to support ObjectId from different npm packages
if(id instanceof ObjectID) return id;
if(!(this instanceof ObjectID)) return new ObjectID(id);
this._bsontype = 'ObjectID';
var __id = null;
var valid = ObjectID.isValid(id);
// Throw an error if it's not a valid setup
if(!valid && id != null){
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
} else if(valid && typeof id == 'string' && id.length == 24) {
return ObjectID.createFromHexString(id);
} else if(id == null || typeof id == 'number') {
// convert to 12 byte binary string
this.id = this.generate(id);
} else if(id != null && id.length === 12) {
// assume 12 byte string
this.id = id;
} else if(id != null && id.toHexString) {
// Duck-typing to support ObjectId from different npm packages
return id;
} else {
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
}
if(ObjectID.cacheHexString) this.__id = this.toHexString();
}n/a
function ObjectID(id) {
// Duck-typing to support ObjectId from different npm packages
if(id instanceof ObjectID) return id;
if(!(this instanceof ObjectID)) return new ObjectID(id);
this._bsontype = 'ObjectID';
var __id = null;
var valid = ObjectID.isValid(id);
// Throw an error if it's not a valid setup
if(!valid && id != null){
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
} else if(valid && typeof id == 'string' && id.length == 24) {
return ObjectID.createFromHexString(id);
} else if(id == null || typeof id == 'number') {
// convert to 12 byte binary string
this.id = this.generate(id);
} else if(id != null && id.length === 12) {
// assume 12 byte string
this.id = id;
} else if(id != null && id.toHexString) {
// Duck-typing to support ObjectId from different npm packages
return id;
} else {
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
}
if(ObjectID.cacheHexString) this.__id = this.toHexString();
}n/a
function createFromHexString(string) {
// Throw an error if it's not a valid setup
if(typeof string === 'undefined' || string != null && string.length != 24)
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
var length = string.length;
if(length > 12*2) {
throw new Error('Id cannot be longer than 12 bytes');
}
// Calculate lengths
var sizeof = length >> 1;
var array = new _Buffer(sizeof);
var n = 0;
var i = 0;
while (i < length) {
array[n++] = decodeLookup[string.charCodeAt(i++)] << 4 | decodeLookup[string.charCodeAt(i++)]
}
return new ObjectID(array);
}n/a
function createFromTime(time) {
var buffer = new Buffer([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]);
// Encode time into first 4 bytes
buffer[3] = time & 0xff;
buffer[2] = (time >> 8) & 0xff;
buffer[1] = (time >> 16) & 0xff;
buffer[0] = (time >> 24) & 0xff;
// Return the new objectId
return new ObjectID(buffer);
}n/a
function createPk() {
return new ObjectID();
}n/a
function isValid(id) {
if(id == null) return false;
if(typeof id == 'number') {
return true;
}
if(typeof id == 'string') {
return id.length == 12 || (id.length == 24 && checkForHexRegExp.test(id));
}
if(id instanceof ObjectID) {
return true;
}
if(id instanceof _Buffer) {
return true;
}
// Duck-Typing detection of ObjectId like objects
if(id.toHexString) {
return id.id.length == 12 || (id.id.length == 24 && checkForHexRegExp.test(id.id));
}
return false;
}n/a
function equals(otherId) {
var id;
if(otherId instanceof ObjectID) {
return this.toString() == otherId.toString();
} else if(typeof otherId == 'string' && ObjectID.isValid(otherId) && otherId.length == 12 && this.id instanceof _Buffer) {
return otherId === this.id.toString('binary');
} else if(typeof otherId == 'string' && ObjectID.isValid(otherId) && otherId.length == 24) {
return otherId.toLowerCase() === this.toHexString();
} else if(typeof otherId == 'string' && ObjectID.isValid(otherId) && otherId.length == 12) {
return otherId === this.id;
} else if(otherId != null && (otherId instanceof ObjectID || otherId.toHexString)) {
return otherId.toHexString() === this.toHexString();
} else {
return false;
}
}n/a
generate = function (time) {
if ('number' != typeof time) {
time = ~~(Date.now()/1000);
}
// Use pid
var pid = (typeof process === 'undefined' ? Math.floor(Math.random() * 100000) : process.pid) % 0xFFFF;
var inc = this.get_inc();
// Buffer used
var buffer = new Buffer(12);
// Encode time
buffer[3] = time & 0xff;
buffer[2] = (time >> 8) & 0xff;
buffer[1] = (time >> 16) & 0xff;
buffer[0] = (time >> 24) & 0xff;
// Encode machine
buffer[6] = MACHINE_ID & 0xff;
buffer[5] = (MACHINE_ID >> 8) & 0xff;
buffer[4] = (MACHINE_ID >> 16) & 0xff;
// Encode pid
buffer[8] = pid & 0xff;
buffer[7] = (pid >> 8) & 0xff;
// Encode index
buffer[11] = inc & 0xff;
buffer[10] = (inc >> 8) & 0xff;
buffer[9] = (inc >> 16) & 0xff;
// Return the buffer
return buffer;
}n/a
getInc = function () {
return this.get_inc();
}n/a
getTimestamp = function () {
var timestamp = new Date();
var time = this.id[3] | this.id[2] << 8 | this.id[1] << 16 | this.id[0] << 24;
timestamp.setTime(Math.floor(time) * 1000);
return timestamp;
}n/a
get_inc = function () {
return ObjectID.index = (ObjectID.index + 1) % 0xFFFFFF;
}n/a
inspect = function () {
return this.toHexString();
}n/a
toHexString = function () {
if(ObjectID.cacheHexString && this.__id) return this.__id;
var hexString = '';
if(!this.id || !this.id.length) {
throw new Error('invalid ObjectId, ObjectId.id must be either a string or a Buffer, but is [' + JSON.stringify(this.id) + ']\
');
}
if(this.id instanceof _Buffer) {
hexString = convertToHex(this.id);
if(ObjectID.cacheHexString) this.__id = hexString;
return hexString;
}
for (var i = 0; i < this.id.length; i++) {
hexString += hexTable[this.id.charCodeAt(i)];
}
if(ObjectID.cacheHexString) this.__id = hexString;
return hexString;
}n/a
toJSON = function () {
return this.toHexString();
}n/a
toString = function () {
return this.toHexString();
}n/a
function ObjectID(id) {
// Duck-typing to support ObjectId from different npm packages
if(id instanceof ObjectID) return id;
if(!(this instanceof ObjectID)) return new ObjectID(id);
this._bsontype = 'ObjectID';
var __id = null;
var valid = ObjectID.isValid(id);
// Throw an error if it's not a valid setup
if(!valid && id != null){
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
} else if(valid && typeof id == 'string' && id.length == 24) {
return ObjectID.createFromHexString(id);
} else if(id == null || typeof id == 'number') {
// convert to 12 byte binary string
this.id = this.generate(id);
} else if(id != null && id.length === 12) {
// assume 12 byte string
this.id = id;
} else if(id != null && id.toHexString) {
// Duck-typing to support ObjectId from different npm packages
return id;
} else {
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
}
if(ObjectID.cacheHexString) this.__id = this.toHexString();
}n/a
function ObjectID(id) {
// Duck-typing to support ObjectId from different npm packages
if(id instanceof ObjectID) return id;
if(!(this instanceof ObjectID)) return new ObjectID(id);
this._bsontype = 'ObjectID';
var __id = null;
var valid = ObjectID.isValid(id);
// Throw an error if it's not a valid setup
if(!valid && id != null){
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
} else if(valid && typeof id == 'string' && id.length == 24) {
return ObjectID.createFromHexString(id);
} else if(id == null || typeof id == 'number') {
// convert to 12 byte binary string
this.id = this.generate(id);
} else if(id != null && id.length === 12) {
// assume 12 byte string
this.id = id;
} else if(id != null && id.toHexString) {
// Duck-typing to support ObjectId from different npm packages
return id;
} else {
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
}
if(ObjectID.cacheHexString) this.__id = this.toHexString();
}n/a
function createFromHexString(string) {
// Throw an error if it's not a valid setup
if(typeof string === 'undefined' || string != null && string.length != 24)
throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
var length = string.length;
if(length > 12*2) {
throw new Error('Id cannot be longer than 12 bytes');
}
// Calculate lengths
var sizeof = length >> 1;
var array = new _Buffer(sizeof);
var n = 0;
var i = 0;
while (i < length) {
array[n++] = decodeLookup[string.charCodeAt(i++)] << 4 | decodeLookup[string.charCodeAt(i++)]
}
return new ObjectID(array);
}n/a
function createFromTime(time) {
var buffer = new Buffer([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]);
// Encode time into first 4 bytes
buffer[3] = time & 0xff;
buffer[2] = (time >> 8) & 0xff;
buffer[1] = (time >> 16) & 0xff;
buffer[0] = (time >> 24) & 0xff;
// Return the new objectId
return new ObjectID(buffer);
}n/a
function createPk() {
return new ObjectID();
}n/a
function isValid(id) {
if(id == null) return false;
if(typeof id == 'number') {
return true;
}
if(typeof id == 'string') {
return id.length == 12 || (id.length == 24 && checkForHexRegExp.test(id));
}
if(id instanceof ObjectID) {
return true;
}
if(id instanceof _Buffer) {
return true;
}
// Duck-Typing detection of ObjectId like objects
if(id.toHexString) {
return id.id.length == 12 || (id.id.length == 24 && checkForHexRegExp.test(id.id));
}
return false;
}n/a
function equals(otherId) {
var id;
if(otherId instanceof ObjectID) {
return this.toString() == otherId.toString();
} else if(typeof otherId == 'string' && ObjectID.isValid(otherId) && otherId.length == 12 && this.id instanceof _Buffer) {
return otherId === this.id.toString('binary');
} else if(typeof otherId == 'string' && ObjectID.isValid(otherId) && otherId.length == 24) {
return otherId.toLowerCase() === this.toHexString();
} else if(typeof otherId == 'string' && ObjectID.isValid(otherId) && otherId.length == 12) {
return otherId === this.id;
} else if(otherId != null && (otherId instanceof ObjectID || otherId.toHexString)) {
return otherId.toHexString() === this.toHexString();
} else {
return false;
}
}n/a
generate = function (time) {
if ('number' != typeof time) {
time = ~~(Date.now()/1000);
}
// Use pid
var pid = (typeof process === 'undefined' ? Math.floor(Math.random() * 100000) : process.pid) % 0xFFFF;
var inc = this.get_inc();
// Buffer used
var buffer = new Buffer(12);
// Encode time
buffer[3] = time & 0xff;
buffer[2] = (time >> 8) & 0xff;
buffer[1] = (time >> 16) & 0xff;
buffer[0] = (time >> 24) & 0xff;
// Encode machine
buffer[6] = MACHINE_ID & 0xff;
buffer[5] = (MACHINE_ID >> 8) & 0xff;
buffer[4] = (MACHINE_ID >> 16) & 0xff;
// Encode pid
buffer[8] = pid & 0xff;
buffer[7] = (pid >> 8) & 0xff;
// Encode index
buffer[11] = inc & 0xff;
buffer[10] = (inc >> 8) & 0xff;
buffer[9] = (inc >> 16) & 0xff;
// Return the buffer
return buffer;
}n/a
getInc = function () {
return this.get_inc();
}n/a
getTimestamp = function () {
var timestamp = new Date();
var time = this.id[3] | this.id[2] << 8 | this.id[1] << 16 | this.id[0] << 24;
timestamp.setTime(Math.floor(time) * 1000);
return timestamp;
}n/a
get_inc = function () {
return ObjectID.index = (ObjectID.index + 1) % 0xFFFFFF;
}n/a
inspect = function () {
return this.toHexString();
}n/a
toHexString = function () {
if(ObjectID.cacheHexString && this.__id) return this.__id;
var hexString = '';
if(!this.id || !this.id.length) {
throw new Error('invalid ObjectId, ObjectId.id must be either a string or a Buffer, but is [' + JSON.stringify(this.id) + ']\
');
}
if(this.id instanceof _Buffer) {
hexString = convertToHex(this.id);
if(ObjectID.cacheHexString) this.__id = hexString;
return hexString;
}
for (var i = 0; i < this.id.length; i++) {
hexString += hexTable[this.id.charCodeAt(i)];
}
if(ObjectID.cacheHexString) this.__id = hexString;
return hexString;
}n/a
toJSON = function () {
return this.toHexString();
}n/a
toString = function () {
return this.toHexString();
}n/a
ReadPreference = function (mode,
tags,
options) {
if(!(this instanceof ReadPreference)) {
return new ReadPreference(mode, tags, options);
}
this._type = 'ReadPreference';
this.mode = mode;
this.tags = tags;
this.options = options;
// If no tags were passed in
if(tags && typeof tags == 'object' && !Array.isArray(tags)) {
if(tags.maxStalenessSeconds) {
this.options = tags;
this.tags = null;
}
}
// Add the maxStalenessSeconds value to the read Preference
if(this.options && this.options.maxStalenessSeconds) {
this.maxStalenessSeconds = this.options.maxStalenessSeconds;
}
}n/a
isValid = function (_mode) {
return (_mode == ReadPreference.PRIMARY || _mode == ReadPreference.PRIMARY_PREFERRED
|| _mode == ReadPreference.SECONDARY || _mode == ReadPreference.SECONDARY_PREFERRED
|| _mode == ReadPreference.NEAREST
|| _mode == true || _mode == false || _mode == null);
}n/a
isValid = function (mode) {
var _mode = typeof mode == 'string' ? mode : this.mode;
return ReadPreference.isValid(_mode);
}n/a
toJSON = function () {
return this.toObject();
}n/a
toObject = function () {
var object = {mode:this.mode};
if(this.tags != null) {
object['tags'] = this.tags;
}
if(this.maxStalenessSeconds) {
object['maxStalenessSeconds'] = this.maxStalenessSeconds;
}
return object;
}n/a
ReplSet = function (servers,
options) {
if(!(this instanceof ReplSet)) return new ReplSet(servers, options);
options = options || {};
var self = this;
// Set up event emitter
EventEmitter.call(this);
// Filter the options
options = filterOptions(options, legalOptionNames);
// Ensure all the instances are Server
for(var i = 0; i < servers.length; i++) {
if(!(servers[i] instanceof Server)) {
throw MongoError.create({message: "all seed list instances must be of the Server type", driver:true});
}
}
// Stored options
var storeOptions = {
force: false
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : MAX_JS_INT
}
// Shared global store
var store = options.store || new Store(self, storeOptions);
// Build seed list
var seedlist = servers.map(function(x) {
return {host: x.host, port: x.port}
});
// Clone options
var clonedOptions = mergeOptions({}, {
disconnectHandler: store,
cursorFactory: Cursor,
reconnect: false,
emitError: typeof options.emitError == 'boolean' ? options.emitError : true,
size: typeof options.poolSize == 'number' ? options.poolSize : 5
});
// Translate any SSL options and other connectivity options
clonedOptions = translateOptions(clonedOptions, options);
// Socket options
var socketOptions = options.socketOptions && Object.keys(options.socketOptions).length > 0
? options.socketOptions : options;
// Translate all the options to the mongodb-core ones
clonedOptions = translateOptions(clonedOptions, socketOptions);
if(typeof clonedOptions.keepAlive == 'number') {
clonedOptions.keepAliveInitialDelay = clonedOptions.keepAlive;
clonedOptions.keepAlive = clonedOptions.keepAlive > 0;
}
// Client info
this.clientInfo = {
driver: {
name: "nodejs",
version: driverVersion
},
os: {
type: type,
name: name,
architecture: architecture,
version: release
},
platform: nodejsversion
}
// Build default client information
clonedOptions.clientInfo = this.clientInfo;
// Do we have an application specific string
if(options.appname) {
clonedOptions.clientInfo.application = { name: options.appname };
}
// Create the ReplSet
var replset = new CReplSet(seedlist, clonedOptions);
// Listen to reconnect event
replset.on('reconnect', function() {
self.emit('reconnect');
store.execute();
});
// Internal state
this.s = {
// Replicaset
replset: replset
// Server capabilities
, sCapabilities: null
// Debug tag
, tag: options.tag
// Store options
, storeOptions: storeOptions
// Cloned options
, clonedOptions: clonedOptions
// Store
, store: store
// Options
, options: options
}
// Debug
if(clonedOptions.debug) {
// Last ismaster
Object.defineProperty(this, 'replset', {
enumerable:true, get: function() { return replset; }
});
}
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
auth = function () {
var args = Array.prototype.slice.call(arguments, 0);
this.s.replset.auth.apply(this.s.replset, args);
}n/a
capabilities = function () {
if(this.s.sCapabilities) return this.s.sCapabilities;
if(this.s.replset.lastIsMaster() == null) return null;
this.s.sCapabilities = new ServerCapabilities(this.s.replset.lastIsMaster());
return this.s.sCapabilities;
}n/a
close = function (forceClosed) {
var self = this;
this.s.replset.destroy();
// We need to wash out all stored processes
if(forceClosed == true) {
this.s.storeOptions.force = forceClosed;
this.s.store.flush();
}
var events = ['timeout', 'error', 'close', 'joined', 'left'];
events.forEach(function(e) {
self.removeAllListeners(e);
});
}...
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
Given that you booted up the **mongod** process earlier the application should connect successfully and print **Connected correc\
tly to server** to the console.
Let's Add some code to show the different CRUD operations available.
...command = function (ns,
cmd,
options,
callback) {
options = translateReadPreference(options);
this.s.replset.command(ns, cmd, options, callback);
}n/a
connect = function (db,
_options,
callback) {
var self = this;
if('function' === typeof _options) callback = _options, _options = {};
if(_options == null) _options = {};
if(!('function' === typeof callback)) callback = null;
self.s.options = _options;
// Update bufferMaxEntries
self.s.storeOptions.bufferMaxEntries = db.bufferMaxEntries;
// Actual handler
var errorHandler = function(event) {
return function(err) {
if(event != 'error') {
self.emit(event, err);
}
}
}
// Connect handler
var connectHandler = function() {
// Clear out all the current handlers left over
["timeout", "error", "close", 'serverOpening', 'serverDescriptionChanged', 'serverHeartbeatStarted',
'serverHeartbeatSucceeded', 'serverHeartbeatFailed', 'serverClosed', 'topologyOpening',
'topologyClosed', 'topologyDescriptionChanged'].forEach(function(e) {
self.s.replset.removeAllListeners(e);
});
// Set up listeners
self.s.replset.once('timeout', errorHandler('timeout'));
self.s.replset.once('error', errorHandler('error'));
self.s.replset.once('close', errorHandler('close'));
// relay the event
var relay = function(event) {
return function(t, server) {
self.emit(event, t, server);
}
}
// Replset events relay
var replsetRelay = function(event) {
return function(t, server) {
self.emit(event, t, server.lastIsMaster(), server);
}
}
// Relay ha
var relayHa = function(t, state) {
self.emit('ha', t, state);
if(t == 'start') {
self.emit('ha_connect', t, state);
} else if(t == 'end') {
self.emit('ha_ismaster', t, state);
}
}
// Set up serverConfig listeners
self.s.replset.on('joined', replsetRelay('joined'));
self.s.replset.on('left', relay('left'));
self.s.replset.on('ping', relay('ping'));
self.s.replset.on('ha', relayHa);
// Set up SDAM listeners
self.s.replset.on('serverDescriptionChanged', relay('serverDescriptionChanged'));
self.s.replset.on('serverHeartbeatStarted', relay('serverHeartbeatStarted'));
self.s.replset.on('serverHeartbeatSucceeded', relay('serverHeartbeatSucceeded'));
self.s.replset.on('serverHeartbeatFailed', relay('serverHeartbeatFailed'));
self.s.replset.on('serverOpening', relay('serverOpening'));
self.s.replset.on('serverClosed', relay('serverClosed'));
self.s.replset.on('topologyOpening', relay('topologyOpening'));
self.s.replset.on('topologyClosed', relay('topologyClosed'));
self.s.replset.on('topologyDescriptionChanged', relay('topologyDescriptionChanged'));
self.s.replset.on('fullsetup', function() {
self.emit('fullsetup', null, self);
});
self.s.replset.on('all', function() {
self.emit('all', null, self);
});
// Emit open event
self.emit('open', null, self);
// Return correctly
try {
callback(null, self);
} catch(err) {
process.nextTick(function() { throw err; })
}
}
// Error handler
var connectErrorHandler = function() {
return function(err) {
['timeout', 'error', 'close'].forEach(function(e) {
self.s.replset.removeListener(e, connectErrorHandler);
});
self.s.replset.removeListener('connect', connectErrorHandler);
// Destroy the replset
self.s.replset.destroy();
// Try to callback
try {
callback(err);
} catch(err) {
if(!self.s.replset.isConnected())
process.nextTick(function() { throw err; })
}
}
}
// Set up listeners
self.s.replset.once('timeout', connectErrorHandler('timeout'));
self.s.replset.once('error', connectErrorHandler('error'));
self.s.replset.once('close', connectErrorHandler('close'));
self.s.replset.once('connect', connectHandler);
// Start connection
self.s.replset.connect(_options);
}...
```js
var MongoClient = require('mongodb').MongoClient
, assert = require('assert');
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
...connections = function () {
return this.s.replset.connections();
}n/a
cursor = function (ns,
cmd,
options) {
options = translateReadPreference(options);
options.disconnectHandler = this.s.store;
return this.s.replset.cursor(ns, cmd, options);
}n/a
insert = function (ns,
ops,
options,
callback) {
this.s.replset.insert(ns, ops, options, callback);
}n/a
isConnected = function (options) {
options = options || {};
// If we passed in a readPreference, translate to
// a CoreReadPreference instance
if(options.readPreference) {
options.readPreference = translateReadPreference(options.readPreference);
}
return this.s.replset.isConnected(options);
}n/a
isDestroyed = function () {
return this.s.replset.isDestroyed();
}n/a
lastIsMaster = function () {
return this.s.replset.lastIsMaster();
}n/a
logout = function () {
var args = Array.prototype.slice.call(arguments, 0);
this.s.replset.logout.apply(this.s.replset, args);
}n/a
remove = function (ns,
ops,
options,
callback) {
this.s.replset.remove(ns, ops, options, callback);
}n/a
update = function (ns,
ops,
options,
callback) {
this.s.replset.update(ns, ops, options, callback);
}n/a
Server = function (host,
port,
options) {
options = options || {};
if(!(this instanceof Server)) return new Server(host, port, options);
EventEmitter.call(this);
var self = this;
// Filter the options
options = filterOptions(options, legalOptionNames);
// Stored options
var storeOptions = {
force: false
, bufferMaxEntries: typeof options.bufferMaxEntries == 'number' ? options.bufferMaxEntries : MAX_JS_INT
}
// Shared global store
var store = options.store || new Store(self, storeOptions);
// Detect if we have a socket connection
if(host.indexOf('\/') != -1) {
if(port != null && typeof port == 'object') {
options = port;
port = null;
}
} else if(port == null) {
throw MongoError.create({message: 'port must be specified', driver:true});
}
// Get the reconnect option
var reconnect = typeof options.auto_reconnect == 'boolean' ? options.auto_reconnect : true;
reconnect = typeof options.autoReconnect == 'boolean' ? options.autoReconnect : reconnect;
// Clone options
var clonedOptions = mergeOptions({}, {
host: host, port: port, disconnectHandler: store,
cursorFactory: Cursor,
reconnect: reconnect,
emitError: typeof options.emitError == 'boolean' ? options.emitError : true,
size: typeof options.poolSize == 'number' ? options.poolSize : 5
});
// Translate any SSL options and other connectivity options
clonedOptions = translateOptions(clonedOptions, options);
// Socket options
var socketOptions = options.socketOptions && Object.keys(options.socketOptions).length > 0
? options.socketOptions : options;
// Translate all the options to the mongodb-core ones
clonedOptions = translateOptions(clonedOptions, socketOptions);
if(typeof clonedOptions.keepAlive == 'number') {
clonedOptions.keepAliveInitialDelay = clonedOptions.keepAlive;
clonedOptions.keepAlive = clonedOptions.keepAlive > 0;
}
// Build default client information
this.clientInfo = {
driver: {
name: "nodejs",
version: driverVersion
},
os: {
type: type,
name: name,
architecture: architecture,
version: release
},
platform: nodejsversion
}
// Build default client information
clonedOptions.clientInfo = this.clientInfo;
// Do we have an application specific string
if(options.appname) {
clonedOptions.clientInfo.application = { name: options.appname };
}
// Create an instance of a server instance from mongodb-core
var server = new CServer(clonedOptions);
// Define the internal properties
this.s = {
// Create an instance of a server instance from mongodb-core
server: server
// Server capabilities
, sCapabilities: null
// Cloned options
, clonedOptions: clonedOptions
// Reconnect
, reconnect: clonedOptions.reconnect
// Emit error
, emitError: clonedOptions.emitError
// Pool size
, poolSize: clonedOptions.size
// Store Options
, storeOptions: storeOptions
// Store
, store: store
// Host
, host: host
// Port
, port: port
// Options
, options: options
}
}n/a
function EventEmitter() {
EventEmitter.init.call(this);
}n/a
auth = function () {
var args = Array.prototype.slice.call(arguments, 0);
this.s.server.auth.apply(this.s.server, args);
}n/a
capabilities = function () {
if(this.s.sCapabilities) return this.s.sCapabilities;
if(this.s.server.lastIsMaster() == null) return null;
this.s.sCapabilities = new ServerCapabilities(this.s.server.lastIsMaster());
return this.s.sCapabilities;
}n/a
close = function (forceClosed) {
this.s.server.destroy();
// We need to wash out all stored processes
if(forceClosed == true) {
this.s.storeOptions.force = forceClosed;
this.s.store.flush();
}
}...
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
Given that you booted up the **mongod** process earlier the application should connect successfully and print **Connected correc\
tly to server** to the console.
Let's Add some code to show the different CRUD operations available.
...command = function (ns,
cmd,
options,
callback) {
this.s.server.command(ns, cmd, options, callback);
}n/a
connect = function (db,
_options,
callback) {
var self = this;
if('function' === typeof _options) callback = _options, _options = {};
if(_options == null) _options = {};
if(!('function' === typeof callback)) callback = null;
self.s.options = _options;
// Update bufferMaxEntries
self.s.storeOptions.bufferMaxEntries = db.bufferMaxEntries;
// Error handler
var connectErrorHandler = function() {
return function(err) {
// Remove all event handlers
var events = ['timeout', 'error', 'close'];
events.forEach(function(e) {
self.s.server.removeListener(e, connectHandlers[e]);
});
self.s.server.removeListener('connect', connectErrorHandler);
// Try to callback
try {
callback(err);
} catch(err) {
process.nextTick(function() { throw err; })
}
}
}
// Actual handler
var errorHandler = function(event) {
return function(err) {
if(event != 'error') {
self.emit(event, err);
}
}
}
// Error handler
var reconnectHandler = function() {
self.emit('reconnect', self);
self.s.store.execute();
}
// Reconnect failed
var reconnectFailedHandler = function(err) {
self.emit('reconnectFailed', err);
self.s.store.flush(err);
}
// Destroy called on topology, perform cleanup
var destroyHandler = function() {
self.s.store.flush();
}
// Connect handler
var connectHandler = function() {
// Clear out all the current handlers left over
["timeout", "error", "close", 'serverOpening', 'serverDescriptionChanged', 'serverHeartbeatStarted',
'serverHeartbeatSucceeded', 'serverHeartbeatFailed', 'serverClosed', 'topologyOpening',
'topologyClosed', 'topologyDescriptionChanged'].forEach(function(e) {
self.s.server.removeAllListeners(e);
});
// Set up listeners
self.s.server.on('timeout', errorHandler('timeout'));
self.s.server.once('error', errorHandler('error'));
self.s.server.on('close', errorHandler('close'));
// Only called on destroy
self.s.server.on('destroy', destroyHandler);
// relay the event
var relay = function(event) {
return function(t, server) {
self.emit(event, t, server);
}
}
// Set up SDAM listeners
self.s.server.on('serverDescriptionChanged', relay('serverDescriptionChanged'));
self.s.server.on('serverHeartbeatStarted', relay('serverHeartbeatStarted'));
self.s.server.on('serverHeartbeatSucceeded', relay('serverHeartbeatSucceeded'));
self.s.server.on('serverHeartbeatFailed', relay('serverHeartbeatFailed'));
self.s.server.on('serverOpening', relay('serverOpening'));
self.s.server.on('serverClosed', relay('serverClosed'));
self.s.server.on('topologyOpening', relay('topologyOpening'));
self.s.server.on('topologyClosed', relay('topologyClosed'));
self.s.server.on('topologyDescriptionChanged', relay('topologyDescriptionChanged'));
self.s.server.on('attemptReconnect', relay('attemptReconnect'));
self.s.server.on('monitoring', relay('monitoring'));
// Emit open event
self.emit('open', null, self);
// Return correctly
try {
callback(null, self);
} catch(err) {
console.log(err.stack)
process.nextTick(function() { throw err; })
}
}
// Set up listeners
var connectHandlers = {
timeout: connectErrorHandler('timeout'),
error: connectErrorHandler('error'),
close: connectErrorHandler('close')
};
// Add the event handlers
self.s.server.once('timeout', connectHandlers.timeout);
self.s.server.once('error', connectHandlers.error);
self.s.server.once('close', connectHandlers.close);
self.s.server.once('connect', connectHandler);
// Reconnect server
self.s.server.on('reconnect', reconnectHandler);
self.s.server.on('reconnectFailed', reconnectFailedHandler);
// Start connection
self.s.server.connect(_options);
}...
```js
var MongoClient = require('mongodb').MongoClient
, assert = require('assert');
// Connection URL
var url = 'mongodb://localhost:27017/myproject';
// Use connect method to connect to the Server
MongoClient.connect(url, function(err, db) {
assert.equal(null, err);
console.log("Connected correctly to server");
db.close();
});
```
...connections = function () {
return this.s.server.connections();
}n/a
cursor = function (ns,
cmd,
options) {
options.disconnectHandler = this.s.store;
return this.s.server.cursor(ns, cmd, options);
}n/a
insert = function (ns,
ops,
options,
callback) {
this.s.server.insert(ns, ops, options, callback);
}n/a
isConnected = function () {
return this.s.server.isConnected();
}n/a
isDestroyed = function () {
return this.s.server.isDestroyed();
}n/a
lastIsMaster = function () {
return this.s.server.lastIsMaster();
}n/a
logout = function () {
var args = Array.prototype.slice.call(arguments, 0);
this.s.server.logout.apply(this.s.server, args);
}n/a
remove = function (ns,
ops,
options,
callback) {
this.s.server.remove(ns, ops, options, callback);
}n/a
unref = function () {
this.s.server.unref();
}n/a
update = function (ns,
ops,
options,
callback) {
this.s.server.update(ns, ops, options, callback);
}n/a
function Symbol(value) {
if(!(this instanceof Symbol)) return new Symbol(value);
this._bsontype = 'Symbol';
this.value = value;
}n/a
inspect = function () {
return this.value;
}n/a
toJSON = function () {
return this.value;
}n/a
toString = function () {
return this.value;
}n/a
valueOf = function () {
return this.value;
}n/a
function Timestamp(low,
high) {
if(!(this instanceof Timestamp)) return new Timestamp(low, high);
this._bsontype = 'Timestamp';
/**
* @type {number}
* @ignore
*/
this.low_ = low | 0; // force into 32 signed bits.
/**
* @type {number}
* @ignore
*/
this.high_ = high | 0; // force into 32 signed bits.
}n/a
fromBits = function (lowBits,
highBits) {
return new Timestamp(lowBits, highBits);
}n/a
fromInt = function (value) {
if (-128 <= value && value < 128) {
var cachedObj = Timestamp.INT_CACHE_[value];
if (cachedObj) {
return cachedObj;
}
}
var obj = new Timestamp(value | 0, value < 0 ? -1 : 0);
if (-128 <= value && value < 128) {
Timestamp.INT_CACHE_[value] = obj;
}
return obj;
}n/a
fromNumber = function (value) {
if (isNaN(value) || !isFinite(value)) {
return Timestamp.ZERO;
} else if (value <= -Timestamp.TWO_PWR_63_DBL_) {
return Timestamp.MIN_VALUE;
} else if (value + 1 >= Timestamp.TWO_PWR_63_DBL_) {
return Timestamp.MAX_VALUE;
} else if (value < 0) {
return Timestamp.fromNumber(-value).negate();
} else {
return new Timestamp(
(value % Timestamp.TWO_PWR_32_DBL_) | 0,
(value / Timestamp.TWO_PWR_32_DBL_) | 0);
}
}n/a
fromString = function (str,
opt_radix) {
if (str.length == 0) {
throw Error('number format error: empty string');
}
var radix = opt_radix || 10;
if (radix < 2 || 36 < radix) {
throw Error('radix out of range: ' + radix);
}
if (str.charAt(0) == '-') {
return Timestamp.fromString(str.substring(1), radix).negate();
} else if (str.indexOf('-') >= 0) {
throw Error('number format error: interior "-" character: ' + str);
}
// Do several (8) digits each time through the loop, so as to
// minimize the calls to the very expensive emulated div.
var radixToPower = Timestamp.fromNumber(Math.pow(radix, 8));
var result = Timestamp.ZERO;
for (var i = 0; i < str.length; i += 8) {
var size = Math.min(8, str.length - i);
var value = parseInt(str.substring(i, i + size), radix);
if (size < 8) {
var power = Timestamp.fromNumber(Math.pow(radix, size));
result = result.multiply(power).add(Timestamp.fromNumber(value));
} else {
result = result.multiply(radixToPower);
result = result.add(Timestamp.fromNumber(value));
}
}
return result;
}n/a
add = function (other) {
// Divide each number into 4 chunks of 16 bits, and then sum the chunks.
var a48 = this.high_ >>> 16;
var a32 = this.high_ & 0xFFFF;
var a16 = this.low_ >>> 16;
var a00 = this.low_ & 0xFFFF;
var b48 = other.high_ >>> 16;
var b32 = other.high_ & 0xFFFF;
var b16 = other.low_ >>> 16;
var b00 = other.low_ & 0xFFFF;
var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
c00 += a00 + b00;
c16 += c00 >>> 16;
c00 &= 0xFFFF;
c16 += a16 + b16;
c32 += c16 >>> 16;
c16 &= 0xFFFF;
c32 += a32 + b32;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c48 += a48 + b48;
c48 &= 0xFFFF;
return Timestamp.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
}n/a
and = function (other) {
return Timestamp.fromBits(this.low_ & other.low_, this.high_ & other.high_);
}n/a
compare = function (other) {
if (this.equals(other)) {
return 0;
}
var thisNeg = this.isNegative();
var otherNeg = other.isNegative();
if (thisNeg && !otherNeg) {
return -1;
}
if (!thisNeg && otherNeg) {
return 1;
}
// at this point, the signs are the same, so subtraction will not overflow
if (this.subtract(other).isNegative()) {
return -1;
} else {
return 1;
}
}n/a
div = function (other) {
if (other.isZero()) {
throw Error('division by zero');
} else if (this.isZero()) {
return Timestamp.ZERO;
}
if (this.equals(Timestamp.MIN_VALUE)) {
if (other.equals(Timestamp.ONE) ||
other.equals(Timestamp.NEG_ONE)) {
return Timestamp.MIN_VALUE; // recall that -MIN_VALUE == MIN_VALUE
} else if (other.equals(Timestamp.MIN_VALUE)) {
return Timestamp.ONE;
} else {
// At this point, we have |other| >= 2, so |this/other| < |MIN_VALUE|.
var halfThis = this.shiftRight(1);
var approx = halfThis.div(other).shiftLeft(1);
if (approx.equals(Timestamp.ZERO)) {
return other.isNegative() ? Timestamp.ONE : Timestamp.NEG_ONE;
} else {
var rem = this.subtract(other.multiply(approx));
var result = approx.add(rem.div(other));
return result;
}
}
} else if (other.equals(Timestamp.MIN_VALUE)) {
return Timestamp.ZERO;
}
if (this.isNegative()) {
if (other.isNegative()) {
return this.negate().div(other.negate());
} else {
return this.negate().div(other).negate();
}
} else if (other.isNegative()) {
return this.div(other.negate()).negate();
}
// Repeat the following until the remainder is less than other: find a
// floating-point that approximates remainder / other *from below*, add this
// into the result, and subtract it from the remainder. It is critical that
// the approximate value is less than or equal to the real value so that the
// remainder never becomes negative.
var res = Timestamp.ZERO;
var rem = this;
while (rem.greaterThanOrEqual(other)) {
// Approximate the result of division. This may be a little greater or
// smaller than the actual value.
var approx = Math.max(1, Math.floor(rem.toNumber() / other.toNumber()));
// We will tweak the approximate result by changing it in the 48-th digit or
// the smallest non-fractional digit, whichever is larger.
var log2 = Math.ceil(Math.log(approx) / Math.LN2);
var delta = (log2 <= 48) ? 1 : Math.pow(2, log2 - 48);
// Decrease the approximation until it is smaller than the remainder. Note
// that if it is too large, the product overflows and is negative.
var approxRes = Timestamp.fromNumber(approx);
var approxRem = approxRes.multiply(other);
while (approxRem.isNegative() || approxRem.greaterThan(rem)) {
approx -= delta;
approxRes = Timestamp.fromNumber(approx);
approxRem = approxRes.multiply(other);
}
// We know the answer can't be zero... and actually, zero would cause
// infinite recursion since we would make no progress.
if (approxRes.isZero()) {
approxRes = Timestamp.ONE;
}
res = res.add(approxRes);
rem = rem.subtract(approxRem);
}
return res;
}n/a
equals = function (other) {
return (this.high_ == other.high_) && (this.low_ == other.low_);
}n/a
getHighBits = function () {
return this.high_;
}n/a
getLowBits = function () {
return this.low_;
}n/a
getLowBitsUnsigned = function () {
return (this.low_ >= 0) ?
this.low_ : Timestamp.TWO_PWR_32_DBL_ + this.low_;
}n/a
getNumBitsAbs = function () {
if (this.isNegative()) {
if (this.equals(Timestamp.MIN_VALUE)) {
return 64;
} else {
return this.negate().getNumBitsAbs();
}
} else {
var val = this.high_ != 0 ? this.high_ : this.low_;
for (var bit = 31; bit > 0; bit--) {
if ((val & (1 << bit)) != 0) {
break;
}
}
return this.high_ != 0 ? bit + 33 : bit + 1;
}
}n/a
greaterThan = function (other) {
return this.compare(other) > 0;
}n/a
greaterThanOrEqual = function (other) {
return this.compare(other) >= 0;
}n/a
isNegative = function () {
return this.high_ < 0;
}n/a
isOdd = function () {
return (this.low_ & 1) == 1;
}n/a
isZero = function () {
return this.high_ == 0 && this.low_ == 0;
}n/a
lessThan = function (other) {
return this.compare(other) < 0;
}n/a
lessThanOrEqual = function (other) {
return this.compare(other) <= 0;
}n/a
modulo = function (other) {
return this.subtract(this.div(other).multiply(other));
}n/a
multiply = function (other) {
if (this.isZero()) {
return Timestamp.ZERO;
} else if (other.isZero()) {
return Timestamp.ZERO;
}
if (this.equals(Timestamp.MIN_VALUE)) {
return other.isOdd() ? Timestamp.MIN_VALUE : Timestamp.ZERO;
} else if (other.equals(Timestamp.MIN_VALUE)) {
return this.isOdd() ? Timestamp.MIN_VALUE : Timestamp.ZERO;
}
if (this.isNegative()) {
if (other.isNegative()) {
return this.negate().multiply(other.negate());
} else {
return this.negate().multiply(other).negate();
}
} else if (other.isNegative()) {
return this.multiply(other.negate()).negate();
}
// If both Timestamps are small, use float multiplication
if (this.lessThan(Timestamp.TWO_PWR_24_) &&
other.lessThan(Timestamp.TWO_PWR_24_)) {
return Timestamp.fromNumber(this.toNumber() * other.toNumber());
}
// Divide each Timestamp into 4 chunks of 16 bits, and then add up 4x4 products.
// We can skip products that would overflow.
var a48 = this.high_ >>> 16;
var a32 = this.high_ & 0xFFFF;
var a16 = this.low_ >>> 16;
var a00 = this.low_ & 0xFFFF;
var b48 = other.high_ >>> 16;
var b32 = other.high_ & 0xFFFF;
var b16 = other.low_ >>> 16;
var b00 = other.low_ & 0xFFFF;
var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
c00 += a00 * b00;
c16 += c00 >>> 16;
c00 &= 0xFFFF;
c16 += a16 * b00;
c32 += c16 >>> 16;
c16 &= 0xFFFF;
c16 += a00 * b16;
c32 += c16 >>> 16;
c16 &= 0xFFFF;
c32 += a32 * b00;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c32 += a16 * b16;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c32 += a00 * b32;
c48 += c32 >>> 16;
c32 &= 0xFFFF;
c48 += a48 * b00 + a32 * b16 + a16 * b32 + a00 * b48;
c48 &= 0xFFFF;
return Timestamp.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
}n/a
negate = function () {
if (this.equals(Timestamp.MIN_VALUE)) {
return Timestamp.MIN_VALUE;
} else {
return this.not().add(Timestamp.ONE);
}
}n/a
not = function () {
return Timestamp.fromBits(~this.low_, ~this.high_);
}n/a
notEquals = function (other) {
return (this.high_ != other.high_) || (this.low_ != other.low_);
}n/a
or = function (other) {
return Timestamp.fromBits(this.low_ | other.low_, this.high_ | other.high_);
}n/a
shiftLeft = function (numBits) {
numBits &= 63;
if (numBits == 0) {
return this;
} else {
var low = this.low_;
if (numBits < 32) {
var high = this.high_;
return Timestamp.fromBits(
low << numBits,
(high << numBits) | (low >>> (32 - numBits)));
} else {
return Timestamp.fromBits(0, low << (numBits - 32));
}
}
}n/a
shiftRight = function (numBits) {
numBits &= 63;
if (numBits == 0) {
return this;
} else {
var high = this.high_;
if (numBits < 32) {
var low = this.low_;
return Timestamp.fromBits(
(low >>> numBits) | (high << (32 - numBits)),
high >> numBits);
} else {
return Timestamp.fromBits(
high >> (numBits - 32),
high >= 0 ? 0 : -1);
}
}
}n/a
shiftRightUnsigned = function (numBits) {
numBits &= 63;
if (numBits == 0) {
return this;
} else {
var high = this.high_;
if (numBits < 32) {
var low = this.low_;
return Timestamp.fromBits(
(low >>> numBits) | (high << (32 - numBits)),
high >>> numBits);
} else if (numBits == 32) {
return Timestamp.fromBits(high, 0);
} else {
return Timestamp.fromBits(high >>> (numBits - 32), 0);
}
}
}n/a
subtract = function (other) {
return this.add(other.negate());
}n/a
toInt = function () {
return this.low_;
}n/a
toJSON = function () {
return this.toString();
}n/a
toNumber = function () {
return this.high_ * Timestamp.TWO_PWR_32_DBL_ +
this.getLowBitsUnsigned();
}n/a
toString = function (opt_radix) {
var radix = opt_radix || 10;
if (radix < 2 || 36 < radix) {
throw Error('radix out of range: ' + radix);
}
if (this.isZero()) {
return '0';
}
if (this.isNegative()) {
if (this.equals(Timestamp.MIN_VALUE)) {
// We need to change the Timestamp value before it can be negated, so we remove
// the bottom-most digit in this base and then recurse to do the rest.
var radixTimestamp = Timestamp.fromNumber(radix);
var div = this.div(radixTimestamp);
var rem = div.multiply(radixTimestamp).subtract(this);
return div.toString(radix) + rem.toInt().toString(radix);
} else {
return '-' + this.negate().toString(radix);
}
}
// Do several (6) digits each time through the loop, so as to
// minimize the calls to the very expensive emulated div.
var radixToPower = Timestamp.fromNumber(Math.pow(radix, 6));
var rem = this;
var result = '';
while (true) {
var remDiv = rem.div(radixToPower);
var intval = rem.subtract(remDiv.multiply(radixToPower)).toInt();
var digits = intval.toString(radix);
rem = remDiv;
if (rem.isZero()) {
return digits + result;
} else {
while (digits.length < 6) {
digits = '0' + digits;
}
result = '' + digits + result;
}
}
}n/a
xor = function (other) {
return Timestamp.fromBits(this.low_ ^ other.low_, this.high_ ^ other.high_);
}n/a