Learn MongoDB With Me - Part Two

Introduction

This is the second article of the series “Learn MongoDB with Me,” and if you haven’t read my previous post on this topic, I strongly recommend you find it here. This is a continuation of exploring the Mongo shells. We will be performing some commands on the Mongo shells. For easy reference I will try to add screenshots for each of the steps I am following. I hope it will help you to come along with me. Thanks for reading. You can always read this article on my blog here.

Background

I believe that you have enough knowledge about Mongo DB and how to set up it, and how Mongo shells can be used. If you are not able to answer these question for yourself, please consider reading my previous posts again.

Mongo shells, the perfect CLI

We can do anything in the Mongo shell, to make a statement clear. I am going to perform some CRUD operations (Create, Read, Update, Delete) within Mongo shells. To do so, we can use Mongo import commands. The Mongo import commands can do the work for you, even if the data is in .tsv, .csv, .json etc. Let’s see those in action.

As a first step, let us see some documentation.

  1. C:\Program Files\MongoDB\Server\3.4\bin>mongoimport --help

The above command will give you all the options available to get started.

  1. Usage:  
  2.     mongoimport < options > < file >  
  3.     Import CSV, TSV or JSON data into MongoDB.If no file is provided, mongoimport reads from stdin.  
  4. See http: //docs.mongodb.org/manual/reference/program/mongoimport/ for more information.  
  5.     general options:  
  6.     /help print usage /  
  7.     version print the tool version and  
  8. exit  
  9. verbosity options:  
  10.     /v, /verbose: < level > more detailed log output(include multiple times  
  11.         for more verbosity, e.g. - vvvvv,  
  12.         or specify a numeric value,  
  13.         e.g.--verbose = N) /  
  14.     quiet hide all log output  
  15. connection options:  
  16.     /h, /host: < hostname > mongodb host to connect to(setname / host1, host2  
  17.         for replica sets) /  
  18.     port: < port > server port(can also use  
  19.         --host hostname: port)  
  20. kerberos options:  
  21.     /gssapiServiceName:<service-name> service name to use when  
  22. authenticating using  
  23. GSSAPI / Kerberos('mongodb'  
  24.         by  
  25.         default) /  
  26.     gssapiHostName: < host - name > hostname to use when  
  27. authenticating using  
  28. GSSAPI / Kerberos(remote server 's address by default)  
  29.     ssl options:  
  30.     /ssl connect to a mongod or mongos  
  31.     that has ssl enabled /  
  32.     sslCAFile: < filename > the.pem file containing the root certificate chain from the certificate authority /  
  33.     sslPEMKeyFile: < filename > the.pem file containing the certificate and key /  
  34.     sslPEMKeyPassword: < password > the password to decrypt the sslPEMKeyFile,  
  35.     if necessary /  
  36.     sslCRLFile: < filename > the.pem file containing the certificate revocation list /  
  37.     sslAllowInvalidCertificates bypass the validation  
  38.     for server certificates /  
  39.     sslAllowInvalidHostnames bypass the validation  
  40.     for server name /  
  41.     sslFIPSMode use FIPS mode of the installed openssl library authentication options:  
  42.     /u, /username: < username > username  
  43.     for authentication /  
  44.     p, /password:<password> password for authentication /  
  45.     authenticationDatabase: < database - name > database that holds the user 's credentials /  
  46.     authenticationMechanism: < mechanism > authentication mechanism to use namespace options:  
  47.     /d, /db: < database - name > database to use /  
  48.     c, /collection:<collection-name> collection to use  
  49.     uri options:  
  50.     /uri:mongodb-uri mongodb uri connection string  
  51.     input options:  
  52.     /f, /fields: < field > [, < field > ] * comma separated list of  
  53.     fields, e.g. - f name, age /  
  54.     fieldFile: < filename > file with field names - 1 per line /  
  55.     file: < filename > file to  
  56.     import from;  
  57.     if not specified, stdin is used /  
  58.     headerline use first line in input source as the field list(CSV and TSV only) /  
  59.     jsonArray treat input source as a JSON array /  
  60.     parseGrace: < grace > controls behavior when type coercion fails - one of:  
  61.     autoCast, skipField, skipRow,  
  62.     stop(defaults to 'stop')  
  63.     (  
  64.         default: stop) /  
  65.     type: < type > input format to  
  66.     import: json,  
  67.     csv, or tsv(defaults to 'json')(  
  68.         default: json) /  
  69.     columnsHaveTypes indicated that the field list(from--fields, --fieldsFile,  
  70.         or--headerline) specifies types; They must be in the form of  
  71.     '<colName>.<type>(<arg>)'.The type can be one of: auto,  
  72.     binary, bool, date, date_go,  
  73.     date_ms, date_oracle, double,  
  74.     int32, int64, string.For each of the date types, the argument is a datetime layout string.For the binary type,  
  75.     the argument can be one of:  
  76.     base32, base64, hex.All other types take an empty argument.Only valid  
  77.     for CSV and TSV imports.e.g.zipcode.string(),  
  78.     thumbnail.binary(base64) ingest options:  
  79.     /drop drop collection before  
  80.     inserting documents /  
  81.     ignoreBlanks ignore fields with empty values in CSV and TSV /  
  82.     maintainInsertionOrder insert documents in the order of their appearance in the input source /  
  83.     j, /numInsertionWorkers:<number> number of insert operations  
  84.     to run concurrently(defaults to 1)(  
  85.         default: 1) /  
  86.     stopOnError stop importing at first insert / upsert error /  
  87.     mode: [insert | upsert | merge] insert: insert only.upsert:  
  88.     insert or replace existing documents.merge: insert or modify existing documents.defaults to insert /  
  89.     upsertFields: < field > [, < field > ] * comma - separated fields  
  90.     for the query part when--mode is set to upsert or merge /  
  91.     writeConcern: < write - concern - specifier > write concern options e.g.  
  92.     --writeConcern majority,  
  93.     --writeConcern '{w: 3,  
  94.     wtimeout: 500, fsync: true,  
  95.     j: true  
  96. }  
  97. ' /  
  98. bypassDocumentValidation bypass document validation  

Insert data to MondoDB using Mongo shell

Now let’s say I have the following JSON data, and we are going to insert the same to our db collection.

  1. [{  
  2.         "color""black",  
  3.         "category""hue",  
  4.         "type""primary",  
  5.         "code": {  
  6.             "rgba": [255, 255, 255, 1],  
  7.             "hex""#000"  
  8.         }  
  9.     },  
  10.     {  
  11.         "color""white",  
  12.         "category""value",  
  13.         "code": {  
  14.             "rgba": [0, 0, 0, 1],  
  15.             "hex""#FFF"  
  16.         }  
  17.     },  
  18.     {  
  19.         "color""red",  
  20.         "category""hue",  
  21.         "type""primary",  
  22.         "code": {  
  23.             "rgba": [255, 0, 0, 1],  
  24.             "hex""#FF0"  
  25.         }  
  26.     },  
  27.     {  
  28.         "color""blue",  
  29.         "category""hue",  
  30.         "type""primary",  
  31.         "code": {  
  32.             "rgba": [0, 0, 255, 1],  
  33.             "hex""#00F"  
  34.         }  
  35.     },  
  36.     {  
  37.         "color""yellow",  
  38.         "category""hue",  
  39.         "type""primary",  
  40.         "code": {  
  41.             "rgba": [255, 255, 0, 1],  
  42.             "hex""#FF0"  
  43.         }  
  44.     },  
  45.     {  
  46.         "color""green",  
  47.         "category""hue",  
  48.         "type""secondary",  
  49.         "code": {  
  50.             "rgba": [0, 255, 0, 1],  
  51.             "hex""#0F0"  
  52.         }  
  53.     }  
  54. ]  

To do so, we need to use the following command.

  1. C:\Program Files\MongoDB\Server\3.4\bin>mongoimport --db mylearning --collection colors --jsonArray --file colors.json

Here, as you can see, we are providing the db name, collection, name, the data type of the file, and finally the file name.

If you ever get the error as “Failed: open colors.json: The system cannot find the file specified.”, please make sure that the document is in the server folder, in my case it is “C:\Program Files\MongoDB\Server\3.4\bin”. If everything is fine, you will be able to see the output as preceding.

  1. C:\Program Files\MongoDB\Server\3.4\bin>mongoimport --db mylearning --collection colors --jsonArray --file colors.json  
  2. 2018-03-01T16:35:35.470+0530 connected to: localhost  
  3. 2018-03-01T16:35:36.012+0530 imported 6 documents  
  4. C:\Program Files\MongoDB\Server\3.4\bin>  

Reading the data from a collection in MongoDB

Now that we have colors collection, let’s go and check whether the database has the data we are expecting.

  1. C: \Program Files\ MongoDB\ Server\ 3.4\ bin > mongo  
  2. MongoDB shell version v3 .4 .9  
  3. connecting to: mongodb: //127.0.0.1:27017  
  4.     MongoDB server version: 3.4 .9  
  5. Server has startup warnings:  
  6.     2018 - 03 - 01 T16: 24: 43.793 + 0530 I CONTROL[initandlisten]  
  7. 2018 - 03 - 01 T16: 24: 43.793 + 0530 I CONTROL[initandlisten] ** WARNING: Access control is not enabled  
  8. for the database.  
  9. 2018 - 03 - 01 T16: 24: 43.793 + 0530 I CONTROL[initandlisten] ** Read and write access to data and configuration is unrestricted.  
  10. 2018 - 03 - 01 T16: 24: 43.793 + 0530 I CONTROL[initandlisten]  
  11. MongoDB Enterprise > use mylearning  
  12. switched to db mylearning  
  13. MongoDB Enterprise > show collections  
  14. chats  
  15. colors  
  16. messages  
  17. MongoDB Enterprise > db.colors.count  
  18.   
  19. function(query, options) {  
  20.     query = this.find(query);  
  21.     // Apply options and return the result of the find  
  22.     return QueryHelpers._applyCountOptions(query, options).count(true);  
  23. }  
  24. MongoDB Enterprise > db.colors.count()  
  25. 6  
  26. MongoDB Enterprise >  

When you use count, make sure you are treating it as a function as count(). We have the count as 6, and that’s what we are expecting. Am I right? Don’t you think that we should go fetch some data from that collection with some filters?

  1. MongoDB Enterprise > db.colors.find({  
  2.     "type""primary"  
  3. }) {  
  4.     "_id": ObjectId("5a97de7f2fcdf731d255a19d"),  
  5.     "color""black",  
  6.     "category""hue",  
  7.     "type""primary",  
  8.     "code": {  
  9.         "rgba": [255, 255, 255, 1],  
  10.         "hex""#000"  
  11.     }  
  12. } {  
  13.     "_id": ObjectId("5a97de7f2fcdf731d255a19e"),  
  14.     "color""yellow",  
  15.     "category""hue",  
  16.     "type""primary",  
  17.     "code": {  
  18.         "rgba": [255, 255, 0, 1],  
  19.         "hex""#FF0"  
  20.     }  
  21. } {  
  22.     "_id": ObjectId("5a97de7f2fcdf731d255a1a1"),  
  23.     "color""red",  
  24.     "category""hue",  
  25.     "type""primary",  
  26.     "code": {  
  27.         "rgba": [255, 0, 0, 1],  
  28.         "hex""#FF0"  
  29.     }  
  30. } {  
  31.     "_id": ObjectId("5a97de7f2fcdf731d255a1a2"),  
  32.     "color""blue",  
  33.     "category""hue",  
  34.     "type""primary",  
  35.     "code": {  
  36.         "rgba": [0, 0, 255, 1],  
  37.         "hex""#00F"  
  38.     }  
  39. }  
  40. MongoDB Enterprise >  

We have successfully imported that data, and we have fetched the colors with type as primary. I think there should be a custom color, which has the type as primary. Can we do that now?

  1. MongoDB Enterprise > db.colors.insert({  
  2.         ..."color""custome",  
  3.         ..."category""hue",  
  4.         ..."type""primary",  
  5.         ..."code": {  
  6.             ..."rgba": [255, 1, 255, 1],  
  7.             ..."hex""#FF1"  
  8.                 ...  
  9.         }  
  10.         ...  
  11.     }  
  12.     ...)  
  13. WriteResult({  
  14.     "nInserted": 1  
  15. })  
  16. MongoDB Enterprise >  

Now if you run our previous query, you can see the output as preceding.

  1. MongoDB Enterprise > db.colors.find({  
  2.     "type""primary"  
  3. }) {  
  4.     "_id": ObjectId("5a97de7f2fcdf731d255a19d"),  
  5.     "color""black",  
  6.     "category""hue",  
  7.     "type""primary",  
  8.     "code": {  
  9.         "rgba": [255, 255, 255, 1],  
  10.         "hex""#000"  
  11.     }  
  12. } {  
  13.     "_id": ObjectId("5a97de7f2fcdf731d255a19e"),  
  14.     "color""yellow",  
  15.     "category""hue",  
  16.     "type""primary",  
  17.     "code": {  
  18.         "rgba": [255, 255, 0, 1],  
  19.         "hex""#FF0"  
  20.     }  
  21. } {  
  22.     "_id": ObjectId("5a97de7f2fcdf731d255a1a1"),  
  23.     "color""red",  
  24.     "category""hue",  
  25.     "type""primary",  
  26.     "code": {  
  27.         "rgba": [255, 0, 0, 1],  
  28.         "hex""#FF0"  
  29.     }  
  30. } {  
  31.     "_id": ObjectId("5a97de7f2fcdf731d255a1a2"),  
  32.     "color""blue",  
  33.     "category""hue",  
  34.     "type""primary",  
  35.     "code": {  
  36.         "rgba": [0, 0, 255, 1],  
  37.         "hex""#00F"  
  38.     }  
  39. } {  
  40.     "_id": ObjectId("5a97e3202c19f0e958477e06"),  
  41.     "color""custome",  
  42.     "category""hue",  
  43.     "type""primary",  
  44.     "code": {  
  45.         "rgba": [255, 1, 255, 1],  
  46.         "hex""#FF1"  
  47.     }  
  48. }  
  49. MongoDB Enterprise >  

Updating a document in MongoDB

Wow, we have the data now. And we performed,Create and Read operations on our DB. It is time for updating the document. Let’s go ahead and add a new property “manuallyCreated” to the color we have created. It is going to help us in finding these kinds of entries easily.

  1. MongoDB Enterprise > db.colors.update({  
  2.         ..."color""custome"  
  3.             ...  
  4.     }  
  5.     ..., {  
  6.         ...$set: {  
  7.             "manuallyCreated""True"  
  8.         }  
  9.     }  
  10.     ...)  
  11. WriteResult({  
  12.     "nMatched": 1,  
  13.     "nUpserted": 0,  
  14.     "nModified": 1  
  15. })  
  16. MongoDB Enterprise >  

Let’s find all the manually created colors now, and we know there is going to be one record.

  1. MongoDB Enterprise > db.colors.find({  
  2.     "manuallyCreated""True"  
  3. }) {  
  4.     "_id": ObjectId("5a97e3202c19f0e958477e06"),  
  5.     "color""custome",  
  6.     "category""hue",  
  7.     "type""primary",  
  8.     "code": {  
  9.         "rgba": [255, 1, 255, 1],  
  10.         "hex""#FF1"  
  11.     },  
  12.     "manuallyCreated""True"  
  13. }  
  14. MongoDB Enterprise >  

Let’s update the color name to “custom” instead of “custome”, sorry for the typo.

  1. MongoDB Enterprise > db.colors.update({  
  2.         "_id": ObjectId("5a97e3202c19f0e958477e06")  
  3.     },  
  4.     ...{  
  5.         $set: {  
  6.             "color""custom"  
  7.         }  
  8.     })  
  9. WriteResult({  
  10.     "nMatched": 1,  
  11.     "nUpserted": 0,  
  12.     "nModified": 1  
  13. })  
  14. MongoDB Enterprise >  

Ah, I made a mistake. I ran the following query by mistake.

  1. MongoDB Enterprise > db.colors.update({  
  2.     "color""custom"  
  3. }, {  
  4.     $set: {  
  5.         "code.rgba": [255, 1, 255]  
  6.     }  
  7. })  
  8. WriteResult({  
  9.     "nMatched": 1,  
  10.     "nUpserted": 0,  
  11.     "nModified": 1  
  12. })  

Do you know what that query just did? It just updated the rgba of our custom color to three point array “[ 255, 1, 255]”. That’s not what I wanted. Now what we can do? We need to add one value to that set. Let’s do that now.

  1. MongoDB Enterprise > db.colors.update({  
  2.     "color""custom"  
  3. }, {  
  4.     $addToSet: {  
  5.         "code.rgba""1"  
  6.     }  
  7. })  
  8. WriteResult({  
  9.     "nMatched": 1,  
  10.     "nUpserted": 0,  
  11.     "nModified": 1  
  12. })  
  13. MongoDB Enterprise > db.colors.find({  
  14.     "manuallyCreated""True"  
  15. }) {  
  16.     "_id": ObjectId("5a97e3202c19f0e958477e06"),  
  17.     "color""custom",  
  18.     "category""hue",  
  19.     "type""primary",  
  20.     "code": {  
  21.         "rgba": [255, 1, 255, "1"],  
  22.         "hex""#FF1"  
  23.     },  
  24.     "manuallyCreated""True"  
  25. }  
  26. MongoDB Enterprise >  

