diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 283c4d4..0af4d51 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -11,10 +11,13 @@ on: workflow_dispatch: schedule: - cron: '0 8 */6 * *' # every 6 days - pull_request: + push: branches: - - master - - main + - earthly-main + - gh_test_ci + # No branch filter, so PRs stacked on other PR branches + # (not just PRs into earthly-main) get CI too. + pull_request: jobs: validate: @@ -28,13 +31,22 @@ jobs: steps: - name: Checkout - uses: actions/checkout@v4 + uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 + - + name: Login to Docker Hub + # Authenticated pulls avoid Docker Hub's anonymous rate limit (429). + # Secrets are unavailable to fork PRs, so skip the login there. + if: ${{ github.event_name != 'pull_request' || github.event.pull_request.head.repo.full_name == github.repository }} + uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3.7.0 + with: + username: ${{ vars.DOCKERHUB_USERNAME }} + password: ${{ secrets.DOCKERHUB_TOKEN }} - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v3 + uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0 - name: Run - uses: docker/bake-action@v4 + uses: docker/bake-action@4a9a8d494466d37134e2bfca2d3a8de8fb2681ad # v5.13.0 with: targets: ${{ matrix.target }} @@ -48,13 +60,22 @@ jobs: steps: - name: Checkout - uses: actions/checkout@v4 + uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 + - + name: Login to Docker Hub + # Authenticated pulls avoid Docker Hub's anonymous rate limit (429). + # Secrets are unavailable to fork PRs, so skip the login there. + if: ${{ github.event_name != 'pull_request' || github.event.pull_request.head.repo.full_name == github.repository }} + uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3.7.0 + with: + username: ${{ vars.DOCKERHUB_USERNAME }} + password: ${{ secrets.DOCKERHUB_TOKEN }} - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v3 + uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0 - name: Run - uses: docker/bake-action@v4 + uses: docker/bake-action@4a9a8d494466d37134e2bfca2d3a8de8fb2681ad # v5.13.0 with: targets: ${{ matrix.target }} @@ -73,18 +94,27 @@ jobs: steps: - name: Checkout - uses: actions/checkout@v4 + uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 + - + name: Login to Docker Hub + # Authenticated pulls avoid Docker Hub's anonymous rate limit (429). + # Secrets are unavailable to fork PRs, so skip the login there. + if: ${{ github.event_name != 'pull_request' || github.event.pull_request.head.repo.full_name == github.repository }} + uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3.7.0 + with: + username: ${{ vars.DOCKERHUB_USERNAME }} + password: ${{ secrets.DOCKERHUB_TOKEN }} - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v3 + uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0 - name: Test - uses: docker/bake-action@v4 + uses: docker/bake-action@4a9a8d494466d37134e2bfca2d3a8de8fb2681ad # v5.13.0 with: targets: test-${{ matrix.mode }} - name: Upload coverage - uses: codecov/codecov-action@v4 + uses: codecov/codecov-action@b9fd7d16f6d7d1b5d2bec1a2887e65ceed900238 # v4.6.0 with: directory: ${{ env.DESTDIR }}/coverage flags: unit,${{ matrix.mode }},go-${{ matrix.go }} @@ -101,24 +131,30 @@ jobs: go: - "1.21" - "1.20" + exclude: + # Go 1.21 test binaries abort on current macOS runner images + # ("dyld: missing LC_UUID load command"); Go 1.20 still covers macOS. + - os: macos-latest + go: "1.21" steps: - name: Checkout - uses: actions/checkout@v4 + uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 - name: Set up Go - uses: actions/setup-go@v5 + uses: actions/setup-go@40f1582b2485089dde7abd97c1529aa768e1baff # v5.6.0 with: go-version: ${{ matrix.go }} - name: Test + shell: bash run: | go test -coverprofile="coverage.txt" -covermode="atomic" ./... go tool cover -func="coverage.txt" - name: Upload coverage if: always() - uses: codecov/codecov-action@v4 + uses: codecov/codecov-action@b9fd7d16f6d7d1b5d2bec1a2887e65ceed900238 # v4.6.0 with: file: ./coverage.txt env_vars: RUNNER_OS @@ -126,54 +162,54 @@ jobs: token: ${{ secrets.CODECOV_TOKEN }} test-freebsd-amd64: - runs-on: macos-13 + # macos-13 (and Vagrant/VirtualBox on it) is retired; run FreeBSD in a VM + # on Linux the way upstream tonistiigi/fsutil does. + runs-on: ubuntu-latest env: - VAGRANT_VAGRANTFILE: hack/Vagrantfile.freebsd13 + GO_VERSION: "1.21" steps: + - + name: Prepare + shell: bash + run: | + goVersion=$(curl --fail --silent --show-error "https://go.dev/dl/?mode=json&include=all" | jq -er --arg version "go${GO_VERSION}." '[.[] | select(.stable and (.version | startswith($version)))][0].version') + echo "GO_VERSION=${goVersion#go}" >> "$GITHUB_ENV" - name: Checkout - uses: actions/checkout@v4 + uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 - - name: Cache Vagrant boxes - uses: actions/cache@v4 + name: Set up FreeBSD + uses: vmactions/freebsd-vm@c46abacb49f09938ca4e1702d15d836285d694cc # v1.5.9 with: - path: ~/.vagrant.d/boxes - key: ${{ runner.os }}-vagrant-${{ hashFiles('hack/Vagrantfile.freebsd13') }} - restore-keys: | - ${{ runner.os }}-vagrant- - - - name: Install Vagrant and VirtualBox - run: | - set -x - brew tap hashicorp/tap - brew install hashicorp/tap/hashicorp-vagrant - brew install --cask virtualbox - env: - HOMEBREW_NO_AUTO_UPDATE: 1 - HOMEBREW_NO_INSTALLED_DEPENDENTS_CHECK: 1 - - - name: Check versions - run: | - set -x - vagrant --version - VBoxManage -v - - - name: Set up vagrant - run: | - vagrant up --no-tty + release: "14.5" + envs: GO_VERSION + custom-shell-name: bsd + prepare: | + set -ex + mkdir -p /var/tmp + chmod 1777 /var/tmp + archive="go${GO_VERSION}.freebsd-amd64.tar.gz" + fetch -o "/var/tmp/$archive" "https://go.dev/dl/$archive" + tar -C /var/tmp -xzf "/var/tmp/$archive" + pw useradd -n fsutil -m -s /bin/sh - name: Test - uses: nick-fields/retry@7152eba30c6575329ac0576536151aca5a72780e # v3.0.0 - with: - timeout_minutes: 20 - max_attempts: 5 - command: | - vagrant ssh -- "cd /vagrant; go test -buildvcs=false -coverprofile=coverage.txt -covermode=atomic ./..." - vagrant ssh -c "sudo cat /vagrant/coverage.txt" > coverage.txt + run: | + bsd /dev/stdin <<'EOF' + set -ex + chown -R fsutil "$GITHUB_WORKSPACE" + su - fsutil -c ' + set -ex + cd "$1" + export TMPDIR=/var/tmp + export PATH="/var/tmp/go/bin:$PATH" + go test -buildvcs=false -coverprofile=coverage.txt -covermode=atomic ./... + ' sh "$GITHUB_WORKSPACE" + EOF - name: Upload coverage if: always() - uses: codecov/codecov-action@v4 + uses: codecov/codecov-action@b9fd7d16f6d7d1b5d2bec1a2887e65ceed900238 # v4.6.0 with: file: ./coverage.txt flags: unit,freebsd diff --git a/receive_test.go b/receive_test.go index 4f3d8e3..4ffff20 100644 --- a/receive_test.go +++ b/receive_test.go @@ -217,6 +217,10 @@ func TestCopySwitchDirToFile(t *testing.T) { } func TestHardlinkFilter(t *testing.T) { + if runtime.GOOS == "windows" { + t.Skip("hardlink stat linknames are not populated on windows") + } + d, err := tmpDir(changeStream([]string{ "ADD bar file data1", "ADD foo file >bar",