Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Shorten ObjectId in node.js and mongoose

my URLs look like this at the moment:

http://www.sitename.com/watch?companyId=507f1f77bcf86cd799439011&employeeId=507f191e810c19729de860ea&someOtherId=.....

So, as you can see, it gets pretty long, pretty fast. I was thinking about shortening these ObjectIds. Idea is that I should add new field called "shortId" to every model in my database. So instead of having:

var CompanySchema = mongoose.Schema({
  /* _id will be added automatically by mongoose */
  name:         {type: String},
  address:      {type: String},
  directorName: {type: String}
});

we would have this:

var CompanySchema = mongoose.Schema({
  /* _id will be added automatically by mongoose */
  shortId:      {type: String}, /* WE SHOULD ADD THIS */
  name:         {type: String},
  address:      {type: String},
  directorName: {type: String},
});

I found a way to do it like this:

// Encode
var b64 = new Buffer('47cc67093475061e3d95369d', 'hex')
  .toString('base64')
  .replace('+','-')
  .replace('/','_')
;
// -> shortID is now: R8xnCTR1Bh49lTad

But I still think it could be shorter.

Also, I found this npm module: https://www.npmjs.com/package/short-mongo-id but I don't see it's being used too much so I can't tell if it's reliable.

Anyone has any suggestions?

like image 685
Drag0 Avatar asked Feb 25 '15 14:02

Drag0


People also ask

What is ObjectId in Mongoose?

An ObjectID is a 12-byte Field Of BSON type. The first 4 bytes representing the Unix Timestamp of the document. The next 3 bytes are the machine Id on which the MongoDB server is running. The next 2 bytes are of process id. The last Field is 3 bytes used for increment the objectid.

Is Mongoose ObjectId unique?

It does. One part of id is a random hash and another is a unique counter common accross collections.

What does schema types ObjectId mean?

Schema. Types. ObjectId and that's means, it looks like a string of an ID when you get it back from the database but it's not, it's actually an object that converts it to a string.

What does Mongoose do in node JS?

Mongoose is a Node. js-based Object Data Modeling (ODM) library for MongoDB. It is akin to an Object Relational Mapper (ORM) such as SQLAlchemy for traditional SQL databases. The problem that Mongoose aims to solve is allowing developers to enforce a specific schema at the application layer.


1 Answers

I ended up doing it like this:

Install shortId module (https://www.npmjs.com/package/shortid) Now you need to somehow stick this shortId to your objects when they're being saved in the database. I found the easiest way to do this is to append this functionality on the end of mongoose's function called "save()" (or "saveAsync()" if you promisified your model). You can do it like this:

var saveRef = Company.save;
Company.save = function() {
  var args = Array.prototype.slice.call(arguments, 0);
  // Add shortId to this company
  args[0].shortId = shortId.generate();
  return saveRef.apply(this, args);
};

So you just basically at each Model.save() function append this functionality to add shortId. That's that.

Edit: Also, I discovered that you can do it better and cleaner like this straight in Schema.

var shortId = require('shortid');
var CompanySchema = mongoose.Schema({
  /* _id will be added automatically by mongoose */
  shortId: {type: String, unique: true, default: shortId.generate}, /* WE SHOULD ADD THIS */
  name: {type: String},
  address: {type: String},
  directorName: {type: String}
});

EDIT : Now you can use the nanoid library which is much more performant and optimized. The documentation is also nice : https://github.com/ai/nanoid/

like image 65
Drag0 Avatar answered Oct 18 '22 18:10

Drag0