name: ci
on:
push:
branches: [main]
pull_request:
jobs:
test:
strategy:
matrix:
include:
- {os: macos-latest, fs: apfs}
- {os: ubuntu-latest, fs: xfs}
- {os: ubuntu-latest, fs: ext4}
runs-on: ${{ matrix.os }}
steps:
- uses: actions/checkout@v4
- uses: dtolnay/rust-toolchain@stable
with:
components: clippy, rustfmt
- run: cargo fmt --check
- run: cargo clippy --all-targets -- -D warnings
- name: XFS reflink volume
if: matrix.fs == 'xfs'
run: |
command -v mkfs.xfs >/dev/null || sudo apt-get install -y xfsprogs
truncate -s 4G /tmp/xfs.img
mkfs.xfs -m reflink=1 /tmp/xfs.img
sudo mkdir -p /mnt/xfs && sudo mount -o loop /tmp/xfs.img /mnt/xfs
sudo mkdir /mnt/xfs/tmp && sudo chown -R "$USER" /mnt/xfs
echo "TMPDIR=/mnt/xfs/tmp" >> "$GITHUB_ENV"
echo "GIT_COW_EXPECT_CLONE=1" >> "$GITHUB_ENV"
- name: Require cloning on APFS
if: matrix.fs == 'apfs'
run: echo "GIT_COW_EXPECT_CLONE=1" >> "$GITHUB_ENV"
- run: cargo test
release:
needs: test
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
runs-on: ubuntu-latest
permissions:
contents: write
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- uses: dtolnay/rust-toolchain@stable
- name: Next version
id: version
run: |
LAST=$(git describe --tags --abbrev=0 2>/dev/null || true)
SUBJECTS=$(git log ${LAST:+"$LAST"..HEAD} --pretty=format:%s)
if [ -z "$SUBJECTS" ] || ! echo "$SUBJECTS" | grep -qvE '^(chore|docs|ci)(\(.*\))?:'; then
echo "nothing to release since ${LAST:-the start}"
exit 0
fi
if [ -z "$LAST" ]; then
V=0.1.0
else
IFS=. read -r MA MI PA <<< "${LAST#v}"
if echo "$SUBJECTS" | grep -qE '^(BREAKING CHANGE:|breaking(\(.*\))?:)'; then V="$((MA + 1)).0.0"
elif echo "$SUBJECTS" | grep -qE '^feat(\(.*\))?:'; then V="$MA.$((MI + 1)).0"
else V="$MA.$MI.$((PA + 1))"; fi
fi
echo "version=$V" >> "$GITHUB_OUTPUT"
echo "releasing v$V"
- name: Publish to crates.io
if: steps.version.outputs.version
env:
CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
VERSION: ${{ steps.version.outputs.version }}
run: |
sed -i "0,/^version = .*/s//version = \"$VERSION\"/" Cargo.toml
cargo publish --allow-dirty
- name: Tag and release
if: steps.version.outputs.version
env:
GH_TOKEN: ${{ github.token }}
VERSION: ${{ steps.version.outputs.version }}
run: gh release create "v$VERSION" --target "$GITHUB_SHA" --title "v$VERSION" --generate-notes