colinjfw

What is the GitHub deployments API?

A lesser known tool to ship your code that’s baked right in to GitHub.

A year or so ago I came across this interesting feature in GitHub called the deployments api. It seemed like a bit of a lost section in the GitHub docs, disconnected from other component and unlike pretty much everything else in GitHub I really hadn’t used this. I’ve spent some time investigating the deployments API over the last month or so and wanted to explain this for those of you who have hit this and wondered, what is this thing?

The GitHub deployments API is effectively a decoupled API for triggering deployments. GitHub doesn’t try and actually deploy the code for us, it just gives us an event to allow our own system to respond to and actually deploy the code.

The workflow seems relatively simple:

When I figured this out I thought this was pretty cool. I can replace my Jenkins pipeline with something more modern and API driven. Additionally, it decouples tools from one another by using GitHub as the source of truth for all the automation that needs to take place. Push events dictate when my code builds and deployment events dictate when my code is deployed.

GitHub has also added in some new UI which gives a picture of deployments for a specific pull request:

We can also view a list of deployments to all environments by visiting the environments tab on your project:

Completing the picture

So far so good. However, when I went to wire up my integration I realized there is a piece missing from this story. The workflow of the GitHub deployments API looks roughly like the picture below.

+---------+             +--------+            +-----------+        +-------------+
| Tooling |             | GitHub |            | 3rd Party |        | Your Server |
+---------+             +--------+            +-----------+        +-------------+
     |                      |                       |                     |
     |  Create Deployment   |                       |                     |
     |--------------------->|                       |                     |
     |                      |                       |                     |
     |  Deployment Created  |                       |                     |
     |<---------------------|                       |                     |
     |                      |                       |                     |
     |                      |   Deployment Event    |                     |
     |                      |---------------------->|                     |
     |                      |                       |     SSH+Deploys     |
     |                      |                       |-------------------->|
     |                      |                       |                     |
     |                      |   Deployment Status   |                     |
     |                      |<----------------------|                     |
     |                      |                       |                     |
     |                      |                       |   Deploy Completed  |
     |                      |                       |<--------------------|
     |                      |                       |                     |
     |                      |   Deployment Status   |                     |
     |                      |<----------------------|                     |
     |                      |                       |                     |

What this means is that the story of a deployment looks like this:

  1. Tooling calls a GitHub API to say “deploy this commit”

  2. GitHub fires webhooks to a system that takes action deploying the commit.

  3. Your code is then deployed when this system receives the webhook.

In the third step we can use GitHub actions or we can even just fire up a lambda function to listen for http events to deploy our code. The second step is all handled by GitHub. The first step of this story here is the problem. We don’t yet have a standardized toolkit to call this API.

I think immediately of a few things I would want here:

  1. I want a way of automatically triggering this API when a push event occurs on a branch.

  2. I want a way of deploying from Slack (ChatOps) using cool slash commands.

  3. I want to deploy ephemeral environments using these in pull requests.

There is also the opportunity for building advanced workflows on top of this. We can require that certain status checks are passing before a deployment can proceed. We can also listen to deployment success events to trigger other deployments to different environments. Having an API and even driven platform gives us a lot of power and freedom.