GitHub Merge Button from CLI

Adam Jahnke
Adam Jahnke

It's no fun to have to clean up git history after a botched command line merge of a GitHub pull request. I love to live life in the shell, and I don't want to open a new browser tab just to click The Merge Button, so sometimes I'm stubborn and I don't. And sometimes I waste a lot of time cleaning up the mess that happens when I try to do all of that with an outdated master branch.

With some prodding and direction from my good friend pengwynn, I put together a script based on the new-to-me Merge Button API Route. So, go forth and merge with glee, in safety, and without leaving our beloved shell. ❤️

See git-merge-pr below or grab it from my dotfiles!


#!/usr/bin/env bash

# Contributors:
#   Adam Jahnke -
#   Wynn Netherland -

#/ Usage:
#/   git merge-pr [<branch>|<pr>]
#/ Looks up the most recent pull requst based on <branch>, <pr>, or the current
#/ branch, and tries to merge it using the merge API (like the Merge Button).
#/ Requirements:
#/   - $GITHUB_TOKEN environment variable
#/   - jq

set -e

if [[ "$1" == "--help" || "$1" == '-h' ]]; then
  grep ^#/ "$0" | cut -c4-

if [[ -z "$GITHUB_TOKEN" ]]; then
  echo "Please export \$GITHUB_TOKEN"
  exit 1

if [[ -z "$(which jq)" ]]; then
  echo "Please install jq:"
  exit 1

remote_url=$(git config --get remote.origin.url)
owner_repo=$(echo $remote_url | sed -En 's_^(git@|https://)?|/)(.*)/(.*)(.git)?_\3 \4_p')
owner=$(echo $owner_repo | sed 's_ .*__')
repo=$(echo $owner_repo | sed 's_.* __; s_.git$__')
branch=${1:-"$(git symbolic-ref HEAD | sed 's_refs/heads/__')"}
auth="Authorization: token $GITHUB_TOKEN"

# Check if $1 is actually a pull request number
if $(test ! -z $1 && echo $1 | grep --silent '^\d*$'); then
  # Get the first matching pull request for $branch
  pull=$(curl --silent --header "$auth"\
    | jq '.[0].number')

# Try to merge
if [[ "$pull" != "null" ]]; then
  response=$(curl --silent --request PUT --data "{}" --header "$auth"\
    | jq '.message'\
    | sed 's_"__g')

  if ! [[ "$response" =~ "success" ]]; then
  response="Couldn't find an open pull request based on $branch."

echo -e "\n$response"