Skip to content

Commit 38f0bdb

Browse files
richarddushimeLukasWallrichCopilot
authored
[Improvement] Spell check only PR-changed files and added manual dispatch for full check (#693)
* spell check only PR changed files * Update .github/workflows/spell-check.yaml Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> * Update scripts/spell_check/check_spelling.py Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> * fix:reqs --------- Co-authored-by: Lukas Wallrich <lukas.wallrich@gmail.com> Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
1 parent 5a07e72 commit 38f0bdb

File tree

2 files changed

+96
-11
lines changed

2 files changed

+96
-11
lines changed

.github/workflows/spell-check.yaml

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,19 @@ name: Spell Check
44
# Automated Spell Checking
55
# =======================
66
# Purpose: Checks for spelling errors in pull requests using codespell
7-
# Triggers: PR opened, synchronized, or reopened
7+
# Triggers: PR opened, synchronized, or reopened; manual dispatch for full check
88
# Reports: Comments on PR with potential typos and suggestions
99

1010
on:
1111
pull_request:
1212
types: [opened, synchronize, reopened]
13+
workflow_dispatch:
14+
inputs:
15+
check_all:
16+
description: 'Check all website content (not just changed files)'
17+
required: false
18+
default: true
19+
type: boolean
1320

1421
permissions:
1522
contents: read
@@ -23,6 +30,18 @@ jobs:
2330
steps:
2431
- name: Checkout repository
2532
uses: actions/checkout@v4
33+
with:
34+
fetch-depth: 0
35+
36+
- name: Get changed files (PR only)
37+
id: changed_files
38+
if: github.event_name == 'pull_request'
39+
run: |
40+
# Get list of changed files in the PR
41+
CHANGED_FILES=$(git diff --name-only ${{ github.event.pull_request.base.sha }} ${{ github.sha }} | grep -E '\.(md|txt|html|yaml|yml|py|js|json|toml)$' || true)
42+
echo "files<<EOF" >> $GITHUB_OUTPUT
43+
echo "$CHANGED_FILES" >> $GITHUB_OUTPUT
44+
echo "EOF" >> $GITHUB_OUTPUT
2645
2746
- name: Set up Python
2847
uses: actions/setup-python@v5
@@ -36,18 +55,23 @@ jobs:
3655
3756
- name: Run Spell Check Script
3857
id: spell_check
58+
env:
59+
CHECK_ALL: ${{ github.event_name == 'workflow_dispatch' && inputs.check_all == true }}
60+
CHANGED_FILES: ${{ steps.changed_files.outputs.files }}
3961
run: |
4062
python scripts/spell_check/check_spelling.py
4163
4264
- name: Find Comment
65+
if: github.event_name == 'pull_request'
4366
uses: peter-evans/find-comment@v3
4467
id: fc
4568
with:
4669
issue-number: ${{ github.event.pull_request.number }}
4770
comment-author: 'github-actions[bot]'
48-
body-includes: Spell Check Results
71+
body-includes: Spell Check
4972

5073
- name: Create or update comment
74+
if: github.event_name == 'pull_request'
5175
uses: peter-evans/create-or-update-comment@v4
5276
with:
5377
comment-id: ${{ steps.fc.outputs.comment-id }}

scripts/spell_check/check_spelling.py

Lines changed: 70 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,10 @@
22
"""
33
Spell-check script for FORRT repository using codespell.
44
Checks for typos in pull requests and generates a formatted comment.
5+
6+
Modes:
7+
- PR mode: Only checks files changed in the pull request (CHANGED_FILES env var)
8+
- Full mode: Checks the default set of paths (content, scripts, .github, CONTRIBUTING.md, README.md) (CHECK_ALL=true env var)
59
"""
610

711
import os
@@ -10,12 +14,61 @@
1014
import json
1115
from pathlib import Path
1216

13-
def run_codespell():
17+
# Default paths to check in full mode
18+
DEFAULT_PATHS = ['content', 'scripts', 'data', '.github', 'CONTRIBUTING.md', 'README.md']
19+
20+
# File extensions to check
21+
ALLOWED_EXTENSIONS = {'.md', '.txt', '.html', '.yaml', '.yml', '.py', '.js', '.json', '.toml'}
22+
23+
24+
def get_files_to_check():
25+
"""Determine which files to check based on environment variables.
26+
27+
Returns a tuple of (paths, is_full_mode).
28+
"""
29+
check_all = os.environ.get('CHECK_ALL', 'false').lower() == 'true'
30+
changed_files_env = os.environ.get('CHANGED_FILES')
31+
32+
# If CHECK_ALL is explicitly requested, always run in full mode.
33+
if check_all:
34+
print("Running in full mode: checking default paths...", file=sys.stderr)
35+
return DEFAULT_PATHS, True
36+
37+
# If CHANGED_FILES is not provided at all, fall back to full mode
38+
# (e.g., local runs or legacy workflows).
39+
if changed_files_env is None:
40+
print("Running in full mode: checking default paths (no CHANGED_FILES provided)...", file=sys.stderr)
41+
return DEFAULT_PATHS, True
42+
43+
# CHANGED_FILES is provided but may be empty (no matching files).
44+
changed_files = changed_files_env.strip()
45+
if not changed_files:
46+
print("No spell-checkable files changed in this PR.", file=sys.stderr)
47+
return [], False
48+
49+
# PR mode: only check changed files
50+
files = [f.strip() for f in changed_files.split('\n') if f.strip()]
51+
52+
# Filter to only existing files with allowed extensions
53+
valid_files = []
54+
for f in files:
55+
path = Path(f)
56+
if path.exists() and path.suffix.lower() in ALLOWED_EXTENSIONS:
57+
valid_files.append(f)
58+
59+
if not valid_files:
60+
print("No spell-checkable files changed in this PR.", file=sys.stderr)
61+
return [], False
62+
print(f"Running in PR mode: checking {len(valid_files)} changed file(s)...", file=sys.stderr)
63+
return valid_files, False
64+
65+
66+
def run_codespell(paths):
1467
"""Run codespell and capture output."""
68+
if not paths:
69+
return "", 0
70+
1571
try:
16-
# Run codespell on specific directories to avoid themes and other large dirs
17-
# Focus on content, scripts, and GitHub workflows
18-
paths = ['content', 'scripts', '.github', 'CONTRIBUTING.md', 'README.md']
1972

2073
# Use repo root - GitHub Actions path or repo root directory
2174
repo_root = os.environ.get('GITHUB_WORKSPACE')
@@ -69,15 +122,20 @@ def parse_codespell_output(output):
69122

70123
return typos
71124

72-
def format_comment(typos):
125+
def format_comment(typos, is_full_mode=False, files_checked=None):
73126
"""Format typos as a GitHub comment."""
127+
mode_info = "all content" if is_full_mode else f"{files_checked} changed file(s)"
128+
74129
if not typos:
75130
comment = "## ✅ Spell Check Passed\n\n"
76-
comment += "No spelling issues found in this PR! 🎉"
131+
if files_checked == 0:
132+
comment += "No spell-checkable files were changed in this PR."
133+
else:
134+
comment += f"No spelling issues found when checking {mode_info}! 🎉"
77135
return comment
78136

79137
comment = "## 📝 Spell Check Results\n\n"
80-
comment += f"Found {len(typos)} potential spelling issue(s) in this PR:\n\n"
138+
comment += f"Found {len(typos)} potential spelling issue(s) when checking {mode_info}:\n\n"
81139

82140
# Group typos by file
83141
typos_by_file = {}
@@ -111,14 +169,17 @@ def main():
111169
"""Main function to run spell check and output comment."""
112170
print("Running spell check...", file=sys.stderr)
113171

172+
# Determine which files to check
173+
paths, is_full_mode = get_files_to_check()
174+
114175
# Run codespell
115-
output, returncode = run_codespell()
176+
output, returncode = run_codespell(paths)
116177

117178
# Parse output
118179
typos = parse_codespell_output(output)
119180

120181
# Format comment
121-
comment = format_comment(typos)
182+
comment = format_comment(typos, is_full_mode, len(paths) if not is_full_mode else None)
122183

123184
# Output comment for GitHub Actions
124185
# Escape special characters for GitHub Actions output

0 commit comments

Comments
 (0)