[Ballerina] Registering a GitHub Webhook

Maryam Ziyad
Ballerina Swan Lake Tech Blog
3 min readAug 13, 2018

In a previous post (Tweet my Stars, Ballerina!) we discussed the steps you could follow to introduce a Ballerina WebSub subscriber service as a GitHub Webhook callback (implementation of the payload URL) and tweet out activity on your GitHub repo.

For more information on WebSub, hubs, publishers, subscribers and topics you could refer [Ballerina] Event Notification via Webhooks.

We discussed how you could annotate your service with a unique secret key which could be used to verify that content is in fact originating from GitHub, and how Ballerina performs this verification for you. For more information on signing content, refer Authenticated Content Distribution.

However, in the previous post we used the GitHub UI to introduce the webhook. While it is not much of a hassle to introduce the webhook via the UI, how cool would it be if your callback service handles this registration for you?

No worries! Ballerina to the rescue! :D

In case you are new to Ballerina, the best point to start would be the learn material on the official website!

Subscription on Start-Up

Ballerina’s WebSub subscriber service allows you to set a configuration subscribeOnStartup to tell the service that you want a subscription request to be sent to a hub for a particular topic on service start up.

With GitHub’s pubsubhubbub (now WebSub) support, the hub is always https://api.github.com/hub and the topic would differ based on the events you want to subscribe to and the repo.

For example if you require notifications on all activity on one of your repositories, the topic URL would be as follows:

https://github.com/<GITHUB_USERNAME>/<REPO_NAME>/events/*.json

In addition, you would only need a GitHub access token with admin:repo_hook scope.

You could generate a personal access token at Settings →Developer settings → Personal access tokens.

Introducing the Webhook

And now, the introduction of the webhook.

The onNotification resource defined in the service is the resource accepting content delivery requests. Right now, we have just printed out the header set by GitHub indicating the event. You could introduce your logic here, to perform whatever action you want (tweet out, trigger a release, send an email, etc.) based on the notification headers/payload here.

Note how we have enabled subscription on start up and introduced the hub, topic and access token as part of the annotation.

The other addition is the callback URL, where we have specified the publicly accessible absolute URL. If the callback field is not specified, Ballerina will construct the callback as follows:

http(s)://<HOST>:<PORT>/<PATH>

Here since we’re running the service on localhost, we’ve used ngrok to expose the service, and appended the path to the ngrok URL to specify the absolute URL.

You could use ngrok with this sample by specifying the port:

./ngrok http 8181

Once you’ve updated your service (saved as b7a_github_webhook.bal) you can now start up the service with

ballerina run b7a_github_webhook.bal

The following should now be logged!

$ ballerina run subscriber.bal ballerina: initiating service(s) in 'b7a_github_webhook.bal'
ballerina: started HTTP/WS endpoint 0.0.0.0:8181
2018-08-13 09:24:02,213 INFO [ballerina/websub] - Subscription Request successful at Hub[https://api.github.com/hub], for Topic[https://github.com/<GITHUB_USERNAME>/<REPO_NAME>/events/*.json], with Callback [<NGROK_URL>/github]
2018-08-13 09:24:02,513 INFO [] - GitHub Notification received for Event: ping

The Subscription Request successful log indicates that you have successfully sent a subscription request to GitHub!

When a webhook is registered with GitHub, it sends a ping event to verify the webhook registered. This event is what caused the next log, also indicating that we have successfully registered the webhook!

You can now test the webhook by triggering notifications via events! For example if you create a new issue, you should see the following log:

GitHub Notification received for Event: issues

So that’s all the code you need to write to introduce a GitHub webhook in Ballerina! O:)

What’s next?

  • Ballerina has now introduced the capability to introduce custom webhook services by extending the WebSub subscriber service, where you can specify the expected events and the resources you need notifications to be dispatched to, for these events
  • You can also data bind the JSON payload to a pre-defined Ballerina record representing the event
  • GitHub’s own webhook service would thus have resources such as onWatch, onIssueOpened, onIssueClosed, etc. where each resource’s signature would include a record mapping the JSON payload for each event

More on this in a future post!

Hope you found this useful, and do stay tuned for updates!

Cheers! :)

--

--