Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
63 commits
Select commit Hold shift + click to select a range
85615b6
feat: remembered preferences, selected-drive details, and shared Guide
debpalash Oct 4, 2026
ae23e3d
feat(cli): flash, completions, stable exit codes, and CLI docs
debpalash Oct 4, 2026
742bc8a
Merge branch 'worktree-agent-a542f8b2ce622355b'
debpalash Oct 4, 2026
91b4e00
site: add honest comparison, Rufus-alternative, and roadmap pages
debpalash Oct 4, 2026
5b1a36a
packaging: add package-manager manifest templates and renderer
debpalash Oct 4, 2026
158f719
release: signing-ready pipeline (macOS, Windows, signed checksums), g…
debpalash Oct 4, 2026
e11627e
feat(core): verify publisher checksum-manifest signatures against pin…
debpalash Oct 4, 2026
297022d
Merge branch 'worktree-agent-ad558ace177c7d3d9'
debpalash Oct 4, 2026
c27b883
docs: changelog for CLI, signatures, packaging, and signing
debpalash Oct 4, 2026
83aa762
docs: point downloads and install script at v0.1.4
debpalash Oct 4, 2026
23d564e
release: publish AUR bootable-tui/gui automatically when a secret is …
debpalash Oct 4, 2026
2b8b5e0
feat: keep the signed-integrity label in the download-complete status…
debpalash Oct 4, 2026
80e67b0
feat(core): shared localization foundation with typed message catalog
debpalash Oct 4, 2026
19db9b8
Merge branch 'worktree-agent-abd640cbe710f5544' into feat/v2-growth
debpalash Oct 4, 2026
c638aa2
feat(core): help entry and labels for the language setting
debpalash Oct 4, 2026
9e68ec7
feat(core): legacy BIOS (CSM) boot sectors for MBR Windows media on L…
debpalash Oct 4, 2026
7a4e402
Merge branch 'worktree-agent-aa37d9e841f4e83c0' into feat/v2-growth
debpalash Oct 4, 2026
044b301
feat(desktop): wire localization core and add header language picker
debpalash Oct 4, 2026
9092c4d
Merge branch 'worktree-agent-a4e2e46c61a49309a' into feat/v2-growth
debpalash Oct 4, 2026
567c011
feat(tui): wire shared localization (language cycle on L, localized c…
debpalash Oct 4, 2026
4e7190f
Merge branch 'worktree-agent-a6852bf8f7baa2e2e' into feat/v2-growth
debpalash Oct 4, 2026
36ec495
fix(tui): reset status to readiness guidance on language change, matc…
debpalash Oct 4, 2026
c133ba3
feat(tui): expose experimental legacy BIOS (CSM) firmware option for …
debpalash Oct 4, 2026
9ce960a
feat(desktop): expose experimental BIOS + UEFI (CSM) boot firmware op…
debpalash Oct 4, 2026
88037a9
Merge branch 'worktree-agent-aa85026c80199b140' into feat/v2-growth
debpalash Oct 4, 2026
e7af05f
feat: Guide entry for boot firmware; docs and changelog for localizat…
debpalash Oct 4, 2026
39b2ea6
feat(core): shared app strings, part 1: header, global actions, toolt…
debpalash Oct 4, 2026
8e0e7bc
feat(core): shared app strings, part 2: source and target panels, foc…
debpalash Oct 4, 2026
7109ec1
feat(core): shared app strings, part 3: setup options (Windows, Linux…
debpalash Oct 4, 2026
a43c520
feat(core): shared app strings, part 4: review, confirmation, result,…
debpalash Oct 4, 2026
3dff657
feat(core): shared app strings, part 5: discovery catalogs, Raspberry…
debpalash Oct 4, 2026
11c42a5
feat(core): shared app strings, part 6: downloads, image/drive/option…
debpalash Oct 4, 2026
ae04afd
feat(core): localized helpers for download/catalog/write/bad-block la…
debpalash Oct 4, 2026
49a17d1
feat(core): shared app strings, part 8: catalog result counts
debpalash Oct 4, 2026
15ec1c9
docs(localization): shared app strings catalogue, unification decisio…
debpalash Oct 4, 2026
d5ac368
fix(linux): refuse to write when the reviewed drive moved or its seri…
debpalash Oct 4, 2026
12b575a
feat(desktop): localize header, source, target and guide through the …
debpalash Oct 4, 2026
9c3c610
feat(desktop): localize setup options, Windows toggles, media tools a…
debpalash Oct 4, 2026
322a07a
fix(linux): prove the partition is unmounted and flush caches around …
debpalash Oct 4, 2026
acdc601
feat(desktop): localize review, confirmation and write status lines; …
debpalash Oct 4, 2026
8d39606
fix(linux): run every BIOS/capacity validation before the first destr…
debpalash Oct 4, 2026
231871a
feat(tui): localize header, source, target, status buttons, review an…
debpalash Oct 4, 2026
fafe747
fix(catalog): count manifest lines once and cap parsed lines to stop …
debpalash Oct 4, 2026
b2bf0f8
fix(signature): accept only SHA-2/SHA-3 OpenPGP signature hashes
debpalash Oct 4, 2026
be0d69a
feat(desktop): localize Discover, DistroWatch, Raspberry Pi and Windo…
debpalash Oct 4, 2026
6e3002f
feat(tui): localize setup options, Windows option captions and toggle…
debpalash Oct 4, 2026
7b1a458
fix(catalog): a signed manifest with only an MD5/SHA-1 digest is chec…
debpalash Oct 4, 2026
cf176b2
feat(desktop): localize downloads panel and the status bar controls
debpalash Oct 4, 2026
0d854f7
feat(tui): localize Discover, Raspberry Pi catalog and downloads pane…
debpalash Oct 4, 2026
48748a0
feat(desktop): localize status lines; replace the Ready-prefix check …
debpalash Oct 4, 2026
7fe8720
feat(desktop): localize search placeholder; tests for the erase phras…
debpalash Oct 4, 2026
757800e
feat(core): mark a missing signature from a signing publisher as a do…
debpalash Oct 4, 2026
6c90ead
feat(tui): localize status lines through shared app strings; explicit…
debpalash Oct 4, 2026
b47c88f
fix(bios): bootmgr limit uses the cluster-rounded size; boot sector b…
debpalash Oct 4, 2026
ecad5af
Merge branch 'worktree-agent-af9fa52e5d2d78050' into feat/v2-growth
debpalash Oct 4, 2026
2809319
fix(locale): call macOS defaults by absolute path
debpalash Oct 4, 2026
f4d7b60
Merge branch 'worktree-agent-ab2fc8dee7e456e7c' into feat/v2-growth
debpalash Oct 4, 2026
f92650f
feat(tui): width-aware wrapping and fitting for localized text; de/ru…
debpalash Oct 4, 2026
ecd114c
fix(tui): keep list actions visible, stack the source button on narro…
debpalash Oct 4, 2026
bc38cf9
Merge branch 'worktree-agent-a6170848a4c0f0cca' into feat/v2-growth
debpalash Oct 4, 2026
a34c395
feat(cli): --require-signature, integrity reporting, and a guaranteed…
debpalash Oct 4, 2026
7f61fef
docs(cli): document --require-signature, exit 4 refusals, integrity o…
debpalash Oct 4, 2026
65f3791
fix(ci): pin signed fixtures, keys and line-parsed files to exact byt…
debpalash Oct 4, 2026
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
10 changes: 10 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Signed manifests, signatures and pinned keys must be byte-exact: a CRLF
# conversion on a Windows checkout invalidates every signature over them.
crates/bootable-core/testdata/** -text
crates/bootable-core/keys/** -text
crates/bootable-core/assets/bios/** -text

# Files parsed or executed by line must keep LF on every platform.
*.lang text eol=lf
*.sh text eol=lf
*.S text eol=lf
119 changes: 119 additions & 0 deletions .github/workflows/aur-publish.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
name: AUR publish

# Keeps the AUR source packages bootable-tui and bootable-gui (one pkgbase, "bootable") in step
# with each stable release by bumping pkgver, the source checksum, and .SRCINFO.
#
# Disabled until the AUR_SSH_PRIVATE_KEY repository secret exists: without it the job reports a
# notice and succeeds without pushing anything. Use a key dedicated to this job, registered on the
# AUR account. This is separate from package-manifests.yml, which never pushes anywhere (it renders
# the bootable-bin manifests for manual submission).
#
# Triggers:
# workflow_run a manually dispatched Release workflow finished successfully.
# workflow_dispatch re-run for a version, for example after adding the secret.
on:
workflow_dispatch:
inputs:
version:
description: Stable version to publish, for example 0.1.5 (default is the Cargo.toml version)
required: false
type: string
workflow_run:
workflows: [Release]
types: [completed]

permissions:
contents: read

concurrency:
group: aur-publish
cancel-in-progress: false

jobs:
publish:
name: Update AUR bootable package
runs-on: ubuntu-24.04
container: archlinux:base-devel
if: >-
(github.event_name == 'workflow_dispatch') ||
(github.event_name == 'workflow_run' &&
github.event.workflow_run.conclusion == 'success' &&
github.event.workflow_run.event == 'workflow_dispatch')
env:
AUR_SSH_PRIVATE_KEY: ${{ secrets.AUR_SSH_PRIVATE_KEY }}
steps:
- name: Check that publishing is configured
id: gate
shell: bash
run: |
if [ -z "$AUR_SSH_PRIVATE_KEY" ]; then
echo "::notice::AUR_SSH_PRIVATE_KEY is not set; skipping AUR publish."
echo "enabled=false" >> "$GITHUB_OUTPUT"
else
echo "enabled=true" >> "$GITHUB_OUTPUT"
fi

- name: Install tools
if: steps.gate.outputs.enabled == 'true'
run: pacman -Syu --noconfirm --needed git openssh

- uses: actions/checkout@v4
if: steps.gate.outputs.enabled == 'true'
with:
ref: ${{ github.event.workflow_run.head_sha || github.sha }}

- name: Resolve the release version
id: version
if: steps.gate.outputs.enabled == 'true'
shell: bash
env:
INPUT_VERSION: ${{ inputs.version }}
run: |
set -euo pipefail
version="${INPUT_VERSION#v}"
if [ -z "$version" ]; then
version="$(sed -n 's/^version = "\([^"]*\)"/\1/p' Cargo.toml | head -1)"
fi
if ! [[ "$version" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
echo "Refusing to publish '$version': only stable MAJOR.MINOR.PATCH releases are supported." >&2
exit 1
fi
echo "version=$version" >> "$GITHUB_OUTPUT"

- name: Update and push the AUR repository
if: steps.gate.outputs.enabled == 'true'
shell: bash
env:
VERSION: ${{ steps.version.outputs.version }}
run: |
set -euo pipefail
# makepkg refuses to run as root.
useradd -m builder
install -d -m 0700 -o builder -g builder /home/builder/.ssh
printf '%s\n' "$AUR_SSH_PRIVATE_KEY" > /home/builder/.ssh/aur
# Pinned AUR host key (SHA256:RFzBCUItH9LZS0cKB5UE6ceAYhBD5C8GeOBip8Z11+4).
echo 'aur.archlinux.org ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIEuBKrPzbawxA/k2g6NcyV5jmqwJ2s+zpgZGZ7tpLIcN' > /home/builder/.ssh/known_hosts
chmod 600 /home/builder/.ssh/aur
chown -R builder:builder /home/builder/.ssh
su builder -c "VERSION='$VERSION' bash -s" <<'BUILDER'
set -euo pipefail
export GIT_SSH_COMMAND='ssh -i ~/.ssh/aur -o IdentitiesOnly=yes -o StrictHostKeyChecking=yes -o BatchMode=yes'
git config --global user.name debpalash
git config --global user.email 4178343+debpalash@users.noreply.github.com
git clone ssh://aur@aur.archlinux.org/bootable.git ~/aur
cd ~/aur
current="$(sed -n 's/^pkgver=//p' PKGBUILD)"
if [ "$(printf '%s\n%s\n' "$current" "$VERSION" | sort -V | tail -1)" != "$VERSION" ] || [ "$current" = "$VERSION" ]; then
echo "::notice::AUR already at $current; nothing to do for $VERSION."
exit 0
fi
sed -i "s/^pkgver=.*/pkgver=$VERSION/; s/^pkgrel=.*/pkgrel=1/; s/^sha256sums=.*/sha256sums=('SKIP')/" PKGBUILD
sum="$(curl -fsSL "https://github.com/debpalash/bootable/archive/refs/tags/v$VERSION.tar.gz" | sha256sum | cut -d' ' -f1)"
test "${#sum}" -eq 64
sed -i "s/^sha256sums=.*/sha256sums=('$sum')/" PKGBUILD
makepkg --verifysource --skippgpcheck
makepkg --printsrcinfo > .SRCINFO
git add PKGBUILD .SRCINFO
git commit -m "Update to $VERSION"
git push origin master
BUILDER
92 changes: 92 additions & 0 deletions .github/workflows/package-manifests.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
name: Package manifests

# Renders submit-ready package-manager manifests (winget, Scoop, Homebrew, Flatpak, AUR, Nix)
# for a published stable release and uploads them as a workflow artifact ONLY.
#
# This workflow never pushes to another repository, never opens pull requests, and uses no
# secrets. A maintainer downloads the artifact and submits each manifest by hand; see
# docs/package-managers.md.
#
# Triggers:
# workflow_dispatch the reliable path; defaults to the version in Cargo.toml.
# release: published only fires for releases NOT created with the default GITHUB_TOKEN
# (GitHub suppresses events from it), so it will not see releases that the
# Release workflow publishes itself.
# workflow_run fires when a manually dispatched Release workflow finishes successfully,
# which is how stable releases are actually published.
on:
workflow_dispatch:
inputs:
version:
description: Stable version to render, for example 0.1.4 (default is the Cargo.toml version)
required: false
type: string
release:
types: [published]
workflow_run:
workflows: [Release]
types: [completed]

permissions:
contents: read

concurrency:
group: package-manifests-${{ github.event.release.tag_name || github.event.workflow_run.id || inputs.version || github.run_id }}
cancel-in-progress: false

jobs:
render:
name: Render package manifests
runs-on: ubuntu-24.04
# Prereleases and release-candidate runs are never packaged.
if: >-
(github.event_name == 'workflow_dispatch') ||
(github.event_name == 'release' && !github.event.release.prerelease) ||
(github.event_name == 'workflow_run' &&
github.event.workflow_run.conclusion == 'success' &&
github.event.workflow_run.event == 'workflow_dispatch')
steps:
- uses: actions/checkout@v4

- name: Resolve the release version
id: version
shell: bash
env:
EVENT_NAME: ${{ github.event_name }}
INPUT_VERSION: ${{ inputs.version }}
RELEASE_TAG: ${{ github.event.release.tag_name }}
run: |
set -euo pipefail
case "$EVENT_NAME" in
release) version="${RELEASE_TAG#v}" ;;
workflow_dispatch)
version="${INPUT_VERSION#v}"
;;
*) version="" ;;
esac
if [ -z "$version" ]; then
version="$(sed -n 's/^version = "\([^"]*\)"/\1/p' Cargo.toml | head -1)"
fi
if ! [[ "$version" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
echo "Refusing to package '$version': only stable MAJOR.MINOR.PATCH releases are supported." >&2
exit 1
fi
echo "version=$version" >> "$GITHUB_OUTPUT"

- name: Lint and self-test the renderer
shell: bash
run: |
shellcheck scripts/render-package-manifests.sh
scripts/render-package-manifests.sh --self-test

- name: Render manifests from the published checksums
shell: bash
env:
VERSION: ${{ steps.version.outputs.version }}
run: scripts/render-package-manifests.sh "$VERSION" --out dist/package-manifests

- uses: actions/upload-artifact@v4
with:
name: package-manifests-${{ steps.version.outputs.version }}
path: dist/package-manifests
if-no-files-found: error
Loading
Loading