-
Notifications
You must be signed in to change notification settings - Fork 1
156 lines (125 loc) · 4.87 KB
/
Copy pathgrading.yml
File metadata and controls
156 lines (125 loc) · 4.87 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
name: Grading
on:
push:
branches:
- 'user/**'
concurrency:
group: scores-update
cancel-in-progress: false
permissions:
contents: write
jobs:
grade:
runs-on: self-hosted
steps:
- name: Checkout user branch
uses: actions/checkout@v6
with:
ref: ${{ github.ref }}
fetch-depth: 0
- name: Configure git
run: |
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"
- name: Prepare database
run: |
rm -rf ../database-worktree
if git ls-remote --exit-code --heads origin database >/dev/null 2>&1; then
git fetch origin database
git worktree add --track -B database ../database-worktree origin/database
else
git worktree add -f ../database-worktree
cd ../database-worktree
git switch --orphan database
git commit --allow-empty -m "chore(actions): initialize database branch"
git push origin database
cd -
fi
- name: Get changed files
id: changed-files
uses: tj-actions/changed-files@v47
with:
json: 'true'
- name: Detect target weeks from changed files
id: targets
run: |
if [ -f "../database-worktree/info.json" ]; then
PKG_FROM_INFO=$(python3 .github/scripts/grading/read_package_from_info.py 2>/dev/null || true)
if [ -n "${PKG_FROM_INFO}" ]; then
PACKAGE="${PKG_FROM_INFO}"
fi
fi
PACKAGE_PATH="${PACKAGE//./\/}"
echo "Package: ${PACKAGE}, Package path: ${PACKAGE_PATH}"
echo "Changed files: ${{ steps.changed-files.outputs.all_changed_files }}"
WEEK_LIST=$(printf "%s\n" "${{ steps.changed-files.outputs.all_changed_files }}" | python3 .github/scripts/grading/extract_target_weeks.py "${PACKAGE}")
if [ -n "${WEEK_LIST}" ]; then
echo "has_target_weeks=true" >> "$GITHUB_OUTPUT"
echo "target_weeks=${WEEK_LIST}" >> "$GITHUB_OUTPUT"
echo "Target weeks: ${WEEK_LIST}"
else
echo "has_target_weeks=false" >> "$GITHUB_OUTPUT"
echo "target_weeks=" >> "$GITHUB_OUTPUT"
echo "No target week changes."
fi
- name: Set up Java 25
if: steps.targets.outputs.has_target_weeks == 'true'
uses: actions/setup-java@v5
with:
java-version: '25'
distribution: 'temurin'
- name: Setup Gradle
if: steps.targets.outputs.has_target_weeks == 'true'
uses: gradle/actions/setup-gradle@v6
- name: Run tests
id: run_tests
if: steps.targets.outputs.has_target_weeks == 'true'
run: |
chmod +x ./gradlew
IFS=',' read -ra WEEKS <<< "${{ steps.targets.outputs.target_weeks }}"
TEST_ARGS=()
for week in "${WEEKS[@]}"; do
TEST_ARGS+=(--tests "*Week${week}Tests")
done
./gradlew cleanTest test --continue "${TEST_ARGS[@]}"
continue-on-error: true
- name: Extract metadata
id: meta
if: steps.targets.outputs.has_target_weeks == 'true'
run: |
BRANCH="${{ github.ref_name }}"
NICKNAME="${BRANCH#user/}"
echo "nickname=${NICKNAME}" >> "$GITHUB_OUTPUT"
COMMIT_TS="${{ github.event.head_commit.timestamp }}"
COMMIT_EPOCH_MS=$(date -d "${COMMIT_TS}" +%s%3N)
echo "commit_epoch_ms=${COMMIT_EPOCH_MS}" >> "$GITHUB_OUTPUT"
- name: Update database
if: steps.targets.outputs.has_target_weeks == 'true'
run: |
python3 .github/scripts/grading/update_result.py "${{ steps.meta.outputs.nickname }}" "${{ steps.meta.outputs.commit_epoch_ms }}" "${{ steps.targets.outputs.target_weeks }}"
cd ../database-worktree
git add ".study" ".docs"
if git diff --cached --quiet; then
echo "No changes to database branch."
exit 0
fi
git commit -m "docs(actions): update results ${NICKNAME}"
MAX_RETRY=3
for i in $(seq 1 $MAX_RETRY); do
if git push origin HEAD:database; then
echo "Push succeeded on attempt ${i}."
exit 0
fi
echo "Push failed (attempt ${i}/${MAX_RETRY}). Pulling with rebase..."
if ! git pull --rebase origin database; then
echo "Rebase conflict detected. Aborting."
git rebase --abort || true
exit 1
fi
done
echo "All ${MAX_RETRY} push attempts failed."
exit 1
- name: Fail workflow if tests failed
if: steps.targets.outputs.has_target_weeks == 'true' && steps.run_tests.outcome == 'failure'
run: |
exit 1