Querying using mongo ruby driver

Suppose you have a db named ‘bands’ with a collection named ‘metal’, finding the band named ‘Dream Theater’ would be like this :-

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'bands')

client[:metal].find(:name => 'Dream Theater').each do |doc|
  #=> Yields a BSON::Document.
puts doc
end
You can then convert the bson document to json by using ‘to_json’ and proceed with manipulation of the data

 

Query Documents – MongoDB

Query Method

MongoDB provides the db.collection.find() method to read documents from a collection. Thedb.collection.find() method returns a cursor to the matching documents.

db.collection.find( <query filter>, <projection> )

For the db.collection.find() method, you can specify the following optional fields:

  • a query filter to specify which documents to return.
  • a query projection to specifies which fields from the matching documents to return. The projection limits the amount of data that MongoDB returns to the client over the network.

You can optionally add a cursor modifier to impose limits, skips, and sort orders. The order of documents returned by a query is not defined unless you specify a sort().

Example Collection

The examples on this page use the db.collection.find() method in the mongo shell. In the mongoshell, if the returned cursor is not assigned to a variable using the var keyword, then the cursor is automatically iterated up to 20 times [2] to print up to the first 20 documents in the results.

To populate the users collection referenced in the examples, run the following in mongo shell:

NOTE

If the users collection already contains documents with the same _id values, you need to drop the collection (db.users.drop()) before inserting the example documents.

db.users.insertMany(
  [
     {
       _id: 1,
       name: "sue",
       age: 19,
       type: 1,
       status: "P",
       favorites: { artist: "Picasso", food: "pizza" },
       finished: [ 17, 3 ],
       badges: [ "blue", "black" ],
       points: [
          { points: 85, bonus: 20 },
          { points: 85, bonus: 10 }
       ]
     },
     {
       _id: 2,
       name: "bob",
       age: 42,
       type: 1,
       status: "A",
       favorites: { artist: "Miro", food: "meringue" },
       finished: [ 11, 25 ],
       badges: [ "green" ],
       points: [
          { points: 85, bonus: 20 },
          { points: 64, bonus: 12 }
       ]
     },
     {
       _id: 3,
       name: "ahn",
       age: 22,
       type: 2,
       status: "A",
       favorites: { artist: "Cassatt", food: "cake" },
       finished: [ 6 ],
       badges: [ "blue", "red" ],
       points: [
          { points: 81, bonus: 8 },
          { points: 55, bonus: 20 }
       ]
     },
     {
       _id: 4,
       name: "xi",
       age: 34,
       type: 2,
       status: "D",
       favorites: { artist: "Chagall", food: "chocolate" },
       finished: [ 5, 11 ],
       badges: [ "red", "black" ],
       points: [
          { points: 53, bonus: 15 },
          { points: 51, bonus: 15 }
       ]
     },
     {
       _id: 5,
       name: "xyz",
       age: 23,
       type: 2,
       status: "D",
       favorites: { artist: "Noguchi", food: "nougat" },
       finished: [ 14, 6 ],
       badges: [ "orange" ],
       points: [
          { points: 71, bonus: 20 }
       ]
     },
     {
       _id: 6,
       name: "abc",
       age: 43,
       type: 1,
       status: "A",
       favorites: { food: "pizza", artist: "Picasso" },
       finished: [ 18, 12 ],
       badges: [ "black", "blue" ],
       points: [
          { points: 78, bonus: 8 },
          { points: 57, bonus: 7 }
       ]
     }
  ]
)

Select All Documents in a Collection

An empty query filter document ({}) selects all documents in the collection:

db.users.find( {} )

Omitting a query filter document to the db.collection.find() is equivalent to specifying an empty query document. As such, the following operation is equivalent to the previous operation:

db.users.find()

 

Specify Query Filter Conditions

Specify Equality Condition

A query filter document can specify equality condition with <field>:<value> expressions to select all documents that contain the <field> with the specified <value>:

{ <field1>: <value1>, ... }

The following example retrieves from the users collection all documents where the status field has the value "A":

db.users.find( { status: "A" } )

Specify Conditions Using Query Operators

A query filter document can use the query operators to specify conditions in the following form:

{ <field1>: { <operator1>: <value1> }, ... }

The following example retrieves all documents from the users collection where status equals either "P"or "D":

db.users.find( { status: { $in: [ "P", "D" ] } } )

Although you can express this query using the $or operator, use the $in operator rather than the $oroperator when performing equality checks on the same field.

Refer to the Query and Projection Operators document for the complete list of query operators.

Specify AND Conditions

A compound query can specify conditions for more than one field in the collection’s documents. Implicitly, a logical AND conjunction connects the clauses of a compound query so that the query selects the documents in the collection that match all the conditions.

The following example retrieves all documents in the users collection where the status equals "A" andage is less than ($lt) 30:

db.users.find( { status: "A", age: { $lt: 30 } } )

See comparison operators for other comparison operators.

Specify OR Conditions

Using the $or operator, you can specify a compound query that joins each clause with a logical ORconjunction so that the query selects the documents in the collection that match at least one condition.

The following example retrieves all documents in the collection where the status equals "A" or age is less than ($lt) 30:

db.users.find(
   {
     $or: [ { status: "A" }, { age: { $lt: 30 } } ]
   }
)

NOTE

Queries which use comparison operators are subject to Type Bracketing.

Specify AND as well as OR Conditions

With additional clauses, you can specify precise conditions for matching documents.

In the following example, the compound query document selects all documents in the collection where the“status“ equals "A" and either age is less than than ($lt) 30 or type equals 1:

db.users.find(
   {
     status: "A",
     $or: [ { age: { $lt: 30 } }, { type: 1 } ]
   }
)

 

Query on Embedded Documents

When the field holds an embedded document, a query can either specify an exact match on the embedded document or specify a match by individual fields in the embedded document using the dot notation.

Exact Match on the Embedded Document

To specify an exact equality match on the whole embedded document, use the query document {<field>: <value> } where <value> is the document to match. Equality matches on an embedded document require an exact match of the specified <value>, including the field order.

In the following example, the query matches all documents where the favorites field is an embedded document that contains only the fields artist equal to "Picasso" and food equal to "pizza", in that order:

db.users.find( { favorites: { artist: "Picasso", food: "pizza" } } )

Equality Match on Fields within an Embedded Document

Use the dot notation to match by specific fields in an embedded document. Equality matches for specific fields in an embedded document will select documents in the collection where the embedded document contains the specified fields with the specified values. The embedded document can contain additional fields.

In the following example, the query uses the dot notation to match all documents where the favorites field is an embedded document that includes the field artist equal to "Picasso" and may contain other fields:

db.users.find( { "favorites.artist": "Picasso" } )

 

Query on Arrays

When the field holds an array, you can query for an exact array match or for specific values in the array. If the array holds embedded documents, you can query for specific fields in the embedded documents using dot notation.

If you specify multiple conditions using the $elemMatch operator, the array must contain at least one element that satisfies all the conditions. See Single Element Satisfies the Criteria.

If you specify multiple conditions without using the $elemMatch operator, then some combination of the array elements, not necessarily a single element, must satisfy all the conditions; i.e. different elements in the array can satisfy different parts of the conditions. See Combination of Elements Satisfies the Criteria.

 

Exact Match on an Array

To specify equality match on an array, use the query document { <field>: <value> } where <value>is the array to match. Equality matches on the array require that the array field match exactly the specified<value>, including the element order.

The following example queries for all documents where the field badges is an array that holds exactly two elements, "blue", and "black", in this order:

db.users.find( { badges: [ "blue", "black" ] } )

The query matches the following document:

{
   "_id" : 1,
   "name" : "sue",
   "age" : 19,
   "type" : 1,
   "status" : "P",
   "favorites" : { "artist" : "Picasso", "food" : "pizza" },
   "finished" : [ 17, 3 ]
   "badges" : [ "blue", "black" ],
   "points" : [ { "points" : 85, "bonus" : 20 }, { "points" : 85, "bonus" : 10 } ]
}

 

Match an Array Element

Equality matches can specify a single element in the array to match. These specifications match if the array contains at least one element with the specified value.

The following example queries for all documents where badges is an array that contains "black" as one of its elements:

db.users.find( { badges: "black" } )

The query matches the following documents:

{
   "_id" : 1,
   "name" : "sue",
   "age" : 19,
   "type" : 1,
   "status" : "P",
   "favorites" : { "artist" : "Picasso", "food" : "pizza" },
   "finished" : [ 17, 3 ]
   "badges" : [ "blue", "black" ],
   "points" : [ { "points" : 85, "bonus" : 20 }, { "points" : 85, "bonus" : 10 } ]
}
{
   "_id" : 4,
   "name" : "xi",
   "age" : 34,
   "type" : 2,
   "status" : "D",
   "favorites" : { "artist" : "Chagall", "food" : "chocolate" },
   "finished" : [ 5, 11 ],
   "badges" : [ "red", "black" ],
   "points" : [ { "points" : 53, "bonus" : 15 }, { "points" : 51, "bonus" : 15 } ]
}
{
   "_id" : 6,
   "name" : "abc",
   "age" : 43,
   "type" : 1,
   "status" : "A",
   "favorites" : { "food" : "pizza", "artist" : "Picasso" },
   "finished" : [ 18, 12 ],
   "badges" : [ "black", "blue" ],
   "points" : [ { "points" : 78, "bonus" : 8 }, { "points" : 57, "bonus" : 7 } ]
}

Match a Specific Element of an Array

Equality matches can specify equality matches for an element at a particular index or position of the array using the dot notation.

In the following example, the query uses the dot notation to match all documents where the badges is an array that contains "black" as the first element:

db.users.find( { "badges.0": "black" } )

The operation returns the following document:

{
   "_id" : 6,
   "name" : "abc",
   "age" : 43,
   "type" : 1,
   "status" : "A",
   "favorites" : { "food" : "pizza", "artist" : "Picasso" },
   "finished" : [ 18, 12 ],
   "badges" : [ "black", "blue" ],
   "points" : [ { "points" : 78, "bonus" : 8 }, { "points" : 57, "bonus" : 7 } ]
}

 

Specify Multiple Criteria for Array Elements

 

Single Element Satisfies the Criteria

Use $elemMatch operator to specify multiple criteria on the elements of an array such that at least one array element satisfies all the specified criteria.

The following example queries for documents where the finished array contains at least one element that is greater than ($gt) 15 and less than ($lt) 20:

db.users.find( { finished: { $elemMatch: { $gt: 15, $lt: 20 } } } )

The operation returns the following documents, whose finished array contains at least one element which meets both criteria:

{
   "_id" : 1,
   "name" : "sue",
   "age" : 19,
   "type" : 1,
   "status" : "P",
   "favorites" : { "artist" : "Picasso", "food" : "pizza" },
   "finished" : [ 17, 3 ]
   "badges" : [ "blue", "black" ],
   "points" : [ { "points" : 85, "bonus" : 20 }, { "points" : 85, "bonus" : 10 } ]
}
{
   "_id" : 6,
   "name" : "abc",
   "age" : 43,
   "type" : 1,
   "status" : "A",
   "favorites" : { "food" : "pizza", "artist" : "Picasso" },
   "finished" : [ 18, 12 ],
   "badges" : [ "black", "blue" ],
   "points" : [ { "points" : 78, "bonus" : 8 }, { "points" : 57, "bonus" : 7 } ]
}

 

