# Desktop Module — ontoref-desktop (Tauri shell) build / sign / bundle # ===================================================================== # The desktop crate is a sibling sub-repo (ontoref/desktop, ADR-054/048); these # recipes drive it from code/ so all project recipes live in one place. Every # recipe operates inside ../desktop. Recipes are namespaced `desktop-*` to avoid # collisions with the protocol recipes (build/check/test/lint). desktop := "../desktop" dt_npm_cache := "/tmp/npm-cache-ontoref" dt_tauri := "npm_config_cache=" + dt_npm_cache + " npx --yes @tauri-apps/cli@latest" dt_icon_svg := "../assets/branding/ontoref-icon-static.svg" dt_app := "target/release/bundle/macos/Ontoref.app" dt_dmg := "target/release/bundle/dmg/Ontoref_0.1.0_aarch64.dmg" dt_linux_image := "ontoref-desktop-linux:22.04" dt_builder_image := "reg.librecloud.online/ontoref/desktop-builder:22.04" # ── Dev oracles ─────────────────────────────────────────────────────────────── # Type-check the desktop crate desktop-check: cd {{desktop}} && cargo check --all-targets # Clippy (deny warnings) — default + nats feature desktop-lint: #!/usr/bin/env bash set -euo pipefail cd {{desktop}} cargo clippy --all-targets -- -D warnings cargo clippy --features nats --all-targets -- -D warnings # Run desktop unit tests desktop-test: cd {{desktop}} && cargo test # ── Icons ───────────────────────────────────────────────────────────────────── # Regenerate the icon set from the brand SVG desktop-icons: #!/usr/bin/env bash set -euo pipefail cd {{desktop}} rsvg-convert -w 1024 -h 1024 --keep-aspect-ratio {{dt_icon_svg}} -o /tmp/ontoref-icon-1024.png {{dt_tauri}} icon /tmp/ontoref-icon-1024.png -o icons # ── Bundles ───────────────────────────────────────────────────────────────────── # macOS ad-hoc bundle — no Apple credentials; runs on this Mac, Gatekeeper-blocked elsewhere desktop-build: cd {{desktop}} && {{dt_tauri}} build # macOS Developer ID signed + notarized bundle — requires APPLE_* env (see desktop-signing-help) desktop-build-signed: #!/usr/bin/env bash set -euo pipefail cd {{desktop}} if [[ -z "${APPLE_SIGNING_IDENTITY:-}" ]]; then echo "✗ APPLE_SIGNING_IDENTITY is not set — run 'just desktop-signing-help'." >&2 exit 1 fi echo "→ signing as: ${APPLE_SIGNING_IDENTITY}" if [[ -z "${APPLE_API_KEY:-}" && -z "${APPLE_PASSWORD:-}" ]]; then echo " (no APPLE_API_KEY / APPLE_PASSWORD — signed but NOT notarized)" >&2 fi {{dt_tauri}} build # Build the Linux bundle Docker image locally (once; cached afterwards) desktop-bundle-linux-image: cd {{desktop}} && docker build -f Dockerfile.linux -t {{dt_linux_image}} . # Linux .deb/.rpm/AppImage via Docker (webkit2gtk can't cross-compile from macOS) desktop-bundle-linux: desktop-bundle-linux-image #!/usr/bin/env bash set -euo pipefail cd {{desktop}} docker run --rm \ -v "$PWD":/src \ -e CARGO_TARGET_DIR=/src/target-linux \ {{dt_linux_image}} \ tauri build echo "→ bundles in: desktop/target-linux/release/bundle/{deb,rpm,appimage}/" find target-linux/release/bundle -maxdepth 2 -type f \( -name '*.deb' -o -name '*.rpm' -o -name '*.AppImage' \) 2>/dev/null || true # Build + push the multi-arch (amd64+arm64) builder image used by CI desktop-builder-push: #!/usr/bin/env bash set -euo pipefail cd {{desktop}} docker buildx create --name ontoref-multi --driver docker-container --bootstrap --use 2>/dev/null || docker buildx use ontoref-multi docker buildx build --builder ontoref-multi --platform linux/amd64,linux/arm64 \ -f Dockerfile.linux -t {{dt_builder_image}} --push . # Windows .msi/.exe — requires a Windows host or CI (no viable cross-build from macOS/Linux) desktop-bundle-windows: @echo "Windows bundling needs a Windows host with WiX/NSIS — it cannot be" @echo "cross-built from macOS or Linux (WebView2 + installer tooling are Windows-only)." @echo "" @echo "Use the GitHub Actions matrix (desktop/.github/workflows/bundle.yml)," @echo "or a windows-latest job — see 'just desktop-ci-windows-snippet'." # Print a GitHub Actions job that bundles + uploads the Windows installer desktop-ci-windows-snippet: @echo ' windows-bundle:' @echo ' runs-on: windows-latest' @echo ' defaults: { run: { working-directory: desktop } }' @echo ' steps:' @echo ' - uses: actions/checkout@v4' @echo ' - uses: dtolnay/rust-toolchain@stable' @echo ' - uses: actions/setup-node@v4' @echo ' with: { node-version: 20 }' @echo ' - run: npx @tauri-apps/cli@latest build' @echo ' - uses: actions/upload-artifact@v4' @echo ' with:' @echo ' name: ontoref-desktop-windows' @echo ' path: desktop/target/release/bundle/**/*.{msi,exe}' # ── Signing / notarization ────────────────────────────────────────────────────── # Persist notarization credentials in the keychain (run once; then desktop-build-signed needs no APPLE_PASSWORD) desktop-notary-store profile="ontoref-notary": xcrun notarytool store-credentials "{{profile}}" \ --apple-id "${APPLE_ID:?set APPLE_ID}" \ --team-id "${APPLE_TEAM_ID:?set APPLE_TEAM_ID}" \ --password "${APPLE_PASSWORD:?set APPLE_PASSWORD (app-specific password)}" # Inspect the built .app signature + Gatekeeper + staple state desktop-verify-signature: #!/usr/bin/env bash cd {{desktop}} echo "── codesign ──" codesign -dvvv {{dt_app}} 2>&1 | grep -iE "Authority|flags|Signature|Identifier" || true echo "── Gatekeeper (spctl) ──" spctl -a -vvv -t install {{dt_app}} 2>&1 || true echo "── staple ──" xcrun stapler validate {{dt_dmg}} 2>&1 || true # Show what to provide for Developer ID signing + notarization desktop-signing-help: #!/usr/bin/env bash echo "Provide via environment (never committed):" echo " export APPLE_SIGNING_IDENTITY=\"Developer ID Application: NAME (TEAMID)\"" echo " export APPLE_ID=\"you@example.com\"" echo " export APPLE_TEAM_ID=\"TEAMID\"" echo " export APPLE_PASSWORD=\"app-specific-password\" # OR App Store Connect API key:" echo " # export APPLE_API_KEY=KEYID APPLE_API_ISSUER=UUID APPLE_API_KEY_PATH=~/keys/AuthKey_KEYID.p8" echo "" echo "Current signing identities in your keychain:" security find-identity -v -p codesigning 2>&1 || true