Skip to content

Commit 9f2caa8

Browse files
2bndy5shenxianpeng
andauthored
better consideration for windows-based runners (#53)
* better consideration for windows-based runners - allow a path to clang-tools be passed to version (on windows platform) - annotate w/ filename using posix path delimiters when env is a CI runner - add some type hinting * ignore invalid version input on non-windows env * add windows runner example to README * append /bin automatically * update README about the last commit * update `cpp-linter -h` output * add more shorthand CLI args * Update cpp_linter/run.py Co-authored-by: Peter Shen <xianpeng.shen@gmail.com> Co-authored-by: Peter Shen <xianpeng.shen@gmail.com>
1 parent b641546 commit 9f2caa8

File tree

4 files changed

+87
-16
lines changed

4 files changed

+87
-16
lines changed

README.md

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,57 @@ jobs:
128128

129129
This action creates 1 output variable named `checks-failed`. Even if the linting checks fail for source files this action will still pass, but users' CI workflows can use this action's output to exit the workflow early if that is desired.
130130

131+
## Using a Windows-based runner
132+
133+
This action can only be run on a runner using the Ubuntu Operating System. However, this action's source code (essentially a python package) can be used on a runner using the Windows Operating System.
134+
135+
Note: MacOS-based runners have not been tested, but the same approach applies.
136+
137+
This example makes use of another action
138+
([KyleMayes/install-llvm-action](https://github.com/KyleMayes/install-llvm-action))
139+
to install a certain version of clang-tidy and clang-format.
140+
141+
```yml
142+
on:
143+
push:
144+
paths-ignore: "docs/**"
145+
pull_request:
146+
paths-ignore: "docs/**"
147+
148+
jobs:
149+
cpp-linter:
150+
runs-on: windows-latest
151+
152+
steps:
153+
- uses: actions/checkout@v3
154+
- uses: actions/setup-python@v3
155+
156+
- name: Install clang-tools
157+
uses: KyleMayes/install-llvm-action@v1
158+
with:
159+
# v12 is the recommended minimum for the Visual Studio compiler
160+
version: 12
161+
# specifying an install path is required because
162+
# Windows runners already have a certain version of LLVM installed
163+
directory: ${{ runner.temp }}/llvm
164+
165+
- name: Install linter python package
166+
run: python3 -m pip install git+https://github.com/shenxianpeng/cpp-linter-action
167+
168+
- name: run linter as a python package
169+
id: linter
170+
# pass the installed path to the '--version' argument
171+
run: cpp-linter --version=${{ runner.temp }}/llvm
172+
173+
- name: Fail fast?!
174+
if: steps.linter.outputs.checks-failed > 0
175+
run: echo "Some files failed the linting checks!"
176+
# for actual deployment
177+
# run: exit 1
178+
```
179+
180+
All input options listed above are specified by pre-pending a `--`. You can also install this repo locally and run `cpp-linter -h` for more detail.
181+
131182
## Example
132183

133184
<!--intro-end-->

cpp_linter/__init__.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
logger.debug("rich module not found")
2626

2727
# global constant variables
28+
IS_ON_RUNNER = bool(os.getenv("CI"))
2829
GITHUB_SHA = os.getenv("GITHUB_SHA", "")
2930
GITHUB_TOKEN = os.getenv("GITHUB_TOKEN", os.getenv("GIT_REST_API", ""))
3031
API_HEADERS = {"Accept": "application/vnd.github.v3.text+json",}

cpp_linter/clang_tidy.py

Lines changed: 17 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
"""Parse output from clang-tidy's stdout"""
22
import os
33
import re
4-
from . import GlobalParser # , logger
4+
from . import GlobalParser, IS_ON_RUNNER # , logger
55

66
NOTE_HEADER = re.compile("^(.*):(\d+):(\d+):\s(\w+):(.*)\[(.*)\]$")
77

@@ -37,11 +37,11 @@ def __init__(self, notification_line: tuple):
3737
self.diagnostic,
3838
) = notification_line
3939

40-
self.note_info = self.note_info.strip()
41-
self.note_type = self.note_type.strip()
40+
self.note_info: str = self.note_info.strip()
41+
self.note_type: str = self.note_type.strip()
4242
self.line = int(self.line)
4343
self.cols = int(self.cols)
44-
self.filename = self.filename.replace(os.getcwd() + os.sep, "")
44+
self.filename: str = self.filename.replace(os.getcwd() + os.sep, "")
4545
self.fixit_lines = []
4646

4747
def __repr__(self) -> str:
@@ -70,15 +70,19 @@ def log_command(self) -> str:
7070
- [A notice message](https://docs.github.com/en/actions/learn-github-
7171
actions/workflow-commands-for-github-actions#setting-a-notice-message)
7272
"""
73-
return "::{} file={},line={},title={}:{}:{} [{}]::{}".format(
74-
"notice" if self.note_type.startswith("note") else self.note_type,
75-
self.filename,
76-
self.line,
77-
self.filename,
78-
self.line,
79-
self.cols,
80-
self.diagnostic,
81-
self.note_info,
73+
filename = self.filename
74+
if IS_ON_RUNNER:
75+
filename = self.filename.replace(os.sep, "/")
76+
return (
77+
"::{} file={file},line={line},title={file}:{line}:{cols} [{diag}]::"
78+
"{info}".format(
79+
"notice" if self.note_type.startswith("note") else self.note_type,
80+
file=filename,
81+
line=self.line,
82+
cols=self.cols,
83+
diag=self.diagnostic,
84+
info=self.note_info,
85+
)
8286
)
8387

8488

cpp_linter/run.py

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,8 @@
8484
"--version",
8585
default="10",
8686
help="The desired version of the clang tools to use. Accepted options are strings "
87-
"which can be 6.0, 7, 8, 9, 10, 11, 12. Defaults to %(default)s.",
87+
"which can be 8, 9, 10, 11, 12, 13, 14. Defaults to %(default)s. On Windows, this "
88+
"can also be a path to the install location of LLVM",
8889
)
8990
cli_arg_parser.add_argument(
9091
"-e",
@@ -107,23 +108,26 @@
107108
help="Set this option with paths to ignore. In the case of multiple "
108109
"paths, you can set this option (multiple times) for each path. This can "
109110
"also have files, but the file's relative path has to be specified as well "
110-
"with the filename.",
111+
"with the filename. Prefix a path with '!' to explicitly not ignore it.",
111112
)
112113
cli_arg_parser.add_argument(
114+
"-l",
113115
"--lines-changed-only",
114116
default="false",
115117
type=lambda input: input.lower() == "true",
116118
help="Set this option to 'true' to only analyse changes in the event's diff. "
117119
"Defaults to %(default)s.",
118120
)
119121
cli_arg_parser.add_argument(
122+
"-f",
120123
"--files-changed-only",
121124
default="false",
122125
type=lambda input: input.lower() == "true",
123126
help="Set this option to 'false' to analyse any source files in the repo. "
124127
"Defaults to %(default)s.",
125128
)
126129
cli_arg_parser.add_argument(
130+
"-t",
127131
"--thread-comments",
128132
default="false",
129133
type=lambda input: input.lower() == "true",
@@ -394,6 +398,11 @@ def run_clang_tidy(
394398
cmds = [f"clang-tidy-{version}"]
395399
if sys.platform.startswith("win32"):
396400
cmds = ["clang-tidy"]
401+
if os.path.exists(version + os.sep + "bin"):
402+
cmds = [f"{version}\\bin\\clang-tidy.exe"]
403+
elif not version.isdigit():
404+
logger.warning("ignoring invalid version number %s.", version)
405+
cmds = ["clang-tidy"]
397406
if checks:
398407
cmds.append(f"-checks={checks}")
399408
cmds.append("--export-fixes=clang_tidy_output.yml")
@@ -440,11 +449,17 @@ def run_clang_format(
440449
lines_changed_only: A flag that forces focus on only changes in the event's
441450
diff info.
442451
"""
452+
is_on_windows = sys.platform.startswith("win32")
443453
cmds = [
444-
"clang-format" + ("" if sys.platform.startswith("win32") else f"-{version}"),
454+
"clang-format" + ("" if is_on_windows else f"-{version}"),
445455
f"-style={style}",
446456
"--output-replacements-xml",
447457
]
458+
if is_on_windows and os.path.exists(version + os.sep + "bin"):
459+
cmds[0] = f"{version}\\bin\\clang-format.exe"
460+
elif not is_on_windows and not version.isdigit():
461+
logger.warning("ignoring invalid version number %s.", version)
462+
cmds[0] = "clang-format"
448463
if lines_changed_only:
449464
for line_range in file_obj["line_filter"]["lines"]:
450465
cmds.append(f"--lines={line_range[0]}:{line_range[1]}")

0 commit comments

Comments
 (0)