A Node.JS bot that automatically runs builds for new, and updated, Pull Requests.

Project maintained by SnapInteractive Hosted on GitHub Pages — Theme by mattgraham


Mergeatron is a Node.js bot that monitors a GitHub account for new, and updated, Pull Requests. When it finds any it will kick off a Jenkins build and reply to the Pull Request with a thumbs up, or down, depending on success or failure.

Mergeatron is intended to assist with reviewing Pull Requests by providing, at a glance, information on whether or not it passes your automated tests.


Installation Instructions

    git clone
    npm install


    npm install mergeatron
    // Copy config.sample.js to config.js and update accordingly
    node mergeatron.js

Configuring Mergeatron

To configure Mergeatron copy the config.sample.js file to config.js in the same directory. The settings you will need to change are:

Mergeatron comes with multiple different plugins you can opt to use. By default any plugin found in your config.js will be included and run. If you want to disable a certain plugin you can either remove it or add enabled: false to that plugins configuration.

Setting Up GitHub

There are two ways you can use the GitHub plugin. You can either have it poll GitHub's REST API periodically looking for changes. The downside to this approach is that it's very inefficienct, especially if you have a low volume of Pull Requests or if pull requests can sit for a while before being merged or closed. You also run into issues with rate limiting if you have too much activity or poll too frequently.

Alternatively you can use GitHub's webhooks and let them push new and updated pull requests to you. This is far more efficient but does mean you have to open a port for them to connect to. They provide the list of public IPs they post from so you can lock down the port for increased security.

To configure your setup for polling you need to set github.method to "polling" and will want to tweak the github.frequency setting to match how often you want to poll their API. Keep in mind they do have rate limiting so don't make it too frequent. The default here, or higher, should be pefectly fine.

To configure your setup for webhooks you need to set github.method to "hooks" and set github.port to the port number you're opening for them. You'll also need to setup he webhook with GitHub. You can execute nodejs bin/github_setup.js and provide the details it asks for to set one you. You'll want to read their documentation for more information on webhooks.

Configuring Jenkins

To configure Jenkins you will need to make sure you have the appropriate git plugin installed. I'm assuming you already know how to do that and already have it up and running successfully. Once you do, follow the below steps.

Use the sample - sample/JenkinsSampleJob/config.xml

Manual version

git status || (git clone . && git remote add upstream

git clean -fdx
git reset --hard HEAD

git fetch upstream
git checkout upstream/master

git remote set-url origin ${REPOSITORY_URL}
git remote prune origin
git fetch origin
git merge origin/${BRANCH_NAME}

git submodule update --init


Extending Mergeatron

Mergeatron is built with extensibility in mind. To help achieve this it's been built around events instead of direct calls between plugins. This enables you to easily write any plugin you want that listens on the existing events and/or emits your own that others can use.

Any file found in your configured plugins_dir directory is assumed to be a plugin and will be loaded unless disabled via your config.js file. To turn off a plugin just provide an entry for it under the plugins config with enabled: false. The file will then not be included.

All plugins are expected to export an init function that is executed and passed two parameters. The first is your plugins config settings and the second is a Mergeatron object. The Mergeatron object contains a reference to mongo but, more importantly, is also an EventEmitter. You can bind your listeners to this object and use it to emit events.

Below is a very basic example:

exports.init = function(config, mergeatron) {
    // Do some stuff we want to execute once on startup/init

    mergeatron.on('build.started', function(job_id, job, build_url) {
        console.log(job_id + ' has started building!');