Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rename .styleguide configs to .wpiformat to match tool name #257

Open
wants to merge 3 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -90,8 +90,8 @@ jobs:
rm -rf branch-test
mkdir branch-test && cd branch-test && git init
git checkout -b master
touch .styleguide
git add .styleguide && git commit -q -m "Initial commit"
touch .wpiformat
git add .wpiformat && git commit -q -m "Initial commit"
wpiformat

# Verify wpiformat reports success if "main" exists
Expand All @@ -101,8 +101,8 @@ jobs:
rm -rf branch-test
mkdir branch-test && cd branch-test && git init
git checkout -b main
touch .styleguide
git add .styleguide && git commit -q -m "Initial commit"
touch .wpiformat
git add .wpiformat && git commit -q -m "Initial commit"
wpiformat

- name: Delete branch-test folder
Expand Down
File renamed without changes.
File renamed without changes.
16 changes: 8 additions & 8 deletions wpiformat/README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -22,14 +22,14 @@ On Linux/OSX, execute::
Project Setup
*************

To use these tools with a new project, copy `.styleguide`_, and `.styleguide-license`_ from the examples folder into the project and create a new ``.clang-format`` file based on the desired C/C++ style.
To use these tools with a new project, copy `.wpiformat`_, and `.wpiformat-license`_ from the examples folder into the project and create a new ``.clang-format`` file based on the desired C/C++ style.

Note: Since wpiformat already handles include ordering, it is recommended to use ``SortIncludes: false`` in ``.clang-format``.

.styleguide
-----------
.wpiformat
----------

wpiformat checks the current directory for the ``.styleguide`` file. If one doesn't exist, all parent directories are tried as well. See the ``.styleguide`` file in the docs/examples directory for all possible groups.
wpiformat checks the current directory for the ``.wpiformat`` file. If one doesn't exist, all parent directories are tried as well. See the ``.wpiformat`` file in the docs/examples directory for all possible groups.

This file contains groups of file name regular expressions. There are two groups of regexes which prevent tasks (i.e., formatters and linters) from running on matching files:

Expand All @@ -54,12 +54,12 @@ The regex for C system headers produces false positives on headers from "other l

``NOLINT`` can be appended in a comment to a header include to prevent wpiformat's header include sorter from modifying it and to maintain its relative ordering with other header includes. This will, in effect, treat it as a barrier across which no header includes will be moved. Header includes on each side of the barrier will still be sorted as normal.

.styleguide-license
-------------------
.wpiformat-license
------------------

This file contains the license header template. It should contain ``Copyright (c)`` followed by the company name and the string ``{year}``. See the ``.styleguide-license`` file in the docs/examples directory.
This file contains the license header template. It should contain ``Copyright (c)`` followed by the company name and the string ``{year}``. See the ``.wpiformat-license`` file in the docs/examples directory.

wpiformat checks the currently processed file's directory for a ``.styleguide`` file first and traverses up the directory tree if one isn't found. This allows templates which are closer to the processed file to override a project's main template.
wpiformat checks the currently processed file's directory for a ``.wpiformat`` file first and traverses up the directory tree if one isn't found. This allows templates which are closer to the processed file to override a project's main template.

The license header is always at the beginning of the file and ends after two newlines. If there isn't one, or it doesn't contain the required copyright contents, wpiformat inserts a new one containing the current year.

Expand Down
File renamed without changes.
38 changes: 34 additions & 4 deletions wpiformat/wpiformat/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,16 @@ def proc_pipeline(name):
Keyword arguments:
name -- file name string
"""
config_file = Config(os.path.dirname(name), ".styleguide")
try:
config_file = Config(os.path.dirname(name), ".wpiformat")
except OSError:
print(
"Warning: '.wpiformat' file not found. Looking for deprecated '.styleguide' file."
)
# TODO: Remove handling for deprecated .styleguide file
config_file = Config(os.path.dirname(name), ".styleguide")
print("Warning: found deprecated '.styleguide' file. Rename to '.wpiformat'.")

if verbose1 or verbose2:
with print_lock:
print("Processing", name)
Expand Down Expand Up @@ -129,7 +138,13 @@ def proc_standalone(name):
Keyword arguments:
name -- file name string
"""
config_file = Config(os.path.dirname(name), ".styleguide")
try:
config_file = Config(os.path.dirname(name), ".wpiformat")
except OSError:
# TODO: Remove handling for deprecated .styleguide file
config_file = Config(os.path.dirname(name), ".styleguide")
print("Warning: found deprecated '.styleguide' file. Rename to '.wpiformat'.")

if verbose2:
with print_lock:
print("Processing", name)
Expand Down Expand Up @@ -179,7 +194,15 @@ def proc_batch(files):
for subtask in task_pipeline:
work = []
for name in files:
config_file = Config(os.path.dirname(name), ".styleguide")
try:
config_file = Config(os.path.dirname(name), ".wpiformat")
except OSError:
# TODO: Remove handling for deprecated .styleguide file
config_file = Config(os.path.dirname(name), ".styleguide")
print(
"Warning: found deprecated '.styleguide' file. Rename to '.wpiformat'."
)

if subtask.should_process_file(config_file, name):
work.append(name)

Expand Down Expand Up @@ -480,7 +503,14 @@ def main():
# Don't run tasks on modifiable or generated files
work = []
for name in files:
config_file = Config(os.path.dirname(name), ".styleguide")
try:
config_file = Config(os.path.dirname(name), ".wpiformat")
except OSError:
# TODO: Remove handling for deprecated .styleguide file
config_file = Config(os.path.dirname(name), ".styleguide")
print(
"Warning: found deprecated '.styleguide' file. Rename to '.wpiformat'."
)

if config_file.is_modifiable_file(name):
continue
Expand Down
35 changes: 17 additions & 18 deletions wpiformat/wpiformat/config.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
"""This class is for handling wpiformat config files."""

import os
import sys

import regex


class Config:
# Dict from filepath to file contents
config_cache: dict[str, list[str]] = {}

def __init__(self, directory, file_name):
"""Constructor for Config object.

Expand Down Expand Up @@ -35,26 +37,23 @@ def read_file(directory, file_name):
Returns tuple of file name and list containing file contents or triggers
program exit.
"""
file_found = False
while not file_found:
while True:
filepath = os.path.join(directory, file_name)
try:
with open(directory + os.sep + file_name, "r") as file_contents:
file_found = True
return (
os.path.join(directory, file_name),
file_contents.read().splitlines(),
)
except OSError:
# If filepath in config cache, return cached version instead
if filepath in Config.config_cache:
return filepath, Config.config_cache[filepath]

with open(filepath, "r") as file_contents:
contents = file_contents.read().splitlines()
Config.config_cache[filepath] = contents
return filepath, contents
except OSError as e:
# .git files are ignored, which are created within submodules
if os.path.isdir(directory + os.sep + ".git"):
print(
"Error: config file '"
+ file_name
+ "' not found in '"
+ directory
+ "'"
)
sys.exit(1)
raise OSError(
f"config file '{file_name}' not found in '{directory}'"
) from e
directory = os.path.dirname(directory)

def group(self, group_name):
Expand Down
15 changes: 12 additions & 3 deletions wpiformat/wpiformat/licenseupdate.py
Original file line number Diff line number Diff line change
Expand Up @@ -135,9 +135,18 @@ def __try_string_search(self, lines, last_year, license_template):
def run_pipeline(self, config_file, name, lines):
linesep = super().get_linesep(lines)

_, license_template = Config.read_file(
os.path.dirname(os.path.abspath(name)), ".styleguide-license"
)
try:
_, license_template = Config.read_file(
os.path.dirname(os.path.abspath(name)), ".wpiformat-license"
)
except OSError:
# TODO: Remove handling for deprecated .styleguide-license file
_, license_template = Config.read_file(
os.path.dirname(os.path.abspath(name)), ".styleguide-license"
)
print(
"Warning: found deprecated '.styleguide-license' file. Rename to '.wpiformat-license'."
)

# Get year when file was most recently modified in Git history
#
Expand Down
2 changes: 1 addition & 1 deletion wpiformat/wpiformat/test/test_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@


def test_config():
config_file = Config(os.path.abspath(os.getcwd()), ".styleguide")
config_file = Config(os.path.abspath(os.getcwd()), ".wpiformat")
assert config_file.is_modifiable_file(
"." + os.sep + "wpiformat" + os.sep + "javaguidelink.png"
)
Expand Down
10 changes: 5 additions & 5 deletions wpiformat/wpiformat/test/test_licenseupdate.py
Original file line number Diff line number Diff line change
Expand Up @@ -307,20 +307,20 @@ def test_licenseupdate():
)

# Ensure excluded files won't be processed
config_file = Config(os.path.abspath(os.getcwd()), ".styleguide")
config_file = Config(os.path.abspath(os.getcwd()), ".wpiformat")
assert not task.should_process_file(config_file, "./Excluded.h")

# Create git repo to test license years for commits
with OpenTemporaryDirectory():
subprocess.run(["git", "init", "-q"])

# Add base files
with open(".styleguide-license", "w") as file:
with open(".wpiformat-license", "w") as file:
file.write("// Copyright (c) {year}")
with open(".styleguide", "w") as file:
with open(".wpiformat", "w") as file:
file.write("cppSrcFileInclude {\n" + r"\.cpp$")
subprocess.run(["git", "add", ".styleguide-license"])
subprocess.run(["git", "add", ".styleguide"])
subprocess.run(["git", "add", ".wpiformat-license"])
subprocess.run(["git", "add", ".wpiformat"])
subprocess.run(["git", "commit", "-q", "-m", '"Initial commit"'])

# Add file with commit date of last year and range through this year
Expand Down
2 changes: 1 addition & 1 deletion wpiformat/wpiformat/test/test_tasktest.py
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ def run(self, output_type):
"""
assert len(self.inputs) == len(self.outputs)

config_file = Config(os.path.abspath(os.getcwd()), ".styleguide")
config_file = Config(os.path.abspath(os.getcwd()), ".wpiformat")

for i in range(len(self.inputs)):
if self.task.should_process_file(config_file, self.inputs[i][0]):
Expand Down