├── .gitattributes
├── .github
├── ISSUE_TEMPLATE
│ ├── bug-report.yml
│ ├── config.yml
│ └── feature-request.yml
├── dependabot.yml
├── release-drafter.yml
└── workflows
│ ├── cpp-linter.yml
│ ├── labeler.yml
│ ├── mkdocs-deploy.yml
│ ├── pre-commit.yml
│ ├── release-drafter.yml
│ ├── release.yml
│ ├── self-test.yml
│ └── stale.yml
├── .gitignore
├── .gitpod.yml
├── .pre-commit-config.yaml
├── .readthedocs.yaml
├── CONTRIBUTING.md
├── LICENSE
├── README.md
├── action.yml
├── docs
├── README.rst
├── action.yml
├── badge_hook.py
├── contributing-guidelines.md
├── examples
│ ├── demo
│ │ ├── .clang-format
│ │ ├── .clang-tidy
│ │ ├── CMakeLists.txt
│ │ ├── compile_flags.txt
│ │ ├── demo.cpp
│ │ └── demo.hpp
│ ├── index.md
│ ├── only-PR-comments.yml
│ ├── only-clang-format.yml
│ └── only-clang-tidy.yml
├── gen_io_doc.py
├── images
│ ├── annotations-clang-format.png
│ ├── annotations-clang-tidy.png
│ ├── comment.png
│ ├── favicon.ico
│ ├── format-review.png
│ ├── format-suggestion.png
│ ├── logo.png
│ ├── step-summary.png
│ └── tidy-review.png
├── index.md
├── permissions.md
├── pr-review-caveats.md
├── requirements.txt
└── stylesheets
│ └── extra.css
├── mkdocs.yml
└── requirements.txt
/.gitattributes:
--------------------------------------------------------------------------------
1 | # Set the default behavior, in case people don't have core.autocrlf set.
2 | * text=auto
3 |
4 | # Explicitly declare text files you want to always be normalized and converted
5 | # to native line endings on checkout.
6 | *.py text eol=lf
7 | *.rst text eol=lf
8 | *.sh text eol=lf
9 | *.cpp text eol=lf
10 | *.hpp text eol=lf
11 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/bug-report.yml:
--------------------------------------------------------------------------------
1 | name: Report a problem
2 | description: Create a report to let us help you
3 | body:
4 | - type: textarea
5 | attributes:
6 | label: What events trigger your workflow?
7 | id: ci-triggers
8 | description: >-
9 | Please copy and paste the workflow triggers.
10 | If you are using a resuable workflow (`workflow_dispatch` event),
11 | then please also include the workflow triggers that the calling workflow uses.
12 | placeholder: |-
13 | on:
14 | pull_request:
15 | branches: [main, master, develop]
16 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
17 | push:
18 | branches: [main, master, develop]
19 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
20 | render: yml
21 | validations:
22 | required: true
23 |
24 | - type: textarea
25 | id: runner-os
26 | attributes:
27 | label: What OS does your workflow use?
28 | description: >-
29 | Please tell us what OS the workflow [`runs-on`](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idruns-on).
30 | If you are using an additional [`container`](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idcontainer),
31 | then please also include that information here.
32 | placeholder: |-
33 | runs-on: ubuntu-latest
34 | container: node:18
35 | render: yml
36 | validations:
37 | required: true
38 |
39 | - type: textarea
40 | id: cpp-linter-config
41 | attributes:
42 | label: How is cpp-linter-action configured?
43 | description: >-
44 | Please copy and paste the version and inputs used to run cpp-linter-action.
45 | placeholder: |-
46 | - uses: cpp-linter/cpp-linter-action@v2
47 | id: linter
48 | env:
49 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
50 | with:
51 | style: 'file'
52 | tidy-checks: ''
53 | render: yml
54 | validations:
55 | required: true
56 |
57 | - type: textarea
58 | id: what-happened
59 | attributes:
60 | label: What was the unexpected behavior?
61 | description: >-
62 | Use this area to describe what behavior you expected and what behavior you observed.
63 | Please be clear and concise as possible. Use screenshots if that would help. Most users
64 | use this to paste the workflow logs.
65 | placeholder: You can use markdown syntax here
66 | validations:
67 | required: true
68 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/config.yml:
--------------------------------------------------------------------------------
1 | # this setting will force users to use the provided issue templates
2 | blank_issues_enabled: false
3 | # if the templates provided don't fit the subject of the user feedback,
4 | # here we can give links to other forms of user feedback
5 | contact_links:
6 | - name: cpp-linter discussions
7 | url: https://github.com/orgs/cpp-linter/discussions
8 | about: A place for feedback not specific to cpp-linter-action
9 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/feature-request.yml:
--------------------------------------------------------------------------------
1 | ---
2 | name: Feature request
3 | description: Suggest an idea for this project
4 | body:
5 | - type: dropdown
6 | id: existing-feature
7 | attributes:
8 | label: Is your idea related to an existing feature?
9 | description: >-
10 | If this idea is related to an already available feature(s), then please list them here.
11 | multiple: true
12 | options:
13 | - version
14 | - database
15 | - thread-comments
16 | - tidy-checks
17 | - style
18 | - lines-changed-only
19 | - ignore
20 | - tidy-ignore
21 | - format-ignore
22 | - files-changed-only
23 | - file-annotations
24 | - step-summary
25 | - no-lgtm
26 | - tidy-review
27 | - format-review
28 | - passive-reviews
29 | - verbosity
30 | - 'output: checks-failed'
31 | - 'output: clang-tidy-checks-failed'
32 | - 'output: clang-format-checks-failed'
33 |
34 | - type: textarea
35 | id: behavior
36 | attributes:
37 | label: Describe the behavior you would like
38 | description: >-
39 | Use this area to describe what behavior you desire.
40 | Please be clear and concise as possible. Use screenshots if that would help.
41 | placeholder: You can use markdown syntax here
42 | validations:
43 | required: true
44 |
45 | - type: textarea
46 | id: alternative
47 | attributes:
48 | label: Describe alternatives you have considered
49 | description: >-
50 | Were you able to achieve the desired behavior in some other/inconvenient way?
51 | placeholder: You can use markdown syntax here
52 |
53 | - type: textarea
54 | id: added-context
55 | attributes:
56 | label: Additional context
57 | description: >-
58 | If there is anything that might be special or specific to your usage, please let us know.
59 | placeholder: You can use markdown syntax here
60 |
--------------------------------------------------------------------------------
/.github/dependabot.yml:
--------------------------------------------------------------------------------
1 | # To get started with Dependabot version updates, you'll need to specify which
2 | # package ecosystems to update and where the package manifests are located.
3 | # Please see the documentation for all configuration options:
4 | # https://docs.github.com/github/administering-a-repository/configuration-options-for-dependency-updates
5 |
6 | version: 2
7 | updates:
8 | - package-ecosystem: github-actions
9 | directory: /
10 | schedule:
11 | interval: "weekly"
12 | groups:
13 | actions:
14 | patterns:
15 | - "*"
16 | - package-ecosystem: pip
17 | directory: /
18 | schedule:
19 | interval: "daily"
20 | groups:
21 | pip:
22 | patterns:
23 | - "*"
24 |
--------------------------------------------------------------------------------
/.github/release-drafter.yml:
--------------------------------------------------------------------------------
1 | _extends: .github
2 |
--------------------------------------------------------------------------------
/.github/workflows/cpp-linter.yml:
--------------------------------------------------------------------------------
1 | name: cpp-linter
2 |
3 | on:
4 | push:
5 | paths:
6 | - "docs/examples/demo/*"
7 | pull_request:
8 | paths:
9 | - "docs/examples/demo/*"
10 |
11 |
12 | jobs:
13 | cpp-linter:
14 | runs-on: ubuntu-latest
15 | steps:
16 | - uses: actions/checkout@v4
17 | - uses: cpp-linter/cpp-linter-action@main
18 | id: linter
19 | continue-on-error: true
20 | env:
21 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
22 | with:
23 | style: file
24 | files-changed-only: false
25 | thread-comments: false
26 |
27 | - name: Fail fast?!
28 | if: steps.linter.outputs.checks-failed != 0
29 | run: |
30 | echo "some linter checks failed. ${{ steps.linter.outputs.checks-failed }}"
31 | # for actual deployment
32 | # run: exit 1
33 |
--------------------------------------------------------------------------------
/.github/workflows/labeler.yml:
--------------------------------------------------------------------------------
1 | name: PR Autolabeler
2 |
3 | on:
4 | # pull_request event is required for autolabeler
5 | pull_request:
6 | types: [opened, reopened, synchronize]
7 |
8 | jobs:
9 | draft-release:
10 | uses: cpp-linter/.github/.github/workflows/release-drafter.yml@main
11 |
--------------------------------------------------------------------------------
/.github/workflows/mkdocs-deploy.yml:
--------------------------------------------------------------------------------
1 | name: MkDocs Deploy
2 |
3 | on:
4 | push:
5 | workflow_dispatch:
6 |
7 | jobs:
8 | build-docs:
9 | uses: cpp-linter/.github/.github/workflows/mkdocs.yml@main
10 |
--------------------------------------------------------------------------------
/.github/workflows/pre-commit.yml:
--------------------------------------------------------------------------------
1 | name: Run pre-commit
2 |
3 | on:
4 | push:
5 | pull_request:
6 | types: opened
7 |
8 | jobs:
9 | pre-commit:
10 | uses: cpp-linter/.github/.github/workflows/pre-commit.yml@main
11 |
--------------------------------------------------------------------------------
/.github/workflows/release-drafter.yml:
--------------------------------------------------------------------------------
1 | name: Release Drafter
2 |
3 | on:
4 | push:
5 | branches:
6 | - "main"
7 | workflow_dispatch:
8 |
9 | jobs:
10 | draft-release:
11 | uses: cpp-linter/.github/.github/workflows/release-drafter.yml@main
12 |
--------------------------------------------------------------------------------
/.github/workflows/release.yml:
--------------------------------------------------------------------------------
1 | name: Release
2 |
3 | on:
4 | release:
5 | branches: [main]
6 | types: [published]
7 | workflow_dispatch:
8 | inputs:
9 | tag:
10 | description: 'which tag to update to'
11 | default: 'v2'
12 | required: true
13 | ref:
14 | description: 'which branch to update the tag on'
15 | default: 'main'
16 | required: true
17 |
18 | jobs:
19 | re-tag:
20 | runs-on: ubuntu-latest
21 | steps:
22 | - uses: actions/checkout@v4
23 | with:
24 | fetch-depth: 0
25 | ref: ${{ inputs.ref }}
26 | - name: Config git name and email
27 | run: |
28 | git config user.name 'github-actions'
29 | git config user.email '41898282+github-actions[bot]@users.noreply.github.com'
30 | - name: Update tag with parameter
31 | if: github.event.inputs.tag != ''
32 | run: |
33 | git tag --delete ${{ inputs.tag }} || true
34 | git push --delete origin ${{ inputs.tag }} || true
35 | git tag -a ${{ inputs.tag }} -m 'Retag ${{ inputs.tag }}'
36 | git push origin ${{ inputs.tag }}
37 | - name: Update tag to v2
38 | if: github.event.inputs.tag == ''
39 | run: |
40 | git tag --delete v2 || true
41 | git push --delete origin v2 || true
42 | git tag -a v2 -m 'Retag v2'
43 | git push origin v2
44 |
--------------------------------------------------------------------------------
/.github/workflows/self-test.yml:
--------------------------------------------------------------------------------
1 | name: Self test action
2 |
3 | on:
4 | push:
5 | branches: [main]
6 | paths:
7 | - 'action.yml'
8 | - 'requirements.txt'
9 | - 'docs/examples/demo/**'
10 | - '.github/workflows/self-test.yml'
11 | pull_request:
12 | branches: main
13 | paths:
14 | - 'action.yml'
15 | - 'requirements.txt'
16 | - 'docs/examples/demo/**'
17 | - '.github/workflows/self-test.yml'
18 | pull_request_target:
19 | branches: main
20 | paths:
21 | - 'action.yml'
22 | - 'requirements.txt'
23 | - 'docs/examples/demo/**'
24 | - '.github/workflows/self-test.yml'
25 |
26 | jobs:
27 | test:
28 | permissions:
29 | contents: write
30 | pull-requests: write
31 | strategy:
32 | matrix:
33 | os: [ ubuntu-latest, macos-latest, windows-latest ]
34 | clang-version: ['8','9','10', '11', '12', '13', '14', '15', '16', '17', '18', '19', '20']
35 | fail-fast: false
36 | runs-on: ${{ matrix.os }}
37 | steps:
38 | - name: Checkout
39 | uses: actions/checkout@v4
40 |
41 | - name: Cache the build artifacts
42 | id: cache-build
43 | uses: actions/cache@v4
44 | with:
45 | path: build
46 | key: ${{ runner.os }}-${{ hashFiles('docs/examples/demo/**') }}
47 |
48 | - name: Generate compilation database
49 | if: steps.cache-build.outputs.cache-hit != 'true'
50 | run: mkdir build && cmake -Bbuild docs/examples/demo
51 |
52 | - name: Self test action
53 | uses: ./
54 | id: linter
55 | env:
56 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
57 | with:
58 | style: file
59 | files-changed-only: false
60 | # to ignore all build folder contents
61 | ignore: build|venv
62 | database: build
63 | verbosity: debug
64 | version: ${{ matrix.clang-version }}
65 | thread-comments: ${{ matrix.clang-version == '12' && 'update' }}
66 | file-annotations: ${{ runner.os == 'Linux' && matrix.clang-version == '12' }}
67 | step-summary: ${{ matrix.clang-version == '12' }}
68 | extra-args: -std=c++14 -Wall
69 |
70 | - name: Fail fast?!
71 | # if: steps.linter.outputs.checks-failed > 0
72 | run: |
73 | echo "some linter checks failed"
74 | echo "total checks-failed: ${{ steps.linter.outputs.checks-failed }}"
75 | echo "clang-tidy checks-failed: ${{ steps.linter.outputs.clang-tidy-checks-failed }}"
76 | echo "clang-format checks-failed: ${{ steps.linter.outputs.clang-format-checks-failed }}"
77 | # for actual deployment
78 | # run: exit 1
79 |
--------------------------------------------------------------------------------
/.github/workflows/stale.yml:
--------------------------------------------------------------------------------
1 | name: 'Close stale issues'
2 | on:
3 | schedule:
4 | - cron: '30 1 * * *'
5 | permissions:
6 | issues: write
7 |
8 | jobs:
9 | stale:
10 | uses: cpp-linter/.github/.github/workflows/stale.yml@main
11 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # local demo specific
2 | .changed_files.json
3 | clang_format*.txt
4 | clang_tidy*.txt
5 | act.exe
6 | clang_tidy_output.yml
7 | clang_format_output.xml
8 | event_payload.json
9 | comments.json
10 |
11 | #### ignores for Python
12 | # Byte-compiled / optimized / DLL files
13 | __pycache__/
14 | *.py[cod]
15 | *$py.class
16 |
17 | # Distribution / packaging
18 | .Python
19 | build/
20 | develop-eggs/
21 | dist/
22 | downloads/
23 | eggs/
24 | .eggs/
25 | lib/
26 | lib64/
27 | parts/
28 | sdist/
29 | var/
30 | wheels/
31 | pip-wheel-metadata/
32 | share/python-wheels/
33 | *.egg-info/
34 | .installed.cfg
35 | *.egg
36 | MANIFEST
37 |
38 | # PyInstaller
39 | # Usually these files are written by a python script from a template
40 | # before PyInstaller builds the exe, so as to inject date/other infos into it.
41 | *.manifest
42 | *.spec
43 |
44 | # Installer logs
45 | pip-log.txt
46 | pip-delete-this-directory.txt
47 |
48 | # Unit test / coverage reports
49 | htmlcov/
50 | .tox/
51 | .nox/
52 | .coverage
53 | .coverage.*
54 | .cache
55 | nosetests.xml
56 | coverage.xml
57 | *.cover
58 | *.py,cover
59 | .hypothesis/
60 | .pytest_cache/
61 | tests/*/test*.json
62 | tests/**/*.c
63 |
64 | # Translations
65 | *.mo
66 | *.pot
67 |
68 | # Django stuff:
69 | *.log
70 | local_settings.py
71 | db.sqlite3
72 | db.sqlite3-journal
73 |
74 | # Flask stuff:
75 | instance/
76 | .webassets-cache
77 |
78 | # Scrapy stuff:
79 | .scrapy
80 |
81 | # Sphinx documentation
82 | docs/_build/
83 |
84 | # PyBuilder
85 | target/
86 |
87 | # Jupyter Notebook
88 | .ipynb_checkpoints
89 |
90 | # IPython
91 | profile_default/
92 | ipython_config.py
93 |
94 | # pyenv
95 | .python-version
96 |
97 | # pipenv
98 | # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
99 | # However, in case of collaboration, if having platform-specific dependencies or dependencies
100 | # having no cross-platform support, pipenv may install dependencies that don't work, or not
101 | # install all needed dependencies.
102 | #Pipfile.lock
103 |
104 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow
105 | __pypackages__/
106 |
107 | # Celery stuff
108 | celerybeat-schedule
109 | celerybeat.pid
110 |
111 | # SageMath parsed files
112 | *.sage.py
113 |
114 | # Environments
115 | .env
116 | .venv
117 | env/
118 | venv/
119 | ENV/
120 | env.bak/
121 | venv.bak/
122 |
123 | # Spyder project settings
124 | .spyderproject
125 | .spyproject
126 |
127 | # Rope project settings
128 | .ropeproject
129 |
130 | # mkdocs documentation
131 | /site
132 |
133 | # mypy
134 | .mypy_cache/
135 | .dmypy.json
136 | dmypy.json
137 |
138 | # Pyre type checker
139 | .pyre/
140 |
141 | # exclude local VSCode's settings folder
142 | .vscode/
143 |
144 | #### ignores for C++
145 | # Prerequisites
146 | *.d
147 |
148 | # Compiled Object files
149 | *.slo
150 | *.lo
151 | *.o
152 | *.obj
153 |
154 | # Precompiled Headers
155 | *.gch
156 | *.pch
157 |
158 | # Compiled Dynamic libraries
159 | *.so
160 | *.dylib
161 | *.dll
162 |
163 | # Fortran module files
164 | *.mod
165 | *.smod
166 |
167 | # Compiled Static libraries
168 | *.lai
169 | *.la
170 | *.a
171 | *.lib
172 |
173 | # Executables
174 | *.exe
175 | *.out
176 | *.app
177 |
178 | # Cmake build-in-source generated stuff
179 | CMakeUserPresets.json
180 | CMakeCache.txt
181 | CPackConfig.cmake
182 | CPackSourceConfig.cmake
183 | CMakeFiles
184 | cmake_install.cmake
185 |
--------------------------------------------------------------------------------
/.gitpod.yml:
--------------------------------------------------------------------------------
1 | # This configuration file was automatically generated by Gitpod.
2 | # Please adjust to your needs (see https://www.gitpod.io/docs/config-gitpod-file)
3 | # and commit this file to your remote git repository to share the goodness with others.
4 |
5 | tasks:
6 | - init: pip install -r requirements.txt pre-commit
7 | command: pre-commit install
8 |
--------------------------------------------------------------------------------
/.pre-commit-config.yaml:
--------------------------------------------------------------------------------
1 | repos:
2 | - repo: https://github.com/pre-commit/pre-commit-hooks
3 | rev: v4.5.0
4 | hooks:
5 | - id: trailing-whitespace
6 | - id: end-of-file-fixer
7 | - id: check-added-large-files
8 | - id: check-yaml
9 | # special mkdocs config to include inline icons fails (see `pymdownx.emoji` in mkdocs.yml)
10 | args: ['--unsafe'] # use `--unsafe` to workaround yaml loading
11 | - id: requirements-txt-fixer
12 |
--------------------------------------------------------------------------------
/.readthedocs.yaml:
--------------------------------------------------------------------------------
1 | # Read the Docs configuration file for MkDocs projects
2 | # See https://docs.readthedocs.io/en/stable/config-file/v2.html for details
3 |
4 | # Required
5 | version: 2
6 |
7 | # Set the version of Python and other tools you might need
8 | build:
9 | os: ubuntu-22.04
10 | tools:
11 | python: "3.12"
12 |
13 | mkdocs:
14 | configuration: mkdocs.yml
15 |
16 | # Optionally declare the Python requirements required to build your docs
17 | python:
18 | install:
19 | - requirements: docs/requirements.txt
20 |
--------------------------------------------------------------------------------
/CONTRIBUTING.md:
--------------------------------------------------------------------------------
1 | # Contributing
2 |
3 | Thank you for investing your time in contributing to our project! We welcome feedback, bug reports, and pull requests!
4 |
5 | ## New contributor guide
6 |
7 | Ours develop branch is `main` not `master` (`master` used to be the develop branch for v1.x).
8 |
9 | The reason we didn't delete the `master` branch is that there are still users whose workflows point to the `master` branch.
10 |
11 | For pull requests, please stick to the following guidelines
12 |
13 | * Add tests for any new features and bug fixes.
14 | * Put a reasonable amount of comments into the code.
15 | * Fork cpp-linter-action on your GitHub user account, do your changes there and then create a PR against `main` branch of cpp-linter-action repository.
16 | * Separate unrelated changes into multiple pull requests.
17 |
18 | If you wish to contribute to the python source package used by this action, then that has moved to it's own repository named [cpp-linter](https://github.com/cpp-linter/cpp-linter) as of v2 of this action.
19 |
20 | Please note that by contributing any code or documentation to this repository (by raising pull requests, or otherwise) you explicitly agree to the [License Agreement](https://github.com/cpp-linter/cpp-linter-action/blob/main/LICENSE).
21 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2021 shenxianpeng
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | [file-annotations]: https://cpp-linter.github.io/cpp-linter-action/inputs-outputs/#file-annotations
2 | [thread-comments]: https://cpp-linter.github.io/cpp-linter-action/inputs-outputs/#thread-comments
3 | [step-summary]: https://cpp-linter.github.io/cpp-linter-action/inputs-outputs/#step-summary
4 | [tidy-review]: https://cpp-linter.github.io/cpp-linter-action/inputs-outputs/#tidy-review
5 | [format-review]: https://cpp-linter.github.io/cpp-linter-action/inputs-outputs/#format-review
6 |
7 | [io-doc]: https://cpp-linter.github.io/cpp-linter-action/inputs-outputs
8 | [recipes-doc]: https://cpp-linter.github.io/cpp-linter-action/examples
9 |
10 | [format-annotations-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/annotations-clang-format.png
11 | [tidy-annotations-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/annotations-clang-tidy.png
12 | [thread-comment-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/comment.png
13 | [step-summary-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/step-summary.png
14 | [tidy-review-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/tidy-review.png
15 | [format-review-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/format-review.png
16 | [format-suggestion-preview]: https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/main/docs/images/format-suggestion.png
17 |
18 |
19 |
20 | # C/C++ Linter Action | clang-format & clang-tidy
21 |
22 | 
23 | [](https://github.com/marketplace/actions/c-c-linter)
24 | [](https://github.com/cpp-linter/cpp-linter-action/actions/workflows/cpp-linter.yml)
25 | [](https://github.com/cpp-linter/cpp-linter-action/actions/workflows/mkdocs-deploy.yml)
26 | 
27 |
28 | A Github Action for linting C/C++ code integrating clang-tidy and clang-format
29 | to collect feedback provided in the form of
30 | [`file-annotations`][file-annotations], [`thread-comments`][thread-comments],
31 | workflow [`step-summary`][step-summary], and Pull Request reviews (with
32 | [`tidy-review`][tidy-review] or [`format-review`][format-review]).
33 |
34 | > [!WARNING]
35 | > We only support Linux runners using a Debian-based Linux OS (like Ubuntu and many others).
36 | >
37 | > MacOS and Windows runners are supported as well.
38 |
39 | ## Usage
40 |
41 | > [!NOTE]
42 | > Python 3.10 needs to be installed in the docker image if your workflow is
43 | > [running jobs in a container](https://docs.github.com/en/actions/using-jobs/running-jobs-in-a-container)
44 | > (see discussion in [#185](https://github.com/cpp-linter/cpp-linter-action/issues/185)).
45 | > Our intention is to synchronize with the default Python version included with Ubuntu's latest LTS releases.
46 |
47 | Create a new GitHub Actions workflow in your project, e.g. at [.github/workflows/cpp-linter.yml](https://github.com/cpp-linter/cpp-linter-action/blob/main/.github/workflows/cpp-linter.yml)
48 |
49 | The content of the file should be in the following format.
50 |
51 | ```yaml
52 | steps:
53 | - uses: actions/checkout@v4
54 | - uses: cpp-linter/cpp-linter-action@v2
55 | id: linter
56 | env:
57 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
58 | with:
59 | style: 'file' # Use .clang-format config file
60 | tidy-checks: '' # Use .clang-tidy config file
61 | # only 'update' a single comment in a pull request thread.
62 | thread-comments: ${{ github.event_name == 'pull_request' && 'update' }}
63 | - name: Fail fast?!
64 | if: steps.linter.outputs.checks-failed > 0
65 | run: exit 1
66 | ```
67 |
68 | For all explanations of our available input parameters and output variables, see our
69 | [Inputs and Outputs document][io-doc].
70 |
71 | See also our [example recipes][recipes-doc].
72 |
73 | ## Used By
74 |
75 |
76 |
77 | Microsoft
78 |
79 | Apache
80 |
81 | NASA
82 |
83 | Samsung
84 |
85 | TheAlgorithms
86 |
87 | CachyOS
88 |
89 |
90 | Nextcloud
91 |
92 | Jupyter
93 |
94 | NNStreamer
95 |
96 | imgproxy
97 |
98 | Zondax
99 |
100 | AppNeta
101 |
102 |
103 | Chocolate Doom
104 | and many more.
105 |
106 |
107 | ## Example
108 |
109 | ### Annotations
110 |
111 | Using [`file-annotations`][file-annotations]:
112 |
113 | #### clang-format annotations
114 |
115 | ![clang-format annotations][format-annotations-preview]
116 |
117 | #### clang-tidy annotations
118 |
119 | ![clang-tidy annotations][tidy-annotations-preview]
120 |
121 | ### Thread Comment
122 |
123 | Using [`thread-comments`][thread-comments]:
124 |
125 | ![sample thread-comment][thread-comment-preview]
126 |
127 | ### Step Summary
128 |
129 | Using [`step-summary`][step-summary]:
130 |
131 | ![step summary][step-summary-preview]
132 |
133 | ### Pull Request Review
134 |
135 | #### Only clang-tidy
136 |
137 | Using [`tidy-review`][tidy-review]:
138 |
139 | ![sample tidy-review][tidy-review-preview]
140 |
141 | #### Only clang-format
142 |
143 | Using [`format-review`][format-review]:
144 |
145 | ![sample format-review][format-review-preview]
146 |
147 | ![sample format-suggestion][format-suggestion-preview]
148 |
149 | ## Add C/C++ Linter Action badge in README
150 |
151 | You can show C/C++ Linter Action status with a badge in your repository README
152 |
153 | Example
154 |
155 | ```markdown
156 | [](https://github.com/cpp-linter/cpp-linter-action/actions/workflows/cpp-linter.yml)
157 | ```
158 |
159 | [](https://github.com/cpp-linter/cpp-linter-action/actions/workflows/cpp-linter.yml)
160 |
161 | ## Have question or feedback?
162 |
163 | To provide feedback (requesting a feature or reporting a bug) please post to [issues](https://github.com/cpp-linter/cpp-linter-action/issues).
164 |
165 | ## License
166 |
167 | The scripts and documentation in this project are released under the [MIT License](https://github.com/cpp-linter/cpp-linter-action/blob/main/LICENSE)
168 |
169 |
170 |
--------------------------------------------------------------------------------
/action.yml:
--------------------------------------------------------------------------------
1 | name: C/C++ Linter
2 | description: Linting C/C++ code with clang-tidy or clang-format to give feedback as comments, PR reviews, and more.
3 | author: cpp-linter
4 | branding:
5 | icon: "check-circle"
6 | color: "green"
7 | inputs:
8 | style:
9 | description: |
10 | The style rules to use.
11 |
12 | - Set this to `file` to have clang-format use the closest relative .clang-format file.
13 | - Set this to a blank string (`''`) to disable the use of clang-format entirely.
14 | - Any code style supported by the specified version of clang-format.
15 | required: false
16 | default: "llvm"
17 | extensions:
18 | description: The file extensions to run the action against. This is a comma-separated string.
19 | required: false
20 | default: "c,h,C,H,cpp,hpp,cc,hh,c++,h++,cxx,hxx"
21 | tidy-checks:
22 | description: |
23 | Comma-separated list of globs with optional `-` prefix.
24 | Globs are processed in order of appearance in the list.
25 | Globs without `-` prefix add checks with matching names to the set,
26 | globs with the `-` prefix remove checks with matching names from the set of enabled checks.
27 | This option's value is appended to the value of the 'Checks' option in a .clang-tidy file (if any).
28 |
29 | - It is possible to disable clang-tidy entirely by setting this option to `'-*'`.
30 | - It is also possible to rely solely on a .clang-tidy config file by specifying this option as a blank string (`''`).
31 | required: false
32 | default: "boost-*,bugprone-*,performance-*,readability-*,portability-*,modernize-*,clang-analyzer-*,cppcoreguidelines-*"
33 | repo-root:
34 | description: >
35 | The relative path to the repository root directory.
36 | This path is relative to the path designated as the runner's `GITHUB_WORKSPACE` environment variable.
37 | required: false
38 | default: '.'
39 | version:
40 | description: |
41 | The desired version of the [clang-tools](https://github.com/cpp-linter/clang-tools-pip) to use.
42 | Accepted options are strings which can be 20, 19, 18, 17, 16, 15, 14, 13, 12, 11, 10, 9, or 8.
43 |
44 | - Set this option to a blank string (`''`) to use the platform's default installed version.
45 | - This value can also be a path to where the clang tools are installed (if using a custom install location).
46 | required: false
47 | default: 16
48 | verbosity:
49 | description: |
50 | This controls the action's verbosity in the workflow's logs.
51 | Supported options are `info` or `debug`.
52 | This option does not affect the verbosity of resulting thread comments or file annotations.
53 |
54 | The verbosity can also be engaged by enabling debug logs when
55 | [re-running jobs or workflows](https://docs.github.com/en/actions/managing-workflow-runs/re-running-workflows-and-jobs).
56 | required: false
57 | default: info
58 | lines-changed-only:
59 | description: |
60 | This controls what part of the files are analyzed. The following values are accepted:
61 |
62 | - `false`: All lines in a file are analyzed.
63 | - `true`: Only lines in the diff that contain additions are analyzed.
64 | - `diff`: All lines in the diff are analyzed (including unchanged lines but not subtractions).
65 |
66 | !!! info "Important"
67 | This feature requires special permissions to perform successfully.
68 | See our [documented permissions](permissions.md)
69 | required: false
70 | default: false
71 | files-changed-only:
72 | description: |
73 | Set this option to false to analyze any source files in the repo.
74 | This is automatically enabled if [`lines-changed-only`](#lines-changed-only) is enabled.
75 |
76 | !!! info "Important"
77 | This feature requires special permissions to perform successfully.
78 | See our [documented permissions](permissions.md)
79 | required: false
80 | default: true
81 | ignore:
82 | description: |
83 | Set this option with string of path(s) to ignore.
84 |
85 | - In the case of multiple paths, you can use a pipe character (`|`)
86 | to separate the multiple paths. Multiple lines are forbidden as an input to this option;
87 | it must be a single string.
88 | - This can also have files, but the file's relative path has to be specified
89 | as well.
90 | - There is no need to use `./` for each entry; a blank string (`''`) represents
91 | the [`repo-root`](#repo-root) path.
92 | - Submodules are automatically ignored. Hidden directories (beginning with a `.`) are also ignored
93 | automatically.
94 | - Prefix a path with a bang (`!`) to make it explicitly _not_ ignored. The order of
95 | multiple paths does _not_ take precedence. The `!` prefix can be applied to
96 | a submodule's path (if desired) but not hidden directories.
97 | - **As of v2.12**, glob patterns are supported here.
98 | All asterisk characters (`*`) were previously literal.
99 | required: false
100 | default: '.github'
101 | ignore-tidy:
102 | description: |-
103 | Use this option to allow clang-tidy to ignore certain paths/files.
104 | See [`ignore`](#ignore) for more details on possible values.
105 | required: false
106 | default: '.github'
107 | ignore-format:
108 | description: |-
109 | Use this option to allow clang-format to ignore certain paths/files.
110 | See [`ignore`](#ignore) for more details on possible values.
111 | required: false
112 | default: '.github'
113 | thread-comments:
114 | description: |
115 | This controls the behavior of posted thread comments as feedback. The following options are supported:
116 |
117 | - `true`: enable the use of thread comments. This will always delete an outdated thread comment and post a new comment (triggering a notification for every comment).
118 | - `update`: update an existing thread comment if one already exists. This option does not trigger a new notification for every thread comment update.
119 | - `false`: disable the use of thread comments.
120 |
121 | !!! info "Important"
122 | This feature requires special permissions to perform successfully.
123 | See our [documented permissions](permissions.md)
124 |
125 | > [!NOTE]
126 | > If run on a private repository, then this feature is disabled because the GitHub REST API behaves differently for thread comments on a private repository.
127 | required: false
128 | default: 'false'
129 | no-lgtm:
130 | description: |
131 | Set this option to true or false to enable or disable the use of a
132 | thread comment or pull request review that basically says 'Looks Good To Me' (when all checks pass).
133 | The default value, `true` means no LGTM comment posted.
134 |
135 | See [`thread-comments`](#thread-comments), [`tidy-review`](#tidy-review),
136 | and [`format-review`](#format-review) options for further details.
137 | required: false
138 | default: true
139 | step-summary:
140 | description: |
141 | Set this option to true to append content as part of workflow's job summary.
142 |
143 | See implementation details in GitHub's documentation about
144 | [Adding a job summary](https://docs.github.com/en/actions/using-workflows/workflow-commands-for-github-actions#adding-a-job-summary).
145 | This option is independent of the [`thread-comments`](#thread-comments) option,
146 | rather this option uses the same content that the
147 | [`thread-comments`](#thread-comments) option would use.
148 |
149 | > [!NOTE]
150 | > The [`no-lgtm`](#no-lgtm) option is _not_ applied to step summaries.
151 | required: false
152 | default: false
153 | file-annotations:
154 | description: |
155 | Set this option to false to disable the use of file annotations as feedback.
156 | required: false
157 | default: true
158 | database:
159 | description: The directory containing compilation database (like compile_commands.json) file.
160 | required: false
161 | default: ""
162 | extra-args:
163 | description: |
164 | A string of extra arguments passed to clang-tidy for use as compiler arguments.
165 | Multiple arguments are separated by spaces so the argument name and value should
166 | use an `=` sign instead of a space.
167 |
168 | !!! example
169 |
170 | ``` yaml
171 | extra-args: '-std=c++17 -Wall'
172 | ```
173 | This will be passed to clang-tidy as multiple `--extra-arg` options:
174 | ```
175 | clang-tidy --extra-arg=-std=c++17 --extra-arg=-Wall
176 | ```
177 | required: false
178 | default: ""
179 | tidy-review:
180 | description: |
181 | Set this option to `true` to enable Pull Request reviews from clang-tidy.
182 |
183 | !!! info "Important"
184 | This feature requires special permissions to perform successfully.
185 | See our [documented permissions](permissions.md).
186 |
187 | See also [the PR review feature caveats](pr-review-caveats.md).
188 |
189 | > [!NOTE]
190 | > The [`no-lgtm`](#no-lgtm) option is applicable to Pull Request reviews.
191 | required: false
192 | default: false
193 | format-review:
194 | description: |
195 | Set this option to `true` to enable Pull Request reviews from clang-format.
196 |
197 | !!! info "Important"
198 | This feature requires special permissions to perform successfully.
199 | See our [documented permissions](permissions.md).
200 |
201 | See also [the PR review feature caveats](pr-review-caveats.md).
202 |
203 | > [!NOTE]
204 | > The [`no-lgtm`](#no-lgtm) option is applicable to Pull Request reviews.
205 | required: false
206 | default: false
207 | passive-reviews:
208 | description: |
209 | Set this option to `true` to prevent Pull Request reviews from approving or requesting changes.
210 | default: false
211 | required: false
212 | jobs:
213 | description: |
214 | The number of jobs to run in parallel.
215 | If less than or equal to 0, the number of jobs is set to
216 | use the number of all available CPU cores.
217 | required: false
218 | default: 0
219 | outputs:
220 | checks-failed:
221 | description: An integer that can be used as a boolean value to indicate if any checks failed by clang-tidy and clang-format.
222 | value: ${{ steps.cpp-linter-unix.outputs.checks-failed || steps.cpp-linter-windows.outputs.checks-failed }}
223 | clang-tidy-checks-failed:
224 | description: An integer that can be used as a boolean value to indicate if any checks failed by clang-tidy only.
225 | value: ${{ steps.cpp-linter-unix.outputs.clang-tidy-checks-failed || steps.cpp-linter-windows.outputs.clang-tidy-checks-failed }}
226 | clang-format-checks-failed:
227 | description: An integer that can be used as a boolean value to indicate if any checks failed by clang-format only.
228 | value: ${{ steps.cpp-linter-unix.outputs.clang-format-checks-failed || steps.cpp-linter-windows.outputs.clang-format-checks-failed }}
229 | runs:
230 | using: "composite"
231 | steps:
232 | - name: Install python
233 | uses: actions/setup-python@v5
234 | id: setup-python
235 | with:
236 | # use python version shipped with latest Ubuntu LTS
237 | python-version: '3.10'
238 | update-environment: false
239 |
240 | - name: Install Linux clang dependencies
241 | if: runner.os == 'Linux'
242 | shell: bash
243 | run: |
244 | sudo apt-get update
245 | # First try installing from default Ubuntu repositories before trying LLVM script
246 | if ! sudo apt-get install -y clang-format-${{ inputs.version }} clang-tidy-${{ inputs.version }}; then
247 | # This LLVM script will add the relevant LLVM PPA: https://apt.llvm.org/
248 | wget https://apt.llvm.org/llvm.sh -O $GITHUB_ACTION_PATH/llvm_install.sh
249 | chmod +x $GITHUB_ACTION_PATH/llvm_install.sh
250 | if sudo $GITHUB_ACTION_PATH/llvm_install.sh ${{ inputs.version }}; then
251 | sudo apt-get install -y clang-format-${{ inputs.version }} clang-tidy-${{ inputs.version }}
252 | fi
253 | fi
254 |
255 | - name: Install MacOS clang dependencies
256 | if: runner.os == 'macOS'
257 | shell: bash
258 | continue-on-error: true
259 | run: |
260 | brew install llvm@${{ inputs.version }}
261 | ln -s "$(brew --prefix llvm@${{ inputs.version }})/bin/clang-format" "/usr/local/bin/clang-format-${{ inputs.version }}"
262 | ln -s "$(brew --prefix llvm@${{ inputs.version }})/bin/clang-tidy" "/usr/local/bin/clang-tidy-${{ inputs.version }}"
263 |
264 | - name: Setup python venv (Unix)
265 | if: runner.os == 'Linux' || runner.os == 'macOS'
266 | shell: bash
267 | run: |
268 | ${{ steps.setup-python.outputs.python-path }} -m venv "$GITHUB_ACTION_PATH/venv"
269 | source "$GITHUB_ACTION_PATH/venv/bin/activate"
270 | pip install -r "$GITHUB_ACTION_PATH/requirements.txt"
271 | clang-tools -i ${{ inputs.version }} -b
272 |
273 | - name: Run cpp-linter (Unix)
274 | id: cpp-linter-unix
275 | if: runner.os == 'Linux' || runner.os == 'macOS'
276 | shell: bash
277 | run: |
278 | source "$GITHUB_ACTION_PATH/venv/bin/activate"
279 |
280 | cpp-linter \
281 | --style="${{ inputs.style }}" \
282 | --extensions=${{ inputs.extensions }} \
283 | --tidy-checks="${{ inputs.tidy-checks }}" \
284 | --repo-root=${{ inputs.repo-root }} \
285 | --version=${{ inputs.version }} \
286 | --verbosity=${{ inputs.verbosity }} \
287 | --lines-changed-only=${{ inputs.lines-changed-only }} \
288 | --files-changed-only=${{ inputs.files-changed-only }} \
289 | --thread-comments=${{ inputs.thread-comments }} \
290 | --no-lgtm=${{ inputs.no-lgtm }} \
291 | --step-summary=${{ inputs.step-summary }} \
292 | --ignore="${{ inputs.ignore }}" \
293 | --ignore-tidy="${{ inputs.ignore-tidy }}" \
294 | --ignore-format="${{ inputs.ignore-format }}" \
295 | --database=${{ inputs.database }} \
296 | --file-annotations=${{ inputs.file-annotations }} \
297 | --extra-arg="${{ inputs.extra-args }}" \
298 | --tidy-review="${{ inputs.tidy-review }}" \
299 | --format-review="${{ inputs.format-review }}" \
300 | --passive-reviews="${{ inputs.passive-reviews }}" \
301 | --jobs=${{ inputs.jobs }}
302 |
303 | - name: Setup python venv (Windows)
304 | if: runner.os == 'Windows'
305 | shell: pwsh
306 | run: |
307 | ${{ steps.setup-python.outputs.python-path }} -m venv "$env:GITHUB_ACTION_PATH/venv"
308 | Invoke-Expression -Command "$env:GITHUB_ACTION_PATH/venv/Scripts/Activate.ps1"
309 | pip install -r "$env:GITHUB_ACTION_PATH/requirements.txt"
310 | clang-tools -i ${{ inputs.version }} -b
311 |
312 | - name: Run cpp-linter (Windows)
313 | id: cpp-linter-windows
314 | if: runner.os == 'Windows'
315 | shell: pwsh
316 | run: |
317 | Invoke-Expression -Command "$env:GITHUB_ACTION_PATH/venv/Scripts/Activate.ps1"
318 |
319 | $app = 'cpp-linter' +
320 | ' --style="${{ inputs.style }}"' +
321 | ' --extensions=${{ inputs.extensions }}' +
322 | ' --tidy-checks="${{ inputs.tidy-checks }}"' +
323 | ' --repo-root=${{ inputs.repo-root }}' +
324 | ' --version=${{ inputs.version }}' +
325 | ' --verbosity=${{ inputs.verbosity }}' +
326 | ' --lines-changed-only=${{ inputs.lines-changed-only }}' +
327 | ' --files-changed-only=${{ inputs.files-changed-only }}' +
328 | ' --thread-comments=${{ inputs.thread-comments }}' +
329 | ' --no-lgtm=${{ inputs.no-lgtm }}' +
330 | ' --step-summary=${{ inputs.step-summary }}' +
331 | ' --ignore="${{ inputs.ignore }}"' +
332 | ' --ignore-tidy="${{ inputs.ignore-tidy }}"' +
333 | ' --ignore-format="${{ inputs.ignore-format }}"' +
334 | ' --database=${{ inputs.database }}' +
335 | ' --file-annotations=${{ inputs.file-annotations }}' +
336 | ' --extra-arg="${{ inputs.extra-args }}"' +
337 | ' --tidy-review="${{ inputs.tidy-review }}"' +
338 | ' --format-review="${{ inputs.format-review }}"' +
339 | ' --passive-reviews="${{ inputs.passive-reviews }}"' +
340 | ' --jobs=${{ inputs.jobs }}'
341 |
342 | Invoke-Expression -Command $app
343 |
--------------------------------------------------------------------------------
/docs/README.rst:
--------------------------------------------------------------------------------
1 | How to build the docs
2 | =====================
3 |
4 | From the root directory of the repository, do the following to steps
5 |
6 | 1. Install docs' dependencies
7 |
8 | .. code-block:: text
9 |
10 | pip install -r docs/requirements.txt
11 |
12 | On Linux, you may need to use `pip3` instead.
13 |
14 | 2. Build the docs
15 |
16 | .. code-block:: text
17 |
18 | mkdocs build
19 |
20 | or use the following command to see changes rendered in realtime.
21 |
22 | .. code-block:: text
23 |
24 | mkdocs serve
25 |
--------------------------------------------------------------------------------
/docs/action.yml:
--------------------------------------------------------------------------------
1 | # file to hold metadata about the action.yml inputs and outputs
2 | inputs:
3 | style:
4 | minimum-version: '1.2.0'
5 | extensions:
6 | minimum-version: '1.2.0'
7 | tidy-checks:
8 | minimum-version: '1.2.0'
9 | repo-root:
10 | minimum-version: '1.2.0'
11 | version:
12 | minimum-version: '1.2.0'
13 | verbosity:
14 | minimum-version: '1.3.0'
15 | lines-changed-only:
16 | minimum-version: '1.5.0'
17 | required-permission: 'contents: read #file-changes'
18 | files-changed-only:
19 | minimum-version: '1.3.0'
20 | required-permission: 'contents: read #file-changes'
21 | ignore:
22 | minimum-version: '1.3.0'
23 | ignore-tidy:
24 | minimum-version: '2.12.0'
25 | ignore-format:
26 | minimum-version: '2.12.0'
27 | thread-comments:
28 | minimum-version: '2.6.2'
29 | required-permission: 'contents: write #thread-comments'
30 | no-lgtm:
31 | minimum-version: '2.6.2'
32 | step-summary:
33 | minimum-version: '2.6.0'
34 | file-annotations:
35 | minimum-version: '1.4.3'
36 | database:
37 | minimum-version: '1.4.0'
38 | extra-args:
39 | minimum-version: '2.1.0'
40 | tidy-review:
41 | experimental: true
42 | minimum-version: '2.9.0'
43 | required-permission: 'pull-requests: write #pull-request-reviews'
44 | format-review:
45 | minimum-version: '2.9.0'
46 | required-permission: 'pull-requests: write #pull-request-reviews'
47 | passive-reviews:
48 | minimum-version: '2.12.0'
49 | required-permission: 'pull-requests: write #pull-request-reviews'
50 | jobs:
51 | minimum-version: '2.11.0'
52 | outputs:
53 | checks-failed:
54 | minimum-version: '1.2.0'
55 | clang-tidy-checks-failed:
56 | minimum-version: '2.7.2'
57 | clang-format-checks-failed:
58 | minimum-version: '2.7.2'
59 |
--------------------------------------------------------------------------------
/docs/badge_hook.py:
--------------------------------------------------------------------------------
1 | """A mkdocs hook that injects an HTML syntax used to generate badges at build time."""
2 |
3 | import re
4 | from re import Match
5 | from mkdocs.config.defaults import MkDocsConfig
6 | from mkdocs.structure.files import Files
7 | from mkdocs.structure.pages import Page
8 |
9 |
10 | def on_page_markdown(markdown: str, *, page: Page, config: MkDocsConfig, files: Files):
11 | # Replace callback
12 | def replace(match: Match):
13 | badge_type, args = match.groups()
14 | args = args.strip()
15 | if badge_type == "version":
16 | return _badge_for_version(args, page, files)
17 | elif badge_type == "flag":
18 | return _badge_for_flags(args, page, files)
19 | elif badge_type == "permission":
20 | return _badge_for_permissions(args, page, files)
21 | elif badge_type == "default":
22 | return _badge_for_default(args, page, files)
23 |
24 | # Otherwise, raise an error
25 | raise RuntimeError(f"Unknown badge type: {badge_type}")
26 |
27 | # Find and replace all external asset URLs in current page
28 | return re.sub(r"", replace, markdown, flags=re.I | re.M)
29 |
30 |
31 | # -----------------------------------------------------------------------------
32 | # Helper functions
33 |
34 |
35 | def _badge_for_flags(arg, page: Page, files: Files):
36 | if arg == "experimental":
37 | return _badge_for_experimental(page, files)
38 | raise ValueError(f"Unsupported badge flag: {arg}")
39 |
40 |
41 | # Create badge
42 | def _badge(icon: str, text: str = ""):
43 | return "".join(
44 | [
45 | '',
46 | *([f'{icon}'] if icon else []),
47 | *([f'{text}'] if text else []),
48 | "",
49 | ]
50 | )
51 |
52 |
53 | # Create badge for version
54 | def _badge_for_version(text: str, page: Page, files: Files):
55 | icon = "material-tag-outline"
56 | href = "https://github.com/cpp-linter/cpp-linter-action/releases/" + (
57 | f"v{text}" if text[0:1].isdigit() else text
58 | )
59 | return _badge(
60 | icon=f'[:{icon}:]({href} "minimum version")',
61 | text=f'[{text}]({href} "minimum version")',
62 | )
63 |
64 |
65 | # Create badge for default value
66 | def _badge_for_default(text: str, page: Page, files: Files):
67 | return _badge(icon="Default", text=f"`#!yaml {text}`")
68 |
69 |
70 | # Create badge for required value flag
71 | def _badge_for_permissions(args: str, page: Page, files: Files):
72 | match_permission = re.match(r"([^#]+)(.*)", args)
73 | if match_permission is None:
74 | raise ValueError(f"failed to parse permissions from {args}")
75 | permission, link = match_permission.groups()[:2]
76 | permission = permission.strip()
77 | link = "permissions.md" + link
78 | icon = "material-lock"
79 | return _badge(
80 | icon=f'[:{icon}:]({link} "required permissions")',
81 | text=f'[`#!yaml {permission}`]({link} "required permission")',
82 | )
83 |
84 |
85 | # Create badge for experimental flag
86 | def _badge_for_experimental(page: Page, files: Files):
87 | icon = "material-flask-outline"
88 | return _badge(icon=f":{icon}:{{ .mdx-badge--heart }}", text="experimental")
89 |
--------------------------------------------------------------------------------
/docs/contributing-guidelines.md:
--------------------------------------------------------------------------------
1 | ---
2 | hide:
3 | - toc
4 | ---
5 |
6 | {%
7 | include-markdown "../CONTRIBUTING.md"
8 | %}
9 |
--------------------------------------------------------------------------------
/docs/examples/demo/.clang-format:
--------------------------------------------------------------------------------
1 | ---
2 | Language: Cpp
3 | BasedOnStyle: WebKit
4 |
--------------------------------------------------------------------------------
/docs/examples/demo/.clang-tidy:
--------------------------------------------------------------------------------
1 | ---
2 | Checks: 'clang-diagnostic-*,clang-analyzer-*,-*,performance-*,bugprone-*,clang-analyzer-*,mpi-*,misc-*,readability-*'
3 | WarningsAsErrors: ''
4 | HeaderFilterRegex: ''
5 | AnalyzeTemporaryDtors: false
6 | FormatStyle: 'file'
7 | CheckOptions:
8 | - key: bugprone-argument-comment.CommentBoolLiterals
9 | value: '0'
10 | - key: bugprone-argument-comment.CommentCharacterLiterals
11 | value: '0'
12 | - key: bugprone-argument-comment.CommentFloatLiterals
13 | value: '0'
14 | - key: bugprone-argument-comment.CommentIntegerLiterals
15 | value: '0'
16 | - key: bugprone-argument-comment.CommentNullPtrs
17 | value: '0'
18 | - key: bugprone-argument-comment.CommentStringLiterals
19 | value: '0'
20 | - key: bugprone-argument-comment.CommentUserDefinedLiterals
21 | value: '0'
22 | - key: bugprone-argument-comment.IgnoreSingleArgument
23 | value: '0'
24 | - key: bugprone-argument-comment.StrictMode
25 | value: '0'
26 | - key: bugprone-assert-side-effect.AssertMacros
27 | value: assert
28 | - key: bugprone-assert-side-effect.CheckFunctionCalls
29 | value: '0'
30 | - key: bugprone-dangling-handle.HandleClasses
31 | value: 'std::basic_string_view;std::experimental::basic_string_view'
32 | - key: bugprone-dynamic-static-initializers.HeaderFileExtensions
33 | value: ',h,hh,hpp,hxx'
34 | - key: bugprone-exception-escape.FunctionsThatShouldNotThrow
35 | value: ''
36 | - key: bugprone-exception-escape.IgnoredExceptions
37 | value: ''
38 | - key: bugprone-misplaced-widening-cast.CheckImplicitCasts
39 | value: '0'
40 | - key: bugprone-not-null-terminated-result.WantToUseSafeFunctions
41 | value: '1'
42 | - key: bugprone-signed-char-misuse.CharTypdefsToIgnore
43 | value: ''
44 | - key: bugprone-sizeof-expression.WarnOnSizeOfCompareToConstant
45 | value: '1'
46 | - key: bugprone-sizeof-expression.WarnOnSizeOfConstant
47 | value: '1'
48 | - key: bugprone-sizeof-expression.WarnOnSizeOfIntegerExpression
49 | value: '0'
50 | - key: bugprone-sizeof-expression.WarnOnSizeOfThis
51 | value: '1'
52 | - key: bugprone-string-constructor.LargeLengthThreshold
53 | value: '8388608'
54 | - key: bugprone-string-constructor.WarnOnLargeLength
55 | value: '1'
56 | - key: bugprone-suspicious-enum-usage.StrictMode
57 | value: '0'
58 | - key: bugprone-suspicious-missing-comma.MaxConcatenatedTokens
59 | value: '5'
60 | - key: bugprone-suspicious-missing-comma.RatioThreshold
61 | value: '0.200000'
62 | - key: bugprone-suspicious-missing-comma.SizeThreshold
63 | value: '5'
64 | - key: bugprone-suspicious-string-compare.StringCompareLikeFunctions
65 | value: ''
66 | - key: bugprone-suspicious-string-compare.WarnOnImplicitComparison
67 | value: '1'
68 | - key: bugprone-suspicious-string-compare.WarnOnLogicalNotComparison
69 | value: '0'
70 | - key: bugprone-too-small-loop-variable.MagnitudeBitsUpperLimit
71 | value: '16'
72 | - key: bugprone-unhandled-self-assignment.WarnOnlyIfThisHasSuspiciousField
73 | value: '1'
74 | - key: bugprone-unused-return-value.CheckedFunctions
75 | value: '::std::async;::std::launder;::std::remove;::std::remove_if;::std::unique;::std::unique_ptr::release;::std::basic_string::empty;::std::vector::empty'
76 | - key: cert-dcl16-c.NewSuffixes
77 | value: 'L;LL;LU;LLU'
78 | - key: cert-oop54-cpp.WarnOnlyIfThisHasSuspiciousField
79 | value: '0'
80 | - key: cppcoreguidelines-explicit-virtual-functions.IgnoreDestructors
81 | value: '1'
82 | - key: cppcoreguidelines-non-private-member-variables-in-classes.IgnoreClassesWithAllMemberVariablesBeingPublic
83 | value: '1'
84 | - key: google-readability-braces-around-statements.ShortStatementLines
85 | value: '1'
86 | - key: google-readability-function-size.StatementThreshold
87 | value: '800'
88 | - key: google-readability-namespace-comments.ShortNamespaceLines
89 | value: '10'
90 | - key: google-readability-namespace-comments.SpacesBeforeComments
91 | value: '2'
92 | - key: misc-definitions-in-headers.HeaderFileExtensions
93 | value: ',h,hh,hpp,hxx'
94 | - key: misc-definitions-in-headers.UseHeaderFileExtension
95 | value: '1'
96 | - key: misc-throw-by-value-catch-by-reference.CheckThrowTemporaries
97 | value: '1'
98 | - key: misc-unused-parameters.StrictMode
99 | value: '0'
100 | - key: modernize-loop-convert.MaxCopySize
101 | value: '16'
102 | - key: modernize-loop-convert.MinConfidence
103 | value: reasonable
104 | - key: modernize-loop-convert.NamingStyle
105 | value: CamelCase
106 | - key: modernize-pass-by-value.IncludeStyle
107 | value: llvm
108 | - key: modernize-replace-auto-ptr.IncludeStyle
109 | value: llvm
110 | - key: modernize-use-nullptr.NullMacros
111 | value: 'NULL'
112 | - key: performance-faster-string-find.StringLikeClasses
113 | value: 'std::basic_string'
114 | - key: performance-for-range-copy.AllowedTypes
115 | value: ''
116 | - key: performance-for-range-copy.WarnOnAllAutoCopies
117 | value: '0'
118 | - key: performance-inefficient-string-concatenation.StrictMode
119 | value: '0'
120 | - key: performance-inefficient-vector-operation.EnableProto
121 | value: '0'
122 | - key: performance-inefficient-vector-operation.VectorLikeClasses
123 | value: '::std::vector'
124 | - key: performance-move-const-arg.CheckTriviallyCopyableMove
125 | value: '1'
126 | - key: performance-move-constructor-init.IncludeStyle
127 | value: llvm
128 | - key: performance-no-automatic-move.AllowedTypes
129 | value: ''
130 | - key: performance-type-promotion-in-math-fn.IncludeStyle
131 | value: llvm
132 | - key: performance-unnecessary-copy-initialization.AllowedTypes
133 | value: ''
134 | - key: performance-unnecessary-value-param.AllowedTypes
135 | value: ''
136 | - key: performance-unnecessary-value-param.IncludeStyle
137 | value: llvm
138 | - key: readability-braces-around-statements.ShortStatementLines
139 | value: '0'
140 | - key: readability-else-after-return.WarnOnUnfixable
141 | value: '1'
142 | - key: readability-function-size.BranchThreshold
143 | value: '4294967295'
144 | - key: readability-function-size.LineThreshold
145 | value: '4294967295'
146 | - key: readability-function-size.NestingThreshold
147 | value: '4294967295'
148 | - key: readability-function-size.ParameterThreshold
149 | value: '4294967295'
150 | - key: readability-function-size.StatementThreshold
151 | value: '800'
152 | - key: readability-function-size.VariableThreshold
153 | value: '4294967295'
154 | - key: readability-identifier-naming.IgnoreFailedSplit
155 | value: '0'
156 | - key: readability-implicit-bool-conversion.AllowIntegerConditions
157 | value: '0'
158 | - key: readability-implicit-bool-conversion.AllowPointerConditions
159 | value: '0'
160 | - key: readability-inconsistent-declaration-parameter-name.IgnoreMacros
161 | value: '1'
162 | - key: readability-inconsistent-declaration-parameter-name.Strict
163 | value: '0'
164 | - key: readability-magic-numbers.IgnoredFloatingPointValues
165 | value: '1.0;100.0;'
166 | - key: readability-magic-numbers.IgnoredIntegerValues
167 | value: '1;2;3;4;'
168 | - key: readability-redundant-member-init.IgnoreBaseInCopyConstructors
169 | value: '0'
170 | - key: readability-redundant-smartptr-get.IgnoreMacros
171 | value: '1'
172 | - key: readability-redundant-string-init.StringNames
173 | value: '::std::basic_string'
174 | - key: readability-simplify-boolean-expr.ChainedConditionalAssignment
175 | value: '0'
176 | - key: readability-simplify-boolean-expr.ChainedConditionalReturn
177 | value: '0'
178 | - key: readability-simplify-subscript-expr.Types
179 | value: '::std::basic_string;::std::basic_string_view;::std::vector;::std::array'
180 | - key: readability-static-accessed-through-instance.NameSpecifierNestingThreshold
181 | value: '3'
182 | - key: readability-uppercase-literal-suffix.IgnoreMacros
183 | value: '1'
184 | - key: readability-uppercase-literal-suffix.NewSuffixes
185 | value: ''
186 | ...
187 |
--------------------------------------------------------------------------------
/docs/examples/demo/CMakeLists.txt:
--------------------------------------------------------------------------------
1 | cmake_minimum_required(VERSION 3.15)
2 |
3 | # Set the project name to your project name
4 | project(demo C CXX)
5 |
6 | set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
7 |
8 | add_executable(demo_app
9 | ${CMAKE_BINARY_SOURCE_DIR}demo.hpp
10 | ${CMAKE_BINARY_SOURCE_DIR}demo.cpp
11 | )
12 | target_include_directories(demo_app PUBLIC ${CMAKE_BINARY_SOURCE_DIR})
13 |
--------------------------------------------------------------------------------
/docs/examples/demo/compile_flags.txt:
--------------------------------------------------------------------------------
1 | -Wall
2 | -Werror
3 |
--------------------------------------------------------------------------------
/docs/examples/demo/demo.cpp:
--------------------------------------------------------------------------------
1 | /** This is a very ugly test code (doomed to fail linting) */
2 | #include "demo.hpp"
3 | #include
4 |
5 |
6 |
7 |
8 | int main(){
9 |
10 | for (;;) break;
11 |
12 |
13 | printf("Hello world!\n");
14 |
15 |
16 |
17 |
18 | return 0;}
19 |
--------------------------------------------------------------------------------
/docs/examples/demo/demo.hpp:
--------------------------------------------------------------------------------
1 | #pragma once
2 |
3 |
4 |
5 | class Dummy {
6 | char* useless;
7 | int numb;
8 | Dummy() :numb(0), useless("\0"){}
9 |
10 | public:
11 | void *not_useful(char *str){useless = str;}
12 | };
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 | struct LongDiff
32 | {
33 |
34 | long diff;
35 |
36 | };
37 |
--------------------------------------------------------------------------------
/docs/examples/index.md:
--------------------------------------------------------------------------------
1 |
2 | [style]: ../inputs-outputs.md#style
3 | [tidy-checks]: ../inputs-outputs.md#tidy-checks
4 | [thread-comments]: ../inputs-outputs.md#thread-comments
5 |
6 | # Recipes
7 |
8 | Here are some example workflows to get started quickly.
9 |
10 | === "only clang-tidy"
11 |
12 | ``` yaml
13 | --8<-- "docs/examples/only-clang-tidy.yml"
14 | ```
15 |
16 | 1. See also [`style`][style]
17 | 2. See also [`tidy-checks`][tidy-checks]
18 |
19 | === "only clang-format"
20 |
21 | ``` yaml
22 | --8<-- "docs/examples/only-clang-format.yml"
23 | ```
24 |
25 | 1. See also [`style`][style]
26 | 2. See also [`tidy-checks`][tidy-checks]
27 |
28 | === "only PR comments"
29 |
30 | ``` yaml
31 | --8<-- "docs/examples/only-PR-comments.yml"
32 | ```
33 |
34 | 1. See also our [token permissions document](../permissions.md)
35 | 2. See also [`style`][style]
36 | 3. See also [`tidy-checks`][tidy-checks]
37 | 4. See also [`thread-comments`][thread-comments]
38 |
--------------------------------------------------------------------------------
/docs/examples/only-PR-comments.yml:
--------------------------------------------------------------------------------
1 | name: cpp-linter
2 | on:
3 | pull_request:
4 | branches: [main, master, develop]
5 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
6 | push:
7 | branches: [main, master, develop]
8 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
9 |
10 | jobs:
11 | cpp-linter:
12 | runs-on: ubuntu-latest
13 | permissions: # (1)!
14 | pull-requests: write
15 | steps:
16 | - uses: actions/checkout@v4
17 |
18 | # ... optionally setup build env to create a compilation database
19 |
20 | - uses: cpp-linter/cpp-linter-action@v2
21 | id: linter
22 | env:
23 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
24 | with:
25 | style: 'file' # Use .clang-format config file. (2)
26 | tidy-checks: '' # Use .clang-tidy config file. (3)
27 | # only 'update' a single comment in a pull request's thread. (4)
28 | thread-comments: ${{ github.event_name == 'pull_request' && 'update' }}
29 |
30 | - name: Fail fast?!
31 | if: steps.linter.outputs.checks-failed > 0
32 | run: exit 1
33 |
--------------------------------------------------------------------------------
/docs/examples/only-clang-format.yml:
--------------------------------------------------------------------------------
1 | name: cpp-linter
2 | on:
3 | pull_request:
4 | branches: [main, master, develop]
5 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
6 | push:
7 | branches: [main, master, develop]
8 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
9 |
10 | jobs:
11 | cpp-linter:
12 | runs-on: ubuntu-latest
13 | steps:
14 | - uses: actions/checkout@v4
15 |
16 | # ... optionally setup build env to create a compilation database
17 |
18 | - uses: cpp-linter/cpp-linter-action@v2
19 | id: linter
20 | env:
21 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
22 | with:
23 | style: 'file' # Use .clang-format config file. (1)
24 | tidy-checks: '-*' # disable clang-tidy checks. (2)
25 |
26 | - name: Fail fast?!
27 | if: steps.linter.outputs.clang-format-checks-failed > 0
28 | run: exit 1
29 |
--------------------------------------------------------------------------------
/docs/examples/only-clang-tidy.yml:
--------------------------------------------------------------------------------
1 | name: cpp-linter
2 | on:
3 | pull_request:
4 | branches: [main, master, develop]
5 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
6 | push:
7 | branches: [main, master, develop]
8 | paths: ['**.c', '**.cpp', '**.h', '**.hpp', '**.cxx', '**.hxx', '**.cc', '**.hh', '**CMakeLists.txt', 'meson.build', '**.cmake']
9 |
10 | jobs:
11 | cpp-linter:
12 | runs-on: ubuntu-latest
13 | steps:
14 | - uses: actions/checkout@v4
15 |
16 | # ... optionally setup build env to create a compilation database
17 |
18 | - uses: cpp-linter/cpp-linter-action@v2
19 | id: linter
20 | env:
21 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
22 | with:
23 | style: '' # disable clang-format checks. (1)
24 | tidy-checks: '' # Use .clang-tidy config file. (2)
25 |
26 | - name: Fail fast?!
27 | if: steps.linter.outputs.clang-tidy-checks-failed > 0
28 | run: exit 1
29 |
--------------------------------------------------------------------------------
/docs/gen_io_doc.py:
--------------------------------------------------------------------------------
1 | from pathlib import Path
2 | from typing import Union, Dict, Any
3 | import yaml
4 | import mkdocs_gen_files
5 |
6 | FILENAME = "inputs-outputs.md"
7 |
8 | with mkdocs_gen_files.open(FILENAME, "w") as io_doc:
9 | action_yml = Path(__file__).parent.parent / "action.yml"
10 | action_doc = Path(__file__).parent / "action.yml"
11 | a_dict: Dict[str, Any] = yaml.safe_load(action_yml.read_bytes())
12 | b_dict: Dict[str, Dict[str, Any]] = yaml.safe_load(action_doc.read_bytes())
13 |
14 | # extract info we need from a_dict and merge into b_dict
15 | for info_key in b_dict:
16 | assert info_key in a_dict and isinstance(a_dict[info_key], dict)
17 | for k, v in a_dict[info_key].items():
18 | if k not in b_dict[info_key]:
19 | print(
20 | "::error file=docs/action.yml,title={title}::{message}".format(
21 | title=f"Undocumented {info_key} field `{k}` in actions.yml",
22 | message=(
23 | f"Field '{k}' not found in docs/action.yml mapping:"
24 | ),
25 | ),
26 | info_key
27 | )
28 | continue
29 | b_dict[info_key][k].update(v)
30 |
31 | doc = "".join(
32 | [
33 | "---\ntitle: Inputs and Outputs\n---\n\n" "\n\n",
37 | "# Inputs and Outputs\n\n",
38 | "These are the action inputs and outputs offered by cpp-linter-action.\n",
39 | ]
40 | )
41 | assert "inputs" in b_dict
42 | doc += "\n## Inputs\n"
43 | for action_input, input_metadata in b_dict["inputs"].items():
44 | doc += f"### `{action_input}`\n\n"
45 |
46 | if "minimum-version" not in input_metadata:
47 | print(
48 | "\n::warning file={name}title={title}::{message}".format(
49 | name="docs/action.yml",
50 | title="Input's minimum-version not found",
51 | message="minimum-version not set for input:",
52 | ),
53 | action_input,
54 | )
55 | else:
56 | min_ver = input_metadata["minimum-version"]
57 | doc += f"\n"
58 |
59 | assert (
60 | "default" in input_metadata
61 | ), f"default value for `{action_input}` not set in action.yml"
62 | default: Union[str, bool] = input_metadata["default"]
63 | if isinstance(default, bool):
64 | default = str(default).lower()
65 | elif isinstance(default, str):
66 | default = repr(default) # add quotes around value
67 | doc += f"\n"
68 |
69 | if "experimental" in input_metadata and input_metadata["experimental"] is True:
70 | doc += "\n"
71 |
72 | if "required-permission" in input_metadata:
73 | permission = input_metadata["required-permission"]
74 | doc += f"\n"
75 |
76 | assert (
77 | "description" in input_metadata
78 | ), f"`{action_input}` description not found in action.yml"
79 | doc += "\n" + input_metadata["description"] + "\n"
80 |
81 | assert "outputs" in b_dict
82 | doc += (
83 | "\n## Outputs\n\nThis action creates 3 output variables. Even if the linting "
84 | "checks fail for source files this action will still pass, but users' CI "
85 | "workflows can use this action's outputs to exit the workflow early if that is "
86 | "desired.\n"
87 | )
88 | for action_output, output_metadata in b_dict["outputs"].items():
89 | doc += f"\n### `{action_output}`\n\n"
90 |
91 | if "minimum-version" not in output_metadata:
92 | print(
93 | "\n::warning file={name}title={title}::{message}".format(
94 | name="docs/action.yml",
95 | title="Output's minimum-version not found",
96 | message="minimum-version not set for output:",
97 | ),
98 | action_output,
99 | )
100 | else:
101 | min_ver = output_metadata["minimum-version"]
102 | doc += f"\n"
103 |
104 | assert (
105 | "description" in output_metadata
106 | ), f"`{action_output}` description not found in action.yml"
107 | doc += "\n" + output_metadata["description"] + "\n"
108 |
109 | print(doc, file=io_doc)
110 |
111 | mkdocs_gen_files.set_edit_path(FILENAME, "gen_io_doc.py")
112 |
--------------------------------------------------------------------------------
/docs/images/annotations-clang-format.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/annotations-clang-format.png
--------------------------------------------------------------------------------
/docs/images/annotations-clang-tidy.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/annotations-clang-tidy.png
--------------------------------------------------------------------------------
/docs/images/comment.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/comment.png
--------------------------------------------------------------------------------
/docs/images/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/favicon.ico
--------------------------------------------------------------------------------
/docs/images/format-review.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/format-review.png
--------------------------------------------------------------------------------
/docs/images/format-suggestion.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/format-suggestion.png
--------------------------------------------------------------------------------
/docs/images/logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/logo.png
--------------------------------------------------------------------------------
/docs/images/step-summary.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/step-summary.png
--------------------------------------------------------------------------------
/docs/images/tidy-review.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cpp-linter/cpp-linter-action/530737f357d479227961c26554c59a4167c552a4/docs/images/tidy-review.png
--------------------------------------------------------------------------------
/docs/index.md:
--------------------------------------------------------------------------------
1 | [file-annotations]: inputs-outputs.md#file-annotations
2 | [thread-comments]: inputs-outputs.md#thread-comments
3 | [step-summary]: inputs-outputs.md#step-summary
4 | [tidy-review]: inputs-outputs.md#tidy-review
5 | [format-review]: inputs-outputs.md#format-review
6 |
7 | [io-doc]: inputs-outputs.md
8 | [recipes-doc]: examples/index.md
9 |
10 | [format-annotations-preview]: images/annotations-clang-format.png
11 | [tidy-annotations-preview]: images/annotations-clang-tidy.png
12 | [thread-comment-preview]: images/comment.png
13 | [step-summary-preview]: images/step-summary.png
14 | [tidy-review-preview]: images/tidy-review.png
15 | [format-review-preview]: images/format-review.png
16 | [format-suggestion-preview]: images/format-suggestion.png
17 |
18 | {%
19 | include-markdown "../README.md"
20 | start=""
21 | end=""
22 | %}
23 |
--------------------------------------------------------------------------------
/docs/permissions.md:
--------------------------------------------------------------------------------
1 | # Token Permissions
2 |
3 | This is an exhaustive list of required permissions organized by features.
4 |
5 | !!! info "Important"
6 | The `GITHUB_TOKEN` environment variable should be supplied when running on a private repository.
7 | Otherwise the runner does not not have the privileges needed for the features mentioned here.
8 |
9 | See also [Authenticating with the `GITHUB_TOKEN`](https://docs.github.com/en/actions/reference/authentication-in-a-workflow)
10 |
11 | ## File Changes
12 |
13 | When using [`files-changed-only`](inputs-outputs.md#files-changed-only) or
14 | [`lines-changed-only`](inputs-outputs.md#lines-changed-only) to get the list
15 | of file changes for a CI event, the following permissions are needed:
16 |
17 | === "`#!yaml on: push`"
18 |
19 | For [push events](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#push)
20 |
21 | ```yaml
22 | permissions:
23 | contents: read # (1)!
24 | ```
25 |
26 | 1. This permission is also needed to download files if the repository is not
27 | checked out before running cpp-linter.
28 |
29 | === "`#!yaml on: pull_request`"
30 |
31 | For [pull_request events](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#pull_request)
32 |
33 | ```yaml
34 | permissions:
35 | contents: read # (1)!
36 | pull-requests: read # (2)!
37 | ```
38 |
39 | 1. For pull requests, this permission is only needed to download files if
40 | the repository is not checked out before running cpp-linter.
41 | 2. Specifying `#!yaml write` is also sufficient as that is required for
42 |
43 | * posting [thread comments](#thread-comments) on pull requests
44 | * posting [pull request reviews](#pull-request-reviews)
45 |
46 | ## Thread Comments
47 |
48 | The [`thread-comments`](inputs-outputs.md#thread-comments) feature requires the following permissions:
49 |
50 | === "`#!yaml on: push`"
51 |
52 | For [push events](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#push)
53 |
54 | ```yaml
55 | permissions:
56 | metadata: read # (1)!
57 | contents: write # (2)!
58 | ```
59 |
60 | 1. needed to fetch existing comments
61 | 2. needed to post or update a commit comment. This also allows us to delete
62 | an outdated comment if needed.
63 |
64 | === "`#!yaml on: pull_request`"
65 |
66 | For [pull_request events](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#pull_request)
67 |
68 | ```yaml
69 | permissions:
70 | pull-requests: write
71 | ```
72 |
73 | ## Pull Request Reviews
74 |
75 | The [`tidy-review`](inputs-outputs.md#tidy-review), [`format-review`](inputs-outputs.md#format-review), and [`passive-reviews`](inputs-outputs.md#passive-reviews) features require the following permissions:
76 |
77 | ```yaml
78 | permissions:
79 | pull-requests: write
80 | ```
81 |
--------------------------------------------------------------------------------
/docs/pr-review-caveats.md:
--------------------------------------------------------------------------------
1 | # Pull Request Review Caveats
2 |
3 | [repository settings]: https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/enabling-features-for-your-repository/managing-github-actions-settings-for-a-repository#preventing-github-actions-from-creating-or-approving-pull-requests
4 | [organization settings]: https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/enabling-features-for-your-repository/managing-github-actions-settings-for-a-repository#preventing-github-actions-from-creating-or-approving-pull-requests
5 | [hiding a comment]: https://docs.github.com/en/communities/moderating-comments-and-conversations/managing-disruptive-comments#hiding-a-comment
6 | [resolve a conversion]: https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/reviewing-changes-in-pull-requests/commenting-on-a-pull-request#resolving-conversations
7 |
8 | [tidy-review]: inputs-outputs.md#tidy-review
9 | [format-review]: inputs-outputs.md#format-review
10 | [lines-changed-only]: inputs-outputs.md#lines-changed-only
11 | [style]: inputs-outputs.md#style
12 |
13 | !!! abstract
14 | This information is specific to GitHub Pull Requests (often abbreviated as "PR").
15 |
16 | While the Pull Request review feature has been diligently tested, there are still some caveats to
17 | beware of when using Pull Request reviews.
18 |
19 | ## Bot Permissions required
20 | The "GitHub Actions" bot may need to be allowed to approve Pull Requests.
21 | By default, the bot cannot approve Pull Request changes, only request more changes.
22 | This will show as a warning in the workflow logs if the given token (set to the
23 | environment variable `GITHUB_TOKEN`) isn't configured with the proper permissions.
24 |
25 | !!! note "See also"
26 | Refer to the GitHub documentation for [repository settings][] or [organization settings][]
27 | about adjusting the required permissions for GitHub Actions's `secrets.GITHUB_TOKEN`.
28 |
29 | See our [documented permissions](permissions.md#pull-request-reviews).
30 |
31 | ## Auto-disabled for certain event types
32 | The feature is auto-disabled for
33 |
34 | - closed Pull Requests
35 | - Pull Requests marked as "draft"
36 | - push events
37 |
38 | ## Posts a new review on each run
39 | Clang-tidy and clang-format suggestions are shown in 1 Pull Request review.
40 |
41 | - Users are encouraged to choose either [`tidy-review`][tidy-review] or [`format-review`][format-review].
42 | Enabling both will likely show duplicate or similar suggestions.
43 | Remember, clang-tidy can be configured to use the same [`style`][style] that clang-format accepts.
44 | There is no current implementation to combine suggestions from both tools (clang-tidy kind of
45 | does that anyway).
46 | - Each generated review is specific to the commit that triggered the Continuous Integration
47 | workflow.
48 | - Outdated reviews are dismissed but not marked as resolved.
49 | Also, the outdated review's summary comment is not automatically hidden.
50 | To reduce the Pull Request's thread noise, users interaction is required.
51 |
52 | !!! note "See also"
53 | Refer to GitHub's documentation about [hiding a comment][].
54 | Hiding a Pull Request review's summary comment will not resolve the suggestions in the diff.
55 | Please also refer to [resolve a conversion][] to collapse outdated or duplicate suggestions
56 | in the diff.
57 |
58 | GitHub REST API does not provide a way to hide comments or mark review suggestions as resolved.
59 |
60 | !!! tip
61 | We do support an environment variable named `CPP_LINTER_PR_REVIEW_SUMMARY_ONLY`.
62 | If the variable is set to ``true``, then the review only contains a summary comment
63 | with no suggestions posted in the diff.
64 |
65 | ## Probable non-exhaustive reviews
66 | If any suggestions did not fit within the Pull Request diff, then the review's summary comment will
67 | indicate how many suggestions were left out.
68 | The full patch of suggestions is always included as a collapsed code block in the review summary
69 | comment. This isn't a problem we can fix.
70 | GitHub won't allow review comments/suggestions to target lines that are not shown in the Pull
71 | Request diff (the summation of file differences in a Pull Request).
72 |
73 | - Users are encouraged to set [`lines-changed-only`][lines-changed-only] to `true`.
74 | This will *help* us keep the suggestions limited to lines that are shown within the Pull
75 | Request diff.
76 | However, there are still some cases where clang-format or clang-tidy will apply fixes to lines
77 | that are not within the diff.
78 | This can't be avoided because the `--line-filter` passed to the clang-tidy (and `--lines`
79 | passed to clang-format) only applies to analysis, not fixes.
80 | - Not every diagnostic from clang-tidy can be automatically fixed.
81 | Some diagnostics require user interaction/decision to properly address.
82 | - Some fixes provided might depend on what compiler is used.
83 | We have made it so clang-tidy takes advantage of any fixes provided by the compiler.
84 | Compilation errors may still prevent clang-tidy from reporting all concerns.
85 |
--------------------------------------------------------------------------------
/docs/requirements.txt:
--------------------------------------------------------------------------------
1 | markdown-gfm-admonition
2 | mkdocs
3 | mkdocs-gen-files
4 | mkdocs-include-markdown-plugin
5 | mkdocs-material
6 | pyyaml
7 |
--------------------------------------------------------------------------------
/docs/stylesheets/extra.css:
--------------------------------------------------------------------------------
1 | th {
2 | background-color: var(--md-default-fg-color--lightest);
3 | }
4 |
5 | .md-header,
6 | .md-nav--primary .md-nav__title[for="__drawer"] {
7 | background-color: #4051b5;
8 | }
9 |
10 | @keyframes heart {
11 |
12 | 0%,
13 | 40%,
14 | 80%,
15 | to {
16 | transform: scale(1)
17 | }
18 |
19 | 20%,
20 | 60% {
21 | transform: scale(1.15)
22 | }
23 | }
24 |
25 | .md-typeset .mdx-heart {
26 | animation: heart 1s infinite
27 | }
28 |
29 | .md-typeset .mdx-badge {
30 | font-size: .85em
31 | }
32 |
33 | .md-typeset .mdx-badge--heart {
34 | color: #ff4281;
35 | }
36 |
37 | .md-typeset .mdx-badge--heart.twemoji {
38 | animation: heart 1s infinite
39 | }
40 |
41 | .md-typeset .mdx-badge--right {
42 | float: right;
43 | margin-left: .35em
44 | }
45 |
46 | [dir=ltr] .md-typeset .mdx-badge__icon {
47 | border-top-left-radius: .1rem
48 | }
49 |
50 | [dir=rtl] .md-typeset .mdx-badge__icon {
51 | border-top-right-radius: .1rem
52 | }
53 |
54 | [dir=ltr] .md-typeset .mdx-badge__icon {
55 | border-bottom-left-radius: .1rem
56 | }
57 |
58 | [dir=rtl] .md-typeset .mdx-badge__icon {
59 | border-bottom-right-radius: .1rem
60 | }
61 |
62 | .md-typeset .mdx-badge__icon {
63 | background: var(--md-accent-fg-color--transparent);
64 | padding: .2rem
65 | }
66 |
67 | .md-typeset .mdx-badge__icon:last-child {
68 | border-radius: .1rem
69 | }
70 |
71 | [dir=ltr] .md-typeset .mdx-badge__text {
72 | border-top-right-radius: .1rem
73 | }
74 |
75 | [dir=rtl] .md-typeset .mdx-badge__text {
76 | border-top-left-radius: .1rem
77 | }
78 |
79 | [dir=ltr] .md-typeset .mdx-badge__text {
80 | border-bottom-right-radius: .1rem
81 | }
82 |
83 | [dir=rtl] .md-typeset .mdx-badge__text {
84 | border-bottom-left-radius: .1rem
85 | }
86 |
87 | .md-typeset .mdx-badge__text {
88 | box-shadow: 0 0 0 1px inset var(--md-accent-fg-color--transparent);
89 | padding: .2rem .3rem
90 | }
91 |
92 | .md-typeset .mdx-social {
93 | height: min(27rem, 80vw);
94 | position: relative
95 | }
96 |
97 | .md-typeset .mdx-social:hover .mdx-social__image {
98 | background-color: #e4e4e40d
99 | }
100 |
101 | .md-typeset .mdx-social__layer {
102 | margin-top: 4rem;
103 | position: absolute;
104 | transform-style: preserve-3d;
105 | transition: .25s cubic-bezier(.7, 0, .3, 1)
106 | }
107 |
108 | .md-typeset .mdx-social__layer:hover .mdx-social__label {
109 | opacity: 1
110 | }
111 |
112 | .md-typeset .mdx-social__layer:hover .mdx-social__image {
113 | background-color: #7f7f7ffc
114 | }
115 |
116 | .md-typeset .mdx-social__layer:hover~.mdx-social__layer {
117 | opacity: 0
118 | }
119 |
120 | .md-typeset .mdx-social__image {
121 | box-shadow: -.25rem .25rem .5rem #0000000d;
122 | transform: rotate(-40deg) skew(15deg, 15deg) scale(.7);
123 | transition: all .25s
124 | }
125 |
126 | .md-typeset .mdx-social__image img {
127 | display: block
128 | }
129 |
130 | .md-typeset .mdx-social__label {
131 | background-color: var(--md-default-fg-color--light);
132 | color: var(--md-default-bg-color);
133 | display: block;
134 | opacity: 0;
135 | padding: .2rem .4rem;
136 | position: absolute;
137 | transition: all .25s
138 | }
139 |
140 | .md-typeset .mdx-social:hover .mdx-social__layer:nth-child(6) {
141 | transform: translateY(-30px)
142 | }
143 |
144 | .md-typeset .mdx-social:hover .mdx-social__layer:nth-child(5) {
145 | transform: translateY(-20px)
146 | }
147 |
148 | .md-typeset .mdx-social:hover .mdx-social__layer:nth-child(4) {
149 | transform: translateY(-10px)
150 | }
151 |
152 | .md-typeset .mdx-social:hover .mdx-social__layer:nth-child(3) {
153 | transform: translateY(0)
154 | }
155 |
156 | .md-typeset .mdx-social:hover .mdx-social__layer:nth-child(2) {
157 | transform: translateY(10px)
158 | }
159 |
160 | .md-typeset .mdx-social:hover .mdx-social__layer:first-child {
161 | transform: translateY(20px)
162 | }
163 |
164 | .md-typeset .mdx-social:hover .mdx-social__layer:nth-child(0) {
165 | transform: translateY(30px)
166 | }
167 |
168 | .md-banner {
169 | color: var(--md-footer-fg-color--lighter)
170 | }
171 |
172 | .md-banner strong {
173 | white-space: nowrap
174 | }
175 |
176 | .md-banner a,
177 | .md-banner strong {
178 | color: var(--md-footer-fg-color)
179 | }
180 |
181 | .md-banner a:focus,
182 | .md-banner a:hover {
183 | color: currentcolor
184 | }
185 |
186 | .md-banner a:focus .twemoji,
187 | .md-banner a:hover .twemoji {
188 | background-color: var(--md-footer-fg-color);
189 | box-shadow: none
190 | }
191 |
192 | .md-banner .twemoji {
193 | border-radius: 100%;
194 | box-shadow: inset 0 0 0 .05rem currentcolor;
195 | display: inline-block;
196 | height: 1.2rem;
197 | padding: .25rem;
198 | transition: all .25s;
199 | vertical-align: bottom;
200 | width: 1.2rem
201 | }
202 |
203 | .md-banner .twemoji svg {
204 | display: block;
205 | max-height: none
206 | }
207 |
208 | /* annotation buttons' pulse animation */
209 | a.md-annotation__index {
210 | border-radius: 2.2ch;
211 | }
212 |
213 | @keyframes pulse {
214 | 0% {
215 | box-shadow: 0 0 0 0 var(--md-accent-fg-color);
216 | transform: scale(.95)
217 | }
218 |
219 | 75% {
220 | box-shadow: 0 0 0 .625em transparent;
221 | transform: scale(1)
222 | }
223 |
224 | to {
225 | box-shadow: 0 0 0 0 transparent;
226 | transform: scale(.95)
227 | }
228 | }
229 |
--------------------------------------------------------------------------------
/mkdocs.yml:
--------------------------------------------------------------------------------
1 | site_name: C/C++ Linter Action
2 | site_description: "Developer documentation from sources."
3 | site_url: "https://cpp-linter.github.io/cpp-linter-action"
4 | repo_url: "https://github.com/cpp-linter/cpp-linter-action"
5 | repo_name: "cpp-linter/cpp-linter-action"
6 | edit_uri: "edit/main/docs/"
7 | nav:
8 | - index.md
9 | - inputs-outputs.md
10 | - pr-review-caveats.md
11 | - permissions.md
12 | - examples/index.md
13 | - contributing-guidelines.md
14 |
15 | theme:
16 | name: material
17 | features:
18 | - navigation.top
19 | - content.tabs.link
20 | - content.tooltips
21 | - content.code.annotate
22 | - content.code.copy
23 | - content.action.view
24 | - content.action.edit
25 | - navigation.footer
26 | - search.suggest
27 | - search.share
28 | - navigation.tracking
29 | - toc.follow
30 | logo: images/logo.png
31 | favicon: images/favicon.ico
32 | icon:
33 | repo: fontawesome/brands/github
34 | palette:
35 | # Palette toggle for automatic mode
36 | - media: "(prefers-color-scheme)"
37 | primary: blue
38 | accent: cyan
39 | toggle:
40 | icon: material/brightness-auto
41 | name: Switch to light mode
42 |
43 | # Palette toggle for light mode
44 | - media: "(prefers-color-scheme: light)"
45 | scheme: default
46 | primary: blue
47 | accent: cyan
48 | toggle:
49 | icon: material/lightbulb-outline
50 | name: Switch to dark mode
51 |
52 | # Palette toggle for dark mode
53 | - media: "(prefers-color-scheme: dark)"
54 | scheme: slate
55 | primary: blue
56 | accent: cyan
57 | toggle:
58 | icon: material/lightbulb
59 | name: Switch to system preference
60 | extra:
61 | social:
62 | - icon: fontawesome/brands/github
63 | link: https://github.com/cpp-linter/cpp-linter
64 |
65 | extra_css:
66 | - stylesheets/extra.css
67 |
68 | plugins:
69 | - search
70 | - include-markdown
71 | - gen-files:
72 | scripts:
73 | - docs/gen_io_doc.py
74 |
75 | markdown_extensions:
76 | - pymdownx.superfences
77 | - pymdownx.tabbed:
78 | alternate_style: true
79 | - pymdownx.emoji:
80 | emoji_index: !!python/name:material.extensions.emoji.twemoji
81 | emoji_generator: !!python/name:material.extensions.emoji.to_svg
82 | - toc:
83 | permalink: true
84 | - pymdownx.highlight:
85 | linenums_style: pymdownx-inline
86 | - pymdownx.inlinehilite
87 | - pymdownx.snippets:
88 | check_paths: true
89 | - attr_list
90 | - admonition
91 | - markdown_gfm_admonition
92 |
93 | # Hooks
94 | hooks:
95 | - docs/badge_hook.py
96 |
--------------------------------------------------------------------------------
/requirements.txt:
--------------------------------------------------------------------------------
1 | # Install clang-tools binaries (clang-format, clang-tidy)
2 | # For details please see: https://github.com/cpp-linter/clang-tools-pip
3 | clang-tools==0.15.1
4 |
5 | # cpp-linter core Python executable package
6 | # For details please see: https://github.com/cpp-linter/cpp-linter
7 | cpp-linter==1.10.7
8 |
--------------------------------------------------------------------------------