-
-
Notifications
You must be signed in to change notification settings - Fork 629
180 lines (159 loc) · 6.96 KB
/
Copy pathbundle-size.yml
File metadata and controls
180 lines (159 loc) · 6.96 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
name: Bundle Size
permissions:
contents: read
on:
pull_request:
paths:
- 'packages/**'
- 'package.json'
- 'pnpm-lock.yaml'
- '.tool-versions'
- '.size-limit.json'
- '.github/workflows/bundle-size.yml'
- '.bundle-size-skip-branch'
jobs:
check-skip:
runs-on: ubuntu-22.04
outputs:
skip: ${{ steps.skip-check.outputs.skip }}
steps:
- name: Checkout PR branch
uses: actions/checkout@v4
- name: Check if branch should skip size check
id: skip-check
env:
BRANCH: ${{ github.head_ref }}
run: |
SKIP_FILE=".bundle-size-skip-branch"
SKIP_BRANCH=$(grep -v '^[[:space:]]*#' "$SKIP_FILE" 2>/dev/null | grep -v '^[[:space:]]*$' | tr -d '[:space:]' || echo "")
if [ "$SKIP_BRANCH" = "$BRANCH" ]; then
echo "skip=true" >> "$GITHUB_OUTPUT"
echo "::notice::Branch '$BRANCH' is set to skip size check"
else
echo "skip=false" >> "$GITHUB_OUTPUT"
fi
check-bundle-size:
needs: check-skip
if: needs.check-skip.outputs.skip != 'true'
runs-on: ubuntu-22.04
permissions:
contents: read
pull-requests: write
env:
CI_JOB_NUMBER: 1
steps:
# 1. Read the PR's runtime before switching branches, then keep that Node
# version for both base and PR builds to avoid cross-version size skew.
# Also keep the PR's size-limit config because the base branch may not have it.
- name: Checkout PR branch for runtime config
uses: actions/checkout@v4
with:
ref: ${{ github.sha }}
persist-credentials: false
# The merge commit and its two parents are enough for the base-SHA
# derivation below; no full-history checkout is needed.
fetch-depth: 2
- name: Determine base SHA from the PR merge commit
id: base-sha
env:
MERGE_SHA: ${{ github.sha }}
HEAD_SHA: ${{ github.event.pull_request.head.sha }}
run: |
# For pull_request events github.sha is the ephemeral merge commit
# (refs/pull/N/merge): the PR head merged into the base-branch tip. The
# PR-head sizes are built from this merge commit, so the base sizes must be
# built from its FIRST PARENT to share the exact same base-branch baseline.
#
# Using the live base tip (github.event.pull_request.base.sha) instead lets
# the two builds drift apart whenever the PR branch is behind the base
# branch: unrelated growth that landed on the base branch gets mis-attributed
# to the PR, producing uniform false-positive size increases across every
# tracked bundle (including OSS bundles the PR never touched).
if [ "$MERGE_SHA" = "$HEAD_SHA" ]; then
echo "::error::Bundle size check needs a mergeable PR: github.sha equals the PR head, so no merge commit exists (the branch likely conflicts with the base branch). Rebase / resolve conflicts and re-run."
exit 1
fi
read -ra parents <<< "$(git rev-list --parents -n 1 "$MERGE_SHA")"
# parents[0] = merge commit, [1] = first parent (base), [2] = second parent (head)
if [ "${#parents[@]}" -eq 0 ]; then
echo "::error::Could not read parents of github.sha ($MERGE_SHA); the commit is not reachable in this checkout. Ensure this job checks out with fetch-depth: 2 or deeper."
exit 1
fi
if [ "${#parents[@]}" -ne 3 ]; then
echo "::error::Expected github.sha ($MERGE_SHA) to be a 2-parent merge commit, found $(( ${#parents[@]} - 1 )) parent(s); cannot determine a matching base baseline. Ensure this job checks out with fetch-depth: 2 or deeper."
exit 1
fi
base_sha="${parents[1]}"
head_parent="${parents[2]}"
if [ "$head_parent" != "$HEAD_SHA" ]; then
echo "::error::Merge commit second parent ($head_parent) does not match the PR head ($HEAD_SHA); unexpected merge structure."
exit 1
fi
echo "base-sha=$base_sha" >> "$GITHUB_OUTPUT"
echo "Base baseline (merge commit first parent): $base_sha"
echo "PR head (merge commit second parent): $head_parent"
- name: Read runtime versions
id: tool-versions
uses: ./.github/actions/read-tool-versions
- name: Setup Node
uses: actions/setup-node@v4
with:
node-version: ${{ steps.tool-versions.outputs.node-version }}
- name: Setup pnpm
uses: pnpm/action-setup@v4
- name: Save size-limit config
run: cp .size-limit.json /tmp/size-limit-config.json
# 2. Get base branch sizes from the merge commit's first parent so the base
# and PR-head builds share the same base-branch baseline (see base-sha step).
- name: Checkout base branch
uses: actions/checkout@v4
with:
# Only the working tree at the base parent is needed (not its history), so
# the default shallow fetch-depth is enough; checkout@v4 fetches this SHA
# directly since it is reachable from the base branch.
ref: ${{ steps.base-sha.outputs.base-sha }}
persist-credentials: false
- name: Copy size-limit config to base branch
run: cp /tmp/size-limit-config.json .size-limit.json
- name: Install base dependencies
run: pnpm install --frozen-lockfile
- name: Build base branch
run: pnpm run build
- name: Verify build artifacts
run: |
missing=0
for pkg in react-on-rails react-on-rails-pro react-on-rails-pro-node-renderer; do
if ! ls packages/$pkg/lib/*.js >/dev/null 2>&1; then
echo "::error::Missing build artifacts in packages/$pkg/lib/"
missing=1
fi
done
if [ $missing -eq 1 ]; then
exit 1
fi
echo "All build artifacts verified"
- name: Measure base branch sizes
run: |
pnpm exec size-limit --json > /tmp/base-sizes.json
echo "Base branch sizes:"
cat /tmp/base-sizes.json
# 3. Checkout PR and set dynamic limits
- name: Checkout PR branch
uses: actions/checkout@v4
with:
ref: ${{ github.sha }}
persist-credentials: false
- name: Install PR dependencies
run: pnpm install --frozen-lockfile
- name: Set dynamic limits (base + 0.5KB)
run: node scripts/bundle-size.mjs set-limits --base /tmp/base-sizes.json
- name: Copy .size-limit.json file with limits to tmp directory
run: cp .size-limit.json /tmp/.size-limit-with-limits.json
# 4. Run the action with dynamic limits
- name: Check bundle size
uses: andresz1/size-limit-action@v1
with:
github_token: ${{ secrets.GITHUB_TOKEN }}
package_manager: pnpm
build_script: build-for-size-limit
skip_step: install