mirror of
https://pagure.io/fedora-qa/os-autoinst-distri-fedora.git
synced 2025-09-11 17:05:48 +00:00
This is pretty dumb and breaks on valid code, but it's okay enough for our purposes I think. If I made it any more complex I'd want to start looking for a third party parser. Signed-off-by: Adam Williamson <awilliam@redhat.com>
150 lines
5.1 KiB
Python
Executable File
150 lines
5.1 KiB
Python
Executable File
#!/usr/bin/python3
|
|
|
|
# Copyright Red Hat
|
|
#
|
|
# This file is part of os-autoinst-distri-fedora.
|
|
#
|
|
# os-autoinst-distri-fedora is free software; you can redistribute it
|
|
# and/or modify it under the terms of the GNU General Public License
|
|
# as published by the Free Software Foundation, either version 2 of
|
|
# the License, or (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
#
|
|
# Author: Adam Williamson <awilliam@redhat.com>
|
|
|
|
"""This is a simple linter for perl files in the repository. It fails
|
|
if any line contains a tab, ends with whitespace characters (which
|
|
includes lines containing *only* whitespace characters), or starts
|
|
with a number of spaces that is not divisible by four. If run with
|
|
--write, it will strip trailing whitespace (including turning lines
|
|
that contain only whitespace into blank lines) and correct indentation
|
|
(including removing tabs in indentation). It does not do anything
|
|
with tabs found outside of leading indentation.
|
|
"""
|
|
|
|
import glob
|
|
import os
|
|
import re
|
|
import sys
|
|
|
|
HEREDOCRE = re.compile(r"<<['\"]?(\w*)['\"]?;\s*$")
|
|
|
|
def run(write):
|
|
"""
|
|
Main run function.
|
|
"""
|
|
exitcode = 0
|
|
scriptloc = os.path.dirname(os.path.realpath(__file__))
|
|
filenames = glob.glob(f"{scriptloc}/**/*.pm", recursive=True)
|
|
for filename in filenames:
|
|
if check_file(filename, write):
|
|
exitcode = 1
|
|
if exitcode == 0:
|
|
print("No errors found!")
|
|
sys.exit(exitcode)
|
|
|
|
|
|
def check_file(filename, write):
|
|
"""
|
|
Do the checks. Returns false if there is no failure, true if there
|
|
is a failure.
|
|
"""
|
|
failed = False
|
|
with open(filename, "r", encoding="UTF-8") as readfh:
|
|
lines = readfh.readlines()
|
|
newlines = []
|
|
indent = 0
|
|
# indicator whether we're in a heredoc block
|
|
heredoc = None
|
|
for (num, line) in enumerate(lines, 1):
|
|
# if we're in a heredoc, skip all checks, and see if we
|
|
# ended it
|
|
if heredoc:
|
|
if line.strip(" \t").rstrip(" \t\n") == heredoc:
|
|
heredoc = None
|
|
# write the line back to newlines
|
|
if write:
|
|
newlines.append(line)
|
|
continue
|
|
# trailing whitespace check and replace
|
|
newline = line.rstrip("\n").rstrip(" \t") + "\n"
|
|
if newline != line:
|
|
print(f"Line {num} of file {filename} ends with a space or tab!")
|
|
failed = True
|
|
if write:
|
|
# if we're writing changes, feed the *changed* line
|
|
# to the next checks
|
|
line = newline
|
|
|
|
# correct number of starting spaces check
|
|
# skip non-indented comment lines
|
|
if line.startswith("# "):
|
|
# write the line back to newlines
|
|
if write:
|
|
newlines.append(line)
|
|
continue
|
|
# first update indent if line closes a block
|
|
if line.strip(" \t").startswith("}") or line.strip(" \t").startswith(")"):
|
|
indent -= 4
|
|
spaces = 0
|
|
for char in line:
|
|
if char != " ":
|
|
break
|
|
spaces += 1
|
|
if spaces != indent and line != "\n":
|
|
print(
|
|
f"Line {num} of file {filename} starts with an invalid number of spaces! Expected {indent} got {spaces}"
|
|
)
|
|
failed = True
|
|
if write:
|
|
line = line.lstrip()
|
|
if line.startswith("\t"):
|
|
print(f"Line {num} of file {filename} has a tab in leading whitespace!")
|
|
line = line.strip(" \t")
|
|
line = " " * indent + line
|
|
# now update indent if line opens a block (and isn't a comment)
|
|
if not line.strip(" \t").startswith("#"):
|
|
if line.rstrip(" \t\n").endswith("{") or line.rstrip(" \t\n").endswith("("):
|
|
indent += 4
|
|
|
|
# tab check
|
|
if "\t" in line:
|
|
print(f"Line {num} of file {filename} contains a tab!")
|
|
failed = True
|
|
|
|
# did the line start a heredoc?
|
|
herematch = HEREDOCRE.search(line)
|
|
if herematch:
|
|
heredoc = herematch.group(1)
|
|
|
|
# write the line back to newlines
|
|
if write:
|
|
newlines.append(line)
|
|
|
|
if write and newlines != lines:
|
|
with open(filename, "w", encoding="UTF-8") as writefh:
|
|
writefh.writelines(newlines)
|
|
|
|
return failed
|
|
|
|
|
|
# Parse args and call run().
|
|
if len(sys.argv) > 2:
|
|
sys.exit("Too many arguments!")
|
|
|
|
if len(sys.argv) > 1:
|
|
if sys.argv[1] == "--write":
|
|
run(write=True)
|
|
else:
|
|
sys.exit("Invalid argument! Only valid argument is --write")
|
|
|
|
# no args
|
|
run(write=False)
|