Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions .github/chainguard/update-uv-lock.sts.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
issuer: https://token.actions.githubusercontent.com
subject_pattern: "repo:github-community-projects/cleanowners:pull_request"
claim_pattern:
job_workflow_ref: "github-community-projects/cleanowners/.github/workflows/update-uv-lock.yml@.*"

permissions:
contents: write
2 changes: 2 additions & 0 deletions .github/linters/.codespellrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
[codespell]
ignore-words-list = astroid
2 changes: 1 addition & 1 deletion .github/linters/.jscpd.json
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
{
"threshold": 25,
"ignore": ["test*"],
"ignore": ["test*", "**/.venv/**"],
"absolute": true
}
2 changes: 1 addition & 1 deletion .github/workflows/auto-labeler.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ jobs:
permissions:
contents: read
pull-requests: write
uses: github/ospo-reusable-workflows/.github/workflows/auto-labeler.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
uses: github-community-projects/ospo-reusable-workflows/.github/workflows/auto-labeler.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
with:
config-name: release-drafter.yml
secrets:
Expand Down
12 changes: 7 additions & 5 deletions .github/workflows/copilot-setup-steps.yml
Original file line number Diff line number Diff line change
Expand Up @@ -30,11 +30,13 @@ jobs:
with:
persist-credentials: false

- name: Set up Python
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
- name: Install uv
uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098 # v7.3.1
with:
python-version: 3.12
enable-cache: true

- name: Set up Python
run: uv python install 3.14

- name: Install dependencies
run: |
pip install -r requirements.txt -r requirements-test.txt
run: uv sync --frozen --python 3.14
2 changes: 1 addition & 1 deletion .github/workflows/pr-title.yml
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,6 @@ jobs:
contents: read
pull-requests: read
statuses: write
uses: github/ospo-reusable-workflows/.github/workflows/pr-title.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
uses: github-community-projects/ospo-reusable-workflows/.github/workflows/pr-title.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
secrets:
github-token: ${{ secrets.GITHUB_TOKEN }}
14 changes: 7 additions & 7 deletions .github/workflows/python-ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,20 +18,20 @@ jobs:
runs-on: ubuntu-latest
strategy:
matrix:
python-version: [3.11, 3.12]
python-version: [3.11, 3.12, 3.13, 3.14]

steps:
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
persist-credentials: false
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
- name: Install uv
uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098 # v7.3.1
with:
python-version: ${{ matrix.python-version }}
enable-cache: true
- name: Set up Python ${{ matrix.python-version }}
run: uv python install ${{ matrix.python-version }}
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install -r requirements.txt -r requirements-test.txt
run: uv sync --frozen --python ${{ matrix.python-version }}
- name: Lint with flake8 and pylint
run: |
make lint
Expand Down
6 changes: 3 additions & 3 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ jobs:
permissions:
contents: write
pull-requests: read
uses: github/ospo-reusable-workflows/.github/workflows/release.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
uses: github-community-projects/ospo-reusable-workflows/.github/workflows/release.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
with:
publish: true
release-config-name: release-drafter.yml
Expand All @@ -25,7 +25,7 @@ jobs:
packages: write
id-token: write
attestations: write
uses: github/ospo-reusable-workflows/.github/workflows/release-image.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
uses: github-community-projects/ospo-reusable-workflows/.github/workflows/release-image.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
with:
image-name: ${{ github.repository }}
full-tag: ${{ needs.release.outputs.full-tag }}
Expand All @@ -40,7 +40,7 @@ jobs:
permissions:
contents: read
discussions: write
uses: github/ospo-reusable-workflows/.github/workflows/release-discussion.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
uses: github-community-projects/ospo-reusable-workflows/.github/workflows/release-discussion.yaml@3b691dff6b68489c8548e1295d125c93c9c29a4e
with:
full-tag: ${{ needs.release.outputs.full-tag }}
body: ${{ needs.release.outputs.body }}
Expand Down
8 changes: 5 additions & 3 deletions .github/workflows/super-linter.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,12 @@ jobs:
with:
fetch-depth: 0
persist-credentials: false
- name: Install uv
uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098 # v7.3.1
with:
enable-cache: true
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install -r requirements.txt -r requirements-test.txt
run: uv sync --frozen
- name: Lint Code Base
uses: super-linter/super-linter@61abc07d755095a68f4987d1c2c3d1d64408f1f9 # v8.5.0
env:
Expand Down
42 changes: 42 additions & 0 deletions .github/workflows/update-uv-lock.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
---
name: Update uv.lock

on:
pull_request:
paths:
- pyproject.toml

permissions:
id-token: write

jobs:
update-lock:
if: github.event.pull_request.user.login == 'dependabot[bot]'
runs-on: ubuntu-latest
steps:
- name: Get GitHub App token via octo-sts
uses: octo-sts/action@f603d3be9d8dd9871a265776e625a27b00effe05 # v1.1.1
id: octo-sts
with:
scope: github-community-projects/cleanowners
identity: update-uv-lock

- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
ref: ${{ github.head_ref }}
persist-credentials: true # Use the workflow temporary token from octo-sts to allow pushing changes back to the dependabot branch
token: ${{ steps.octo-sts.outputs.token }}

- name: Install uv
uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098 # v7.3.1

- name: Update uv.lock
run: uv lock