Combination of Elements Satisfies the Criteria

The following example queries for documents where the finished array contains elements that in some combination satisfy the query conditions; e.g., one element can satisfy the greater than 15 condition and another element can satisfy the less than 20 condition, or a single element can satisfy both:

db.users.find( { finished: { $gt: 15, $lt: 20 } } )

The operation returns the following documents:

{
   "_id" : 1,
   "name" : "sue",
   "age" : 19,
   "type" : 1,
   "status" : "P",
   "favorites" : { "artist" : "Picasso", "food" : "pizza" },
   "finished" : [ 17, 3 ]
   "badges" : [ "blue", "black" ],
   "points" : [ { "points" : 85, "bonus" : 20 }, { "points" : 85, "bonus" : 10 } ]
}
{
   "_id" : 2,
   "name" : "bob",
   "age" : 42,
   "type" : 1,
   "status" : "A",
   "favorites" : { "artist" : "Miro", "food" : "meringue" },
   "finished" : [ 11, 20 ],
   "badges" : [ "green" ],
   "points" : [ { "points" : 85, "bonus" : 20 }, { "points" : 64, "bonus" : 12 } ]
}
{
   "_id" : 6,
   "name" : "abc",
   "age" : 43,
   "type" : 1,
   "status" : "A",
   "favorites" : { "food" : "pizza", "artist" : "Picasso" },
   "finished" : [ 18, 12 ],
   "badges" : [ "black", "blue" ],
   "points" : [ { "points" : 78, "bonus" : 8 }, { "points" : 57, "bonus" : 7 } ]
}

 

Array of Embedded Documents

Match a Field in the Embedded Document Using the Array Index

If you know the array index of the embedded document, you can specify the document using the embedded document’s position using the dot notation.

The following example selects all documents where the points contains an array whose first element (i.e. index is 0) is a document that contains the field points whose value is less than or equal to 55:

db.users.find( { 'points.0.points': { $lte: 55 } } )

The operation returns the following documents:

{
   "_id" : 4,
   "name" : "xi",
   "age" : 34,
   "type" : 2,
   "status" : "D",
   "favorites" : { "artist" : "Chagall", "food" : "chocolate" },
   "finished" : [ 5, 11 ],
   "badges" : [ "red", "black" ],
   "points" : [ { "points" : 53, "bonus" : 15 }, { "points" : 51, "bonus" : 15 } ]
}

Match a Field Without Specifying Array Index

If you do not know the index position of the document in the array, concatenate the name of the field that contains the array, with a dot (.) and the name of the field in the embedded document.

The following example selects all documents where the points is an array with at least one embedded document that contains the field points whose value is less than or equal to 55:

db.users.find( { 'points.points': { $lte: 55 } } )

The operation returns the following documents:

{
   "_id" : 3,
   "name" : "ahn",
   "age" : 22,
   "type" : 2,
   "status" : "A",
   "favorites" : { "artist" : "Cassatt", "food" : "cake" },
   "finished" : [ 6 ],
   "badges" : [ "blue", "red" ],
   "points" : [ { "points" : 81, "bonus" : 8 }, { "points" : 55, "bonus" : 20 } ]
}
{
   "_id" : 4,
   "name" : "xi",
   "age" : 34,
   "type" : 2,
   "status" : "D",
   "favorites" : { "artist" : "Chagall", "food" : "chocolate" },
   "finished" : [ 5, 11 ],
   "badges" : [ "red", "black" ],
   "points" : [ { "points" : 53, "bonus" : 15 }, { "points" : 51, "bonus" : 15 } ]
}

 

Specify Multiple Criteria for Array of Documents

Single Element Satisfies the Criteria

Use $elemMatch operator to specify multiple criteria on an array of embedded documents such that at least one embedded document satisfies all the specified criteria.

The following example queries for documents where the points array has at least one embedded document that contains both the field points less than or equal to 70 and the field bonus equal to 20:

db.users.find( { points: { $elemMatch: { points: { $lte: 70 }, bonus: 20 } } } )

The operation returns the following document:

{
   "_id" : 3,
   "name" : "ahn",
   "age" : 22,
   "type" : 2,
   "status" : "A",
   "favorites" : { "artist" : "Cassatt", "food" : "cake" },
   "finished" : [ 6 ],
   "badges" : [ "blue", "red" ],
   "points" : [ { "points" : 81, "bonus" : 8 }, { "points" : 55, "bonus" : 20 } ]
}

Combination of Elements Satisfies the Criteria

The following example queries for documents where the points array contains elements that in some combination satisfy the query conditions; e.g. one element satisfies the points less than or equal to 70condition and another element satisfies the bonus equal to 20 condition, or a single element satisfies both criteria:

db.users.find( { "points.points": { $lte: 70 }, "points.bonus": 20 } )

The query returns the following documents:

{
   "_id" : 2,
   "name" : "bob",
   "age" : 42,
   "type" : 1,
   "status" : "A",
   "favorites" : { "artist" : "Miro", "food" : "meringue" },
   "finished" : [ 11, 20 ],
   "badges" : [ "green" ],
   "points" : [ { "points" : 85, "bonus" : 20 }, { "points" : 64, "bonus" : 12 } ]
}
{
   "_id" : 3,
   "name" : "ahn",
   "age" : 22,
   "type" : 2,
   "status" : "A",
   "favorites" : { "artist" : "Cassatt", "food" : "cake" },
   "finished" : [ 6 ],
   "badges" : [ "blue", "red" ],
   "points" : [ { "points" : 81, "bonus" : 8 }, { "points" : 55, "bonus" : 20 } ]
}

find – MongoDB

Definition

find

New in version 3.2.

Executes a query and returns the first batch of results and the cursor id, from which the client can construct a cursor.

The find command has the following form:

{
   "find": <string>,
   "filter": <document>,
   "sort": <document>,
   "projection": <document>,
   "hint": <document or string>,
   "skip": <int>,
   "limit": <int>,
   "batchSize": <int>,
   "singleBatch": <bool>,
   "comment": <string>,
   "maxScan": <int>,
   "maxTimeMS": <int>,
   "readConcern": <document>,
   "max": <document>,
   "min": <document>,
   "returnKey": <bool>,
   "showRecordId": <bool>,
   "snapshot": <bool>,
   "tailable": <bool>,
   "oplogReplay": <bool>,
   "noCursorTimeout": <bool>,
   "awaitData": <bool>,
   "allowPartialResults": <bool>
}

The command accepts the following fields:

Field Type Description
find string The name of the collection to query.
filter document Optional. The query predicate. If unspecified, then all documents in the collection will match the predicate.
sort document Optional. The sort specification for the ordering of the results.
projection document Optional. The projection specification to determine which fields to include in the returned documents. See Project Fields to Return from Query and Projection Operators.
hint string or document Optional. Index specification. Specify either the index name as a string or the index key pattern. If specified, then the query system will only consider plans using the hinted index.
skip Positive integer Optional. Number of documents to skip. Defaults to 0.
limit Non-negative integer Optional. The maximum number of documents to return. If unspecified, then defaults to no limit. A limit of 0 is equivalent to setting no limit.
batchSize non-negative integer

Optional. The number of documents to return in the first batch. Defaults to 101. A batchSize of 0 means that the cursor will be established, but no documents will be returned in the first batch.

Unlike the previous wire protocol version, a batchSize of 1 for thefind command does not close the cursor.

singleBatch boolean Optional. Determines whether to close the cursor after the first batch. Defaults to false.
comment string Optional. A comment to attach to the query to help interpret and trace query profile data.
maxScan positive integer Optional. Maximum number of documents or index keys to scan when executing the query.
maxTimeMS positive integer Optional. The cumulative time limit in milliseconds for processing operations on the cursor. MongoDB aborts the operation at the earliest following interrupt point.
readConcern document

Optional. Specifies the read concern. The default level is "local".

To use a read concern level of "majority", you must use the WiredTiger storage engine and start the mongod instances with the –enableMajorityReadConcern command line option (or thereplication.enableMajorityReadConcern setting if using a configuration file).

Only replica sets using protocol version 1 support"majority" read concern. Replica sets running protocol version 0 do not support "majority" read concern.

To ensure that a single thread can read its own writes, use"majority" read concern and "majority" write concern against the primary of the replica set.

NOTE

The getMore command uses the readConcern level specified in the originating find command.

max document Optional. The exclusive upper bound for a specific index. Seecursor.max() for details.
min document Optional. The inclusive lower bound for a specific index. Seecursor.min() for details.
returnKey boolean Optional. If true, returns only the index keys in the resulting documents. Default value is false. If returnKey is true and the find command does not use an index, the returned documents will be empty.
showRecordId boolean Optional. Determines whether to return the record identifier for each document. If true, adds a field $recordId to the returned documents.
snapshot boolean Optional. Prevents the cursor from returning a document more than once because of an intervening write operation.
tailable boolean Optional. Returns a tailable cursor for a capped collections.
awaitData boolean Optional. Use in conjunction with the tailable option to block agetMore command on the cursor temporarily if at the end of data rather than returning no data. After a timeout period, find returns as normal.
oplogReplay boolean

Optional. Internal use for replica sets. To use oplogReplay, you must include the following condition in the filter:

{ ts: { $gte: <timestamp> } }
noCursorTimeout boolean Optional. Prevents the server from timing out idle cursors after an inactivity period (10 minutes).
allowPartialResults boolean Optional. For queries against a sharded collection, returns partial results from the mongos if some shards are unavailable instead of throwing an error.

Examples

Specify a Sort and Limit

The following command runs the find command filtering on the rating field and the cuisine field. The command includes a projection to only return the following fields in the matching documents: _id,name, rating, and address fields.

The command sorts the documents in the result set by the name field and limits the result set to 5 documents.

db.runCommand(
   {
     find: "restaurants",
     filter: { rating: { $gte: 9 }, cuisine: "italian" },
     projection: { name: 1, rating: 1, address: 1 },
     sort: { name: 1 },
     limit: 5
   }
)

Override Default Read Concern

To override the default read concern level of "local", use the readConcern option.

The following operation on a replica set specifies a read concern of "majority" to read the most recent copy of the data confirmed as having been written to a majority of the nodes.

NOTE

db.runCommand(
   {
     find: "restaurants",
     filter: { rating: { $lt: 5 } },
     readConcern: { level: "majority" }
   }
)

To ensure that a single thread can read its own writes, use "majority" read concern and "majority"write concern against the primary of the replica set.

The getMore command uses the readConcern level specified in the originating find command.

A readConcern can be specified for the mongo shell method db.collection.find() using thecursor.readConcern method:

db.restaurants.find( { rating: { $lt: 5 } } ).readConcern("majority")

 

Courtesy: MongoDB Website

CRUD Operations

CRUD operations are those which deal with creating, reading, updating, and deleting documents.

Key-value Pair Notation

Key-value pairs appear in many different contexts in the MongoDB Ruby driver, and there are some quirks of syntax with regard to how they can be notated which depend on which version of Ruby you’re using.

When constructing a document, the following syntax is acceptable and correct for Ruby version 1.9 and later:

document = { name: "Harriet", age: 36 }

If you’re using Ruby version 2.2 or greater, you can optionally enclose your keys in quotes.

document = { "name": "Harriet", "age": 36 }

If you need to use any MongoDB operator which begins with $, such as $set, $gte, or $near, you must enclose it in quotes. If you’re using Ruby version 2.2 or greater, you can notate it as follows:

collection.update_one({ name: "Harriet" }, { "$set": { age: 42 } })

If you’re using an earlier version of Ruby, use the hashrocket symbol:

collection.update_one({ name: "Harriet" }, { "$set" => { age: 42 } })

Quoted strings and hashrockets for key-value pairs will work with any version of Ruby:

collection.update_one({ "name" => "Harriet" }, { "$set" => { age: 42 } })

Creating Documents

To insert documents into a collection, select a collection on the client and call insert_one orinsert_many.

Insert operations return a Mongo::Operation::Result object which gives you information about the insert itself.

On MongoDB 2.6 and later, if the insert fails, an exception is raised, because write commands are used.

On MongoDB 2.4, an exception is only raised if the insert fails and the write concern is 1 or higher.

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')

result = client[:artists].insert_one( { :name => 'FKA Twigs' } )
result.n # returns 1, because 1 document was inserted.

result = client[:artists].insert_many([
  { :name => 'Flying Lotus' },
  { :name => 'Aphex Twin' }
])
result.inserted_count # returns 2, because 2 documents were inserted.

Reading

The Ruby driver provides a fluent interface for queries using the find method on the collection. Various options are available to the find method.

The query is lazily executed against the server only when iterating the results – at that point the query is dispatched and a Mongo::Cursor is returned.

To find all documents for a given filter, call find with the query:

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')

client[:artists].find(:name => 'Flying Lotus').each do |document|
  #=> Yields a BSON::Document.
end

 

Query Options

To add options to a query, chain the appropriate methods after the find method. Note that the underlying object, the Mongo::Collection::View, is immutable and a new object will be returned after each method call.

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')

documents = client[:artists].find(:name => 'Flying Lotus').skip(10).limit(10)
documents.each do |document|
  #=> Yields a BSON::Document.
end

The following is a full list of the available options that can be added when querying and their corresponding methods as examples.

Option Description
allow_partial_results For use with sharded clusters. If a shard is down, allows the query to return results from the shards that are up, potentially only getting a portion of the results.
batch_size(Integer) Specifies the size of each batch of documents the cursor will return on eachGETMORE operation.
comment(String) Adds a comment to the query.
hint(Hash) Provides the query with an index hint to use.
limit(Integer) Limits the number of returned documents to the provided value.
max_scan(Integer) Sets the maximum number of documents to scan if a full collection scan would be performed.
no_cursor_timeout MongoDB automatically closes inactive cursors after a period of 10 minutes. Call this for cursors to remain open indefinitely on the server.
projection(Hash)

Specifies the fields to include or exclude from the results.

client[:artists].find.projection(:name => 1)
read(Hash)

Changes the read preference for this query only.

client[:artists].find.read(:mode => :secondary_preferred)
show_disk_loc(Boolean) Tells the results to also include the location of the documents on disk.
skip(Integer) Skip the provided number of documents in the results.
snapshot Execute the query in snapshot mode.
sort(Hash)

Specifies sort criteria for the query.

client[:artists].find.sort(:name => -1)

Additional Query Operations

count
Get the total number of documents an operation returns.
client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')

client[:artists].find(:name => 'Flying Lotus').count
distinct
Filters out documents with duplicate values. Equivalent to the SQL distinct clause.
client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')

client[:artists].find.distinct(:name )

Tailable Cursors

For capped collections you may use a tailable cursor that remains open after the client exhausts the results in the initial cursor. The following code example shows how a tailable cursor might be used:

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
client[:artists].drop
client[:artists, capped: true, size: 512].create

result = client[:artists].insert_many([
  { :name => 'Flying Lotus' },
  { :name => 'Aphex Twin' }
])

enum = client[:artists].find({}, cursor_type: :tailable_await).to_enum

while true
  doc = enum.next
  # do something
  sleep(1)
end

 

Read Preference

Read preference determines the candidate replica set members to which a query or command can be sent. They consist of a mode specified as a symbol, an array of hashes known as tag_sets, and two timing options: local_threshold and server_selection_timeout.

local_threshold
Defines the upper limit in seconds of the latency window between the nearest server and suitable servers to which an operation may be sent. The default is 15 milliseconds, or 0.015 seconds.
server_selection_timeout
Defines how long to block for server selection before throwing an exception. The default is 30,000 milliseconds, or 30 seconds.

For more information on the algorithm used to select a server, please refer to the Server Selection documentation, available on GitHub.

The read preference is set as an option on the client or passed an option when a command is run on a database.

# Set read preference on a client, used for all operations
client = Mongo::Client.new([ '127.0.0.1:27017' ],
                           read: { mode: :secondary,
                                   tag_sets: [ { 'dc' => 'nyc' } ]
                                  } )

# Set read preference for a given command
client.database.command( { collstats: 'test' }, read: { mode: secondary,
                                                     tag_sets: [ { 'dc' => 'nyc' } ] } )

Mode

There are five possible read preference modes. They are :primary, :secondary,:primary_preferred, :secondary_preferred, :nearest. Please see the read preference documentation in the MongoDB Manual for an explanation of the modes and tag sets.

Tag sets

The tag_sets parameter is an ordered list of tag sets used to restrict the eligibility of servers for selection, such as for data center awareness.

A read preference tag set (T) matches a server tag set (S) – or equivalently a server tag set (S) matches a read preference tag set (T) — if T is a subset of S.

For example, the read preference tag set { dc: 'ny', rack: 2 } matches a secondary server with tag set { dc: 'ny', rack: 2, size: 'large' }.

A tag set that is an empty document matches any server, because the empty tag set is a subset of any tag set. This means the default tag_sets parameter [{}] matches all servers.

 

Updating

Updating documents is possible by executing a single or multiple update, or by using the $findAndModifycommand.

update_one

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
artists = client[:artists]

result = artists.find(:name => 'Goldie').update_one("$inc" => { :plays =>  1 } )
result.n # Returns 1.

result = artists.update_one( { :name => 'Goldie' }, { "$inc" => { :plays =>  1 } } )
result.n # Returns 1.

update_many

result = artists.find(:label => 'Hospital').update_many( "$inc" => { :plays =>  1 } )
result.modified_count # Returns the number of documents that were updated.

result = artists.update_many( { :label => 'Hospital' }, { "$inc" => { :plays =>  1 } } )
result.modified_count # Returns the number of documents that were updated.

replace_one

result = artists.find(:name => 'Aphex Twin').replace_one(:name => 'Richard James')
result.modified_count # Returns 1.

result = artists.replace_one( { :name => 'Aphex Twin' }, { :name => 'Richard James' } )
result.modified_count # Returns 1.

To update documents and return a document via $findAndModify, use one of the three provided helpers:find_one_and_delete, find_one_and_replace, or find_one_and_update. You can opt to return the document before or after the modification occurs.

find_one_and_delete

client = Mongo::Client.new( [ '127.0.0.1:27017' ], :database => 'music')
artists = client[:artists]

artists.find(:name => 'José James').find_one_and_delete # Returns the document.

find_one_and_replace

doc = artists.find(:name => 'José James').find_one_and_replace(:name => 'José')
doc # Return the document before the update.

doc = artists.find_one_and_replace({ :name => 'José James' }, { :name => 'José' })
doc # Return the document before the update.

doc = artists.find(:name => 'José James').
  find_one_and_replace( { :name => 'José' }, :return_document => :after )
doc # Return the document after the update.

find_one_and_update

doc = artists.find(:name => 'José James').
  find_one_and_update( '$set' => { :name => 'José' } )
doc # Return the document before the update.

doc = artists.find_one_and_update( { :name => 'José James' }, { '$set' => { :name => 'José' } } )
doc # Return the document before the update.

find_one_and_replace

doc = artists.find(:name => 'José James').
  find_one_and_replace( { '$set' => { :name => 'José' } }, :return_document => :after )
doc # Return the document after the update.

doc = artists.find_one_and_replace(
  { :name => 'José James' },
  { '$set' => { :name => 'José' } },
  :return_document => :after
)
doc # Return the document after the update.

Deleting

delete_one

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
artists = client[:artists]

result = artists.find(:name => 'Björk').delete_one
result.deleted_count # Returns 1.

result = artists.delete_one(:name => 'Björk')
result.deleted_count # Returns 1.

delete_many

result = artists.find(:label => 'Mute').delete_many
result.deleted_count # Returns the number deleted.

result = artists.delete_many(:label => 'Mute')
result.deleted_count # Returns the number deleted.

Courtesy: MongoDB Website

The mongo Shell

Introduction

The mongo shell is an interactive JavaScript interface to MongoDB. You can use the mongo shell to query and update data as well as perform administrative operations.

The mongo shell is a component of the MongoDB distributions. Once you have installed and have started MongoDB, connect the mongo shell to your running MongoDB instance.

Most examples in the MongoDB Manual use the mongo shell; however, many drivers provide similar interfaces to MongoDB.

Start the mongo Shell

IMPORTANT

Ensure that MongoDB is running before attempting to start the mongo shell.

To start the mongo shell and connect to your MongoDB instance running on localhost with default port:

  1. At a prompt in a terminal window (or a command prompt for Windows), go to your <mongodbinstallation dir>:

    cd <mongodb installation dir>
    
  2. Type ./bin/mongo to start mongo:

    ./bin/mongo
    

    If you have added the <mongodb installation dir>/bin to the PATH environment variable, you can just type mongo instead of ./bin/mongo.

Options

When you run mongo without any arguments, the mongo shell will attempt to connect to the MongoDB instance running on the localhost interface on port 27017. To specify a different host or port number, as well as other options, see examples of starting up mongo and mongo reference which provides details on the available options.

.mongorc.js File

When starting, mongo checks the user’s HOME directory for a JavaScript file named .mongorc.js. If found,mongo interprets the content of .mongorc.js before displaying the prompt for the first time. If you use the shell to evaluate a JavaScript file or expression, either by using the –eval option on the command line or by specifying a .js file to mongo, mongo will read the .mongorc.js file after the JavaScript has finished processing. You can prevent .mongorc.js from being loaded by using the –norc option.

Working with the mongo Shell

To display the database you are using, type db:

db

The operation should return test, which is the default database. To switch databases, issue the use <db>helper, as in the following example:

use <database>

To list the available databases, use the helper show dbs. See also db.getSiblingDB() method to access a different database from the current database without switching your current database context (i.e.db).

You can switch to non-existing databases. When you first store data in the database, such as by creating a collection, MongoDB creates the database. For example, the following creates both the databasemyNewDatabase and the collection myCollection during the insert() operation:

use myNewDatabase
db.myCollection.insert( { x: 1 } );

The db.myCollection.insert() is one of the methods available in the mongo shell

  • db refers to the current database.
  • myCollection is the name of the collection.