Please be aware that there is one more update, which will just update the entire document. In this case, if you are not providing the value for each attribute, it will be overwriting the same. Let’s see an example.

  1. MongoDB Enterprise > db.colors.update({"color":"red"},{"color":"test"})  
  2. WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })  
  3. MongoDB Enterprise > db.colors.find({})  

Here we just gave a command to update the color red to color test, as we have not provided other attributes as part of our query. After running the query, there will be only one attribute, that is color.

  1. MongoDB Enterprise > db.colors.find({}) {  
  2.     "_id": ObjectId("5a97f73f2fcdf731d255a1f1"),  
  3.     "color""black",  
  4.     "category""hue",  
  5.     "type""primary",  
  6.     "code": {  
  7.         "rgba": [255, 255, 255, 1],  
  8.         "hex""#000"  
  9.     }  
  10. } {  
  11.     "_id": ObjectId("5a97f73f2fcdf731d255a1f2"),  
  12.     "color""test"  
  13. } {  
  14.     "_id": ObjectId("5a97f73f2fcdf731d255a1f3"),  
  15.     "color""white",  
  16.     "category""value",  
  17.     "code": {  
  18.         "rgba": [0, 0, 0, 1],  
  19.         "hex""#FFF"  
  20.     }  
  21. } {  
  22.     "_id": ObjectId("5a97f73f2fcdf731d255a1f4"),  
  23.     "color""blue",  
  24.     "category""hue",  
  25.     "type""primary",  
  26.     "code": {  
  27.         "rgba": [0, 0, 255, 1],  
  28.         "hex""#00F"  
  29.     }  
  30. } {  
  31.     "_id": ObjectId("5a97f73f2fcdf731d255a1f5"),  
  32.     "color""yellow",  
  33.     "category""hue",  
  34.     "type""primary",  
  35.     "code": {  
  36.         "rgba": [255, 255, 0, 1],  
  37.         "hex""#FF0"  
  38.     }  
  39. } {  
  40.     "_id": ObjectId("5a97f73f2fcdf731d255a1f6"),  
  41.     "color""green",  
  42.     "category""hue",  
  43.     "type""secondary",  
  44.     "code": {  
  45.         "rgba": [0, 255, 0, 1],  
  46.         "hex""#0F0"  
  47.     }  
  48. }  
  49. MongoDB Enterprise > db.colors.find({  
  50.     "color""test"  
  51. }) {  
  52.     "_id": ObjectId("5a97f73f2fcdf731d255a1f2"),  
  53.     "color""test"  
  54. }  
  55. MongoDB Enterprise >  

Deleting a document in MongoDB shell

So, we added a custom color, and later we found that it is no longer needed in our document as we found an exact match with a different color. Now we need to remove the one we have added.

  1. MongoDB Enterprise > db.colors.remove({"color":"custom"})  
  2. WriteResult({ "nRemoved" : 1 })  
  3. MongoDB Enterprise >  

Let’s go and check again whether it is actually removed or not.

  1. MongoDB Enterprise > db.colors.find({"color":"custom"})  
  2. MongoDB Enterprise >  

The find query returns no records.

Deleting an entire collection

We have performed CRUD operations on a collection, what if we need to remove the entire collection?

  1. MongoDB Enterprise > db.colors.drop()  
  2. true  
  3. MongoDB Enterprise >  

With that, we are done with this post. I will be posting the continuation part of this series very soon. 

Conclusion

Thanks a lot for reading. Did I miss anything that you may think is needed? Did you find this post useful? I hope you liked this article. Please share with me your valuable suggestions and feedback.

Your turn. What do you think?

A blog isn’t a blog without comments, but do try to stay on topic. If you have a question unrelated to this post, you’re better off posting it on C# Corner, Code Project, Stack Overflow, Asp.Net Forum instead of commenting here. Tweet or email me a link to your question there and I’ll definitely try to help if I can.

Kindest Regards
Sibeesh Venu