- name: Commit and push updated lockfile
run: |
git config user.name "octo-sts[bot]"
git config user.email "801323+octo-sts[bot]@users.noreply.github.com"
git add uv.lock
git diff --cached --quiet || git commit -s -m "chore(deps): update uv.lock"
git push
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -144,4 +144,4 @@ cython_debug/
.DS_Store

# AI
.claude/
**/.claude/*.local.*
10 changes: 7 additions & 3 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@ FROM python:3.14.0-slim@sha256:0aecac02dc3d4c5dbb024b753af084cafe41f5416e02193f1
LABEL org.opencontainers.image.source https://github.com/github-community-projects/cleanowners

WORKDIR /action/workspace
COPY requirements.txt *.py /action/workspace/
COPY pyproject.toml uv.lock *.py /action/workspace/

RUN python3 -m pip install --no-cache-dir --no-deps -r requirements.txt \
COPY --from=ghcr.io/astral-sh/uv:0.10.9@sha256:10902f58a1606787602f303954cea099626a4adb02acbac4c69920fe9d278f82 /uv /uvx /bin/

RUN uv sync --frozen --no-dev --no-editable \
&& apt-get -y update \
&& apt-get -y install --no-install-recommends git=1:2.47.3-0+deb13u1 \
&& rm -rf /var/lib/apt/lists/*
Expand All @@ -16,5 +18,7 @@ RUN python3 -m pip install --no-cache-dir --no-deps -r requirements.txt \
HEALTHCHECK --interval=30s --timeout=10s --start-period=10s --retries=3 \
CMD python3 -c "import os,sys; sys.exit(0 if os.path.exists('/action/workspace/cleanowners.py') else 1)"

ENV PYTHONUNBUFFERED=1

CMD ["/action/workspace/cleanowners.py"]
ENTRYPOINT ["python3", "-u"]
ENTRYPOINT ["uv", "run"]
14 changes: 7 additions & 7 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
.PHONY: test
test:
pytest -v --cov=. --cov-config=.coveragerc --cov-fail-under=80 --cov-report term-missing
uv run pytest -v --cov=. --cov-config=.coveragerc --cov-fail-under=80 --cov-report term-missing

.PHONY: clean
clean:
Expand All @@ -9,10 +9,10 @@ clean:
.PHONY: lint
lint:
# stop the build if there are Python syntax errors or undefined names
flake8 . --config=.github/linters/.flake8 --count --select=E9,F63,F7,F82 --show-source
uv run flake8 . --config=.github/linters/.flake8 --count --select=E9,F63,F7,F82 --show-source
# exit-zero treats all errors as warnings. The GitHub editor is 127 chars wide
flake8 . --config=.github/linters/.flake8 --count --exit-zero --max-complexity=15 --max-line-length=150
isort --settings-file=.github/linters/.isort.cfg .
pylint --rcfile=.github/linters/.python-lint --fail-under=9.0 *.py
mypy --config-file=.github/linters/.mypy.ini *.py
black .
uv run flake8 . --config=.github/linters/.flake8 --count --exit-zero --max-complexity=15 --max-line-length=150
uv run isort --settings-file=.github/linters/.isort.cfg .
uv run pylint --rcfile=.github/linters/.python-lint --fail-under=9.0 *.py
uv run mypy --config-file=.github/linters/.mypy.ini *.py
uv run black .
5 changes: 3 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -169,11 +169,12 @@ jobs:
## Local usage without Docker

1. Make sure you have at least Python3.11 installed
1. Install [uv](https://docs.astral.sh/uv/getting-started/installation/)
1. Copy `.env-example` to `.env`
1. Fill out the `.env` file with a _token_ from a user that has access to the organization (listed below). Tokens should have at least write:org and write:repository access.
1. Fill out the `.env` file with the configuration parameters you want to use
1. `pip3 install -r requirements.txt`
1. Run `python3 ./cleanowners.py`, which will output everything in the terminal
1. `uv sync`
1. Run `uv run python3 ./cleanowners.py`, which will output everything in the terminal

## License

Expand Down
23 changes: 23 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
[project]
name = "cleanowners"
version = "2.0.0"
description = "GitHub Action that cleans up CODEOWNERS files by removing users who are no longer part of the organization."
requires-python = ">=3.11"
dependencies = [
"github3-py==4.0.1",
"python-dotenv==1.2.1",
"requests==2.32.5",
]

[dependency-groups]
dev = [
"black==26.1.0",
"flake8==7.3.0",
"isort==7.0.0",
"mypy==1.19.1",
"mypy-extensions==1.1.0",
"pylint==4.0.5",
"pytest==9.0.2",
"pytest-cov==7.0.0",
"types-requests==2.32.4.20260107",
]
8 changes: 0 additions & 8 deletions requirements-test.txt

This file was deleted.

28 changes: 0 additions & 28 deletions requirements.txt

This file was deleted.

7 changes: 4 additions & 3 deletions test_markdown_writer.py
Original file line number Diff line number Diff line change
Expand Up @@ -209,9 +209,10 @@ def test_noop_when_env_var_not_set(self):
with patch.dict(os.environ, {}, clear=False):
os.environ.pop("GITHUB_STEP_SUMMARY", None)
mock_file = mock_open()
with patch("builtins.open", mock_file), patch(
"builtins.print"
) as mock_print:
with (
patch("builtins.open", mock_file),
patch("builtins.print") as mock_print,
):
write_step_summary(
pull_count=0,
eligble_for_pr_count=0,
Expand Down
Loading