Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

NodeJS/Express API versioning

I'd like to set up an API versioning, similar to how Stripe does it but I'm not quite sure how to make express do what I need. https://stripe.com/docs/api#versioning

What I'm looking for is, the proper route would be something like:

/api/v1/call

The kicker is, I'd like them to pass in a version revision like stripe allows, so if they sent a header like "API-Version: 2015-08-15", it would map to that specific version of the major version. So, v1 but the version updated on 2015-08-15.

Essentially, if there is an update to the API call that is not backwards compatible, I'd roll a new version for that particular call. Express would be smart enough to know that if a version isn't passed, use the latest. If a version is passed, use the latest version for each call up until the version date.

I'd assume the directory structure would be something like:

  • /router/
  • /router/v1
  • /router/v1/call
  • /router/v1/anotherCall

And maybe in the call directories, there is a index that checks for the header version and uses the proper file.

So maybe for instance

  • /router/v1/call/index.js
  • /router/v1/call/20150810.js -- First version
  • /router/v1/call/20150815.js -- Updated version that isn't backwards compat.

Thoughts? Ideas?

like image 797
Beta4 Avatar asked Mar 16 '23 02:03

Beta4


1 Answers

If you are managing version in routes(url) and client sends version in headers then express doesn't provide any elegant way to handle versioning. Also, doing versioning in routes is not restful.

I wrote an simple npm module to solve this problem. https://www.npmjs.com/package/express-routes-versioning

Express routes versioning

Module allows individual routes to be versioned separately. It is agnostic about specific versioning strategies and allows the application to set the version, so you should be able to parse version from headers and set it to req.version in a middleware. It supports semver versioning format and symbols to map multiple versions to single function. Sample code on how it works.

var app = require('express')();
var versionRoutes = require('express-routes-versioning')();
app.listen(3000);
app.use(function(req, res, next) {
    //req.version is used to determine the version
   req.version = req.headers['accept-version'];
   next();
});
app.get('/users', versionRoutes({
   "1.0.0": respondV1, 
   "~2.2.1": respondV2
}));

// curl -s -H 'accept-version: 1.0.0' localhost:3000/users
// version 1.0.0 or 1.0 or 1 !
function respondV1(req, res, next) {
   res.status(200).send('ok v1');
}

//curl -s -H 'accept-version: 2.2.0' localhost:3000/users
//Anything from 2.2.0 to 2.2.9
function respondV2(req, res, next) {
   res.status(200).send('ok v2');
}

By default, if the client version doesn't match the version provided in the server, module servers the latest version callback available in that route. This behavior can be overridden by providing an additional callback. More info and source code available at https://github.com/Prasanna-sr/express-routes-versioning

like image 187
prasanna ramanujam Avatar answered Mar 24 '23 00:03

prasanna ramanujam