When you work for a large number of clients, you find yourself setting up a lot of projects. While it would be nice to create a template project to speed up this process, the reality is that technology moves fast and each project has its own unique requirements.

So the next best thing is to use a libraries that solve specific problems with minimal integration overhead. In 2015, one of these common problems was having your front-end Javascript application talk to a web server. This is how Helpful Human ended up creating Portals.

Nowadays, the fetch API is widely supported and is the go-to solution for making XHR requests. But that wasn’t the case in 2015 and certain browsers, like Internet Explorer, were requirements for some of our clients.

So the next best thing was to use an existing library that could solve this problem. This was easier said than done, as different libraries had different conflicts with different project requirements.

# Creating the first version

So we decided to create our own library that would meet the needs of our clients and projects.

These requirements were:

  • No issues related to licensing or intellectual property (MIT license).
  • Very small footprint and bundle size.
  • No dependencies for the library itself, but build tools were fine.
  • Support for promises.
  • Support for Typescript, though this became a requirement later on.
  • Had to support browsers as old as Internet Explorer 8.
  • Ability to modify intercept requests in order to add authentication information, perform logging and caching, etc.

The intial API was largely modeled after Angular 1.5’s $http service.

var portals = require("portals");
var http = new portals.Portal();

http.useDefaultInterceptors();

http.onRequest(function (config) {
  console.log("logging: ", config.url);

  return config;
});

http.send({
  method: "GET",
  url: "/some-endpoint",
  headers: {
    "Accept": "application/json"
  }
})
.then(function (res) {
  // do something with response
});

# Expanding the library with version 2

In 2018, I decided to give the library a much needed facelift. Version 2 was a complete rewrite added type support, improved test coverage, and had more built-in middlewares. I also moved away from classes and used a function-oriented style to match the growing trend of the Javascript ecosystem.

import { createPortal, supportsJson, withPrefix, withBearer } from "portals";

const http = createPortal(
  supportsJson(),
  withPrefix("https://api.example.com"),
  withBearer(req => `Bearer ${localStorage.getItem("token")}`),
);

http({
  url: "/some-endpoint"
}).then(function (res) {
  // do something with response
});

Version 3 would come a few months later and only saw some minor improvements and type corrections from version 2. I don’t remember why the major version was bumped, only that it was necessary for some reason.

# So where is version 4?

There was never a fourth version as it was never needed. Eventually the project requirements we had began to change and the aforementioned fetch API became widely supported. This made the library obsolete (at least for us) and any on-going support was abandoned.