Skip to content

Instantly share code, notes, and snippets.

@berngp
Last active August 29, 2015 14:00
Show Gist options
  • Save berngp/1318aee8f8939e8302b8 to your computer and use it in GitHub Desktop.
Save berngp/1318aee8f8939e8302b8 to your computer and use it in GitHub Desktop.
Mesos Development Support Scripts (./support)
feature/MESOS-1259* → ./support/post-reviews-2.py
Running post-review across all of ...
369c6fa83ce3e6929646b1304bce918dc37b8274 - (HEAD, berngp/feature/MESOS-1259, feature/MESOS-1259) [MESOS-1259]:Enrich the Java Docs in the src/java files. -- ZooKeeperState.java (2 minutes ago)
7edb638b38c832040f9cf0b35a4ea79d1db8e389 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- Variable.java (2 minutes ago)
d8868252011c4653c856ef37a257eafa3112b0e9 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- State.java (2 minutes ago)
c1b9e284ba1ed79c50cdd53f0f66cd52a221217c - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- SchedulerDriver.java (2 minutes ago)
cb4d252ac5863e58e63352748733d40faaf50b1c - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- Scheduler.java (2 minutes ago)
f634fcd394273751dc8ee260d5485df384fc052c - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- MesosSchedulerDriver.java (2 minutes ago)
2ac673c718a96f307ed288577d24b7a036045013 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- Log.java (2 minutes ago)
89c8df4762a2710e96e0382d167b6771d8c4d6a2 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- Log.java (2 minutes ago)
8e1b78912c09ee6a4580fe150644f3f2aa960784 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- ExecutorDriver.java (2 minutes ago)
fdce59cbaa03549e09af595b8ea5f23e1c0dabe4 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- Executor.java (2 minutes ago)
Creating diff of:
fdce59cbaa03549e09af595b8ea5f23e1c0dabe4 - [MESOS-1259]:Enrich the Java Docs in the src/java files. -- Executor.java
... with parent diff created from:
Press enter to continue or 'Ctrl-C' to skip.
Failed to execute: 'rbt post --repository-url=git://git.apache.org/mesos.git --tracking-branch=master master:fdce59cbaa03549e09af595b8ea5f23e1c0dabe4':
Failed to execute command: ['git', 'rev-parse', 'master:fdce59cbaa03549e09af595b8ea5f23e1c0dabe4']
fatal: Path 'fdce59cbaa03549e09af595b8ea5f23e1c0dabe4' does not exist in 'master'
master:fdce59cbaa03549e09af595b8ea5f23e1c0dabe4
#!/usr/bin/env python
# This is a wrapper around the 'post-review' tool provided by
# Review Board. This is currently used by Apache Mesos development.
#
# What does this do?
# It provides the ability to send a review for each commit on the
# current branch.
#
# Why is that useful?
# No one likes a 5000 line review request. Using this tool forces one
# to create logical commits which can be reviewed independently.
#
# How do I use it?
# First install 'post-review' from Review Board.
# http://www.reviewboard.org/docs/manual/dev/users/tools/post-review/
#
# $ cd /path/to/mesos
# $ [ do some work on your branch off of master, make commit(s) ]
# $ ./support/post-reviews.py --server=https://reviews.apache.org \
# --tracking-branch=origin/master --target-groups=mesos --open
#
# NOTE: post-reviews is currently specific to Mesos development,
# but can easily be adapted for other projects.
import atexit
import os
import sys
from subprocess import *
def readline(prompt):
try:
return raw_input(prompt)
except KeyboardInterrupt:
sys.exit(1)
def execute(command, ignore_errors=False):
process = Popen(command,
stdin=PIPE,
stdout=PIPE,
stderr=STDOUT,
shell=False)
data = process.stdout.read()
status = process.wait()
if status != 0 and not ignore_errors:
cmdline = ' '.join(command) if isinstance(command, list) else command
print 'Failed to execute: \'' + cmdline + '\':'
print data
sys.exit(1)
elif status != 0:
return None
return data
# TODO(benh): Make sure this is a git repository, apologize if not.
# Don't do anything if people have uncommitted changes.
diff_stat = execute(['git', 'diff', '--shortstat']).strip()
if diff_stat:
print 'Please commit or stash any changes before using post-reviews!'
sys.exit(1)
top_level_dir = execute(['git', 'rev-parse', '--show-toplevel']).strip()
repository = 'git://git.apache.org/mesos.git'
parent_branch = 'master'
branch_ref = execute(['git', 'symbolic-ref', 'HEAD']).strip()
branch = branch_ref.replace('refs/heads/', '', 1)
temporary_branch = '_post-reviews_' + branch
# Always delete the temporary branch.
atexit.register(lambda: execute(['git', 'branch', '-D', temporary_branch], True))
# Always put us back on the original branch.
atexit.register(lambda: execute(['git', 'checkout', branch]))
merge_base = execute(['git', 'merge-base', parent_branch, branch_ref]).strip()
print 'Running post-review across all of ...'
call(['git',
'--no-pager',
'log',
'--pretty=format:%Cred%H%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr)%Creset',
merge_base + '..HEAD'])
log = execute(['git',
'--no-pager',
'log',
'--pretty=oneline',
'--reverse',
merge_base + '..HEAD']).strip()
shas = []
for line in log.split('\n'):
sha = line.split()[0]
shas.append(sha)
previous = 'master'
for i in range(len(shas)):
sha = shas[i]
execute(['git', 'branch', '-D', temporary_branch], True)
message = execute(['git',
'--no-pager',
'log',
'--pretty=format:%B',
previous + '..' + sha])
review_request_id = None
if message.find('Review: ') != -1:
url = message[(message.index('Review: ') + len('Review: ')):].strip()
# TODO(benh): Handle bad (or not Review Board) URLs.
review_request_id = os.path.basename(url.strip('/'))
# Show the commit.
if review_request_id is None:
print '\nCreating diff of:\n'
call(['git',
'--no-pager',
'log',
'--pretty=format:%Cred%H%Creset -%C(yellow)%d%Creset %s',
previous + '..' + sha])
else:
print '\nUpdating diff of:\n'
call(['git',
'--no-pager',
'log',
'--pretty=format:%Cred%H%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr)%Creset',
previous + '..' + sha])
# Show the "parent" commit(s).
print '\n... with parent diff created from:\n'
call(['git',
'--no-pager',
'log',
'--pretty=format:%Cred%H%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr)%Creset',
parent_branch + '..' + previous])
try:
raw_input('\nPress enter to continue or \'Ctrl-C\' to skip.\n')
except KeyboardInterrupt:
i = i + 1
previous = sha
continue
revision_range = previous + ':' + sha
if review_request_id is None:
command = [
'rbt',
'post',
'--repository-url=' + repository,
'--tracking-branch=' + parent_branch
] + sys.argv[1:]
command.append(revision_range)
output = execute(command).strip()
else:
command = [
'rbt',
'post',
'--review-request-id=' + review_request_id,
'--repository-url=' + repository,
'--tracking-branch=' + parent_branch
] + sys.argv[1:]
command.append(revision_range)
output = execute(command).strip()
print output
if review_request_id is not None:
i = i + 1
previous = sha
continue
lines = output.split('\n')
url = lines[len(lines) - 1]
url = url.strip('/')
# Construct new commit message.
message = message + '\n' + 'Review: ' + url + '\n'
execute(['git', 'checkout', '-b', temporary_branch])
execute(['git', 'reset', '--hard', sha])
execute(['git', 'commit', '--amend', '-m', message])
# Now rebase all remaining shas on top of this amended commit.
j = i + 1
old_sha = execute(['cat', os.path.join(top_level_dir, '.git/refs/heads', temporary_branch)]).strip()
previous = old_sha
while j < len(shas):
execute(['git', 'checkout', shas[j]])
execute(['git', 'rebase', temporary_branch])
# Get the sha for our detached HEAD.
new_sha = execute(['git', '--no-pager', 'log', '--pretty=format:%H', '-n', '1', 'HEAD']).strip()
execute(['git',
'update-ref',
'refs/heads/' + temporary_branch,
new_sha,
old_sha])
old_sha = new_sha
shas[j] = new_sha
j = j + 1
# Okay, now update the actual branch to our temporary branch.
new_sha = old_sha
old_sha = execute(['cat', os.path.join(top_level_dir, '.git/refs/heads', branch)]).strip()
execute(['git', 'update-ref', 'refs/heads/' + branch, new_sha, old_sha])
i = i + 1
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment