#!/usr/bin/env python # Copyright (c) 2009 Giampaolo Rodola'. All rights reserved. # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. """ This gets executed on 'git commit' and rejects the commit in case the submitted code does not pass validation. Install it with "make install-git-hooks". """ from __future__ import print_function import os import subprocess import sys def term_supports_colors(): try: import curses assert sys.stderr.isatty() curses.setupterm() assert curses.tigetnum("colors") > 0 except Exception: return False else: return True def hilite(s, ok=True, bold=False): """Return an highlighted version of 'string'.""" attr = [] if ok is None: # no color pass elif ok: # green attr.append('32') else: # red attr.append('31') if bold: attr.append('1') return '\x1b[%sm%s\x1b[0m' % (';'.join(attr), s) def exit(msg): if term_supports_colors(): msg = hilite(msg, ok=False) print(msg, file=sys.stderr) sys.exit(1) def main(): out = subprocess.check_output("git diff --cached --name-only", shell=True) py_files = [x for x in out.split(b'\n') if x.endswith(b'.py') and os.path.exists(x)] lineno = 0 for path in py_files: with open(path) as f: for line in f: lineno += 1 # space at end of line if line.endswith(' '): print("%s:%s %r" % (path, lineno, line)) return exit( "commit aborted: space at end of line") line = line.rstrip() # pdb if "pdb.set_trace" in line: print("%s:%s %s" % (path, lineno, line)) return exit( "commit aborted: you forgot a pdb in your python code") # bare except clause if "except:" in line and not line.endswith("# NOQA"): print("%s:%s %s" % (path, lineno, line)) return exit("commit aborted: bare except clause") # flake8 if py_files: try: import flake8 # NOQA except ImportError: return exit("commit aborted: flake8 is not installed; " "run 'make setup-dev-env'") # XXX: we should scape spaces and possibly other amenities here ret = subprocess.call( "%s -m flake8 %s" % (sys.executable, " ".join(py_files)), shell=True) if ret != 0: return exit("commit aborted: python code is not flake8 compliant") main()