Ohm-Management - Projektarbeit B-ME
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

README.md 36KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375
  1. # mquery
  2. `mquery` is a fluent mongodb query builder designed to run in multiple environments.
  3. [![Build Status](https://travis-ci.org/aheckmann/mquery.svg?branch=master)](https://travis-ci.org/aheckmann/mquery)
  4. [![NPM version](https://badge.fury.io/js/mquery.svg)](http://badge.fury.io/js/mquery)
  5. [![npm](https://nodei.co/npm/mquery.png)](https://www.npmjs.com/package/mquery)
  6. ## Features
  7. - fluent query builder api
  8. - custom base query support
  9. - MongoDB 2.4 geoJSON support
  10. - method + option combinations validation
  11. - node.js driver compatibility
  12. - environment detection
  13. - [debug](https://github.com/visionmedia/debug) support
  14. - separated collection implementations for maximum flexibility
  15. ## Use
  16. ```js
  17. require('mongodb').connect(uri, function (err, db) {
  18. if (err) return handleError(err);
  19. // get a collection
  20. var collection = db.collection('artists');
  21. // pass it to the constructor
  22. mquery(collection).find({..}, callback);
  23. // or pass it to the collection method
  24. mquery().find({..}).collection(collection).exec(callback)
  25. // or better yet, create a custom query constructor that has it always set
  26. var Artist = mquery(collection).toConstructor();
  27. Artist().find(..).where(..).exec(callback)
  28. })
  29. ```
  30. `mquery` requires a collection object to work with. In the example above we just pass the collection object created using the official [MongoDB driver](https://github.com/mongodb/node-mongodb-native).
  31. ## Fluent API
  32. - [find](#find)
  33. - [findOne](#findOne)
  34. - [count](#count)
  35. - [remove](#remove)
  36. - [update](#update)
  37. - [findOneAndUpdate](#findoneandupdate)
  38. - [findOneAndDelete, findOneAndRemove](#findoneandremove)
  39. - [distinct](#distinct)
  40. - [exec](#exec)
  41. - [stream](#stream)
  42. - [all](#all)
  43. - [and](#and)
  44. - [box](#box)
  45. - [circle](#circle)
  46. - [elemMatch](#elemmatch)
  47. - [equals](#equals)
  48. - [exists](#exists)
  49. - [geometry](#geometry)
  50. - [gt](#gt)
  51. - [gte](#gte)
  52. - [in](#in)
  53. - [intersects](#intersects)
  54. - [lt](#lt)
  55. - [lte](#lte)
  56. - [maxDistance](#maxdistance)
  57. - [mod](#mod)
  58. - [ne](#ne)
  59. - [nin](#nin)
  60. - [nor](#nor)
  61. - [near](#near)
  62. - [or](#or)
  63. - [polygon](#polygon)
  64. - [regex](#regex)
  65. - [select](#select)
  66. - [selected](#selected)
  67. - [selectedInclusively](#selectedinclusively)
  68. - [selectedExclusively](#selectedexclusively)
  69. - [size](#size)
  70. - [slice](#slice)
  71. - [within](#within)
  72. - [where](#where)
  73. - [$where](#where-1)
  74. - [batchSize](#batchsize)
  75. - [collation](#collation)
  76. - [comment](#comment)
  77. - [hint](#hint)
  78. - [j](#j)
  79. - [limit](#limit)
  80. - [maxScan](#maxscan)
  81. - [maxTime, maxTimeMS](#maxtime)
  82. - [skip](#skip)
  83. - [sort](#sort)
  84. - [read, setReadPreference](#read)
  85. - [readConcern, r](#readconcern)
  86. - [slaveOk](#slaveok)
  87. - [snapshot](#snapshot)
  88. - [tailable](#tailable)
  89. - [writeConcern, w](#writeconcern)
  90. - [wtimeout, wTimeout](#wtimeout)
  91. ## Helpers
  92. - [collection](#collection)
  93. - [then](#then)
  94. - [thunk](#thunk)
  95. - [merge](#mergeobject)
  96. - [setOptions](#setoptionsoptions)
  97. - [setTraceFunction](#settracefunctionfunc)
  98. - [mquery.setGlobalTraceFunction](#mquerysetglobaltracefunctionfunc)
  99. - [mquery.canMerge](#mquerycanmerge)
  100. - [mquery.use$geoWithin](#mqueryusegeowithin)
  101. ### find()
  102. Declares this query a _find_ query. Optionally pass a match clause and / or callback. If a callback is passed the query is executed.
  103. ```js
  104. mquery().find()
  105. mquery().find(match)
  106. mquery().find(callback)
  107. mquery().find(match, function (err, docs) {
  108. assert(Array.isArray(docs));
  109. })
  110. ```
  111. ### findOne()
  112. Declares this query a _findOne_ query. Optionally pass a match clause and / or callback. If a callback is passed the query is executed.
  113. ```js
  114. mquery().findOne()
  115. mquery().findOne(match)
  116. mquery().findOne(callback)
  117. mquery().findOne(match, function (err, doc) {
  118. if (doc) {
  119. // the document may not be found
  120. console.log(doc);
  121. }
  122. })
  123. ```
  124. ### count()
  125. Declares this query a _count_ query. Optionally pass a match clause and / or callback. If a callback is passed the query is executed.
  126. ```js
  127. mquery().count()
  128. mquery().count(match)
  129. mquery().count(callback)
  130. mquery().count(match, function (err, number){
  131. console.log('we found %d matching documents', number);
  132. })
  133. ```
  134. ### remove()
  135. Declares this query a _remove_ query. Optionally pass a match clause and / or callback. If a callback is passed the query is executed.
  136. ```js
  137. mquery().remove()
  138. mquery().remove(match)
  139. mquery().remove(callback)
  140. mquery().remove(match, function (err){})
  141. ```
  142. ### update()
  143. Declares this query an _update_ query. Optionally pass an update document, match clause, options or callback. If a callback is passed, the query is executed. To force execution without passing a callback, run `update(true)`.
  144. ```js
  145. mquery().update()
  146. mquery().update(match, updateDocument)
  147. mquery().update(match, updateDocument, options)
  148. // the following all execute the command
  149. mquery().update(callback)
  150. mquery().update({$set: updateDocument, callback)
  151. mquery().update(match, updateDocument, callback)
  152. mquery().update(match, updateDocument, options, function (err, result){})
  153. mquery().update(true) // executes (unsafe write)
  154. ```
  155. ##### the update document
  156. All paths passed that are not `$atomic` operations will become `$set` ops. For example:
  157. ```js
  158. mquery(collection).where({ _id: id }).update({ title: 'words' }, callback)
  159. ```
  160. becomes
  161. ```js
  162. collection.update({ _id: id }, { $set: { title: 'words' }}, callback)
  163. ```
  164. This behavior can be overridden using the `overwrite` option (see below).
  165. ##### options
  166. Options are passed to the `setOptions()` method.
  167. - overwrite
  168. Passing an empty object `{ }` as the update document will result in a no-op unless the `overwrite` option is passed. Without the `overwrite` option, the update operation will be ignored and the callback executed without sending the command to MongoDB to prevent accidently overwritting documents in the collection.
  169. ```js
  170. var q = mquery(collection).where({ _id: id }).setOptions({ overwrite: true });
  171. q.update({ }, callback); // overwrite with an empty doc
  172. ```
  173. The `overwrite` option isn't just for empty objects, it also provides a means to override the default `$set` conversion and send the update document as is.
  174. ```js
  175. // create a base query
  176. var base = mquery({ _id: 108 }).collection(collection).toConstructor();
  177. base().findOne(function (err, doc) {
  178. console.log(doc); // { _id: 108, name: 'cajon' })
  179. base().setOptions({ overwrite: true }).update({ changed: true }, function (err) {
  180. base.findOne(function (err, doc) {
  181. console.log(doc); // { _id: 108, changed: true }) - the doc was overwritten
  182. });
  183. });
  184. })
  185. ```
  186. - multi
  187. Updates only modify a single document by default. To update multiple documents, set the `multi` option to `true`.
  188. ```js
  189. mquery()
  190. .collection(coll)
  191. .update({ name: /^match/ }, { $addToSet: { arr: 4 }}, { multi: true }, callback)
  192. // another way of doing it
  193. mquery({ name: /^match/ })
  194. .collection(coll)
  195. .setOptions({ multi: true })
  196. .update({ $addToSet: { arr: 4 }}, callback)
  197. // update multiple documents with an empty doc
  198. var q = mquery(collection).where({ name: /^match/ });
  199. q.setOptions({ multi: true, overwrite: true })
  200. q.update({ });
  201. q.update(function (err, result) {
  202. console.log(arguments);
  203. });
  204. ```
  205. ### findOneAndUpdate()
  206. Declares this query a _findAndModify_ with update query. Optionally pass a match clause, update document, options, or callback. If a callback is passed, the query is executed.
  207. When executed, the first matching document (if found) is modified according to the update document and passed back to the callback.
  208. ##### options
  209. Options are passed to the `setOptions()` method.
  210. - `new`: boolean - true to return the modified document rather than the original. defaults to true
  211. - `upsert`: boolean - creates the object if it doesn't exist. defaults to false
  212. - `sort`: if multiple docs are found by the match condition, sets the sort order to choose which doc to update
  213. ```js
  214. query.findOneAndUpdate()
  215. query.findOneAndUpdate(updateDocument)
  216. query.findOneAndUpdate(match, updateDocument)
  217. query.findOneAndUpdate(match, updateDocument, options)
  218. // the following all execute the command
  219. query.findOneAndUpdate(callback)
  220. query.findOneAndUpdate(updateDocument, callback)
  221. query.findOneAndUpdate(match, updateDocument, callback)
  222. query.findOneAndUpdate(match, updateDocument, options, function (err, doc) {
  223. if (doc) {
  224. // the document may not be found
  225. console.log(doc);
  226. }
  227. })
  228. ```
  229. ### findOneAndRemove()
  230. Declares this query a _findAndModify_ with remove query. Alias of findOneAndDelete.
  231. Optionally pass a match clause, options, or callback. If a callback is passed, the query is executed.
  232. When executed, the first matching document (if found) is modified according to the update document, removed from the collection and passed to the callback.
  233. ##### options
  234. Options are passed to the `setOptions()` method.
  235. - `sort`: if multiple docs are found by the condition, sets the sort order to choose which doc to modify and remove
  236. ```js
  237. A.where().findOneAndDelete()
  238. A.where().findOneAndRemove()
  239. A.where().findOneAndRemove(match)
  240. A.where().findOneAndRemove(match, options)
  241. // the following all execute the command
  242. A.where().findOneAndRemove(callback)
  243. A.where().findOneAndRemove(match, callback)
  244. A.where().findOneAndRemove(match, options, function (err, doc) {
  245. if (doc) {
  246. // the document may not be found
  247. console.log(doc);
  248. }
  249. })
  250. ```
  251. ### distinct()
  252. Declares this query a _distinct_ query. Optionally pass the distinct field, a match clause or callback. If a callback is passed the query is executed.
  253. ```js
  254. mquery().distinct()
  255. mquery().distinct(match)
  256. mquery().distinct(match, field)
  257. mquery().distinct(field)
  258. // the following all execute the command
  259. mquery().distinct(callback)
  260. mquery().distinct(field, callback)
  261. mquery().distinct(match, callback)
  262. mquery().distinct(match, field, function (err, result) {
  263. console.log(result);
  264. })
  265. ```
  266. ### exec()
  267. Executes the query.
  268. ```js
  269. mquery().findOne().where('route').intersects(polygon).exec(function (err, docs){})
  270. ```
  271. ### stream()
  272. Executes the query and returns a stream.
  273. ```js
  274. var stream = mquery().find().stream(options);
  275. stream.on('data', cb);
  276. stream.on('close', fn);
  277. ```
  278. Note: this only works with `find()` operations.
  279. Note: returns the stream object directly from the node-mongodb-native driver. (currently streams1 type stream). Any options will be passed along to the [driver method](http://mongodb.github.io/node-mongodb-native/api-generated/cursor.html#stream).
  280. -------------
  281. ### all()
  282. Specifies an `$all` query condition
  283. ```js
  284. mquery().where('permission').all(['read', 'write'])
  285. ```
  286. [MongoDB documentation](http://docs.mongodb.org/manual/reference/operator/all/)
  287. ### and()
  288. Specifies arguments for an `$and` condition
  289. ```js
  290. mquery().and([{ color: 'green' }, { status: 'ok' }])
  291. ```
  292. [MongoDB documentation](http://docs.mongodb.org/manual/reference/operator/and/)
  293. ### box()
  294. Specifies a `$box` condition
  295. ```js
  296. var lowerLeft = [40.73083, -73.99756]
  297. var upperRight= [40.741404, -73.988135]
  298. mquery().where('location').within().box(lowerLeft, upperRight)
  299. ```
  300. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/box/)
  301. ### circle()
  302. Specifies a `$center` or `$centerSphere` condition.
  303. ```js
  304. var area = { center: [50, 50], radius: 10, unique: true }
  305. query.where('loc').within().circle(area)
  306. query.circle('loc', area);
  307. // for spherical calculations
  308. var area = { center: [50, 50], radius: 10, unique: true, spherical: true }
  309. query.where('loc').within().circle(area)
  310. query.circle('loc', area);
  311. ```
  312. - [MongoDB Documentation - center](http://docs.mongodb.org/manual/reference/operator/center/)
  313. - [MongoDB Documentation - centerSphere](http://docs.mongodb.org/manual/reference/operator/centerSphere/)
  314. ### elemMatch()
  315. Specifies an `$elemMatch` condition
  316. ```js
  317. query.where('comment').elemMatch({ author: 'autobot', votes: {$gte: 5}})
  318. query.elemMatch('comment', function (elem) {
  319. elem.where('author').equals('autobot');
  320. elem.where('votes').gte(5);
  321. })
  322. ```
  323. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/elemMatch/)
  324. ### equals()
  325. Specifies the complementary comparison value for the path specified with `where()`.
  326. ```js
  327. mquery().where('age').equals(49);
  328. // is the same as
  329. mquery().where({ 'age': 49 });
  330. ```
  331. ### exists()
  332. Specifies an `$exists` condition
  333. ```js
  334. // { name: { $exists: true }}
  335. mquery().where('name').exists()
  336. mquery().where('name').exists(true)
  337. mquery().exists('name')
  338. // { name: { $exists: false }}
  339. mquery().where('name').exists(false);
  340. mquery().exists('name', false);
  341. ```
  342. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/exists/)
  343. ### geometry()
  344. Specifies a `$geometry` condition
  345. ```js
  346. var polyA = [[[ 10, 20 ], [ 10, 40 ], [ 30, 40 ], [ 30, 20 ]]]
  347. query.where('loc').within().geometry({ type: 'Polygon', coordinates: polyA })
  348. // or
  349. var polyB = [[ 0, 0 ], [ 1, 1 ]]
  350. query.where('loc').within().geometry({ type: 'LineString', coordinates: polyB })
  351. // or
  352. var polyC = [ 0, 0 ]
  353. query.where('loc').within().geometry({ type: 'Point', coordinates: polyC })
  354. // or
  355. query.where('loc').intersects().geometry({ type: 'Point', coordinates: polyC })
  356. // or
  357. query.where('loc').near().geometry({ type: 'Point', coordinates: [3,5] })
  358. ```
  359. `geometry()` **must** come after `intersects()`, `within()`, or `near()`.
  360. The `object` argument must contain `type` and `coordinates` properties.
  361. - type `String`
  362. - coordinates `Array`
  363. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/geometry/)
  364. ### gt()
  365. Specifies a `$gt` query condition.
  366. ```js
  367. mquery().where('clicks').gt(999)
  368. ```
  369. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/gt/)
  370. ### gte()
  371. Specifies a `$gte` query condition.
  372. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/gte/)
  373. ```js
  374. mquery().where('clicks').gte(1000)
  375. ```
  376. ### in()
  377. Specifies an `$in` query condition.
  378. ```js
  379. mquery().where('author_id').in([3, 48901, 761])
  380. ```
  381. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/in/)
  382. ### intersects()
  383. Declares an `$geoIntersects` query for `geometry()`.
  384. ```js
  385. query.where('path').intersects().geometry({
  386. type: 'LineString'
  387. , coordinates: [[180.0, 11.0], [180, 9.0]]
  388. })
  389. // geometry arguments are supported
  390. query.where('path').intersects({
  391. type: 'LineString'
  392. , coordinates: [[180.0, 11.0], [180, 9.0]]
  393. })
  394. ```
  395. **Must** be used after `where()`.
  396. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/geoIntersects/)
  397. ### lt()
  398. Specifies a `$lt` query condition.
  399. ```js
  400. mquery().where('clicks').lt(50)
  401. ```
  402. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/lt/)
  403. ### lte()
  404. Specifies a `$lte` query condition.
  405. ```js
  406. mquery().where('clicks').lte(49)
  407. ```
  408. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/lte/)
  409. ### maxDistance()
  410. Specifies a `$maxDistance` query condition.
  411. ```js
  412. mquery().where('location').near({ center: [139, 74.3] }).maxDistance(5)
  413. ```
  414. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/maxDistance/)
  415. ### mod()
  416. Specifies a `$mod` condition
  417. ```js
  418. mquery().where('count').mod(2, 0)
  419. ```
  420. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/mod/)
  421. ### ne()
  422. Specifies a `$ne` query condition.
  423. ```js
  424. mquery().where('status').ne('ok')
  425. ```
  426. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/ne/)
  427. ### nin()
  428. Specifies an `$nin` query condition.
  429. ```js
  430. mquery().where('author_id').nin([3, 48901, 761])
  431. ```
  432. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/nin/)
  433. ### nor()
  434. Specifies arguments for an `$nor` condition.
  435. ```js
  436. mquery().nor([{ color: 'green' }, { status: 'ok' }])
  437. ```
  438. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/nor/)
  439. ### near()
  440. Specifies arguments for a `$near` or `$nearSphere` condition.
  441. These operators return documents sorted by distance.
  442. #### Example
  443. ```js
  444. query.where('loc').near({ center: [10, 10] });
  445. query.where('loc').near({ center: [10, 10], maxDistance: 5 });
  446. query.near('loc', { center: [10, 10], maxDistance: 5 });
  447. // GeoJSON
  448. query.where('loc').near({ center: { type: 'Point', coordinates: [10, 10] }});
  449. query.where('loc').near({ center: { type: 'Point', coordinates: [10, 10] }, maxDistance: 5, spherical: true });
  450. query.where('loc').near().geometry({ type: 'Point', coordinates: [10, 10] });
  451. // For a $nearSphere condition, pass the `spherical` option.
  452. query.near({ center: [10, 10], maxDistance: 5, spherical: true });
  453. ```
  454. [MongoDB Documentation](http://www.mongodb.org/display/DOCS/Geospatial+Indexing)
  455. ### or()
  456. Specifies arguments for an `$or` condition.
  457. ```js
  458. mquery().or([{ color: 'red' }, { status: 'emergency' }])
  459. ```
  460. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/or/)
  461. ### polygon()
  462. Specifies a `$polygon` condition
  463. ```js
  464. mquery().where('loc').within().polygon([10,20], [13, 25], [7,15])
  465. mquery().polygon('loc', [10,20], [13, 25], [7,15])
  466. ```
  467. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/polygon/)
  468. ### regex()
  469. Specifies a `$regex` query condition.
  470. ```js
  471. mquery().where('name').regex(/^sixstepsrecords/)
  472. ```
  473. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/regex/)
  474. ### select()
  475. Specifies which document fields to include or exclude
  476. ```js
  477. // 1 means include, 0 means exclude
  478. mquery().select({ name: 1, address: 1, _id: 0 })
  479. // or
  480. mquery().select('name address -_id')
  481. ```
  482. ##### String syntax
  483. When passing a string, prefixing a path with `-` will flag that path as excluded. When a path does not have the `-` prefix, it is included.
  484. ```js
  485. // include a and b, exclude c
  486. query.select('a b -c');
  487. // or you may use object notation, useful when
  488. // you have keys already prefixed with a "-"
  489. query.select({a: 1, b: 1, c: 0});
  490. ```
  491. _Cannot be used with `distinct()`._
  492. ### selected()
  493. Determines if the query has selected any fields.
  494. ```js
  495. var query = mquery();
  496. query.selected() // false
  497. query.select('-name');
  498. query.selected() // true
  499. ```
  500. ### selectedInclusively()
  501. Determines if the query has selected any fields inclusively.
  502. ```js
  503. var query = mquery().select('name');
  504. query.selectedInclusively() // true
  505. var query = mquery();
  506. query.selected() // false
  507. query.select('-name');
  508. query.selectedInclusively() // false
  509. query.selectedExclusively() // true
  510. ```
  511. ### selectedExclusively()
  512. Determines if the query has selected any fields exclusively.
  513. ```js
  514. var query = mquery().select('-name');
  515. query.selectedExclusively() // true
  516. var query = mquery();
  517. query.selected() // false
  518. query.select('name');
  519. query.selectedExclusively() // false
  520. query.selectedInclusively() // true
  521. ```
  522. ### size()
  523. Specifies a `$size` query condition.
  524. ```js
  525. mquery().where('someArray').size(6)
  526. ```
  527. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/size/)
  528. ### slice()
  529. Specifies a `$slice` projection for a `path`
  530. ```js
  531. mquery().where('comments').slice(5)
  532. mquery().where('comments').slice(-5)
  533. mquery().where('comments').slice([-10, 5])
  534. ```
  535. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/projection/slice/)
  536. ### within()
  537. Sets a `$geoWithin` or `$within` argument for geo-spatial queries.
  538. ```js
  539. mquery().within().box()
  540. mquery().within().circle()
  541. mquery().within().geometry()
  542. mquery().where('loc').within({ center: [50,50], radius: 10, unique: true, spherical: true });
  543. mquery().where('loc').within({ box: [[40.73, -73.9], [40.7, -73.988]] });
  544. mquery().where('loc').within({ polygon: [[],[],[],[]] });
  545. mquery().where('loc').within([], [], []) // polygon
  546. mquery().where('loc').within([], []) // box
  547. mquery().where('loc').within({ type: 'LineString', coordinates: [...] }); // geometry
  548. ```
  549. As of mquery 2.0, `$geoWithin` is used by default. This impacts you if running MongoDB < 2.4. To alter this behavior, see [mquery.use$geoWithin](#mqueryusegeowithin).
  550. **Must** be used after `where()`.
  551. [MongoDB Documentation](http://docs.mongodb.org/manual/reference/operator/geoWithin/)
  552. ### where()
  553. Specifies a `path` for use with chaining
  554. ```js
  555. // instead of writing:
  556. mquery().find({age: {$gte: 21, $lte: 65}});
  557. // we can instead write:
  558. mquery().where('age').gte(21).lte(65);
  559. // passing query conditions is permitted too
  560. mquery().find().where({ name: 'vonderful' })
  561. // chaining
  562. mquery()
  563. .where('age').gte(21).lte(65)
  564. .where({ 'name': /^vonderful/i })
  565. .where('friends').slice(10)
  566. .exec(callback)
  567. ```
  568. ### $where()
  569. Specifies a `$where` condition.
  570. Use `$where` when you need to select documents using a JavaScript expression.
  571. ```js
  572. query.$where('this.comments.length > 10 || this.name.length > 5').exec(callback)
  573. query.$where(function () {
  574. return this.comments.length > 10 || this.name.length > 5;
  575. })
  576. ```
  577. Only use `$where` when you have a condition that cannot be met using other MongoDB operators like `$lt`. Be sure to read about all of [its caveats](http://docs.mongodb.org/manual/reference/operator/where/) before using.
  578. -----------
  579. ### batchSize()
  580. Specifies the batchSize option.
  581. ```js
  582. query.batchSize(100)
  583. ```
  584. _Cannot be used with `distinct()`._
  585. [MongoDB documentation](http://docs.mongodb.org/manual/reference/method/cursor.batchSize/)
  586. ### collation()
  587. Specifies the collation option.
  588. ```js
  589. query.collation({ locale: "en_US", strength: 1 })
  590. ```
  591. [MongoDB documentation](https://docs.mongodb.com/manual/reference/method/cursor.collation/#cursor.collation)
  592. ### comment()
  593. Specifies the comment option.
  594. ```js
  595. query.comment('login query');
  596. ```
  597. _Cannot be used with `distinct()`._
  598. [MongoDB documentation](http://docs.mongodb.org/manual/reference/operator/)
  599. ### hint()
  600. Sets query hints.
  601. ```js
  602. mquery().hint({ indexA: 1, indexB: -1 })
  603. ```
  604. _Cannot be used with `distinct()`._
  605. [MongoDB documentation](http://docs.mongodb.org/manual/reference/operator/hint/)
  606. ### j()
  607. Requests acknowledgement that this operation has been persisted to MongoDB's on-disk journal.
  608. This option is only valid for operations that write to the database:
  609. - `deleteOne()`
  610. - `deleteMany()`
  611. - `findOneAndDelete()`
  612. - `findOneAndUpdate()`
  613. - `remove()`
  614. - `update()`
  615. - `updateOne()`
  616. - `updateMany()`
  617. Defaults to the `j` value if it is specified in [writeConcern](#writeconcern)
  618. ```js
  619. mquery().j(true);
  620. ```
  621. ### limit()
  622. Specifies the limit option.
  623. ```js
  624. query.limit(20)
  625. ```
  626. _Cannot be used with `distinct()`._
  627. [MongoDB documentation](http://docs.mongodb.org/manual/reference/method/cursor.limit/)
  628. ### maxScan()
  629. Specifies the maxScan option.
  630. ```js
  631. query.maxScan(100)
  632. ```
  633. _Cannot be used with `distinct()`._
  634. [MongoDB documentation](http://docs.mongodb.org/manual/reference/operator/maxScan/)
  635. ### maxTime()
  636. Specifies the maxTimeMS option.
  637. ```js
  638. query.maxTime(100)
  639. query.maxTimeMS(100)
  640. ```
  641. [MongoDB documentation](http://docs.mongodb.org/manual/reference/method/cursor.maxTimeMS/)
  642. ### skip()
  643. Specifies the skip option.
  644. ```js
  645. query.skip(100).limit(20)
  646. ```
  647. _Cannot be used with `distinct()`._
  648. [MongoDB documentation](http://docs.mongodb.org/manual/reference/method/cursor.skip/)
  649. ### sort()
  650. Sets the query sort order.
  651. If an object is passed, key values allowed are `asc`, `desc`, `ascending`, `descending`, `1`, and `-1`.
  652. If a string is passed, it must be a space delimited list of path names. The sort order of each path is ascending unless the path name is prefixed with `-` which will be treated as descending.
  653. ```js
  654. // these are equivalent
  655. query.sort({ field: 'asc', test: -1 });
  656. query.sort('field -test');
  657. ```
  658. _Cannot be used with `distinct()`._
  659. [MongoDB documentation](http://docs.mongodb.org/manual/reference/method/cursor.sort/)
  660. ### read()
  661. Sets the readPreference option for the query.
  662. ```js
  663. mquery().read('primary')
  664. mquery().read('p') // same as primary
  665. mquery().read('primaryPreferred')
  666. mquery().read('pp') // same as primaryPreferred
  667. mquery().read('secondary')
  668. mquery().read('s') // same as secondary
  669. mquery().read('secondaryPreferred')
  670. mquery().read('sp') // same as secondaryPreferred
  671. mquery().read('nearest')
  672. mquery().read('n') // same as nearest
  673. mquery().setReadPreference('primary') // alias of .read()
  674. ```
  675. ##### Preferences:
  676. - `primary` - (default) Read from primary only. Operations will produce an error if primary is unavailable. Cannot be combined with tags.
  677. - `secondary` - Read from secondary if available, otherwise error.
  678. - `primaryPreferred` - Read from primary if available, otherwise a secondary.
  679. - `secondaryPreferred` - Read from a secondary if available, otherwise read from the primary.
  680. - `nearest` - All operations read from among the nearest candidates, but unlike other modes, this option will include both the primary and all secondaries in the random selection.
  681. Aliases
  682. - `p` primary
  683. - `pp` primaryPreferred
  684. - `s` secondary
  685. - `sp` secondaryPreferred
  686. - `n` nearest
  687. ##### Preference Tags:
  688. To keep the separation of concerns between `mquery` and your driver
  689. clean, `mquery#read()` no longer handles specifying a second `tags` argument as of version 0.5.
  690. If you need to specify tags, pass any non-string argument as the first argument.
  691. `mquery` will pass this argument untouched to your collections methods later.
  692. For example:
  693. ```js
  694. // example of specifying tags using the Node.js driver
  695. var ReadPref = require('mongodb').ReadPreference;
  696. var preference = new ReadPref('secondary', [{ dc:'sf', s: 1 },{ dc:'ma', s: 2 }]);
  697. mquery(..).read(preference).exec();
  698. ```
  699. Read more about how to use read preferences [here](http://docs.mongodb.org/manual/applications/replication/#read-preference) and [here](http://mongodb.github.com/node-mongodb-native/driver-articles/anintroductionto1_1and2_2.html#read-preferences).
  700. ### readConcern()
  701. Sets the readConcern option for the query.
  702. ```js
  703. // local
  704. mquery().readConcern('local')
  705. mquery().readConcern('l')
  706. mquery().r('l')
  707. // available
  708. mquery().readConcern('available')
  709. mquery().readConcern('a')
  710. mquery().r('a')
  711. // majority
  712. mquery().readConcern('majority')
  713. mquery().readConcern('m')
  714. mquery().r('m')
  715. // linearizable
  716. mquery().readConcern('linearizable')
  717. mquery().readConcern('lz')
  718. mquery().r('lz')
  719. // snapshot
  720. mquery().readConcern('snapshot')
  721. mquery().readConcern('s')
  722. mquery().r('s')
  723. ```
  724. ##### Read Concern Level:
  725. - `local` - The query returns from the instance with no guarantee guarantee that the data has been written to a majority of the replica set members (i.e. may be rolled back). (MongoDB 3.2+)
  726. - `available` - The query returns from the instance with no guarantee guarantee that the data has been written to a majority of the replica set members (i.e. may be rolled back). (MongoDB 3.6+)
  727. - `majority` - The query returns the data that has been acknowledged by a majority of the replica set members. The documents returned by the read operation are durable, even in the event of failure. (MongoDB 3.2+)
  728. - `linearizable` - The query returns data that reflects all successful majority-acknowledged writes that completed prior to the start of the read operation. The query may wait for concurrently executing writes to propagate to a majority of replica set members before returning results. (MongoDB 3.4+)
  729. - `snapshot` - Only available for operations within multi-document transactions. Upon transaction commit with write concern "majority", the transaction operations are guaranteed to have read from a snapshot of majority-committed data. (MongoDB 4.0+)
  730. Aliases
  731. - `l` local
  732. - `a` available
  733. - `m` majority
  734. - `lz` linearizable
  735. - `s` snapshot
  736. Read more about how to use read concern [here](https://docs.mongodb.com/manual/reference/read-concern/).
  737. ### writeConcern()
  738. Sets the writeConcern option for the query.
  739. This option is only valid for operations that write to the database:
  740. - `deleteOne()`
  741. - `deleteMany()`
  742. - `findOneAndDelete()`
  743. - `findOneAndUpdate()`
  744. - `remove()`
  745. - `update()`
  746. - `updateOne()`
  747. - `updateMany()`
  748. ```js
  749. mquery().writeConcern(0)
  750. mquery().writeConcern(1)
  751. mquery().writeConcern({ w: 1, j: true, wtimeout: 2000 })
  752. mquery().writeConcern('majority')
  753. mquery().writeConcern('m') // same as majority
  754. mquery().writeConcern('tagSetName') // if the tag set is 'm', use .writeConcern({ w: 'm' }) instead
  755. mquery().w(1) // w is alias of writeConcern
  756. ```
  757. ##### Write Concern:
  758. writeConcern({ w: `<value>`, j: `<boolean>`, wtimeout: `<number>` }`)
  759. - the w option to request acknowledgement that the write operation has propagated to a specified number of mongod instances or to mongod instances with specified tags
  760. - the j option to request acknowledgement that the write operation has been written to the journal
  761. - the wtimeout option to specify a time limit to prevent write operations from blocking indefinitely
  762. Can be break down to use the following syntax:
  763. mquery().w(`<value>`).j(`<boolean>`).wtimeout(`<number>`)
  764. Read more about how to use write concern [here](https://docs.mongodb.com/manual/reference/write-concern/)
  765. ### slaveOk()
  766. Sets the slaveOk option. `true` allows reading from secondaries.
  767. **deprecated** use [read()](#read) preferences instead if on mongodb >= 2.2
  768. ```js
  769. query.slaveOk() // true
  770. query.slaveOk(true)
  771. query.slaveOk(false)
  772. ```
  773. [MongoDB documentation](http://docs.mongodb.org/manual/reference/method/rs.slaveOk/)
  774. ### snapshot()
  775. Specifies this query as a snapshot query.
  776. ```js
  777. mquery().snapshot() // true
  778. mquery().snapshot(true)
  779. mquery().snapshot(false)
  780. ```
  781. _Cannot be used with `distinct()`._
  782. [MongoDB documentation](http://docs.mongodb.org/manual/reference/operator/snapshot/)
  783. ### tailable()
  784. Sets tailable option.
  785. ```js
  786. mquery().tailable() <== true
  787. mquery().tailable(true)
  788. mquery().tailable(false)
  789. ```
  790. _Cannot be used with `distinct()`._
  791. [MongoDB Documentation](http://docs.mongodb.org/manual/tutorial/create-tailable-cursor/)
  792. ### wtimeout()
  793. Specifies a time limit, in milliseconds, for the write concern. If `w > 1`, it is maximum amount of time to
  794. wait for this write to propagate through the replica set before this operation fails. The default is `0`, which means no timeout.
  795. This option is only valid for operations that write to the database:
  796. - `deleteOne()`
  797. - `deleteMany()`
  798. - `findOneAndDelete()`
  799. - `findOneAndUpdate()`
  800. - `remove()`
  801. - `update()`
  802. - `updateOne()`
  803. - `updateMany()`
  804. Defaults to `wtimeout` value if it is specified in [writeConcern](#writeconcern)
  805. ```js
  806. mquery().wtimeout(2000)
  807. mquery().wTimeout(2000)
  808. ```
  809. ## Helpers
  810. ### collection()
  811. Sets the querys collection.
  812. ```js
  813. mquery().collection(aCollection)
  814. ```
  815. ### then()
  816. Executes the query and returns a promise which will be resolved with the query results or rejected if the query responds with an error.
  817. ```js
  818. mquery().find(..).then(success, error);
  819. ```
  820. This is very useful when combined with [co](https://github.com/visionmedia/co) or [koa](https://github.com/koajs/koa), which automatically resolve promise-like objects for you.
  821. ```js
  822. co(function*(){
  823. var doc = yield mquery().findOne({ _id: 499 });
  824. console.log(doc); // { _id: 499, name: 'amazing', .. }
  825. })();
  826. ```
  827. _NOTE_:
  828. The returned promise is a [bluebird](https://github.com/petkaantonov/bluebird/) promise but this is customizable. If you want to
  829. use your favorite promise library, simply set `mquery.Promise = YourPromiseConstructor`.
  830. Your `Promise` must be [promises A+](http://promisesaplus.com/) compliant.
  831. ### thunk()
  832. Returns a thunk which when called runs the query's `exec` method passing the results to the callback.
  833. ```js
  834. var thunk = mquery(collection).find({..}).thunk();
  835. thunk(function(err, results) {
  836. })
  837. ```
  838. ### merge(object)
  839. Merges other mquery or match condition objects into this one. When an mquery instance is passed, its match conditions, field selection and options are merged.
  840. ```js
  841. var drum = mquery({ type: 'drum' }).collection(instruments);
  842. var redDrum = mquery({ color: 'red' }).merge(drum);
  843. redDrum.count(function (err, n) {
  844. console.log('there are %d red drums', n);
  845. })
  846. ```
  847. Internally uses `mquery.canMerge` to determine validity.
  848. ### setOptions(options)
  849. Sets query options.
  850. ```js
  851. mquery().setOptions({ collection: coll, limit: 20 })
  852. ```
  853. ##### options
  854. - [tailable](#tailable) *
  855. - [sort](#sort) *
  856. - [limit](#limit) *
  857. - [skip](#skip) *
  858. - [maxScan](#maxscan) *
  859. - [maxTime](#maxtime) *
  860. - [batchSize](#batchSize) *
  861. - [comment](#comment) *
  862. - [snapshot](#snapshot) *
  863. - [hint](#hint) *
  864. - [slaveOk](#slaveOk) *
  865. - [safe](http://docs.mongodb.org/manual/reference/write-concern/): Boolean - passed through to the collection. Setting to `true` is equivalent to `{ w: 1 }`
  866. - [collection](#collection): the collection to query against
  867. _* denotes a query helper method is also available_
  868. ### setTraceFunction(func)
  869. Set a function to trace this query. Useful for profiling or logging.
  870. ```js
  871. function traceFunction (method, queryInfo, query) {
  872. console.log('starting ' + method + ' query');
  873. return function (err, result, millis) {
  874. console.log('finished ' + method + ' query in ' + millis + 'ms');
  875. };
  876. }
  877. mquery().setTraceFunction(traceFunction).findOne({name: 'Joe'}, cb);
  878. ```
  879. The trace function is passed (method, queryInfo, query)
  880. - method is the name of the method being called (e.g. findOne)
  881. - queryInfo contains information about the query:
  882. - conditions: query conditions/criteria
  883. - options: options such as sort, fields, etc
  884. - doc: document being updated
  885. - query is the query object
  886. The trace function should return a callback function which accepts:
  887. - err: error, if any
  888. - result: result, if any
  889. - millis: time spent waiting for query result
  890. NOTE: stream requests are not traced.
  891. ### mquery.setGlobalTraceFunction(func)
  892. Similar to `setTraceFunction()` but automatically applied to all queries.
  893. ```js
  894. mquery.setTraceFunction(traceFunction);
  895. ```
  896. ### mquery.canMerge(conditions)
  897. Determines if `conditions` can be merged using `mquery().merge()`.
  898. ```js
  899. var query = mquery({ type: 'drum' });
  900. var okToMerge = mquery.canMerge(anObject)
  901. if (okToMerge) {
  902. query.merge(anObject);
  903. }
  904. ```
  905. ## mquery.use$geoWithin
  906. MongoDB 2.4 introduced the `$geoWithin` operator which replaces and is 100% backward compatible with `$within`. As of mquery 0.2, we default to using `$geoWithin` for all `within()` calls.
  907. If you are running MongoDB < 2.4 this will be problematic. To force `mquery` to be backward compatible and always use `$within`, set the `mquery.use$geoWithin` flag to `false`.
  908. ```js
  909. mquery.use$geoWithin = false;
  910. ```
  911. ## Custom Base Queries
  912. Often times we want custom base queries that encapsulate predefined criteria. With `mquery` this is easy. First create the query you want to reuse and call its `toConstructor()` method which returns a new subclass of `mquery` that retains all options and criteria of the original.
  913. ```js
  914. var greatMovies = mquery(movieCollection).where('rating').gte(4.5).toConstructor();
  915. // use it!
  916. greatMovies().count(function (err, n) {
  917. console.log('There are %d great movies', n);
  918. });
  919. greatMovies().where({ name: /^Life/ }).select('name').find(function (err, docs) {
  920. console.log(docs);
  921. });
  922. ```
  923. ## Validation
  924. Method and options combinations are checked for validity at runtime to prevent creation of invalid query constructs. For example, a `distinct` query does not support specifying options like `hint` or field selection. In this case an error will be thrown so you can catch these mistakes in development.
  925. ## Debug support
  926. Debug mode is provided through the use of the [debug](https://github.com/visionmedia/debug) module. To enable:
  927. DEBUG=mquery node yourprogram.js
  928. Read the debug module documentation for more details.
  929. ## General compatibility
  930. #### ObjectIds
  931. `mquery` clones query arguments before passing them to a `collection` method for execution.
  932. This prevents accidental side-affects to the objects you pass.
  933. To clone `ObjectIds` we need to make some assumptions.
  934. First, to check if an object is an `ObjectId`, we check its constructors name. If it matches either
  935. `ObjectId` or `ObjectID` we clone it.
  936. To clone `ObjectIds`, we call its optional `clone` method. If a `clone` method does not exist, we fall
  937. back to calling `new obj.constructor(obj.id)`. We assume, for compatibility with the
  938. Node.js driver, that the `ObjectId` instance has a public `id` property and that
  939. when creating an `ObjectId` instance we can pass that `id` as an argument.
  940. #### Read Preferences
  941. `mquery` supports specifying [Read Preferences]() to control from which MongoDB node your query will read.
  942. The Read Preferences spec also support specifying tags. To pass tags, some
  943. drivers (Node.js driver) require passing a special constructor that handles both the read preference and its tags.
  944. If you need to specify tags, pass an instance of your drivers ReadPreference constructor or roll your own. `mquery` will store whatever you provide and pass later to your collection during execution.
  945. ## Future goals
  946. - mongo shell compatibility
  947. - browser compatibility
  948. ## Installation
  949. $ npm install mquery
  950. ## License
  951. [MIT](https://github.com/aheckmann/mquery/blob/master/LICENSE)