If the mongo shell does not accept the name of the collection, for instance if the name contains a space, hyphen, or starts with a number, you can use an alternate syntax to refer to the collection, as in the following:

db["3test"].find()

db.getCollection("3test").find()

Format Printed Results

The db.collection.find() method returns a cursor to the results; however, in the mongo shell, if the returned cursor is not assigned to a variable using the var keyword, then the cursor is automatically iterated up to 20 times to print up to the first 20 documents that match the query. The mongo shell will prompt Typeit to iterate another 20 times.

To format the printed result, you can add the .pretty() to the operation, as in the following:

db.myCollection.find().pretty()

In addition, you can use the following explicit print methods in the mongo shell:

  • print() to print without formatting
  • print(tojson(<obj>)) to print with JSON formatting and equivalent to printjson()
  • printjson() to print with JSON formatting and equivalent to print(tojson(<obj>))

For more information and examples on cursor handling in the mongo shell, see Iterate a Cursor in the mongo Shell. See also Cursor Help for list of cursor help in the mongo shell.

Multi-line Operations in the mongo Shell

If you end a line with an open parenthesis ('('), an open brace ('{'), or an open bracket ('['), then the subsequent lines start with ellipsis ("...") until you enter the corresponding closing parenthesis (')'), the closing brace ('}') or the closing bracket (']'). The mongo shell waits for the closing parenthesis, closing brace, or the closing bracket before evaluating the code, as in the following example:

> if ( x > 0 ) {
... count++;
... print (x);
... }

You can exit the line continuation mode if you enter two blank lines, as in the following example:

> if (x > 0
...
...
>

Tab Completion and Other Keyboard Shortcuts

The mongo shell supports keyboard shortcuts. For example,

  • Use the up/down arrow keys to scroll through command history. See .dbshell documentation for more information on the .dbshell file.

  • Use <Tab> to autocomplete or to list the completion possibilities, as in the following example which uses <Tab> to complete the method name starting with the letter 'c':

    db.myCollection.c<Tab>
    

    Because there are many collection methods starting with the letter 'c', the <Tab> will list the various methods that start with 'c'.

For a full list of the shortcuts, see Shell Keyboard Shortcuts

Exit the Shell

To exit the shell, type quit() or use the <Ctrl-c> shortcut.

 

Courtesy : MongoDB Website

Installation of MongoDB on Ubuntu

1.Import the public key used by the package management system.

The Ubuntu package management tools (i.e. dpkg and apt) ensure package consistency and authenticity by requiring that distributors sign packages with GPG keys. Issue the following command to import the MongoDB public GPG Key:

sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv EA312927

2.Create a list file for MongoDB.

Create the /etc/apt/sources.list.d/mongodb-org-3.2.list list file using the command appropriate for your version of Ubuntu:

Ubuntu 12.04

echo "deb http://repo.mongodb.org/apt/ubuntu precise/mongodb-org/3.2 multiverse" | sudo tee /etc/apt/sources.list.d/mongodb-org-3.2.list

Ubuntu 14.04

echo "deb http://repo.mongodb.org/apt/ubuntu trusty/mongodb-org/3.2 multiverse" | sudo tee /etc/apt/sources.list.d/mongodb-org-3.2.list

Ubuntu 16.04

echo "deb http://repo.mongodb.org/apt/ubuntu xenial/mongodb-org/3.2 multiverse" | sudo tee /etc/apt/sources.list.d/mongodb-org-3.2.list
3.Reload local package database.

Issue the following command to reload the local package database:

sudo apt-get update
4.Install the MongoDB packages.

You can install either the latest stable version of MongoDB or a specific version of MongoDB.

Install the latest stable version of MongoDB.

Issue the following command:

sudo apt-get install -y mongodb-org

Install a specific release of MongoDB.

To install a specific release, you must specify each component package individually along with the version number, as in the following example:

sudo apt-get install -y mongodb-org=3.2.9 mongodb-org-server=3.2.9 mongodb-org-shell=3.2.9 mongodb-org-mongos=3.2.9 mongodb-org-tools=3.2.9

If you only install mongodb-org=3.2.9 and do not include the component packages, the latest version of each MongoDB package will be installed regardless of what version you specified.

Pin a specific version of MongoDB.

Although you can specify any available version of MongoDB, apt-get will upgrade the packages when a newer version becomes available. To prevent unintended upgrades, pin the package. To pin the version of MongoDB at the currently installed version, issue the following command sequence:

echo "mongodb-org hold" | sudo dpkg --set-selections
echo "mongodb-org-server hold" | sudo dpkg --set-selections
echo "mongodb-org-shell hold" | sudo dpkg --set-selections
echo "mongodb-org-mongos hold" | sudo dpkg --set-selections
echo "mongodb-org-tools hold" | sudo dpkg --set-selections
(Ubuntu 16.04-only) Create systemd service file

NOTE

Follow this step ONLY if you are running Ubuntu 16.04.

Create a new file at /lib/systemd/system/mongod.service with the following contents:

[Unit]
Description=High-performance, schema-free document-oriented database
After=network.target
Documentation=https://docs.mongodb.org/manual

[Service]
User=mongodb
Group=mongodb
ExecStart=/usr/bin/mongod --quiet --config /etc/mongod.conf

[Install]
WantedBy=multi-user.target

Run MongoDB Community Edition

The MongoDB instance stores its data files in /var/lib/mongodb and its log files in/var/log/mongodb by default, and runs using the mongodb user account. You can specify alternate log and data file directories in /etc/mongod.conf. See systemLog.path and storage.dbPath for additional information.

If you change the user that runs the MongoDB process, you must modify the access control rights to the/var/lib/mongodb and /var/log/mongodb directories to give this user access to these directories.

Start MongoDB.

Issue the following command to start mongod:

sudo service mongod start

Verify that MongoDB has started successfully

Verify that the mongod process has started successfully by checking the contents of the log file at/var/log/mongodb/mongod.log for a line reading

[initandlisten] waiting for connections on port <port>

where <port> is the port configured in /etc/mongod.conf, 27017 by default.

Stop MongoDB.

As needed, you can stop the mongod process by issuing the following command:

sudo service mongod stop
Restart MongoDB.

Issue the following command to restart mongod:

sudo service mongod restart
Begin using MongoDB.

To help you start using MongoDB, MongoDB provides Getting Started Guides in various driver editions. See Getting Started for the available editions.

Before deploying MongoDB in a production environment, consider the Production Notes document.

Later, to stop MongoDB, press Control+C in the terminal where the mongod instance is running.

 

Courtesy: MongoDB Website

Ruby Variables

Variables are the memory locations which hold any data to be used by any program.

There are five types of variables supported by Ruby. You already have gone through a small description of these variables in previous chapter as well. These five types of variables are explained in this chapter.

Ruby Global Variables:

Global variables begin with $. Uninitialized global variables have the value nil and produce warnings with the -w option.

Assignment to global variables alters global status. It is not recommended to use global variables. They make programs cryptic.

Here is an example showing usage of global variable.

#!/usr/bin/ruby

$global_variable = 10
class Class1
  def print_global
     puts "Global variable in Class1 is #$global_variable"
  end
end
class Class2
  def print_global
     puts "Global variable in Class2 is #$global_variable"
  end
end

class1obj = Class1.new
class1obj.print_global
class2obj = Class2.new
class2obj.print_global

Here $global_variable is a global variable. This will produce the following result:

NOTE: In Ruby you CAN access value of any variable or constant by putting a hash (#) character just before that variable or constant.

Global variable in Class1 is 10
Global variable in Class2 is 10

Ruby Instance Variables:

Instance variables begin with @. Uninitialized instance variables have the value nil and produce warnings with the -w option.

Here is an example showing usage of Instance Variables.

#!/usr/bin/ruby

class Customer
   def initialize(id, name, addr)
      @cust_id=id
      @cust_name=name
      @cust_addr=addr
   end
   def display_details()
      puts "Customer id #@cust_id"
      puts "Customer name #@cust_name"
      puts "Customer address #@cust_addr"
    end
end

# Create Objects
cust1=Customer.new("1", "John", "Wisdom Apartments, Ludhiya")
cust2=Customer.new("2", "Poul", "New Empire road, Khandala")

# Call Methods
cust1.display_details()
cust2.display_details()

Here, @cust_id, @cust_name and @cust_addr are instance variables. This will produce the following result:

Customer id 1
Customer name John
Customer address Wisdom Apartments, Ludhiya
Customer id 2
Customer name Poul
Customer address New Empire road, Khandala

Ruby Class Variables:

Class variables begin with @@ and must be initialized before they can be used in method definitions.

Referencing an uninitialized class variable produces an error. Class variables are shared among descendants of the class or module in which the class variables are defined.

Overriding class variables produce warnings with the -w option.

Here is an example showing usage of class variable:

#!/usr/bin/ruby

class Customer
   @@no_of_customers=0
   def initialize(id, name, addr)
      @cust_id=id
      @cust_name=name
      @cust_addr=addr
      @@no_of_customers += 1
   end
   def display_details()
      puts "Customer id #@cust_id"
      puts "Customer name #@cust_name"
      puts "Customer address #@cust_addr"
    end
    def total_no_of_customers()
       puts "Total number of customers: #@@no_of_customers"
    end
end

# Create Objects
cust1=Customer.new("1", "John", "Wisdom Apartments, Ludhiya")
cust2=Customer.new("2", "Poul", "New Empire road, Khandala")

# Call Methods
cust1.total_no_of_customers()
cust2.total_no_of_customers()

Here @@no_of_customers is a class variable. This will produce the following result:

Total number of customers: 1
Total number of customers: 2

Ruby Local Variables:

Local variables begin with a lowercase letter or _. The scope of a local variable ranges from class, module, def, or do to the corresponding end or from a block’s opening brace to its close brace {}.

When an uninitialized local variable is referenced, it is interpreted as a call to a method that has no arguments.

Assignment to uninitialized local variables also serves as variable declaration. The variables start to exist until the end of the current scope is reached. The lifetime of local variables is determined when Ruby parses the program.

In the above example local variables are id, name and addr.

Ruby Constants:

Constants begin with an uppercase letter. Constants defined within a class or module can be accessed from within that class or module, and those defined outside a class or module can be accessed globally.

Constants may not be defined within methods. Referencing an uninitialized constant produces an error. Making an assignment to a constant that is already initialized produces a warning.

#!/usr/bin/ruby

class Example
   VAR1 = 100
   VAR2 = 200
   def show
       puts "Value of first Constant is #{VAR1}"
       puts "Value of second Constant is #{VAR2}"
   end
end

# Create Objects
object=Example.new()
object.show

Here VAR1 and VAR2 are constant. This will produce the following result:

Value of first Constant is 100
Value of second Constant is 200

Ruby Pseudo-Variables:

They are special variables that have the appearance of local variables but behave like constants. You can not assign any value to these variables.

  • self: The receiver object of the current method.
  • true: Value representing true.
  • false: Value representing false.
  • nil: Value representing undefined.
  • __FILE__: The name of the current source file.
  • __LINE__: The current line number in the source file.

Courtesy: Tutorials Point