Skip to content

Instantly share code, notes, and snippets.

@gortok
Last active June 8, 2020 12:39
Show Gist options
  • Star 6 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save gortok/b204ac4997e9916ec6c6ef0987251530 to your computer and use it in GitHub Desktop.
Save gortok/b204ac4997e9916ec6c6ef0987251530 to your computer and use it in GitHub Desktop.
Python Pre Receive hook for checking commit messages
#!/bin/python
import sys
import re
import subprocess
#Format: "oldref newref branch"
line = sys.stdin.read()
(base, commit, ref) = line.strip().split()
new_branch_push = re.match(r'[^1-9]+', base)
branch_deleted = re.match(r'[^1-9]+', commit)
contains_commit_msg = False
if not new_branch_push:
revs = base + "..." + commit
proc = subprocess.Popen(['git', 'rev-list','--oneline','--first-parent', revs], stdout=subprocess.PIPE)
lines = proc.stdout.readlines()
if lines:
for line in lines:
rev = str(line)
match = re.search(r'TICKET-[0-9]{2,5}|#TICKET-[0-9]{2,5}|HOTFIX|FORCE', rev)
if match is not None:
contains_commit_msg = True
if contains_commit_msg or new_branch_push or branch_deleted:
exit(0)
else:
print "Commit does not contain the story associated with the commit in the format: TICKET-123 or #TICKET-123"
exit(1)
@gortok
Copy link
Author

gortok commented Dec 2, 2016

This has a bug; specifically it fails when creating a new branch off of an existing branch with no new commits. You'll see this error:

Total 2 (delta 1), reused 1 (delta 1)
remote: fatal: Invalid symmetric difference expression 0000000000000000000000000000000000000000...a24f6efa7c5328c84d01eb15b327bada8f516729
remote: 0000000000000000000000000000000000000000 a24f6efa7c5328c84d01eb15b327bada8f516729 refs/heads/Nex-000-my-new-test-branch
remote:
remote: Traceback (most recent call last):
remote:   File "/data/opt/gitlab/git-data/repositories/MyProject/www.git/custom_hooks/pre-receive", line 13, in <module>
remote:     rev = str(proc.stdout.readlines()[0])
remote: IndexError: list index out of range

To fix this error, do this:

#!/bin/python
import sys
import re
import subprocess


#Format: "oldref newref branch"
line = sys.stdin.read()
(base, commit, ref) = line.strip().split()
new_branch_push = re.match(r'[^1-9]+', base) #handles new branches being pushed
if not new_branch_push:
    revs = base + "..." + commit
    proc = subprocess.Popen(['git', 'rev-list','--oneline','--first-parent', revs], stdout=subprocess.PIPE)
    lines = proc.stdout.readlines()
    if lines:
        rev = str(lines[0])
        match = re.search(r'[#][0-9]{2,5}|NEX-[0-9]{2,5}|#NEX-[0-9]{2,5}', rev)
        if match is None:
            match = re.search('HOTFIX|FORCE', rev, flags = re.IGNORECASE)
        if match is None:
            exit(1)
exit(0)

@gortok
Copy link
Author

gortok commented Dec 2, 2016

Updated gist to fix bug with new branch pushes with no commits.

@gortok
Copy link
Author

gortok commented Dec 6, 2016

I think the latest version works with multiple line commits. The Previous revision did not.

@gortok
Copy link
Author

gortok commented Dec 15, 2016

This version did not handle branch deletes; new version does.

@marcellodesales
Copy link

marcellodesales commented Feb 28, 2017

@gortok, I'm facing the problem of the new branch at the moment...

Since I need to read which files changed, when a new branch is added I get the list of all files.

    if "0000000000" not in base:
      (results, code) = GitRepo.git(('git', 'show', base + ".." + commit, '--pretty=format:', '--name-only'))

    else:
      # All files in the current revision. No way to know which files changed in new branch
      (results, code) = GitRepo.git(('git', 'ls-tree', '-r', 'HEAD', '--name-only'))

@frakman1
Copy link

Thank you for sharing this script. However, ignoring the new branch case is not 'handling' it. A user can still incorrectly format the commit message and push it to the repo and get away with it as long as he does it in a new branch. This is in fact what I just tested and observed.

@andrewt82
Copy link

thank's! very helpful script!!!

@kinglamer
Copy link

What is python version required?

@danlyh5288
Copy link

Learned so much from this little script, really appreciated.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment