From 74578fdeb35bf931abf5553888e5c017a187d477 Mon Sep 17 00:00:00 2001 From: Lachlan Kermode Date: Mon, 26 Jan 2026 15:53:06 +0100 Subject: [PATCH 1/3] Updates Typst flake repo --- flake.lock | 70 ++++++++++++++++++++++++++++++++++-------------------- flake.nix | 2 +- 2 files changed, 45 insertions(+), 27 deletions(-) diff --git a/flake.lock b/flake.lock index 3d689e0..d36ce5c 100644 --- a/flake.lock +++ b/flake.lock @@ -17,11 +17,11 @@ }, "crane_2": { "locked": { - "lastModified": 1755993354, - "narHash": "sha256-FCRRAzSaL/+umLIm3RU3O/+fJ2ssaPHseI2SSFL8yZU=", + "lastModified": 1767461147, + "narHash": "sha256-TH/xTeq/RI+DOzo+c+4F431eVuBpYVwQwBxzURe7kcI=", "owner": "ipetkov", "repo": "crane", - "rev": "25bd41b24426c7734278c2ff02e53258851db914", + "rev": "7d59256814085fd9666a2ae3e774dc5ee216b630", "type": "github" }, "original": { @@ -39,11 +39,11 @@ "rust-analyzer-src": "rust-analyzer-src" }, "locked": { - "lastModified": 1755585599, - "narHash": "sha256-tl/0cnsqB/Yt7DbaGMel2RLa7QG5elA8lkaOXli6VdY=", + "lastModified": 1767596244, + "narHash": "sha256-P4NRZUjYbeuzv4hGrXxfdg0QpdGVoeNn0CMmzIyr398=", "owner": "nix-community", "repo": "fenix", - "rev": "6ed03ef4c8ec36d193c18e06b9ecddde78fb7e42", + "rev": "eedfb5a27900e82ec0390acc83d4d226ce86e714", "type": "github" }, "original": { @@ -57,11 +57,11 @@ "nixpkgs-lib": "nixpkgs-lib" }, "locked": { - "lastModified": 1754487366, - "narHash": "sha256-pHYj8gUBapuUzKV/kN/tR3Zvqc7o6gdFB9XKXIp1SQ8=", + "lastModified": 1767609335, + "narHash": "sha256-feveD98mQpptwrAEggBQKJTYbvwwglSbOv53uCfH9PY=", "owner": "hercules-ci", "repo": "flake-parts", - "rev": "af66ad14b28a127c5c0f3bbb298218fc63528a18", + "rev": "250481aafeb741edfe23d29195671c19b36b6dca", "type": "github" }, "original": { @@ -106,11 +106,11 @@ }, "nixpkgs-lib": { "locked": { - "lastModified": 1753579242, - "narHash": "sha256-zvaMGVn14/Zz8hnp4VWT9xVnhc8vuL3TStRqwk22biA=", + "lastModified": 1765674936, + "narHash": "sha256-k00uTP4JNfmejrCLJOwdObYC9jHRrr/5M/a/8L2EIdo=", "owner": "nix-community", "repo": "nixpkgs.lib", - "rev": "0f36c44e01a6129be94e3ade315a5883f0228a6e", + "rev": "2075416fcb47225d9b68ac469a5c4801a9c4dd85", "type": "github" }, "original": { @@ -137,11 +137,11 @@ }, "nixpkgs_3": { "locked": { - "lastModified": 1756125398, - "narHash": "sha256-XexyKZpf46cMiO5Vbj+dWSAXOnr285GHsMch8FBoHbc=", + "lastModified": 1767379071, + "narHash": "sha256-EgE0pxsrW9jp9YFMkHL9JMXxcqi/OoumPJYwf+Okucw=", "owner": "nixos", "repo": "nixpkgs", - "rev": "3b9f00d7a7bf68acd4c4abb9d43695afb04e03a5", + "rev": "fb7944c166a3b630f177938e478f0378e64ce108", "type": "github" }, "original": { @@ -163,11 +163,11 @@ "rust-analyzer-src": { "flake": false, "locked": { - "lastModified": 1755504847, - "narHash": "sha256-VX0B9hwhJypCGqncVVLC+SmeMVd/GAYbJZ0MiiUn2Pk=", + "lastModified": 1767551763, + "narHash": "sha256-lcA/e3++3aZQSj6xCsBi2VpYyC3Q+oO/oukgfHiL+Ts=", "owner": "rust-lang", "repo": "rust-analyzer", - "rev": "a905e3b21b144d77e1b304e49f3264f6f8d4db75", + "rev": "6a1246b69ca761480b9278df019f717b549cface", "type": "github" }, "original": { @@ -180,13 +180,13 @@ "rust-manifest": { "flake": false, "locked": { - "narHash": "sha256-nzhgCEnR/ggzYuS1CGIrvJyTElA5hPY12NGkSgIfl6A=", + "narHash": "sha256-Mrw0LDR4i/CDGhDZ10IUTGkFow/+yIJGeBKMIWi/nqg=", "type": "file", - "url": "https://static.rust-lang.org/dist/channel-rust-1.89.0.toml" + "url": "https://static.rust-lang.org/dist/channel-rust-1.91.0.toml" }, "original": { "type": "file", - "url": "https://static.rust-lang.org/dist/channel-rust-1.89.0.toml" + "url": "https://static.rust-lang.org/dist/channel-rust-1.91.0.toml" } }, "rust-overlay": { @@ -244,19 +244,37 @@ "flake-parts": "flake-parts", "nixpkgs": "nixpkgs_3", "rust-manifest": "rust-manifest", - "systems": "systems_2" + "systems": "systems_2", + "typst": "typst_2" }, "locked": { - "lastModified": 1761296626, - "narHash": "sha256-gpxS+htknDL75TRbp+Dt4UYmvndkMjvz4bOWe/aCLog=", + "lastModified": 1767654408, + "narHash": "sha256-7YhRyF2u7CuhBLMpKnHZy9D5Y2L6k9LRLGf3SE0AUYc=", "owner": "typst", - "repo": "typst", - "rev": "58ae098d3d99a9874411be3eb0b72c1bfc39ed09", + "repo": "typst-flake", + "rev": "ec2389e45e1014c746a3a1d6a222cde352c56886", "type": "github" }, "original": { "owner": "typst", "ref": "main", + "repo": "typst-flake", + "type": "github" + } + }, + "typst_2": { + "flake": false, + "locked": { + "lastModified": 1765535432, + "narHash": "sha256-KCNFCl7vFWHGmQPrie1BoncQtu5G/rN5qf45jPiYrT4=", + "owner": "typst", + "repo": "typst", + "rev": "b33de9de113c91c184214b299bd7a8eb3070c3ab", + "type": "github" + }, + "original": { + "owner": "typst", + "ref": "0.14", "repo": "typst", "type": "github" } diff --git a/flake.nix b/flake.nix index a45c42b..1b995d1 100644 --- a/flake.nix +++ b/flake.nix @@ -4,7 +4,7 @@ inputs = { nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; flake-utils.url = "github:numtide/flake-utils"; - typst.url = "github:typst/typst/main"; + typst.url = "github:typst/typst-flake/main"; rust-overlay.url = "github:oxalica/rust-overlay"; crane.url = "github:ipetkov/crane"; }; From ade9a5744e6a3f49c34354b4e557d34fa5e3bc1f Mon Sep 17 00:00:00 2001 From: Lachlan Kermode Date: Thu, 5 Feb 2026 08:26:32 +0100 Subject: [PATCH 2/3] Updates GH workflows --- .github/workflows/pre-release.yml | 79 ++++++++++++++++++ .github/workflows/release.yml | 134 +++++++++++++----------------- CLAUDE.md | 39 +++++++++ 3 files changed, 174 insertions(+), 78 deletions(-) create mode 100644 .github/workflows/pre-release.yml diff --git a/.github/workflows/pre-release.yml b/.github/workflows/pre-release.yml new file mode 100644 index 0000000..cda996e --- /dev/null +++ b/.github/workflows/pre-release.yml @@ -0,0 +1,79 @@ +name: Pre-release + +on: + pull_request: + branches: + - "main" + types: [opened,labeled,edited,synchronize] + +jobs: + test-artifacts: + if: contains(github.event.pull_request.labels.*.name, 'release') + + env: + RUST_BACKTRACE: 1 + RUST_LIB_BACKTRACE: 1 + TOKIO_WORKER_THREADS: 1 + + strategy: + matrix: + include: + - target: x86_64-unknown-linux-gnu + os: ubuntu-22.04 + command: test + - target: aarch64-unknown-linux-gnu + os: ubuntu-24.04-arm + command: test + - target: x86_64-apple-darwin + os: macos-latest + command: build + - target: aarch64-apple-darwin + os: macos-latest + command: test + # disabling windows tests for now bc of a bunch of biome issues + - target: x86_64-pc-windows-msvc + os: windows-latest + command: build + - target: aarch64-pc-windows-msvc + os: windows-11-arm + command: build + + runs-on: ${{ matrix.os }} + steps: + - name: Checkout + uses: actions/checkout@v4 + - name: Add target + run: rustup target add ${{ matrix.target }} + - name: Setup + uses: ./.github/workflows/setup + - name: Compile binary + run: cargo ${{ matrix.command }} --locked --target ${{ matrix.target }} + - name: Compress artifacts (Windows) + if: runner.os == 'Windows' + run: | + cd target/${{ matrix.target }}/debug + Compress-Archive -Path ${{ github.event.repository.name }}.exe -Destination ${{ matrix.target }}.zip + - name: Compress artifacts (Non-Windows) + if: runner.os != 'Windows' + run: | + cd target/${{ matrix.target }}/debug + zip -9 ${{ matrix.target }}.zip ${{ github.event.repository.name }} + + publish-dry-run: + if: contains(github.event.pull_request.labels.*.name, 'release') + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + - name: Login to crates.io + run: cargo login ${{ secrets.CRATES_IO_TOKEN }} + - name: Dry run of crate publish + run: cargo publish --workspace --dry-run + + check-pr-name: + if: contains(github.event.pull_request.labels.*.name, 'release') + runs-on: ubuntu-latest + steps: + - name: Check that PR name is a release number + run: echo "${{ github.event.pull_request.title }}" | grep -q -E "^v[0-9]+\.[0-9]+\.[0-9]+$" + diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 411c4f2..d16faae 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -5,107 +5,85 @@ on: branches: [main] types: [labeled,closed] -permissions: - contents: write - pull-requests: read - jobs: - create-release: + build-artifacts: if: github.event.pull_request.merged == true && contains(github.event.pull_request.labels.*.name, 'release') - runs-on: ubuntu-latest - outputs: - version: ${{ steps.version.outputs.version }} - tag: ${{ steps.version.outputs.tag }} - steps: - - name: Checkout - uses: actions/checkout@v4 - - - name: Extract version from Cargo.toml - id: version - run: | - VERSION=$(grep '^version = ' Cargo.toml | head -1 | sed 's/version = "\(.*\)"/\1/') - echo "version=$VERSION" >> $GITHUB_OUTPUT - echo "tag=v$VERSION" >> $GITHUB_OUTPUT - echo "Extracted version: $VERSION" - - name: Create GitHub Release - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - run: | - gh release create ${{ steps.version.outputs.tag }} \ - --title "Release ${{ steps.version.outputs.version }}" \ - --notes "Release ${{ steps.version.outputs.version }}" \ - --draft=false \ - --prerelease=false - - build-artifacts: - needs: create-release strategy: matrix: include: - target: x86_64-unknown-linux-gnu - os: ubuntu-latest + os: ubuntu-22.04 + - target: aarch64-unknown-linux-gnu + os: ubuntu-24.04-arm - target: x86_64-apple-darwin os: macos-latest + - target: aarch64-apple-darwin + os: macos-latest - target: x86_64-pc-windows-msvc os: windows-latest + - target: aarch64-pc-windows-msvc + os: windows-11-arm runs-on: ${{ matrix.os }} steps: - name: Checkout uses: actions/checkout@v4 - - - name: Install Rust toolchain for target - uses: dtolnay/rust-toolchain@stable - with: - targets: ${{ matrix.target }} - - - name: Build for target - run: cargo build --release --target ${{ matrix.target }} --verbose - - - name: Package artifacts (Unix) - if: runner.os != 'Windows' - run: | - cd target/${{ matrix.target }}/release - tar czf rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.tar.gz rheo - shasum -a 256 rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.tar.gz > rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.tar.gz.sha256 - - - name: Package artifacts (Windows) + - name: Add target + run: rustup target add ${{ matrix.target }} + - name: Setup + uses: ./.github/workflows/setup + - name: Compile binary + run: cargo build --locked --release --target ${{ matrix.target }} + - name: Compress artifacts (Windows) if: runner.os == 'Windows' run: | cd target/${{ matrix.target }}/release - 7z a rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.zip rheo.exe - certutil -hashfile rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.zip SHA256 > rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.zip.sha256 - - - name: Upload Release Assets - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + Compress-Archive -Path ${{ github.event.repository.name }}.exe -Destination ${{ matrix.target }}.zip + - name: Compress artifacts (Non-Windows) + if: runner.os != 'Windows' run: | - gh release upload ${{ needs.create-release.outputs.tag }} target/${{ matrix.target }}/release/rheo-${{ needs.create-release.outputs.version }}-${{ matrix.target }}.* --clobber + cd target/${{ matrix.target }}/release + zip -9 ${{ matrix.target }}.zip ${{ github.event.repository.name }} + - name: Upload artifacts + uses: actions/upload-artifact@v4 + with: + name: ${{ matrix.target }} + path: target/${{ matrix.target }}/release/${{ matrix.target }}.zip - publish-crate: - needs: [create-release, build-artifacts] + publish-crates: + needs: build-artifacts runs-on: ubuntu-latest steps: - name: Checkout uses: actions/checkout@v4 + - name: Login to crates.io + run: cargo login ${{ secrets.CRATES_IO_TOKEN }} + - name: Publish crates + run: cargo publish --workspace + - name: Add a tag for the merged commit + uses: christophebedard/tag-version-commit@v1 + with: + token: ${{ secrets.GITHUB_TOKEN }} + version_regex: 'v([0-9]+\.[0-9]+\.[0-9]+)' + version_tag_prefix: 'v' - - name: Install Rust toolchain - uses: dtolnay/rust-toolchain@stable - - - name: Check version has been bumped - run: | - VERSION="${{ needs.create-release.outputs.version }}" - echo "Releasing version: $VERSION" - - # Check if version exists on crates.io - if cargo search rheo --limit 1 | grep -q "rheo = \"$VERSION\""; then - echo "Error: Version $VERSION already exists on crates.io" - echo "Please bump the version in Cargo.toml before releasing" - exit 1 - fi - - echo "Version check passed: $VERSION is new" - - - name: Publish to crates.io - run: cargo publish --token ${{ secrets.CRATES_IO_TOKEN }} + publish-artifacts: + needs: publish-crates + runs-on: ubuntu-latest + permissions: + contents: write + steps: + - name: Download artifacts + uses: actions/download-artifact@v4 + - name: Publish artifacts + uses: softprops/action-gh-release@v2 + with: + tag_name: ${{ github.event.pull_request.title }} + files: | + x86_64-unknown-linux-gnu/x86_64-unknown-linux-gnu.zip + aarch64-unknown-linux-gnu/aarch64-unknown-linux-gnu.zip + x86_64-apple-darwin/x86_64-apple-darwin.zip + aarch64-apple-darwin/aarch64-apple-darwin.zip + x86_64-pc-windows-msvc/x86_64-pc-windows-msvc.zip + aarch64-pc-windows-msvc/aarch64-pc-windows-msvc.zip diff --git a/CLAUDE.md b/CLAUDE.md index 12b0cb0..b2bfd77 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -533,6 +533,45 @@ cargo test test_warning_formatting -- --nocapture - Typst libraries are pulled from git main branch - Keep dependencies minimal and well-justified +### Branching and Release Workflow + +**Development Model:** +- All development happens via pull requests to `main` +- The `main` branch is the primary development branch +- No long-lived feature branches; PRs are merged directly to main + +**Release Process:** + +When ready to cut a new release: + +1. **Update version in Cargo.toml** to the new version number + +2. **Create a release PR:** + - PR title MUST be the version tag (e.g., `v0.2.0`) + - Add the `release` label to the PR + +3. **Pre-release validation** (automated via `.github/workflows/pre-release.yml`): + - Builds and tests on all supported platforms (Linux x86_64/ARM, macOS x86_64/ARM, Windows x86_64/ARM) + - Validates PR title matches `vX.Y.Z` format + - Runs `cargo publish --dry-run` to verify crates.io readiness + +4. **Merge the PR** - triggers release automation (`.github/workflows/release.yml`): + - Builds release binaries for all platforms + - Publishes to crates.io + - Creates a git tag matching the PR title + - Creates a GitHub Release with platform-specific zip files + +**Supported Platforms:** +- `x86_64-unknown-linux-gnu` (Linux x86_64) +- `aarch64-unknown-linux-gnu` (Linux ARM64) +- `x86_64-apple-darwin` (macOS Intel) +- `aarch64-apple-darwin` (macOS Apple Silicon) +- `x86_64-pc-windows-msvc` (Windows x86_64) +- `aarch64-pc-windows-msvc` (Windows ARM64) + +**Release Artifacts:** +Each release includes zip files for each platform containing the `rheo` binary, available on the GitHub Releases page. + --- ## Version Control with Jujutsu From 8ad827b1b9a7ab23b7cd8b1df2f7a4e3a6fa19e7 Mon Sep 17 00:00:00 2001 From: Lachlan Kermode Date: Thu, 5 Feb 2026 08:41:44 +0100 Subject: [PATCH 3/3] Adds install.sh script --- install.sh | 57 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 57 insertions(+) create mode 100755 install.sh diff --git a/install.sh b/install.sh new file mode 100755 index 0000000..539af9a --- /dev/null +++ b/install.sh @@ -0,0 +1,57 @@ +#!/bin/sh +set -e + +BASE_URL="https://github.com/freecomputinglab/rheo" +INSTALL_DIR=$HOME/.local/bin +PROJECT_NAME=rheo + +download() { + cd $(mktemp -d) + + echo 'Downloading prebuilt binary from Github...' + curl --silent --location "${BASE_URL}/releases/latest/download/$1.zip" --output $1.zip + unzip $1.zip + + mkdir -p $INSTALL_DIR + mv $PROJECT_NAME $INSTALL_DIR/$PROJECT_NAME +} + +ARCH=$(uname -m) +OS=$(uname -o) + +pick_target() { + echo "Selecting target for $ARCH / $OS..." + + if [ -n "$1" ]; then + cargo install $PROJECT_NAME --locked --git $BASE_URL --rev $1 + return + elif [ "$OS" = "Linux" ] || [ "$OS" = "GNU/Linux" ]; then + if [ "$ARCH" = "x86_64" ]; then + download "x86_64-unknown-linux-gnu" + return + fi + elif [ "$OS" = "Darwin" ]; then + if [ "$ARCH" = "arm64" ]; then + download "aarch64-apple-darwin" + return + elif [ "$ARCH" = "x86_64" ]; then + download "x86_64-apple-darwin" + return + fi + elif [ "$OS" = "Msys" ]; then + if [ "$ARCH" = "arm64" ]; then + download "aarch64-pc-windows-msvc" + return + elif [ "$ARCH" = "x86_64" ]; then + download "x86_64-pc-windows-msvc" + return + fi + fi + + echo 'Prebuilt binary not available, installing from source. This may take a few minutes.' + cargo install $PROJECT_NAME --locked +} + +pick_target $1 + +echo '$PROJECT_NAME installation is complete.'