Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
36 changes: 16 additions & 20 deletions .beads/issues.jsonl

Large diffs are not rendered by default.

10 changes: 5 additions & 5 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ name: Build

on:
push:
branches: [main, 003-standalone-client]
branches: [main, 003-standalone-client, 005-macos-signed-release]
pull_request:
branches: [main, 003-standalone-client]
branches: [main, 003-standalone-client, 005-macos-signed-release]

jobs:
build:
Expand All @@ -15,9 +15,9 @@ jobs:
os: [ubuntu-latest, macos-latest, windows-latest]

steps:
- uses: actions/checkout@v4
- uses: actions/checkout@v6

- uses: actions/setup-python@v5
- uses: actions/setup-python@v6
with:
python-version: "3.12"

Expand All @@ -39,7 +39,7 @@ jobs:
shell: pwsh

- name: Upload artifact
uses: actions/upload-artifact@v4
uses: actions/upload-artifact@v7
with:
name: risus-${{ matrix.os }}
path: dist/risus*
98 changes: 86 additions & 12 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,25 +10,25 @@ permissions:

jobs:
build:
name: Build (${{ matrix.os }})
name: Build & Sign (${{ matrix.os }})
runs-on: ${{ matrix.os }}
strategy:
matrix:
include:
- os: ubuntu-latest
artifact: risus-linux-x86_64
binary: dist/risus
- os: macos-latest
artifact: risus-macos-arm64
binary: dist/risus
- os: windows-latest
artifact: risus-windows-x86_64.exe
binary: dist/risus.exe

env:
APPLE_CERTIFICATE: ${{ secrets.APPLE_CERTIFICATE }}

steps:
- uses: actions/checkout@v4
- uses: actions/checkout@v6

- uses: actions/setup-python@v5
- uses: actions/setup-python@v6
with:
python-version: "3.12"

Expand All @@ -47,8 +47,72 @@ jobs:
run: Rename-Item dist\risus.exe ${{ matrix.artifact }}
shell: pwsh

- name: Compute checksum (Unix)
if: runner.os != 'Windows'
- name: Assert signing secrets
if: runner.os == 'macOS' && github.ref_type == 'tag'
run: |
if [ -z "$APPLE_CERTIFICATE" ]; then
echo "ERROR: APPLE_CERTIFICATE secret is not configured. Refusing to publish an unsigned release artifact."
echo "Configure the 6 Apple signing secrets in repository Settings → Secrets before pushing a release tag."
echo "See specs/005-macos-signed-release/quickstart.md for setup instructions."
exit 1
fi

- name: Import signing certificate
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
uses: apple-actions/import-codesign-certs@v7
with:
p12-file-base64: ${{ secrets.APPLE_CERTIFICATE }}
p12-password: ${{ secrets.APPLE_CERTIFICATE_PASSWORD }}

- name: Sign binary
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
run: |
codesign --force --verbose --timestamp \
--sign "$APPLE_SIGNING_IDENTITY" \
--options=runtime --no-strict \
--entitlements build/entitlements.plist \
dist/risus-macos-arm64
env:
APPLE_SIGNING_IDENTITY: ${{ secrets.APPLE_SIGNING_IDENTITY }}

- name: Package signed binary
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
run: |
mkdir -p /tmp/risus-macos-arm64
cp dist/risus-macos-arm64 /tmp/risus-macos-arm64/
ditto -c -k --keepParent /tmp/risus-macos-arm64 dist/risus-macos-arm64.zip

- name: Notarize
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
timeout-minutes: 15
run: |
echo "$APPLE_API_KEY_CONTENT" | base64 --decode > /tmp/apple_api_key.p8
xcrun notarytool submit dist/risus-macos-arm64.zip \
--wait \
--key /tmp/apple_api_key.p8 \
--key-id "$APPLE_API_KEY_ID" \
--issuer "$APPLE_API_ISSUER_ID"
env:
APPLE_API_KEY_CONTENT: ${{ secrets.APPLE_API_KEY_CONTENT }}
APPLE_API_KEY_ID: ${{ secrets.APPLE_API_KEY_ID }}
APPLE_API_ISSUER_ID: ${{ secrets.APPLE_API_ISSUER_ID }}

- name: Clean up API key
if: always() && runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
run: rm -f /tmp/apple_api_key.p8

- name: Verify signature
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
run: codesign --verify --deep --strict --verbose=2 dist/risus-macos-arm64

- name: Compute checksum (macOS, signed)
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
run: |
cd dist
sha256sum risus-macos-arm64.zip > risus-macos-arm64.zip.sha256

- name: Compute checksum (non-signed)
if: runner.os != 'Windows' && (runner.os != 'macOS' || env.APPLE_CERTIFICATE == '')
run: |
cd dist
sha256sum ${{ matrix.artifact }} > ${{ matrix.artifact }}.sha256
Expand All @@ -60,8 +124,18 @@ jobs:
"$hash ${{ matrix.artifact }}" | Out-File -FilePath dist\${{ matrix.artifact }}.sha256 -Encoding ascii
shell: pwsh

- name: Upload artifact (macOS, signed)
if: runner.os == 'macOS' && env.APPLE_CERTIFICATE != ''
uses: actions/upload-artifact@v7
with:
name: ${{ matrix.artifact }}
path: |
dist/risus-macos-arm64.zip
dist/risus-macos-arm64.zip.sha256

- name: Upload artifact
uses: actions/upload-artifact@v4
if: runner.os != 'macOS' || env.APPLE_CERTIFICATE == ''
uses: actions/upload-artifact@v7
with:
name: ${{ matrix.artifact }}
path: |
Expand All @@ -73,16 +147,16 @@ jobs:
needs: build
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/checkout@v6

- name: Download all artifacts
uses: actions/download-artifact@v4
uses: actions/download-artifact@v8
with:
path: release-assets
merge-multiple: true

- name: Create GitHub Release
uses: softprops/action-gh-release@v2
uses: softprops/action-gh-release@v3
with:
files: |
release-assets/*
Expand Down
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# MCP secrets
.mcp.json

# Oh My Claude Code state - block all, then carve out what to share
!.omc/
.omc/*
Expand Down
Loading