Commit 6b653e27 authored by Antti Tanhuanpää's avatar Antti Tanhuanpää

Add support for config files

parent a81b3288
#!/usr/bin/env python3
from os import path
import json
import pathlib
import shlex
import subprocess
import sys
import termios
linters = {
DEFAULT_LINTERS = {
'js': ('eslint', '--stdin'),
'py': ('flake8', '--ignore=E121,E123,E126,E266,E501,E704,E731', '-'),
'scss': ('scss-lint', '--stdin-file-path', '{filename}', '-'),
}
class InvalidLinterConfigError(Exception):
def __init__(self, path):
self.path = path
class NoLinterFound(Exception):
pass
......@@ -79,6 +85,22 @@ class Terminal:
termios.tcsetattr(fd, termios.TCSAFLUSH, attrs)
def find_git_project_root():
path = pathlib.Path.cwd()
while True:
parent = path.parent
if path == parent:
break
if (path / '.git').exists():
return path
path = parent
return None
def get_files():
files = []
......@@ -88,27 +110,53 @@ def get_files():
break
filename = line.strip()
files.append(filename)
files.append(pathlib.Path(filename))
return files
def get_linter(filename):
def get_linter(linters, filename):
extension = filename.suffix[1:]
try:
_, extension = filename.rsplit('.', 1)
linter_args = linters[extension]
except (KeyError, ValueError):
except KeyError:
raise NoLinterFound
return (arg.format(filename=filename) for arg in linter_args)
def lint(filename, require_linter=False):
if not path.exists(filename):
def get_linter_config(config_filename='.gitlint.json'):
git_root = find_git_project_root()
if git_root:
config = git_root / config_filename
if config.exists():
return config
config = pathlib.Path.home() / config_filename
if config.exists():
return config
return None
def get_linters():
config = get_linter_config()
if config:
try:
with config.open() as f:
return json.load(f)
except (json.JSONDecodeError, OSError):
raise InvalidLinterConfigError(config)
return DEFAULT_LINTERS
def lint(linters, filename, require_linter=False):
if not filename.exists():
return True
try:
linter_args = get_linter(filename)
linter_args = get_linter(linters, filename)
except NoLinterFound:
print('No linter found for', filename, file=sys.stderr)
return not require_linter
......@@ -121,14 +169,14 @@ def lint(filename, require_linter=False):
return ret == 0
def lint_all(files):
def lint_all(linters, files):
success = False
while not success:
success = True
for filename in files:
success &= lint(filename)
success &= lint(linters, filename)
if not success:
retry, skip = prompt_for_retry()
......@@ -174,9 +222,15 @@ def main():
for signum in exit_signals:
signal(signum, sig_handler)
try:
linters = get_linters()
except InvalidLinterConfigError as e:
print('Cannot read linter config: %s' % e.path, file=sys.stderr)
return 1
try:
files = get_files()
success = lint_all(files)
success = lint_all(linters, files)
except Exit:
success = False
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment