This commit is contained in:
root
2019-11-28 20:40:02 +00:00
commit 1c78566f5b
2275 changed files with 272351 additions and 0 deletions
+3
View File
@@ -0,0 +1,3 @@
*.sw*
node_modules/
coverage/
+8
View File
@@ -0,0 +1,8 @@
language: node_js
node_js:
- "0.10"
- "0.12"
- "4"
- "5"
services:
- mongodb
+302
View File
@@ -0,0 +1,302 @@
2.3.3 / 2017-11-19
==================
* fixed; catch sync errors in cursor.toArray() re: Automattic/mongoose#5812
2.3.2 / 2017-09-27
==================
* fixed; bumped debug -> 2.6.9 re: #89
2.3.1 / 2017-05-22
==================
* fixed; bumped debug -> 2.6.7 re: #86
2.3.0 / 2017-03-05
==================
* added; replaceOne function
* added; deleteOne and deleteMany functions
2.2.3 / 2017-01-31
==================
* fixed; throw correct error when passing incorrectly formatted array to sort()
2.2.2 / 2017-01-31
==================
* fixed; allow passing maps to sort()
2.2.1 / 2017-01-29
==================
* fixed; allow passing string to hint()
2.2.0 / 2017-01-08
==================
* added; updateOne and updateMany functions
2.1.0 / 2016-12-22
==================
* added; ability to pass an array to select() #81 [dciccale](https://github.com/dciccale)
2.0.0 / 2016-09-25
==================
* added; support for mongodb driver 2.0 streams
1.12.0 / 2016-09-25
===================
* added; `retainKeyOrder` option re: Automattic/mongoose#4542
1.11.0 / 2016-06-04
===================
* added; `.minDistance()` helper and minDistance for `.near()` Automattic/mongoose#4179
1.10.1 / 2016-04-26
===================
* fixed; ensure conditions is an object before assigning #75
1.10.0 / 2016-03-16
==================
* updated; bluebird to latest 2.10.2 version #74 [matskiv](https://github.com/matskiv)
1.9.0 / 2016-03-15
==================
* added; `.eq` as a shortcut for `.equals` #72 [Fonger](https://github.com/Fonger)
* added; ability to use array syntax for sort re: https://jira.mongodb.org/browse/NODE-578 #67
1.8.0 / 2016-03-01
==================
* fixed; dont throw an error if count used with sort or select Automattic/mongoose#3914
1.7.0 / 2016-02-23
==================
* fixed; don't treat objects with a length property as argument objects #70
* added; `.findCursor()` method #69 [nswbmw](https://github.com/nswbmw)
* added; `_compiledUpdate` property #68 [nswbmw](https://github.com/nswbmw)
1.6.2 / 2015-07-12
==================
* fixed; support exec cb being called synchronously #66
1.6.1 / 2015-06-16
==================
* fixed; do not treat $meta projection as inclusive [vkarpov15](https://github.com/vkarpov15)
1.6.0 / 2015-05-27
==================
* update dependencies #65 [bachp](https://github.com/bachp)
1.5.0 / 2015-03-31
==================
* fixed; debug output
* fixed; allow hint usage with count #61 [trueinsider](https://github.com/trueinsider)
1.4.0 / 2015-03-29
==================
* added; object support to slice() #60 [vkarpov15](https://github.com/vkarpov15)
* debug; improved output #57 [flyvictor](https://github.com/flyvictor)
1.3.0 / 2014-11-06
==================
* added; setTraceFunction() #53 from [jlai](https://github.com/jlai)
1.2.1 / 2014-09-26
==================
* fixed; distinct assignment in toConstructor() #51 from [esco](https://github.com/esco)
1.2.0 / 2014-09-18
==================
* added; stream() support for find()
1.1.0 / 2014-09-15
==================
* add #then for co / koa support
* start checking code coverage
1.0.0 / 2014-07-07
==================
* Remove broken require() calls until they're actually implemented #48 [vkarpov15](https://github.com/vkarpov15)
0.9.0 / 2014-05-22
==================
* added; thunk() support
* release 0.8.0
0.8.0 / 2014-05-15
==================
* added; support for maxTimeMS #44 [yoitsro](https://github.com/yoitsro)
* updated; devDependency (driver to 1.4.4)
0.7.0 / 2014-05-02
==================
* fixed; pass $maxDistance in $near object as described in docs #43 [vkarpov15](https://github.com/vkarpov15)
* fixed; cloning buffers #42 [gjohnson](https://github.com/gjohnson)
* tests; a little bit more `mongodb` agnostic #34 [refack](https://github.com/refack)
0.6.0 / 2014-04-01
==================
* fixed; Allow $meta args in sort() so text search sorting works #37 [vkarpov15](https://github.com/vkarpov15)
0.5.3 / 2014-02-22
==================
* fixed; cloning mongodb.Binary
0.5.2 / 2014-01-30
==================
* fixed; cloning ObjectId constructors
* fixed; cloning of ReadPreferences #30 [ashtuchkin](https://github.com/ashtuchkin)
* tests; use specific mongodb version #29 [AvianFlu](https://github.com/AvianFlu)
* tests; remove dependency on ObjectId #28 [refack](https://github.com/refack)
* tests; add failing ReadPref test
0.5.1 / 2014-01-17
==================
* added; deprecation notice to tags parameter #27 [ashtuchkin](https://github.com/ashtuchkin)
* readme; add links
0.5.0 / 2014-01-16
==================
* removed; mongodb driver dependency #26 [ashtuchkin](https://github.com/ashtuchkin)
* removed; first class support of read preference tags #26 (still supported though) [ashtuchkin](https://github.com/ashtuchkin)
* added; better ObjectId clone support
* fixed; cloning objects that have no constructor #21
* docs; cleaned up [ashtuchkin](https://github.com/ashtuchkin)
0.4.2 / 2014-01-08
==================
* updated; debug module 0.7.4 [refack](https://github.com/refack)
0.4.1 / 2014-01-07
==================
* fixed; inclusive/exclusive logic
0.4.0 / 2014-01-06
==================
* added; selected()
* added; selectedInclusively()
* added; selectedExclusively()
0.3.3 / 2013-11-14
==================
* Fix Mongo DB Dependency #20 [rschmukler](https://github.com/rschmukler)
0.3.2 / 2013-09-06
==================
* added; geometry support for near()
0.3.1 / 2013-08-22
==================
* fixed; update retains key order #19
0.3.0 / 2013-08-22
==================
* less hardcoded isNode env detection #18 [vshulyak](https://github.com/vshulyak)
* added; validation of findAndModify varients
* clone update doc before execution
* stricter env checks
0.2.7 / 2013-08-2
==================
* Now support GeoJSON point values for Query#near
0.2.6 / 2013-07-30
==================
* internally, 'asc' and 'desc' for sorts are now converted into 1 and -1, respectively
0.2.5 / 2013-07-30
==================
* updated docs
* changed internal representation of `sort` to use objects instead of arrays
0.2.4 / 2013-07-25
==================
* updated; sliced to 0.0.5
0.2.3 / 2013-07-09
==================
* now using a callback in collection.find instead of directly calling toArray() on the cursor [ebensing](https://github.com/ebensing)
0.2.2 / 2013-07-09
==================
* now exposing mongodb export to allow for better testing [ebensing](https://github.com/ebensing)
0.2.1 / 2013-07-08
==================
* select no longer accepts arrays as parameters [ebensing](https://github.com/ebensing)
0.2.0 / 2013-07-05
==================
* use $geoWithin by default
0.1.2 / 2013-07-02
==================
* added use$geoWithin flag [ebensing](https://github.com/ebensing)
* fix read preferences typo [ebensing](https://github.com/ebensing)
* fix reference to old param name in exists() [ebensing](https://github.com/ebensing)
0.1.1 / 2013-06-24
==================
* fixed; $intersects -> $geoIntersects #14 [ebensing](https://github.com/ebensing)
* fixed; Retain key order when copying objects #15 [ebensing](https://github.com/ebensing)
* bump mongodb dev dep
0.1.0 / 2013-05-06
==================
* findAndModify; return the query
* move mquery.proto.canMerge to mquery.canMerge
* overwrite option now works with non-empty objects
* use strict mode
* validate count options
* validate distinct options
* add aggregate to base collection methods
* clone merge arguments
* clone merged update arguments
* move subclass to mquery.prototype.toConstructor
* fixed; maxScan casing
* use regexp-clone
* added; geometry/intersects support
* support $and
* near: do not use "radius"
* callbacks always fire on next turn of loop
* defined collection interface
* remove time from tests
* clarify goals
* updated docs;
0.0.1 / 2012-12-15
==================
* initial release
+22
View File
@@ -0,0 +1,22 @@
(The MIT License)
Copyright (c) 2012 [Aaron Heckmann](aaron.heckmann+github@gmail.com)
Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
'Software'), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+22
View File
@@ -0,0 +1,22 @@
test:
@NODE_ENV=test ./node_modules/.bin/mocha $(T) $(TESTS)
test-cov:
@NODE_ENV=test node \
node_modules/.bin/istanbul cover \
./node_modules/.bin/_mocha \
-- -u exports \
open-cov:
open coverage/lcov-report/index.html
test-travis:
@NODE_ENV=test node \
node_modules/.bin/istanbul cover \
./node_modules/.bin/_mocha \
--report lcovonly \
-- -u exports \
--bail
.PHONY: test test-cov open-cov test-travis
+1219
View File
File diff suppressed because it is too large Load Diff
+46
View File
@@ -0,0 +1,46 @@
'use strict';
/**
* methods a collection must implement
*/
var methods = [
'find'
, 'findOne'
, 'update'
, 'updateMany',
, 'updateOne'
, 'replaceOne'
, 'remove'
, 'count'
, 'distinct'
, 'findAndModify'
, 'aggregate'
, 'findStream'
, 'deleteOne'
, 'deleteMany'
];
/**
* Collection base class from which implementations inherit
*/
function Collection () {}
for (var i = 0, len = methods.length; i < len; ++i) {
var method = methods[i];
Collection.prototype[method] = notImplemented(method);
}
module.exports = exports = Collection;
Collection.methods = methods;
/**
* creates a function which throws an implementation error
*/
function notImplemented (method) {
return function () {
throw new Error('collection.' + method + ' not implemented');
}
}
+13
View File
@@ -0,0 +1,13 @@
'use strict';
var env = require('../env')
if ('unknown' == env.type) {
throw new Error('Unknown environment')
}
module.exports =
env.isNode ? require('./node') :
env.isMongo ? require('./collection') :
require('./collection');
+151
View File
@@ -0,0 +1,151 @@
'use strict';
/**
* Module dependencies
*/
var Collection = require('./collection');
var utils = require('../utils');
function NodeCollection (col) {
this.collection = col;
this.collectionName = col.collectionName;
}
/**
* inherit from collection base class
*/
utils.inherits(NodeCollection, Collection);
/**
* find(match, options, function(err, docs))
*/
NodeCollection.prototype.find = function (match, options, cb) {
this.collection.find(match, options, function (err, cursor) {
if (err) return cb(err);
try {
cursor.toArray(cb);
} catch (error) {
cb(error);
}
});
}
/**
* findOne(match, options, function(err, doc))
*/
NodeCollection.prototype.findOne = function (match, options, cb) {
this.collection.findOne(match, options, cb);
}
/**
* count(match, options, function(err, count))
*/
NodeCollection.prototype.count = function (match, options, cb) {
this.collection.count(match, options, cb);
}
/**
* distinct(prop, match, options, function(err, count))
*/
NodeCollection.prototype.distinct = function (prop, match, options, cb) {
this.collection.distinct(prop, match, options, cb);
}
/**
* update(match, update, options, function(err[, result]))
*/
NodeCollection.prototype.update = function (match, update, options, cb) {
this.collection.update(match, update, options, cb);
}
/**
* update(match, update, options, function(err[, result]))
*/
NodeCollection.prototype.updateMany = function (match, update, options, cb) {
this.collection.updateMany(match, update, options, cb);
}
/**
* update(match, update, options, function(err[, result]))
*/
NodeCollection.prototype.updateOne = function (match, update, options, cb) {
this.collection.updateOne(match, update, options, cb);
}
/**
* replaceOne(match, update, options, function(err[, result]))
*/
NodeCollection.prototype.replaceOne = function (match, update, options, cb) {
this.collection.replaceOne(match, update, options, cb);
}
/**
* deleteOne(match, options, function(err[, result])
*/
NodeCollection.prototype.deleteOne = function (match, options, cb) {
this.collection.deleteOne(match, options, cb);
}
/**
* deleteMany(match, options, function(err[, result])
*/
NodeCollection.prototype.deleteMany = function (match, options, cb) {
this.collection.deleteMany(match, options, cb);
}
/**
* remove(match, options, function(err[, result])
*/
NodeCollection.prototype.remove = function (match, options, cb) {
this.collection.remove(match, options, cb);
}
/**
* findAndModify(match, update, options, function(err, doc))
*/
NodeCollection.prototype.findAndModify = function (match, update, options, cb) {
var sort = Array.isArray(options.sort) ? options.sort : [];
this.collection.findAndModify(match, sort, update, options, cb);
}
/**
* var stream = findStream(match, findOptions, streamOptions)
*/
NodeCollection.prototype.findStream = function(match, findOptions, streamOptions) {
return this.collection.find(match, findOptions);
}
/**
* var cursor = findCursor(match, findOptions)
*/
NodeCollection.prototype.findCursor = function(match, findOptions) {
return this.collection.find(match, findOptions);
}
/**
* aggregation(operators..., function(err, doc))
* TODO
*/
/**
* Expose
*/
module.exports = exports = NodeCollection;
+22
View File
@@ -0,0 +1,22 @@
'use strict';
exports.isNode = 'undefined' != typeof process
&& 'object' == typeof module
&& 'object' == typeof global
&& 'function' == typeof Buffer
&& process.argv
exports.isMongo = !exports.isNode
&& 'function' == typeof printjson
&& 'function' == typeof ObjectId
&& 'function' == typeof rs
&& 'function' == typeof sh;
exports.isBrowser = !exports.isNode
&& !exports.isMongo
&& 'undefined' != typeof window;
exports.type = exports.isNode ? 'node'
: exports.isMongo ? 'mongo'
: exports.isBrowser ? 'browser'
: 'unknown'
+3041
View File
File diff suppressed because it is too large Load Diff
+88
View File
@@ -0,0 +1,88 @@
'use strict';
var denied = exports;
denied.distinct = function (self) {
if (self._fields && Object.keys(self._fields).length > 0) {
return 'field selection and slice'
}
var keys = Object.keys(denied.distinct);
var err;
keys.every(function (option) {
if (self.options[option]) {
err = option;
return false;
}
return true;
});
return err;
};
denied.distinct.select =
denied.distinct.slice =
denied.distinct.sort =
denied.distinct.limit =
denied.distinct.skip =
denied.distinct.batchSize =
denied.distinct.comment =
denied.distinct.maxScan =
denied.distinct.snapshot =
denied.distinct.hint =
denied.distinct.tailable = true;
// aggregation integration
denied.findOneAndUpdate =
denied.findOneAndRemove = function (self) {
var keys = Object.keys(denied.findOneAndUpdate);
var err;
keys.every(function (option) {
if (self.options[option]) {
err = option;
return false;
}
return true;
});
return err;
}
denied.findOneAndUpdate.limit =
denied.findOneAndUpdate.skip =
denied.findOneAndUpdate.batchSize =
denied.findOneAndUpdate.maxScan =
denied.findOneAndUpdate.snapshot =
denied.findOneAndUpdate.hint =
denied.findOneAndUpdate.tailable =
denied.findOneAndUpdate.comment = true;
denied.count = function (self) {
if (self._fields && Object.keys(self._fields).length > 0) {
return 'field selection and slice'
}
var keys = Object.keys(denied.count);
var err;
keys.every(function (option) {
if (self.options[option]) {
err = option;
return false;
}
return true;
});
return err;
}
denied.count.slice =
denied.count.batchSize =
denied.count.comment =
denied.count.maxScan =
denied.count.snapshot =
denied.count.tailable = true;
+342
View File
@@ -0,0 +1,342 @@
'use strict';
/*!
* Module dependencies.
*/
var RegExpClone = require('regexp-clone')
/**
* Clones objects
*
* @param {Object} obj the object to clone
* @param {Object} options
* @return {Object} the cloned object
* @api private
*/
var clone = exports.clone = function clone (obj, options) {
if (obj === undefined || obj === null)
return obj;
if (Array.isArray(obj))
return exports.cloneArray(obj, options);
if (obj.constructor) {
if (/ObjectI[dD]$/.test(obj.constructor.name)) {
return 'function' == typeof obj.clone
? obj.clone()
: new obj.constructor(obj.id);
}
if ('ReadPreference' === obj._type && obj.isValid && obj.toObject) {
return 'function' == typeof obj.clone
? obj.clone()
: new obj.constructor(obj.mode, clone(obj.tags, options));
}
if ('Binary' == obj._bsontype && obj.buffer && obj.value) {
return 'function' == typeof obj.clone
? obj.clone()
: new obj.constructor(obj.value(true), obj.sub_type);
}
if ('Date' === obj.constructor.name || 'Function' === obj.constructor.name)
return new obj.constructor(+obj);
if ('RegExp' === obj.constructor.name)
return RegExpClone(obj);
if ('Buffer' === obj.constructor.name)
return exports.cloneBuffer(obj);
}
if (isObject(obj))
return exports.cloneObject(obj, options);
if (obj.valueOf)
return obj.valueOf();
};
/*!
* ignore
*/
var cloneObject = exports.cloneObject = function cloneObject (obj, options) {
var retainKeyOrder = options && options.retainKeyOrder
, minimize = options && options.minimize
, ret = {}
, hasKeys
, keys
, val
, k
, i
if (retainKeyOrder) {
for (k in obj) {
val = clone(obj[k], options);
if (!minimize || ('undefined' !== typeof val)) {
hasKeys || (hasKeys = true);
ret[k] = val;
}
}
} else {
// faster
keys = Object.keys(obj);
i = keys.length;
while (i--) {
k = keys[i];
val = clone(obj[k], options);
if (!minimize || ('undefined' !== typeof val)) {
if (!hasKeys) hasKeys = true;
ret[k] = val;
}
}
}
return minimize
? hasKeys && ret
: ret;
};
var cloneArray = exports.cloneArray = function cloneArray (arr, options) {
var ret = [];
for (var i = 0, l = arr.length; i < l; i++)
ret.push(clone(arr[i], options));
return ret;
};
/**
* process.nextTick helper.
*
* Wraps the given `callback` in a try/catch. If an error is
* caught it will be thrown on nextTick.
*
* node-mongodb-native had a habit of state corruption when
* an error was immediately thrown from within a collection
* method (find, update, etc) callback.
*
* @param {Function} [callback]
* @api private
*/
var tick = exports.tick = function tick (callback) {
if ('function' !== typeof callback) return;
return function () {
// callbacks should always be fired on the next
// turn of the event loop. A side benefit is
// errors thrown from executing the callback
// will not cause drivers state to be corrupted
// which has historically been a problem.
var args = arguments;
soon(function(){
callback.apply(this, args);
});
}
}
/**
* Merges `from` into `to` without overwriting existing properties.
*
* @param {Object} to
* @param {Object} from
* @api private
*/
var merge = exports.merge = function merge (to, from) {
var keys = Object.keys(from)
, i = keys.length
, key
while (i--) {
key = keys[i];
if ('undefined' === typeof to[key]) {
to[key] = from[key];
} else {
if (exports.isObject(from[key])) {
merge(to[key], from[key]);
} else {
to[key] = from[key];
}
}
}
}
/**
* Same as merge but clones the assigned values.
*
* @param {Object} to
* @param {Object} from
* @api private
*/
var mergeClone = exports.mergeClone = function mergeClone (to, from) {
var keys = Object.keys(from)
, i = keys.length
, key
while (i--) {
key = keys[i];
if ('undefined' === typeof to[key]) {
// make sure to retain key order here because of a bug handling the $each
// operator in mongodb 2.4.4
to[key] = clone(from[key], { retainKeyOrder : 1});
} else {
if (exports.isObject(from[key])) {
mergeClone(to[key], from[key]);
} else {
// make sure to retain key order here because of a bug handling the
// $each operator in mongodb 2.4.4
to[key] = clone(from[key], { retainKeyOrder : 1});
}
}
}
}
/**
* Read pref helper (mongo 2.2 drivers support this)
*
* Allows using aliases instead of full preference names:
*
* p primary
* pp primaryPreferred
* s secondary
* sp secondaryPreferred
* n nearest
*
* @param {String} pref
*/
exports.readPref = function readPref (pref) {
switch (pref) {
case 'p':
pref = 'primary';
break;
case 'pp':
pref = 'primaryPreferred';
break;
case 's':
pref = 'secondary';
break;
case 'sp':
pref = 'secondaryPreferred';
break;
case 'n':
pref = 'nearest';
break;
}
return pref;
}
/**
* Object.prototype.toString.call helper
*/
var _toString = Object.prototype.toString;
var toString = exports.toString = function (arg) {
return _toString.call(arg);
}
/**
* Determines if `arg` is an object.
*
* @param {Object|Array|String|Function|RegExp|any} arg
* @return {Boolean}
*/
var isObject = exports.isObject = function (arg) {
return '[object Object]' == exports.toString(arg);
}
/**
* Determines if `arg` is an array.
*
* @param {Object}
* @return {Boolean}
* @see nodejs utils
*/
var isArray = exports.isArray = function (arg) {
return Array.isArray(arg) ||
'object' == typeof arg && '[object Array]' == exports.toString(arg);
}
/**
* Object.keys helper
*/
exports.keys = Object.keys || function (obj) {
var keys = [];
for (var k in obj) if (obj.hasOwnProperty(k)) {
keys.push(k);
}
return keys;
}
/**
* Basic Object.create polyfill.
* Only one argument is supported.
*
* Based on https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Object/create
*/
exports.create = 'function' == typeof Object.create
? Object.create
: create;
function create (proto) {
if (arguments.length > 1) {
throw new Error("Adding properties is not supported")
}
function F () {}
F.prototype = proto;
return new F;
}
/**
* inheritance
*/
exports.inherits = function (ctor, superCtor) {
ctor.prototype = exports.create(superCtor.prototype);
ctor.prototype.constructor = ctor;
}
/**
* nextTick helper
* compat with node 0.10 which behaves differently than previous versions
*/
var soon = exports.soon = 'function' == typeof setImmediate
? setImmediate
: process.nextTick;
/**
* Clones the contents of a buffer.
*
* @param {Buffer} buff
* @return {Buffer}
*/
exports.cloneBuffer = function (buff) {
var dupe = new Buffer(buff.length);
buff.copy(dupe, 0, 0, buff.length);
return dupe;
};
/**
* Check if this object is an arguments object
*
* @param {Any} v
* @return {Boolean}
*/
exports.isArgumentsObject = function(v) {
return Object.prototype.toString.call(v) === '[object Arguments]';
};
+2
View File
@@ -0,0 +1,2 @@
*.sw*
node_modules/
+4
View File
@@ -0,0 +1,4 @@
language: node_js
node_js:
- 0.6
- 0.8
+30
View File
@@ -0,0 +1,30 @@
0.0.5 / 2013-02-05
==================
* optimization: remove use of arguments [jkroso](https://github.com/jkroso)
* add scripts to component.json [jkroso](https://github.com/jkroso)
* tests; remove time for travis
0.0.4 / 2013-01-07
==================
* added component.json #1 [jkroso](https://github.com/jkroso)
* reversed array loop #1 [jkroso](https://github.com/jkroso)
* remove fn params
0.0.3 / 2012-09-29
==================
* faster with negative start args
0.0.2 / 2012-09-29
==================
* support full [].slice semantics
0.0.1 / 2012-09-29
===================
* initial release
+22
View File
@@ -0,0 +1,22 @@
(The MIT License)
Copyright (c) 2012 [Aaron Heckmann](aaron.heckmann+github@gmail.com)
Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
'Software'), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+5
View File
@@ -0,0 +1,5 @@
test:
@./node_modules/.bin/mocha $(T) $(TESTS)
.PHONY: test
+62
View File
@@ -0,0 +1,62 @@
#sliced
==========
A faster alternative to `[].slice.call(arguments)`.
[![Build Status](https://secure.travis-ci.org/aheckmann/sliced.png)](http://travis-ci.org/aheckmann/sliced)
Example output from [benchmark.js](https://github.com/bestiejs/benchmark.js)
Array.prototype.slice.call x 1,320,205 ops/sec ±2.35% (92 runs sampled)
[].slice.call x 1,314,605 ops/sec ±1.60% (95 runs sampled)
cached slice.call x 10,468,380 ops/sec ±1.45% (95 runs sampled)
sliced x 16,608,237 ops/sec ±1.40% (92 runs sampled)
fastest is sliced
Array.prototype.slice.call(arguments, 1) x 1,383,584 ops/sec ±1.73% (97 runs sampled)
[].slice.call(arguments, 1) x 1,494,735 ops/sec ±1.33% (95 runs sampled)
cached slice.call(arguments, 1) x 10,085,270 ops/sec ±1.51% (97 runs sampled)
sliced(arguments, 1) x 16,620,480 ops/sec ±1.29% (95 runs sampled)
fastest is sliced(arguments, 1)
Array.prototype.slice.call(arguments, -1) x 1,303,262 ops/sec ±1.62% (94 runs sampled)
[].slice.call(arguments, -1) x 1,325,615 ops/sec ±1.36% (97 runs sampled)
cached slice.call(arguments, -1) x 9,673,603 ops/sec ±1.70% (96 runs sampled)
sliced(arguments, -1) x 16,384,575 ops/sec ±1.06% (91 runs sampled)
fastest is sliced(arguments, -1)
Array.prototype.slice.call(arguments, -2, -10) x 1,404,390 ops/sec ±1.61% (95 runs sampled)
[].slice.call(arguments, -2, -10) x 1,514,367 ops/sec ±1.21% (96 runs sampled)
cached slice.call(arguments, -2, -10) x 9,836,017 ops/sec ±1.21% (95 runs sampled)
sliced(arguments, -2, -10) x 18,544,882 ops/sec ±1.30% (91 runs sampled)
fastest is sliced(arguments, -2, -10)
Array.prototype.slice.call(arguments, -2, -1) x 1,458,604 ops/sec ±1.41% (97 runs sampled)
[].slice.call(arguments, -2, -1) x 1,536,547 ops/sec ±1.63% (99 runs sampled)
cached slice.call(arguments, -2, -1) x 10,060,633 ops/sec ±1.37% (96 runs sampled)
sliced(arguments, -2, -1) x 18,608,712 ops/sec ±1.08% (93 runs sampled)
fastest is sliced(arguments, -2, -1)
_Benchmark [source](https://github.com/aheckmann/sliced/blob/master/bench.js)._
##Usage
`sliced` accepts the same arguments as `Array#slice` so you can easily swap it out.
```js
function zing () {
var slow = [].slice.call(arguments, 1, 8);
var args = slice(arguments, 1, 8);
var slow = Array.prototype.slice.call(arguments);
var args = slice(arguments);
// etc
}
```
## install
npm install sliced
[LICENSE](https://github.com/aheckmann/sliced/blob/master/LICENSE)
+95
View File
@@ -0,0 +1,95 @@
var sliced = require('./')
var Bench = require('benchmark');
var s = new Bench.Suite;
var slice = [].slice;
s.add('Array.prototype.slice.call', function () {
Array.prototype.slice.call(arguments);
}).add('[].slice.call', function () {
[].slice.call(arguments);
}).add('cached slice.call', function () {
slice.call(arguments)
}).add('sliced', function () {
sliced(arguments)
}).on('cycle', function (evt) {
console.log(String(evt.target));
}).on('complete', function () {
console.log('fastest is %s', this.filter('fastest').pluck('name'));
})
.run();
var s = new Bench.Suite;
s.add('Array.prototype.slice.call(arguments, 1)', function () {
Array.prototype.slice.call(arguments, 1);
}).add('[].slice.call(arguments, 1)', function () {
[].slice.call(arguments, 1);
}).add('cached slice.call(arguments, 1)', function () {
slice.call(arguments, 1)
}).add('sliced(arguments, 1)', function () {
sliced(arguments, 1)
}).on('cycle', function (evt) {
console.log(String(evt.target));
}).on('complete', function () {
console.log('fastest is %s', this.filter('fastest').pluck('name'));
})
.run();
var s = new Bench.Suite;
s.add('Array.prototype.slice.call(arguments, -1)', function () {
Array.prototype.slice.call(arguments, -1);
}).add('[].slice.call(arguments, -1)', function () {
[].slice.call(arguments, -1);
}).add('cached slice.call(arguments, -1)', function () {
slice.call(arguments, -1)
}).add('sliced(arguments, -1)', function () {
sliced(arguments, -1)
}).on('cycle', function (evt) {
console.log(String(evt.target));
}).on('complete', function () {
console.log('fastest is %s', this.filter('fastest').pluck('name'));
})
.run();
var s = new Bench.Suite;
s.add('Array.prototype.slice.call(arguments, -2, -10)', function () {
Array.prototype.slice.call(arguments, -2, -10);
}).add('[].slice.call(arguments, -2, -10)', function () {
[].slice.call(arguments, -2, -10);
}).add('cached slice.call(arguments, -2, -10)', function () {
slice.call(arguments, -2, -10)
}).add('sliced(arguments, -2, -10)', function () {
sliced(arguments, -2, -10)
}).on('cycle', function (evt) {
console.log(String(evt.target));
}).on('complete', function () {
console.log('fastest is %s', this.filter('fastest').pluck('name'));
})
.run();
var s = new Bench.Suite;
s.add('Array.prototype.slice.call(arguments, -2, -1)', function () {
Array.prototype.slice.call(arguments, -2, -1);
}).add('[].slice.call(arguments, -2, -1)', function () {
[].slice.call(arguments, -2, -1);
}).add('cached slice.call(arguments, -2, -1)', function () {
slice.call(arguments, -2, -1)
}).add('sliced(arguments, -2, -1)', function () {
sliced(arguments, -2, -1)
}).on('cycle', function (evt) {
console.log(String(evt.target));
}).on('complete', function () {
console.log('fastest is %s', this.filter('fastest').pluck('name'));
})
.run();
/**
* Output:
*
* Array.prototype.slice.call x 1,289,592 ops/sec ±2.88% (87 runs sampled)
* [].slice.call x 1,345,451 ops/sec ±1.68% (97 runs sampled)
* cached slice.call x 10,719,886 ops/sec ±1.04% (99 runs sampled)
* sliced x 15,809,545 ops/sec ±1.46% (93 runs sampled)
* fastest is sliced
*
*/
+14
View File
@@ -0,0 +1,14 @@
{
"name": "sliced",
"version": "0.0.5",
"description": "A faster Node.js alternative to Array.prototype.slice.call(arguments)",
"repo" : "aheckmann/sliced",
"keywords": [
"arguments",
"slice",
"array"
],
"scripts": ["lib/sliced.js", "index.js"],
"author": "Aaron Heckmann <aaron.heckmann+github@gmail.com>",
"license": "MIT"
}
+1
View File
@@ -0,0 +1 @@
module.exports = exports = require('./lib/sliced');
+33
View File
@@ -0,0 +1,33 @@
/**
* An Array.prototype.slice.call(arguments) alternative
*
* @param {Object} args something with a length
* @param {Number} slice
* @param {Number} sliceEnd
* @api public
*/
module.exports = function (args, slice, sliceEnd) {
var ret = [];
var len = args.length;
if (0 === len) return ret;
var start = slice < 0
? Math.max(0, slice + len)
: slice || 0;
if (sliceEnd !== undefined) {
len = sliceEnd < 0
? sliceEnd + len
: sliceEnd
}
while (len-- > start) {
ret[len - start] = args[len];
}
return ret;
}
+56
View File
@@ -0,0 +1,56 @@
{
"_from": "sliced@0.0.5",
"_id": "sliced@0.0.5",
"_inBundle": false,
"_integrity": "sha1-XtwETKTrb3gW1Qui/GPiXY/kcH8=",
"_location": "/mquery/sliced",
"_phantomChildren": {},
"_requested": {
"type": "version",
"registry": true,
"raw": "sliced@0.0.5",
"name": "sliced",
"escapedName": "sliced",
"rawSpec": "0.0.5",
"saveSpec": null,
"fetchSpec": "0.0.5"
},
"_requiredBy": [
"/mquery"
],
"_resolved": "https://registry.npmjs.org/sliced/-/sliced-0.0.5.tgz",
"_shasum": "5edc044ca4eb6f7816d50ba2fc63e25d8fe4707f",
"_spec": "sliced@0.0.5",
"_where": "/app/node_modules/mquery",
"author": {
"name": "Aaron Heckmann",
"email": "aaron.heckmann+github@gmail.com"
},
"bugs": {
"url": "https://github.com/aheckmann/sliced/issues"
},
"bundleDependencies": false,
"deprecated": false,
"description": "A faster Node.js alternative to Array.prototype.slice.call(arguments)",
"devDependencies": {
"benchmark": "~1.0.0",
"mocha": "1.5.0"
},
"homepage": "https://github.com/aheckmann/sliced#readme",
"keywords": [
"arguments",
"slice",
"array"
],
"license": "MIT",
"main": "index.js",
"name": "sliced",
"repository": {
"type": "git",
"url": "git://github.com/aheckmann/sliced.git"
},
"scripts": {
"test": "make test"
},
"version": "0.0.5"
}
+80
View File
@@ -0,0 +1,80 @@
var sliced = require('../')
var assert = require('assert')
describe('sliced', function(){
it('exports a function', function(){
assert.equal('function', typeof sliced);
})
describe('with 1 arg', function(){
it('returns an array of the arg', function(){
var o = [3, "4", {}];
var r = sliced(o);
assert.equal(3, r.length);
assert.equal(o[0], r[0]);
assert.equal(o[1], r[1]);
assert.equal(o[1], r[1]);
})
})
describe('with 2 args', function(){
it('returns an array of the arg starting at the 2nd arg', function(){
var o = [3, "4", 5, null];
var r = sliced(o, 2);
assert.equal(2, r.length);
assert.equal(o[2], r[0]);
assert.equal(o[3], r[1]);
})
})
describe('with 3 args', function(){
it('returns an array of the arg from the 2nd to the 3rd arg', function(){
var o = [3, "4", 5, null];
var r = sliced(o, 1, 2);
assert.equal(1, r.length);
assert.equal(o[1], r[0]);
})
})
describe('with negative start and no end', function(){
it('begins at an offset from the end and includes all following elements', function(){
var o = [3, "4", 5, null];
var r = sliced(o, -2);
assert.equal(2, r.length);
assert.equal(o[2], r[0]);
assert.equal(o[3], r[1]);
var r = sliced(o, -12);
assert.equal(4, r.length);
assert.equal(o[0], r[0]);
assert.equal(o[1], r[1]);
})
})
describe('with negative start and positive end', function(){
it('begins at an offset from the end and includes `end` elements', function(){
var o = [3, "4", {x:1}, null];
var r = sliced(o, -2, 1);
assert.equal(0, r.length);
var r = sliced(o, -2, 2);
assert.equal(0, r.length);
var r = sliced(o, -2, 3);
assert.equal(1, r.length);
assert.equal(o[2], r[0]);
})
})
describe('with negative start and negative end', function(){
it('begins at `start` offset from the end and includes all elements up to `end` offset from the end', function(){
var o = [3, "4", {x:1}, null];
var r = sliced(o, -3, -1);
assert.equal(2, r.length);
assert.equal(o[1], r[0]);
assert.equal(o[2], r[1]);
var r = sliced(o, -3, -3);
assert.equal(0, r.length);
var r = sliced(o, -3, -4);
assert.equal(0, r.length);
})
})
})
+63
View File
@@ -0,0 +1,63 @@
{
"_from": "mquery@2.3.3",
"_id": "mquery@2.3.3",
"_inBundle": false,
"_integrity": "sha512-NC8L14kn+qxJbbJ1gbcEMDxF0sC3sv+1cbRReXXwVvowcwY1y9KoVZFq0ebwARibsadu8lx8nWGvm3V0Pf0ZWQ==",
"_location": "/mquery",
"_phantomChildren": {},
"_requested": {
"type": "version",
"registry": true,
"raw": "mquery@2.3.3",
"name": "mquery",
"escapedName": "mquery",
"rawSpec": "2.3.3",
"saveSpec": null,
"fetchSpec": "2.3.3"
},
"_requiredBy": [
"/mongoose"
],
"_resolved": "https://registry.npmjs.org/mquery/-/mquery-2.3.3.tgz",
"_shasum": "221412e5d4e7290ca5582dd16ea8f190a506b518",
"_spec": "mquery@2.3.3",
"_where": "/app/node_modules/mongoose",
"author": {
"name": "Aaron Heckmann",
"email": "aaron.heckmann+github@gmail.com"
},
"bugs": {
"url": "https://github.com/aheckmann/mquery/issues/new"
},
"bundleDependencies": false,
"dependencies": {
"bluebird": "3.5.0",
"debug": "2.6.9",
"regexp-clone": "0.0.1",
"sliced": "0.0.5"
},
"deprecated": false,
"description": "Expressive query building for MongoDB",
"devDependencies": {
"istanbul": "0.3.2",
"mocha": "3.2.0",
"mongodb": "~2.2"
},
"homepage": "https://github.com/aheckmann/mquery/",
"keywords": [
"mongodb",
"query",
"builder"
],
"license": "MIT",
"main": "lib/mquery.js",
"name": "mquery",
"repository": {
"type": "git",
"url": "git://github.com/aheckmann/mquery.git"
},
"scripts": {
"test": "mocha test/index.js test/*.test.js"
},
"version": "2.3.3"
}
View File
View File
+28
View File
@@ -0,0 +1,28 @@
var assert = require('assert')
var slice = require('sliced')
var mongo = require('mongodb')
var utils = require('../../').utils;
var uri = process.env.MQUERY_URI || 'mongodb://localhost/mquery';
var db;
exports.getCollection = function (cb) {
mongo.MongoClient.connect(uri, function (err, db_) {
assert.ifError(err);
db = db_;
var collection = db.collection('stuff');
// clean test db before starting
db.dropDatabase(function () {
cb(null, collection);
});
})
}
exports.dropCollection = function (cb) {
db.dropDatabase(function () {
db.close(cb);
})
}
+20
View File
@@ -0,0 +1,20 @@
var assert = require('assert')
var env = require('../').env;
console.log('environment: %s', env.type);
var col;
switch (env.type) {
case 'node':
col = require('./collection/node');
break;
case 'mongo':
col = require('./collection/mongo');
case 'browser':
col = require('./collection/browser');
default:
throw new Error('missing collection implementation for environment: ' + env.type);
}
module.exports = exports = col;
+2944
View File
File diff suppressed because it is too large Load Diff
+143
View File
@@ -0,0 +1,143 @@
var utils = require('../lib/utils');
var assert = require('assert');
var mongo;
try {
mongo = new require('mongodb');
} catch (e) {}
describe('lib/utils', function() {
describe('clone', function() {
it('clones constructors named ObjectId', function(done) {
function ObjectId (id) {
this.id = id;
}
var o1 = new ObjectId('1234');
var o2 = utils.clone(o1);
assert.ok(o2 instanceof ObjectId);
done();
});
it('clones constructors named ObjectID', function(done) {
function ObjectID (id) {
this.id = id;
}
var o1 = new ObjectID('1234');
var o2 = utils.clone(o1);
assert.ok(o2 instanceof ObjectID);
done();
});
it('does not clone constructors named ObjectIdd', function(done) {
function ObjectIdd (id) {
this.id = id;
}
var o1 = new ObjectIdd('1234');
var o2 = utils.clone(o1);
assert.ok(!(o2 instanceof ObjectIdd));
done();
});
it('optionally clones ObjectId constructors using its clone method', function(done) {
function ObjectID (id) {
this.id = id;
this.cloned = false;
}
ObjectID.prototype.clone = function () {
var ret = new ObjectID(this.id);
ret.cloned = true;
return ret;
}
var id = 1234;
var o1 = new ObjectID(id);
assert.equal(id, o1.id);
assert.equal(false, o1.cloned);
var o2 = utils.clone(o1);
assert.ok(o2 instanceof ObjectID);
assert.equal(id, o2.id);
assert.ok(o2.cloned);
done();
});
it('clones mongodb.ReadPreferences', function (done) {
if (!mongo) return done();
var tags = [
{dc: 'tag1'}
];
var prefs = [
new mongo.ReadPreference("primary"),
new mongo.ReadPreference(mongo.ReadPreference.PRIMARY_PREFERRED),
new mongo.ReadPreference("primary", tags),
mongo.ReadPreference("primary", tags)
];
var prefsCloned = utils.clone(prefs);
for (var i = 0; i < prefsCloned.length; i++) {
assert.notEqual(prefs[i], prefsCloned[i]);
assert.ok(prefsCloned[i] instanceof mongo.ReadPreference);
assert.ok(prefsCloned[i].isValid());
if (prefs[i].tags) {
assert.ok(prefsCloned[i].tags);
assert.notEqual(prefs[i].tags, prefsCloned[i].tags);
assert.notEqual(prefs[i].tags[0], prefsCloned[i].tags[0]);
} else {
assert.equal(prefsCloned[i].tags, null);
}
}
done();
});
it('clones mongodb.Binary', function(done){
if (!mongo) return done();
var buf = new Buffer('hi');
var binary= new mongo.Binary(buf, 2);
var clone = utils.clone(binary);
assert.equal(binary.sub_type, clone.sub_type);
assert.equal(String(binary.buffer), String(buf));
assert.ok(binary !== clone);
done();
})
it('handles objects with no constructor', function(done) {
var name ='335';
var o = Object.create(null);
o.name = name;
var clone;
assert.doesNotThrow(function() {
clone = utils.clone(o);
});
assert.equal(name, clone.name);
assert.ok(o != clone);
done();
});
it('handles buffers', function(done){
var buff = new Buffer(10);
buff.fill(1);
var clone = utils.clone(buff);
for (var i = 0; i < buff.length; i++) {
assert.equal(buff[i], clone[i]);
}
done();
});
});
});