forked from BasedHardware/omi
-
Notifications
You must be signed in to change notification settings - Fork 0
268 lines (236 loc) · 10.6 KB
/
Copy pathrepo-checks.yml
File metadata and controls
268 lines (236 loc) · 10.6 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
name: Repo Checks
on:
push:
branches: main
pull_request:
branches: main
types: [opened, synchronize, reopened, edited, labeled, unlabeled]
permissions:
contents: read
pull-requests: read
concurrency:
# Metadata events (edited/labeled/unlabeled) and code events (push/synchronize)
# run disjoint job sets: `metadata-preflight` for the former, `changes`/`hygiene`
# for the latter. Sharing one cancel-in-progress group let a PR-title/body edit
# cancel an in-flight code run it shares no work with, and cancelled jobs render
# as red "fail" checks on the PR — flaky red with no code cause. Key the group by
# lane so newer-cancels-older still holds within each lane, but never across them.
group: repo-checks-${{ github.event.pull_request.number || github.ref }}-${{ github.event_name == 'pull_request' && contains(fromJSON('["edited", "labeled", "unlabeled"]'), github.event.action) && 'metadata' || 'code' }}
cancel-in-progress: true
jobs:
metadata-preflight:
name: PR Metadata Preflight
if: github.event_name == 'pull_request' && contains(fromJSON('["edited", "labeled", "unlabeled"]'), github.event.action)
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Set up Python
uses: actions/setup-python@v6
with:
python-version-file: backend/.python-version
# Metadata edits reuse the source verdict from Hygiene. These manifest
# checks consume only Python stdlib + Git; do not install code-test tools.
- name: Run current PR metadata preflight
env:
GITHUB_TOKEN: ${{ github.token }}
run: |
# The PR event payload's base-branch SHA field is frozen at whatever PR
# event last delivered it; a metadata-only edited/labeled/unlabeled event
# days later can carry a value main has long since moved past. actions/checkout
# already fetched origin/${{ github.base_ref }} live (fetch-depth: 0
# above), so diff against that instead of the stale payload field.
scripts/pr-preflight --metadata-only \
--base "origin/${{ github.base_ref }}" \
--repository "${{ github.repository }}" \
--pr-number "${{ github.event.pull_request.number }}"
changes:
name: Detect Changes
if: github.event_name != 'pull_request' || !contains(fromJSON('["edited", "labeled", "unlabeled"]'), github.event.action)
runs-on: ubuntu-latest
outputs:
diff_base: ${{ steps.changes.outputs.diff_base }}
has_arb: ${{ steps.changes.outputs.has_arb }}
has_dart: ${{ steps.changes.outputs.has_dart }}
has_firmware: ${{ steps.changes.outputs.has_firmware }}
has_format: ${{ steps.changes.outputs.has_format }}
has_python: ${{ steps.changes.outputs.has_python }}
has_workflows: ${{ steps.changes.outputs.has_workflows }}
steps:
- name: Checkout code
uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Detect changed paths
id: changes
uses: ./.github/actions/detect-changes
hygiene:
name: Hygiene
runs-on: ubuntu-latest
needs: changes
if: github.event_name != 'pull_request' || !contains(fromJSON('["edited", "labeled", "unlabeled"]'), github.event.action)
steps:
- name: Checkout code
uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Set up Python
uses: actions/setup-python@v6
with:
python-version-file: backend/.python-version
- name: Set up uv
uses: astral-sh/setup-uv@ecd24dd710f2fb0dca1693a67af11fc4a5c5ec84
with:
# See the metadata-preflight job: an exact version keeps the action from
# fetching the astral-sh/versions manifest to resolve "latest".
version: "0.11.13"
enable-cache: true
cache-dependency-glob: backend/openapi-requirements.txt
- name: Install runtime environment validator dependency
run: uv pip install --system pyyaml==6.0.1
- name: Set up Java for manifest-selected Firestore checks
uses: actions/setup-java@v5
with:
distribution: temurin
java-version: '21'
- name: Set up Bun for manifest-selected web/app checks
uses: oven-sh/setup-bun@v2
with:
bun-version: 1.3.14
- name: Save changed files
run: |
scripts/changed-files "${{ needs.changes.outputs.diff_base }}"...HEAD > /tmp/changed-files.txt
cat /tmp/changed-files.txt
- name: Run shared PR contract preflight
if: github.event_name == 'pull_request'
env:
GITHUB_TOKEN: ${{ github.token }}
run: |
scripts/pr-preflight \
--base "${{ needs.changes.outputs.diff_base }}" \
--repository "${{ github.repository }}" \
--pr-number "${{ github.event.pull_request.number }}" \
--event-payload-file "$GITHUB_EVENT_PATH"
- name: Run deterministic check manifest on main pushes
if: github.event_name != 'pull_request'
env:
PR_BODY_FILE: /tmp/main-push-commit-body.txt
GITHUB_TOKEN: ${{ github.token }}
run: |
# On main pushes there is no PR event payload. #10965 / #9744 pass
# the merge-commit body through --pr-body-file so product-invariants
# and failure-class-protocol still run. That is necessary but not
# sufficient here: this repo squashes with the commit list, not the
# PR description, so INV-* citations that already made PR Hygiene
# green disappear on the main push (see #11835). Recover the live
# (#NNNN) PR body and append it. Fail-closed is preserved: a direct
# push with no PR number still uses only the commit message.
git log -1 --format=%B HEAD > /tmp/main-push-commit-message.txt
python3 .github/scripts/pr_metadata.py \
--repository "${{ github.repository }}" \
--from-commit-body-file /tmp/main-push-commit-message.txt \
--output "$PR_BODY_FILE"
python3 .github/scripts/run_checks.py --lane ci \
--base "${{ needs.changes.outputs.diff_base }}" \
--pr-body-file "$PR_BODY_FILE"
- name: Check typed error flow-control ratchet
run: python3 .github/scripts/check_isinstance_return_ratchet.py
- name: Check desktop prod promotion policy
run: python3 .github/scripts/check-desktop-prod-promotion-policy.py
- name: Test deployment concurrency policy
run: python3 .github/scripts/check-deployment-concurrency.py --self-test
- name: Check deployment concurrency policy
run: python3 .github/scripts/check-deployment-concurrency.py
- name: Check release process guards
run: bash scripts/run-release-process-guards.sh
- name: Check GitHub Actions workflows
if: needs.changes.outputs.has_workflows == 'true'
run: |
GOBIN=/tmp/actionlint-bin go install github.com/rhysd/actionlint/cmd/actionlint@v1.7.12
mapfile -t files < <(grep -E '^\.github/workflows/.*\.ya?ml$' /tmp/changed-files.txt | while IFS= read -r f; do [ -f "$f" ] && echo "$f"; done || true)
if [ "${#files[@]}" -gt 0 ]; then
/tmp/actionlint-bin/actionlint -shellcheck "" "${files[@]}"
fi
formatting:
name: Formatting
runs-on: ubuntu-latest
needs: changes
if: needs.changes.outputs.has_format == 'true'
steps:
- name: Checkout code
uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Save changed files
run: |
scripts/changed-files "${{ needs.changes.outputs.diff_base }}"...HEAD > /tmp/changed-files.txt
cat /tmp/changed-files.txt
- name: Set up uv for Python formatting
if: needs.changes.outputs.has_python == 'true'
uses: astral-sh/setup-uv@ecd24dd710f2fb0dca1693a67af11fc4a5c5ec84
with:
version: "0.11.13"
enable-cache: true
- name: Setup Flutter
if: needs.changes.outputs.has_dart == 'true'
uses: subosito/flutter-action@v2
with:
channel: stable
# Keep formatter output reproducible across runner images and local hooks.
flutter-version: 3.44.5
cache: true
- name: Resolve Flutter dependencies for formatting
if: needs.changes.outputs.has_dart == 'true'
working-directory: app
run: flutter pub get
- name: Check Dart formatting
if: needs.changes.outputs.has_dart == 'true'
run: |
FILES=$(grep '\.dart$' /tmp/changed-files.txt | grep -v -e '\.gen\.dart$' -e '\.g\.dart$' | while IFS= read -r f; do [ -f "$f" ] && echo "$f"; done || true)
if [ -n "$FILES" ]; then
echo "$FILES" | xargs "$FLUTTER_ROOT/bin/cache/dart-sdk/bin/dart" format --line-length 120 --set-exit-if-changed --output=none
fi
- name: Check Python formatting
if: needs.changes.outputs.has_python == 'true'
run: |
FILES=$(grep 'backend/.*\.py$' /tmp/changed-files.txt | while IFS= read -r f; do [ -f "$f" ] && echo "$f"; done || true)
if [ -n "$FILES" ]; then
echo "$FILES" | xargs scripts/backend-python-format --check
fi
- name: Check ARB formatting
if: needs.changes.outputs.has_arb == 'true'
run: |
FILES=$(grep '\.arb$' /tmp/changed-files.txt | while IFS= read -r f; do [ -f "$f" ] && echo "$f"; done || true)
failed=0
for f in $FILES; do
if ! python3 -m json.tool "$f" > /dev/null 2>&1; then
echo "FAIL: $f is not valid JSON"
failed=1
continue
fi
if ! python3 -c "
import json, sys
f = sys.argv[1]
with open(f) as fh:
original = fh.read()
formatted = json.dumps(json.loads(original), indent=4, ensure_ascii=False) + '\n'
if original != formatted:
sys.exit(1)
" "$f" 2>/dev/null; then
echo "FAIL: $f not formatted with 4-space indent"
failed=1
fi
done
if [ "$failed" -eq 1 ]; then
echo "Fix: jq --indent 4 '.' <file> > tmp && mv tmp <file>"
exit 1
fi
- name: Check C/C++ formatting
if: needs.changes.outputs.has_firmware == 'true'
run: |
FILES=$(grep -E '^(omi|omiGlass)/.*\.(c|cpp|cc|cxx|h|hpp)$' /tmp/changed-files.txt | while IFS= read -r f; do [ -f "$f" ] && echo "$f"; done || true)
if [ -n "$FILES" ]; then
echo "$FILES" | xargs clang-format --dry-run --Werror
fi