pithos/.github/workflows/desktop-macos.yml
Local Dev f4d38bc4d6 Pithos desktop: macOS builds on a GitHub-hosted Mac
macOS packages can only be made on macOS. The workflow builds dmg and zip
for Apple Silicon and Intel, ad-hoc signed (Apple Silicon will not start
an unsigned app; there is no Developer ID yet, so Gatekeeper asks once),
then smoke-tests the packaged server, the macOS s3d install and the pty
before uploading the files with their checksums.
2026-10-05 01:31:03 +02:00

77 lines
3 KiB
YAML

# macOS builds of the Pithos desktop app. Windows and Linux are built on
# those systems directly; this runs on a GitHub-hosted Mac because macOS
# packages can only be made on macOS. Builds are ad-hoc signed (no Apple
# Developer ID), so Apple Silicon runs them and Gatekeeper asks once.
name: desktop-macos
on:
workflow_dispatch:
push:
tags: ['v*']
jobs:
build:
strategy:
fail-fast: false
matrix:
include:
- arch: arm64
runner: macos-14
- arch: x64
runner: macos-13
runs-on: ${{ matrix.runner }}
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 22
- name: Install
run: npm ci --no-audit --no-fund
- name: Tests
run: npm test
- name: Build
env:
CSC_IDENTITY_AUTO_DISCOVERY: 'false'
run: npx electron-builder --mac dmg zip --${{ matrix.arch }} --publish never
# The packaged server starts, installs the pinned macOS s3d (checksum
# checked) and runs it, and the bundled pty spawns: what a first run needs.
- name: Smoke test the packaged app
run: |
APP=$(ls -d dist/desktop/mac*/Pithos.app | head -1)
codesign --verify --deep --strict "$APP" && echo "signature ok"
cat > smoke.mjs <<'JS'
const asar = process.argv[2];
const { createPithos } = await import(`file://${asar}/core/server.js`);
const { installS3d } = await import(`file://${asar}/core/binary.js`);
const { execFileSync } = await import('node:child_process');
const os = await import('node:os');
const p = await createPithos({ host: '127.0.0.1', port: 0, hostName: 'desktop', binDir: os.tmpdir() + '/pithos-bin' });
console.log('server up', new URL(p.url).host);
const bin = await installS3d(os.tmpdir() + '/pithos-bin');
console.log(execFileSync(bin, ['version'], { encoding: 'utf8' }).split('\n')[0]);
const ptyMod = await import(`file://${asar}.unpacked/node_modules/@lydell/node-pty/lib/index.js`).catch(() => null);
if (ptyMod) {
const pty = ptyMod.default || ptyMod;
const t = pty.spawn('/bin/sh', ['-c', 'echo pty-ok'], {});
await new Promise((r) => { let o = ''; t.onData((d) => { o += d; }); t.onExit(() => { console.log('pty:', o.trim()); r(); }); });
} else console.log('pty: loaded on demand');
await p.close();
JS
ELECTRON_RUN_AS_NODE=1 "$APP/Contents/MacOS/Pithos" smoke.mjs "$APP/Contents/Resources/app.asar"
- name: Checksums
run: cd dist/desktop && shasum -a 256 *.dmg *.zip | tee SHA256SUMS-${{ matrix.arch }}.txt
- uses: actions/upload-artifact@v4
with:
name: pithos-macos-${{ matrix.arch }}
path: |
dist/desktop/*.dmg
dist/desktop/*.zip
dist/desktop/SHA256SUMS-*.txt
retention-days: 14