sapling/scripts/lint.py
Jun Wu 2698cf1d22 scripts: unify spwaning run-test logic
Summary:
Previously, lint.py and unit.py have different logic spawning
run-tests.py.

The logic in `unit.py` is more robust: it sets `PYTHONPATH` and
`cwd`. It sets `-j` according to CPU cores. It can find `run-tests.py`
even if `MERCURIALRUNTESTS` is not set. You can run the script
from any directory (not only reporoot).

Test Plan: Run `lint.py` and `unit.py`, from the `scripts` directory and reporoot.

Reviewers: #sourcecontrol, stash

Reviewed By: stash

Subscribers: stash, mjpieters

Differential Revision: https://phabricator.intern.facebook.com/D4095437

Signature: t1:4095437:1477663516:13a7ac4270435c272077132915f9d02cc98a5afb
2016-10-28 13:58:48 +01:00

91 lines
2.4 KiB
Python
Executable File

#!/usr/bin/env python
""" Convert mercurial check-code errors into a format
that plays nicely with arc lint """
import errno
import os
import subprocess
import re
import sys
sys.path.insert(0, os.path.dirname(__file__))
import utils
# Normalize the list of files that we should report on
wanted = set()
for path in sys.argv[1:]:
wanted.add(os.path.relpath(path))
# Export LINTFILES so tests can skip unrelated files
if wanted:
os.environ['LINTFILES'] = '\n'.join(sorted(wanted))
args = ['-l', 'test-check-code-hg.t', 'test-check-pyflakes-hg.t']
try:
proc = utils.spawnruntests(args, stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
except OSError as ex:
if ex.errno == errno.ENOENT:
print 'lint.py:1: ERROR:ENVIRON: Please either set ' + \
'MERCURIALRUNTEST var to the full path to run-tests.py, ' + \
'or add the containing directory to your $PATH'
else:
print 'lint.py:1: ERROR:OSError: %r' % ex
sys.exit(0)
output, error = proc.communicate()
context_file = None
lines = error.split('\n')
# We expect a run of 3 lines to describe the error, with the first
# of those to look like a filename and line number location
while lines:
line = lines[0]
lines.pop(0)
# test-check-pyflakes-hg style output
m = re.match('^\+ ([a-zA-Z0-9_./-]+):(\d+): (.*)$', line)
if m:
filename, location, why = m.groups()
if filename in wanted:
print '%s:%s: ERROR:Pyflakes: %s' % (filename, location, why)
continue
# test-check-code-hg style output
if re.match('^--- (.*)$', line):
context_file = os.path.relpath(line[4:])
continue
m = re.match('^\+ (Skipping (.*) it has no.*)$', line)
if m:
filename = m.group(2)
if filename in wanted:
print '%s:0: ERROR:CheckCode: Update %s to add %s' % (
filename, context_file, m.group(1))
continue
if not re.match('^\+ +[a-zA-Z0-9_./-]+:\d+:$', line):
continue
if len(lines) < 2:
continue
location = line
context = lines.pop(0) # we ignore this
why = lines.pop(0)
location = location[1:].strip() # strip off the "+ " bit
location = location.rstrip(':')
filename, lineno = location.split(':')
if filename not in wanted:
# lint doesn't care about this file.
continue
why = why[1:].strip()
print '%s: ERROR:CheckCode: %s' % (location, why)