Databases, Collections & Documents

MongoDB · Lesson 3 of 28 7 min read Updated

A MongoDB server holds databases, a database holds collections, and a collection holds documents. These three levels are all you need to organise data. Unlike SQL, you rarely create any of them in advance: MongoDB creates a database and a collection the first time you store a document in them.

In this lesson you will switch databases, create collections both automatically and explicitly, insert a couple of documents, and learn the rules for documents and names. You will also meet three special kinds of collection for later use.

Switching to a database

Start mongosh and use the use command to choose a database. The command works even if the database does not exist yet:

MongoDB Shell
use practice
db
show collections
Output
switched to db practice
practice

db is a variable that always points at the current database, so typing it prints the name. show collections printed nothing because practice is still empty. In fact, the database does not exist on disk yet, which is why show dbs would not list it.

Creating a collection by inserting

Inside a database you reach a collection with db.<collection name>. Insert a document into a students collection and MongoDB creates both the collection and the database on the spot:

MongoDB Shell
db.students.insertOne({ name: 'Meera Iyer', city: 'Pune', course: 'MongoDB' })
show collections
Output
{
  acknowledged: true,
  insertedId: ObjectId('6ae41d48c3f5e8a91d2b7a01')
}
students

The result tells you the write was acknowledged by the server and shows the _id that was created for the document. You did not give an _id, so MongoDB generated an ObjectId, a 12-byte unique value. Yours will be different, because it is based partly on the current time.

Notice how the document is written: it is a JavaScript object. In mongosh the field names do not need quotes and strings can use single or double quotes. MongoDB stores it as BSON, a binary form of JSON.

Documents in one collection can differ

Insert a second student with extra fields and look at both:

MongoDB Shell
db.students.insertOne({ name: 'Kabir Singh', city: 'Rohtak', course: 'MongoDB', skills: ['HTML', 'CSS'], fees: { total: 12000, paid: 8000 } })
db.students.find()
Output
{
  acknowledged: true,
  insertedId: ObjectId('6ae41d6ac3f5e8a91d2b7a02')
}
[
  {
    _id: ObjectId('6ae41d48c3f5e8a91d2b7a01'),
    name: 'Meera Iyer',
    city: 'Pune',
    course: 'MongoDB'
  },
  {
    _id: ObjectId('6ae41d6ac3f5e8a91d2b7a02'),
    name: 'Kabir Singh',
    city: 'Rohtak',
    course: 'MongoDB',
    skills: [ 'HTML', 'CSS' ],
    fees: { total: 12000, paid: 8000 }
  }
]

Kabir's document has a skills array and a fees embedded document (a document inside a document). Meera's has neither, and MongoDB is happy with that. This flexibility is useful, but in a real application you still want documents of one collection to share a predictable shape. Schema Validation with $jsonSchema shows how to enforce one.

find() with no filter returns every document in the collection. mongosh prints the results as an array and adds _id as the first field of each document.

Creating a collection explicitly

You can also create an empty collection with db.createCollection(). This is needed when you want to set options at creation time, such as validation rules:

MongoDB Shell
db.createCollection('teachers')
show collections
Output
{ ok: 1 }
students
teachers

{ ok: 1 } is how MongoDB reports that a command succeeded. Notice that show collections lists names in alphabetical order.

Rules for documents and names

Every document follows a few rules:

  • It must have an _id field whose value is unique within the collection. MongoDB adds one if you leave it out, and you cannot change it after the document is created.
  • A single document can be at most 16 MB. That is a lot of text, but an array that grows forever can reach it; design for that, as you will see in Schema Design: Embed or Reference.
  • Field names are strings. Avoid starting them with $ and avoid dots (.) in them, because both have special meanings in queries.
  • Field order is kept as you inserted it, and _id is always stored first.

For database and collection names, stay with lowercase letters, digits and underscores, such as shop or order_items. Names are case-sensitive, so Students and students would be two different collections, which is a common source of "my data disappeared" confusion. Collection names must not start with system., which is reserved for MongoDB.

Dropping collections and databases

drop() deletes a collection with all its documents and indexes. db.dropDatabase() deletes the current database completely:

MongoDB Shell
db.teachers.drop()
db.dropDatabase()
Output
true
{ ok: 1, dropped: 'practice' }

There is no undo and no confirmation prompt, so check the prompt shows the database you mean before you press Enter.

Advanced: special kinds of collection

Most collections are ordinary, but createCollection() can make a few special ones:

  • Capped collections have a fixed size and overwrite the oldest documents when full, like a ring buffer for recent log lines: db.createCollection('recent_logs', { capped: true, size: 1048576 }).
  • Time series collections store measurements over time, such as temperature readings from sensors in a Kochi warehouse, very compactly: db.createCollection('readings', { timeseries: { timeField: 'ts', metaField: 'sensor' } }).
  • Views are read-only collections defined by a query, created with db.createView(). They store no data of their own.

You will not need these in the rest of the course, but it helps to recognise them in other people's code.

Common mistakes

  • Typos create new collections. db.studnets.insertOne(...) silently creates a collection called studnets. If data seems to vanish, run show collections and look for near-duplicates.
  • Forgetting which database you are in. The prompt shows the current database. Inserting while in test puts your data in test.
  • Dropping the wrong thing. db.dropDatabase() acts on the current database. Type db first if you are not sure.

Key points

  • A server holds databases, a database holds collections, and a collection holds documents.
  • use <name> switches database; db shows the current one; show dbs and show collections list what exists.
  • Inserting into a collection that does not exist creates the collection (and the database).
  • db.createCollection() creates a collection explicitly, which is needed when you want options.
  • Every document has a unique, unchangeable _id, and a document can be at most 16 MB.
  • drop() removes a collection and db.dropDatabase() removes the current database, with no undo.

Exercise

Create a database called library. Insert two documents into a books collection: one with a title, author and year, and one that also has an array of genres. Create an empty members collection explicitly, list the collections, then drop the whole library database.

Show solution
MongoDB Shell
use library
db.books.insertOne({ title: 'Godan', author: 'Premchand', year: 1936 })
db.books.insertOne({ title: 'The Guide', author: 'R. K. Narayan', year: 1958, genres: ['novel', 'classic'] })
db.createCollection('members')
show collections
db.dropDatabase()

show collections lists books and members. The two books have different fields, which MongoDB accepts, and db.dropDatabase() removes the database together with both collections.

Quick Quiz

1. When does MongoDB create a new collection automatically?

2. What happens if you insert a document without an _id field?

3. What is the maximum size of a single MongoDB document?

Learn MongoDB with a mentor

Free lessons get you started. Our Full Stack Web Development training adds real projects and code reviews from working developers.

  • Project-based learning
  • Mentor code reviews
  • Free counselling call