-
Notifications
You must be signed in to change notification settings - Fork 0
141 lines (130 loc) · 7.42 KB
/
Copy pathamicode-release.yml
File metadata and controls
141 lines (130 loc) · 7.42 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
# AMICODE fork: tag-triggered binary release.
# Push a tag `v<base-version>-amicode.<n>` (e.g. v1.17.3-amicode.4) → builds
# linux-x64 (native) + darwin-arm64 and linux-arm64 (both cross-compiled),
# verifies the channel gate (AMICODE-PATCHES.md gotcha 2), and publishes a
# GitHub release with sha256s. Replaces the hand-rolled releases (amicode.1–.3).
name: amicode-release
on:
push:
tags:
- "v*-amicode.*"
workflow_dispatch:
inputs:
tag:
description: "Existing tag to build and release (e.g. v1.17.3-amicode.4)"
required: true
concurrency: ${{ github.workflow }}-${{ github.ref }}
permissions:
contents: write
jobs:
release:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
ref: ${{ inputs.tag || github.ref_name }}
- uses: ./.github/actions/setup-bun
- name: Derive base version from tag
id: v
run: |
TAG="${{ inputs.tag || github.ref_name }}"
VERSION="${TAG#v}"; VERSION="${VERSION%%-amicode.*}"
echo "tag=$TAG" >> "$GITHUB_OUTPUT"
echo "version=$VERSION" >> "$GITHUB_OUTPUT"
- name: Build linux-x64 (native) + darwin-arm64, linux-arm64 (cross)
working-directory: packages/opencode
env:
OPENCODE_VERSION: ${{ steps.v.outputs.version }}
# NOT "latest": that compiles the web UI with VITE_OPENCODE_CHANNEL=prod,
# defaulting newLayoutDesigns OFF and hiding every amicode surface
# (gotcha 2 in AMICODE-PATCHES.md; bit releases amicode.1/.2).
OPENCODE_CHANNEL: dev
# linux-arm64 serves devcontainers on Apple Silicon (amicode ships it as
# a third lean .vsix target). Bun cross-compiles it from this x64 runner,
# same as darwin-arm64.
OPENCODE_BUILD_TARGETS: "opencode-linux-x64,opencode-darwin-arm64,opencode-linux-arm64"
run: bun run script/build.ts
- name: Gate check — amicode UI default must be ON in every binary
run: |
set -euo pipefail
check() {
local BIN="$1"
test -f "$BIN"
# Shape A (current, since ead3274d3 "lock down appearance settings; force v2 layout"):
# settings.tsx sets `newLayoutDesigns: createMemo(() => true)` — unconditional, no
# channel dependency. Minifies to `newLayoutDesigns:<F>(()=>!0)`.
if grep -aq 'newLayoutDesigns:[A-Za-z$_]\{1,8\}(()=>!0)' "$BIN"; then
echo "OK: gate hardcoded ON (unconditional memo) in $BIN"
return 0
fi
# `if`, not `grep && { ... }` — under `set -e` a failing grep in an AND-list aborts
# the step with no message, which would silently pass as a green gate.
if grep -aq 'newLayoutDesigns:[A-Za-z$_]\{1,8\}(()=>!1)' "$BIN"; then
echo "FAIL: unconditional memo is OFF (=>!1) in $BIN"
exit 1
fi
# Shape C (1.18.10 merge): the memo survived but the property went SHORTHAND —
# `newLayoutDesigns:<VAR>` with `<VAR>=[wrapper](()=>!0)` at the assignment site
# (the wrapper call is optional — it minifies differently per target). The ON
# probe is an `if`, not `grep && { }` — a failing grep in an AND-list aborts the
# step under set -e with no message (that silent abort bit amicode.1's first run).
local VAR
VAR=$( { grep -aoh 'newLayoutDesigns:[$_A-Za-z0-9]\{1,20\}[,}]' "$BIN" || true; } | head -1 | sed 's/newLayoutDesigns://; s/[,}]//')
if test -n "$VAR"; then
# `\$`, never `$`, inside these double-quoted classes: `$_A` is a
# valid shell name and `set -u` kills the step on expansion
# (bit amicode.1's second run).
if grep -aq "[^A-Za-z0-9_\$]${VAR}=[\$_A-Za-z]\{0,8\}(()=>!1)" "$BIN"; then
echo "FAIL: shorthand memo is OFF (=>!1) in $BIN — built with channel latest/prod?"; exit 1
fi
if grep -aq "[^A-Za-z0-9_\$]${VAR}=[\$_A-Za-z]\{0,8\}(()=>!0)" "$BIN"; then
echo "OK: gate hardcoded ON (shorthand memo ${VAR}=…(()=>!0)) in $BIN"
return 0
fi
echo "FAIL: shorthand memo var ${VAR} found but its assignment matches neither (()=>!0) nor (()=>!1) in $BIN (minifier drift?)"
exit 1
fi
# Shape B (legacy, channel-gated): `...general?.newLayoutDesigns,<VAR>)` with
# `<VAR>=!0` (on) / `=!1` (off). Kept so this check still works if the setting is
# ever wired back to the channel default.
# `|| true` — under `set -o pipefail` a no-match grep would abort the step here with
# no message, so the "pattern not found" diagnostic below could never fire.
VAR=$( { grep -aoh 'newLayoutDesigns,[A-Za-z$_]\{1,8\})' "$BIN" || true; } | head -1 | sed 's/newLayoutDesigns,//; s/)//')
test -n "$VAR" || { echo "FAIL: gate pattern not found in $BIN (minifier drift? update this check)"; exit 1; }
grep -aq "[^A-Za-z0-9_\$]${VAR}=!0" "$BIN" \
|| { echo "FAIL: channel gate OFF (${VAR}=!1) in $BIN — built with channel latest/prod?"; exit 1; }
echo "OK: gate ON (${VAR}=!0) in $BIN"
}
LIN=packages/opencode/dist/opencode-linux-x64/bin/opencode
check "$LIN"
check packages/opencode/dist/opencode-darwin-arm64/bin/opencode
check packages/opencode/dist/opencode-linux-arm64/bin/opencode
# Only the native binary can be executed here; the two cross builds are
# grep-gated above and smoke-tested downstream (amicode's boot-smoke job
# runs linux-arm64 natively on an arm runner).
GOT=$("$LIN" --version)
[ "$GOT" = "${{ steps.v.outputs.version }}" ] || { echo "FAIL: --version=$GOT expected ${{ steps.v.outputs.version }}"; exit 1; }
- name: Package assets (flat 'opencode' inside, per amicode fetcher contract)
run: |
set -euo pipefail
mkdir -p out
for ARCH in x64 arm64; do
cp "packages/opencode/dist/opencode-linux-$ARCH/bin/opencode" out/opencode
tar -czf "out/opencode-linux-$ARCH.tar.gz" -C out opencode && rm out/opencode
done
(cd packages/opencode/dist/opencode-darwin-arm64/bin && zip -qj "$GITHUB_WORKSPACE/out/opencode-darwin-arm64.zip" opencode)
sha256sum out/opencode-linux-x64.tar.gz out/opencode-linux-arm64.tar.gz out/opencode-darwin-arm64.zip | sed 's|out/||' | tee out/SHA256SUMS.txt
- name: Create GitHub release
env:
GH_TOKEN: ${{ github.token }}
run: |
set -euo pipefail
TAG="${{ steps.v.outputs.tag }}"
NOTES="opencode fork binary for amicode bundling. Built by the amicode-release workflow from \`$TAG\` @ $GITHUB_SHA; base opencode ${{ steps.v.outputs.version }}; OPENCODE_CHANNEL=dev (UI gate verified ON in every binary).
Assets: linux-x64 (native, smoke-tested), linux-arm64 and darwin-arm64 (cross-compiled from Linux — not smoke-tested here; amicode's boot-smoke covers linux-arm64 natively).
sha256 (pin these in amicode's opencode.lock.json):
\`\`\`
$(cat out/SHA256SUMS.txt)
\`\`\`"
gh release create "$TAG" --title "Amicode binary $TAG" --notes "$NOTES" \
out/opencode-linux-x64.tar.gz out/opencode-linux-arm64.tar.gz out/opencode-darwin-arm64.zip