Search code examples
mongodbtimestampunix-timestamp

uses for mongodb ObjectId creation time


The ObjectId used as the default key in mongodb documents has embedded timestamp (calling objectid.generation_time returns a datetime object). So it is possible to use this generation time instead of keeping a separate creation timestamp? How will you be able to sort by creation time or query for the last N items efficiently using this embedded timestamp?


Solution

  • I suppose since MongoDB ObjectId contain a timestamp, you can sort by 'created date' if you will sort by objectId:

    items.find.sort( [['_id', -1]] ) // get all items desc by created date.
    

    And if you want last 30 created items you can use following query:

    items.find.sort( [['_id', -1]] ).limit(30) // get last 30 createad items 
    

    I am actualy not sure,i just suppose that ordering by _id should work as described above. I'll create some tests later.

    Update:

    Yes it is so. If you order by _id you will automatically order by _id created date. I've done small test in c#, mb someone interest in it:

      public class Item
      {
        [BsonId]
        public ObjectId Id { get; set; }
    
        public DateTime CreatedDate { get; set; }
    
        public int Index { get; set; }
      }
    
    
    
     [TestMethod]
     public void IdSortingTest()
     {
       var server = MongoServer.Create("mongodb://localhost:27020");
       var database = server.GetDatabase("tesdb");
    
       var collection = database.GetCollection("idSortTest");
       collection.RemoveAll();
    
       for (int i = 0; i <= 500; i++)
       {
         collection.Insert(new Item() { 
                 Id = ObjectId.GenerateNewId(), 
                 CreatedDate = DateTime.Now, 
                 Index = i });
       }
    
       var cursor = collection.FindAllAs<Item>();
       cursor.SetSortOrder(SortBy.Descending("_id"));
       var itemsOrderedById = cursor.ToList();
    
       var cursor2 = collection.FindAllAs<Item>();
       cursor2.SetSortOrder(SortBy.Descending("CreatedDate"));
       var itemsOrderedCreatedDate = cursor.ToList();
    
       for (int i = 0; i <= 500; i++)
       {
         Assert.AreEqual(itemsOrderedById[i].Index, itemsOrderedCreatedDate[i].Index);
       }
    }