Skip to content

Commit ea08722

Browse files
committed
Add preview workflows for Windows and Linux bundles
1 parent 40e2718 commit ea08722

14 files changed

Lines changed: 208 additions & 40 deletions

.github/workflows/ci.yml

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,12 +27,24 @@ jobs:
2727
run: npm run typecheck
2828

2929
rust-quality:
30-
runs-on: macos-latest
30+
strategy:
31+
fail-fast: false
32+
matrix:
33+
platform:
34+
- ubuntu-22.04
35+
- macos-latest
36+
- windows-latest
37+
38+
runs-on: ${{ matrix.platform }}
3139

3240
steps:
3341
- name: Checkout
3442
uses: actions/checkout@v4
3543

44+
- name: Install Linux system deps
45+
if: matrix.platform == 'ubuntu-22.04'
46+
run: bash scripts/install-tauri-linux-deps.sh
47+
3648
- name: Setup Rust (stable + rustfmt)
3749
uses: dtolnay/rust-toolchain@stable
3850
with:
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
name: Preview Bundles
2+
3+
on:
4+
workflow_dispatch:
5+
inputs:
6+
version:
7+
description: Version label to validate against package metadata
8+
required: false
9+
type: string
10+
include-macos:
11+
description: Also build the existing macOS bundles
12+
required: false
13+
default: true
14+
type: boolean
15+
16+
jobs:
17+
build-preview:
18+
strategy:
19+
fail-fast: false
20+
matrix:
21+
include:
22+
- platform: ubuntu-22.04
23+
os: linux
24+
bundles: deb,appimage
25+
artifact_name: trajectory-linux-bundles
26+
artifact_paths: |
27+
src-tauri/target/release/bundle/deb/*.deb
28+
src-tauri/target/release/bundle/appimage/*.AppImage
29+
- platform: windows-latest
30+
os: windows
31+
bundles: nsis,msi
32+
artifact_name: trajectory-windows-bundles
33+
artifact_paths: |
34+
src-tauri/target/release/bundle/nsis/*.exe
35+
src-tauri/target/release/bundle/msi/*.msi
36+
- platform: macos-latest
37+
os: macos
38+
bundles: app,dmg
39+
artifact_name: trajectory-macos-bundles
40+
artifact_paths: |
41+
src-tauri/target/release/bundle/macos/*.app
42+
src-tauri/target/release/bundle/dmg/*.dmg
43+
44+
runs-on: ${{ matrix.platform }}
45+
if: ${{ matrix.os != 'macos' || inputs.include-macos }}
46+
47+
steps:
48+
- name: Checkout
49+
uses: actions/checkout@v4
50+
51+
- name: Install Linux system deps
52+
if: matrix.os == 'linux'
53+
run: bash scripts/install-tauri-linux-deps.sh
54+
55+
- name: Setup Node
56+
uses: actions/setup-node@v4
57+
with:
58+
node-version: 22
59+
cache: npm
60+
61+
- name: Setup Rust (stable)
62+
uses: dtolnay/rust-toolchain@stable
63+
64+
- name: Rust cache
65+
uses: swatinem/rust-cache@v2
66+
with:
67+
workspaces: ./src-tauri -> target
68+
69+
- name: Install frontend deps
70+
run: npm ci
71+
72+
- name: Verify version alignment
73+
shell: bash
74+
run: |
75+
expected_version="${{ inputs.version }}"
76+
if [[ -z "$expected_version" ]]; then
77+
expected_version="$(node -p "require('./package.json').version")"
78+
fi
79+
bash scripts/verify-version-alignment.sh "$expected_version"
80+
81+
- name: Build desktop bundles
82+
run: npm run tauri build -- --bundles ${{ matrix.bundles }}
83+
84+
- name: Upload preview artifacts
85+
uses: actions/upload-artifact@v4
86+
with:
87+
name: ${{ matrix.artifact_name }}
88+
path: ${{ matrix.artifact_paths }}
89+
if-no-files-found: error
90+
retention-days: 14

.github/workflows/release.yml

Lines changed: 29 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,33 @@ on:
66
- 'v*'
77

88
jobs:
9-
build-macos:
10-
runs-on: macos-latest
9+
build-release:
10+
strategy:
11+
fail-fast: false
12+
matrix:
13+
include:
14+
- platform: macos-latest
15+
os: macos
16+
bundles: app,dmg
17+
- platform: windows-latest
18+
os: windows
19+
bundles: nsis,msi
20+
- platform: ubuntu-22.04
21+
os: linux
22+
bundles: deb,appimage
23+
24+
runs-on: ${{ matrix.platform }}
1125
permissions:
1226
contents: write
1327

1428
steps:
1529
- name: Checkout
1630
uses: actions/checkout@v4
1731

32+
- name: Install Linux system deps
33+
if: matrix.os == 'linux'
34+
run: bash scripts/install-tauri-linux-deps.sh
35+
1836
- name: Setup Node
1937
uses: actions/setup-node@v4
2038
with:
@@ -24,21 +42,20 @@ jobs:
2442
- name: Setup Rust (stable)
2543
uses: dtolnay/rust-toolchain@stable
2644

45+
- name: Rust cache
46+
uses: swatinem/rust-cache@v2
47+
with:
48+
workspaces: ./src-tauri -> target
49+
2750
- name: Install frontend deps
2851
run: npm ci
2952

3053
- name: Verify tag/version alignment
31-
run: |
32-
TAG_VERSION="${GITHUB_REF_NAME#v}"
33-
APP_VERSION=$(node -p "require('./package.json').version")
34-
TAURI_VERSION=$(node -p "require('./src-tauri/tauri.conf.json').version")
35-
CARGO_VERSION=$(sed -n 's/^version = "\(.*\)"/\1/p' src-tauri/Cargo.toml | head -n 1)
36-
if [ "$TAG_VERSION" != "$APP_VERSION" ] || [ "$TAG_VERSION" != "$TAURI_VERSION" ] || [ "$TAG_VERSION" != "$CARGO_VERSION" ]; then
37-
echo "Tag ($TAG_VERSION), package.json ($APP_VERSION), tauri.conf.json ($TAURI_VERSION), and Cargo.toml ($CARGO_VERSION) must match"
38-
exit 1
39-
fi
54+
shell: bash
55+
run: bash scripts/verify-version-alignment.sh "${GITHUB_REF_NAME#v}"
4056

4157
- name: Configure macOS ad-hoc signing (no notarization)
58+
if: matrix.os == 'macos'
4259
run: |
4360
echo "Building macOS release artifacts with ad-hoc signing (APPLE_SIGNING_IDENTITY='-')."
4461
echo "Apple Developer ID signing and notarization are intentionally disabled for CI prototype builds."
@@ -55,23 +72,4 @@ jobs:
5572
releaseDraft: false
5673
prerelease: false
5774
includeUpdaterJson: false
58-
args: --bundles app,dmg
59-
60-
- name: Verify bundled artifacts exist
61-
run: |
62-
shopt -s nullglob
63-
app_bundles=(src-tauri/target/release/bundle/macos/*.app)
64-
dmg_bundles=(src-tauri/target/release/bundle/dmg/*.dmg)
65-
66-
if [ ${#app_bundles[@]} -eq 0 ]; then
67-
echo "No .app bundle was generated."
68-
exit 1
69-
fi
70-
71-
if [ ${#dmg_bundles[@]} -eq 0 ]; then
72-
echo "No .dmg installer was generated."
73-
exit 1
74-
fi
75-
76-
echo "App bundle: ${app_bundles[0]}"
77-
echo "DMG installer: ${dmg_bundles[0]}"
75+
args: --bundles ${{ matrix.bundles }}

README.md

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# Trajectory
22

33
[![License](https://img.shields.io/badge/license-MIT-blue)](LICENSE)
4-
![Platform](https://img.shields.io/badge/platform-macOS-lightgrey)
4+
![Platform](https://img.shields.io/badge/platform-macOS%20%7C%20Windows%20%7C%20Linux-lightgrey)
55
[![Framework](https://img.shields.io/badge/framework-Tauri%20v2-yellow)](https://tauri.app/)
66
[![Backend](https://img.shields.io/badge/backend-Rust-orange)](https://www.rust-lang.org/)
77
[![Frontend](https://img.shields.io/badge/frontend-React%20%2B%20TypeScript-3178c6)](https://reactjs.org/)
@@ -33,6 +33,7 @@ There is no single reason for why I built Trajectory, but rather a combination o
3333
Notes:
3434
- Current release builds are ad-hoc signed, so macOS may show a security warning on first launch.
3535
- If you cannot open the app, follow the instructions on [Apple's support site](https://support.apple.com/guide/mac-help/open-a-mac-app-from-an-unknown-developer-mh40616/mac).
36+
- Windows and Linux bundles can be built as preview artifacts from the `Preview Bundles` GitHub Actions workflow before publishing an official release.
3637

3738

3839

@@ -206,7 +207,9 @@ can be useful to convince your loved ones that your hobby is not that dangerous
206207

207208
## Platform Support
208209

209-
- macOS
210+
- macOS release artifacts
211+
- Windows preview bundles via GitHub Actions
212+
- Linux preview bundles via GitHub Actions
210213

211214
## Developer Setup (Build From Source)
212215

@@ -240,6 +243,10 @@ Output artifacts are generated under:
240243

241244
- `src-tauri/target/release/bundle/macos/*.app`
242245
- `src-tauri/target/release/bundle/dmg/*.dmg`
246+
- `src-tauri/target/release/bundle/nsis/*.exe`
247+
- `src-tauri/target/release/bundle/msi/*.msi`
248+
- `src-tauri/target/release/bundle/deb/*.deb`
249+
- `src-tauri/target/release/bundle/appimage/*.AppImage`
243250

244251
### Documentation
245252

@@ -255,7 +262,7 @@ Output artifacts are generated under:
255262
## Roadmap
256263

257264
- Route planner.
258-
- Windows and Linux support.
265+
- Code signing / hardening for Windows and Linux releases.
259266

260267

261268

docs/DEVELOPER_GUIDE.md

Lines changed: 29 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# Trajectory Developer Guide
22

3-
> Last verified against the codebase: **April 7, 2026**
3+
> Last verified against the codebase: **April 8, 2026**
44
55
This guide is for contributors working on Trajectory's desktop app codebase.
66
It is intentionally practical: what exists today, how it fits together, and how to extend it safely.
@@ -11,7 +11,8 @@ It is intentionally practical: what exists today, how it fits together, and how
1111

1212
- Node.js 22+
1313
- Rust stable toolchain
14-
- macOS (primary supported platform for local dev and release)
14+
- macOS (primary supported platform for local dev)
15+
- GitHub Actions for preview/release builds on macOS, Windows, and Linux
1516

1617
### Install and run
1718

@@ -41,6 +42,10 @@ Artifacts are created under:
4142

4243
- `src-tauri/target/release/bundle/macos/*.app`
4344
- `src-tauri/target/release/bundle/dmg/*.dmg`
45+
- `src-tauri/target/release/bundle/nsis/*.exe`
46+
- `src-tauri/target/release/bundle/msi/*.msi`
47+
- `src-tauri/target/release/bundle/deb/*.deb`
48+
- `src-tauri/target/release/bundle/appimage/*.AppImage`
4449

4550
## 2. Product Scope (Current)
4651

@@ -74,7 +79,8 @@ Important behavior:
7479
| `src-tauri/` | Tauri shell + Rust backend |
7580
| `docs/DEVELOPER_GUIDE.md` | This document |
7681
| `.github/workflows/ci.yml` | Typecheck + Rust quality gate |
77-
| `.github/workflows/release.yml` | Tag-based macOS release pipeline |
82+
| `.github/workflows/preview-bundles.yml` | Manual preview bundle pipeline for artifact testing |
83+
| `.github/workflows/release.yml` | Tag-based macOS/Windows/Linux release pipeline |
7884

7985
### Project Structure
8086

@@ -103,6 +109,7 @@ Important behavior:
103109
└── .github/
104110
└── workflows/
105111
├── ci.yml
112+
├── preview-bundles.yml
106113
└── release.yml
107114
```
108115

@@ -369,10 +376,23 @@ Design choices:
369376
- frontend quality job on Ubuntu:
370377
- `npm ci`
371378
- `npm run typecheck`
372-
- rust quality job on macOS:
379+
- rust quality job on Ubuntu, macOS, and Windows:
380+
- Linux runner installs Tauri system dependencies (`libwebkit2gtk-4.1-dev`, `libappindicator3-dev`, `librsvg2-dev`, `patchelf`)
373381
- `cargo check --manifest-path src-tauri/Cargo.toml`
374382
- `cargo fmt --manifest-path src-tauri/Cargo.toml --all -- --check`
375383

384+
### Preview bundles (`.github/workflows/preview-bundles.yml`)
385+
386+
Triggered manually from GitHub Actions.
387+
388+
Builds downloadable artifacts without creating a GitHub release:
389+
390+
- macOS: `.app` + `.dmg` (optional)
391+
- Windows: `.exe` (NSIS) + `.msi`
392+
- Linux: `.deb` + `.AppImage`
393+
394+
Use this workflow to validate that a branch is release-ready and hand the generated bundles to testers before tagging a real release.
395+
376396
### Release (`.github/workflows/release.yml`)
377397

378398
Triggered by tags matching `v*`.
@@ -384,7 +404,11 @@ Pipeline verifies version alignment across:
384404
- `src-tauri/tauri.conf.json`
385405
- `src-tauri/Cargo.toml`
386406

387-
Then builds and publishes `.app` + `.dmg` via `tauri-apps/tauri-action` with ad-hoc signing.
407+
Then builds and publishes platform bundles via `tauri-apps/tauri-action`:
408+
409+
- macOS: `.app` + `.dmg` with ad-hoc signing
410+
- Windows: `.exe` (NSIS) + `.msi`
411+
- Linux: `.deb` + `.AppImage`
388412

389413
## 11. Common Extension Tasks
390414

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
#!/usr/bin/env bash
2+
3+
set -euo pipefail
4+
5+
sudo apt-get update
6+
sudo apt-get install -y \
7+
libwebkit2gtk-4.1-dev \
8+
libappindicator3-dev \
9+
librsvg2-dev \
10+
patchelf
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
#!/usr/bin/env bash
2+
3+
set -euo pipefail
4+
5+
if [[ $# -ne 1 ]]; then
6+
echo "usage: $0 <version>" >&2
7+
exit 1
8+
fi
9+
10+
expected_version="$1"
11+
package_version="$(node -p "require('./package.json').version")"
12+
tauri_version="$(node -p "require('./src-tauri/tauri.conf.json').version")"
13+
cargo_version="$(sed -n 's/^version = "\(.*\)"/\1/p' src-tauri/Cargo.toml | head -n 1)"
14+
15+
if [[ "$expected_version" != "$package_version" ]] || [[ "$expected_version" != "$tauri_version" ]] || [[ "$expected_version" != "$cargo_version" ]]; then
16+
echo "Version mismatch detected." >&2
17+
echo "Expected: $expected_version" >&2
18+
echo "package.json: $package_version" >&2
19+
echo "src-tauri/tauri.conf.json: $tauri_version" >&2
20+
echo "src-tauri/Cargo.toml: $cargo_version" >&2
21+
exit 1
22+
fi

src-tauri/icons/128x128.png

2.06 KB
Loading

src-tauri/icons/128x128@2x.png

4.23 KB
Loading

src-tauri/icons/32x32.png

653 Bytes
Loading

0 commit comments

Comments
 (0)