Skip to content

Instantly share code, notes, and snippets.

@SmartFinn
Last active September 17, 2019 19:45
Show Gist options
  • Save SmartFinn/10a185782cd15c801f482587f9756521 to your computer and use it in GitHub Desktop.
Save SmartFinn/10a185782cd15c801f482587f9756521 to your computer and use it in GitHub Desktop.
An OBS (Open Build Service) Build Trigger System for GitHub Repositories
#!/usr/bin/python3
"""OBS Build Trigger System for GitHub Repositories
This script looks into a specific repository branch on GitHub and triggers
a build request through the OBS API if the last commit hash has changed.
To get the API Token for your OBS Project run:
$ osc token --create [PROJECT] [PACKAGE]
based on https://github.com/mschnitzer/obs-build-trigger
"""
import os
import http.client
import json
PROGNAME = os.path.basename(__file__)
GITHUB_API = os.environ.get('GITHUB_API', default='api.github.com')
GITHUB_AUTH_TOKEN = os.environ.get('GITHUB_AUTH_TOKEN')
GITHUB_REPO = dict(
owner=os.environ.get('GITHUB_REPO_OWNER'),
name=os.environ.get('GITHUB_REPO_NAME'),
branch=os.environ.get('GITHUB_REPO_BRANCH', default='master'),
)
OBS_API = os.environ.get('OBS_API', default='api.opensuse.org')
OBS_PROJECT = os.environ.get('OBS_PROJECT',
default=f"home:{GITHUB_REPO['owner']}:{GITHUB_REPO['name']}")
OBS_PACKAGE = os.environ.get('OBS_PACKAGE', default=GITHUB_REPO['name'])
OBS_TOKEN = os.environ.get('OBS_TOKEN')
DATA_FILE = os.environ.get('DATA_FILE', default=f"{GITHUB_REPO['name']}.hash")
def get_saved_commit_hash():
try:
with open(DATA_FILE, 'r') as f:
return f.read()
except FileNotFoundError:
return None
def save_commit_hash(commit_hash):
with open(DATA_FILE, 'w') as f:
f.write(commit_hash)
def get_commit_hash():
headers = {'User-Agent': PROGNAME}
if GITHUB_AUTH_TOKEN:
headers['Authorization'] = f"Token {GITHUB_AUTH_TOKEN}"
uri_path = "/repos/{owner}/{name}/git/refs/heads/{branch}".format(**GITHUB_REPO)
conn = http.client.HTTPSConnection(GITHUB_API)
conn.request('GET', uri_path, None, headers)
try:
response = conn.getresponse()
data = json.loads(response.read())
finally:
conn.close()
if response.status != 200:
raise ConnectionError(response.status, response.reason)
return data['object']['sha']
def trigger_rebuild():
headers = {'Authorization': f"Token {OBS_TOKEN}"}
uri_path = f"/trigger/runservice/?project={OBS_PROJECT}&package={OBS_PACKAGE}"
conn = http.client.HTTPSConnection(OBS_API)
conn.request('POST', uri_path, None, headers)
try:
response = conn.getresponse()
finally:
conn.close()
if response.status != 200:
raise ConnectionError(response.status, response.reason)
return response.read()
if __name__ == '__main__':
if not GITHUB_REPO['owner']:
raise ValueError('$GITHUB_REPO_OWNER is not set or empty')
if not GITHUB_REPO['name']:
raise ValueError('$GITHUB_REPO_NAME is not set or empty')
if not OBS_TOKEN:
raise ValueError('$OBS_TOKEN is not set or empty')
saved_commit_hash = get_saved_commit_hash()
latest_commit_hash = get_commit_hash()
if saved_commit_hash != latest_commit_hash:
print("New commit detected. Triggered rebuild for", latest_commit_hash)
trigger_rebuild()
save_commit_hash(latest_commit_hash)
#!/bin/sh
# Add this script to crontab by running:
# $ echo "@daily $PWD/obs_build_trigger_runner.sh" | crontab -
SCRIPT_DIR="$(dirname "$0")"
export GITHUB_REPO_OWNER=bilelmoussaoui
export GITHUB_REPO_NAME=Hardcode-Tray
export GITHUB_REPO_BRANCH=master
export OBS_PROJECT=home:SmartFinn:hardcode-tray
export OBS_PACKAGE=hardcode-tray
export OBS_TOKEN=xxxxxxxxxxxxxxxxxxxxxxxx
export DATA_FILE="$HOME/.cache/$GITHUB_REPO_OWNER-$GITHUB_REPO_NAME.hash"
mkdir -p "${DATA_FILE%/*}"
python3 "$SCRIPT_DIR/obs_build_trigger.py"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment