weavegraph 0.3.0

Graph-driven, concurrent agent workflow framework with versioned state, deterministic barrier merges, and rich diagnostics.
Documentation
name: Release

on:
  workflow_dispatch:
    inputs:
      version:
        description: 'Version to release (e.g., 0.3.0)'
        required: true
        type: string
      dry_run:
        description: 'Dry run (skip publish and tag)'
        required: false
        type: boolean
        default: false

env:
  RUST_VERSION: 1.90.0

jobs:
  release:
    name: Release weavegraph
    runs-on: ubuntu-latest
    permissions:
      actions: read
      contents: write
    steps:
      - name: Checkout repository
        uses: actions/checkout@v4
        with:
          fetch-depth: 0

      - name: Ensure release runs from main
        if: ${{ !inputs.dry_run }}
        run: |
          if [ "${{ github.ref }}" != "refs/heads/main" ]; then
            echo "Error: Releases must be run from main"
            echo "Current ref: ${{ github.ref }}"
            exit 1
          fi

      - name: Ensure main commit has green CI
        if: ${{ !inputs.dry_run }}
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
        run: |
          RESPONSE=$(curl -fsSL \
            -H "Accept: application/vnd.github+json" \
            -H "Authorization: Bearer ${GITHUB_TOKEN}" \
            "https://api.github.com/repos/${{ github.repository }}/actions/workflows/ci.yml/runs?branch=main&event=push&status=success&per_page=1")

          LATEST_GREEN_SHA=$(echo "$RESPONSE" | jq -r '.workflow_runs[0].head_sha // empty')
          if [ -z "$LATEST_GREEN_SHA" ]; then
            echo "Error: No successful ci.yml run found on main"
            exit 1
          fi

          if [ "$LATEST_GREEN_SHA" != "${{ github.sha }}" ]; then
            echo "Error: Current commit does not match latest green ci.yml run on main"
            echo "Current SHA: ${{ github.sha }}"
            echo "Latest green CI SHA: $LATEST_GREEN_SHA"
            exit 1
          fi

      - name: Install Rust toolchain
        uses: dtolnay/rust-toolchain@stable
        with:
          toolchain: ${{ env.RUST_VERSION }}

      - name: Install nightly toolchain (doc parity)
        uses: dtolnay/rust-toolchain@stable
        with:
          toolchain: nightly

      - name: Validate version format
        run: |
          if ! [[ "${{ inputs.version }}" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
            echo "Error: Version must be in format X.Y.Z (e.g., 0.3.0)"
            exit 1
          fi

      - name: Check version in Cargo.toml
        run: |
          CARGO_VERSION=$(grep '^version = ' Cargo.toml | head -1 | sed 's/version = "\(.*\)"/\1/')
          if [ "$CARGO_VERSION" != "${{ inputs.version }}" ]; then
            echo "Error: Cargo.toml version ($CARGO_VERSION) doesn't match input version (${{ inputs.version }})"
            echo "Please update Cargo.toml version field first"
            exit 1
          fi

      - name: Check CHANGELOG.md updated
        run: |
          if ! grep -q "## \[${{ inputs.version }}\]" CHANGELOG.md; then
            echo "Error: CHANGELOG.md doesn't contain release notes for v${{ inputs.version }}"
            echo "Please update CHANGELOG.md before releasing"
            exit 1
          fi

      - name: Run docs check
        run: |
          RUSTDOCFLAGS='--cfg docsrs -D warnings' cargo +nightly doc --workspace --all-features --no-deps

      - name: Dry run cargo publish
        run: cargo publish --dry-run

      - name: Publish to crates.io
        if: ${{ !inputs.dry_run }}
        env:
          CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
        run: cargo publish

      - name: Create git tag
        if: ${{ !inputs.dry_run }}
        run: |
          git config user.name "github-actions[bot]"
          git config user.email "github-actions[bot]@users.noreply.github.com"
          git tag -a "weavegraph-v${{ inputs.version }}" -m "Release weavegraph v${{ inputs.version }}"
          git push origin "weavegraph-v${{ inputs.version }}"

      - name: Create GitHub release
        if: ${{ !inputs.dry_run }}
        uses: actions/create-release@v1
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
        with:
          tag_name: weavegraph-v${{ inputs.version }}
          release_name: Weavegraph v${{ inputs.version }}
          body: |
            See [CHANGELOG.md](https://github.com/${{ github.repository }}/blob/main/CHANGELOG.md#${{ inputs.version }}) for details.
          draft: false
          prerelease: false

      - name: Dry run summary
        if: ${{ inputs.dry_run }}
        run: |
          echo "✓ Dry run complete - no changes published"
          echo "Version validated: ${{ inputs.version }}"
          echo "Tag would be created: weavegraph-v${{ inputs.version }}"