chore: bump version to 9.11.2 (#4909) #4622
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: .NET Nugets | |
| on: | |
| push: | |
| branches: | |
| - master | |
| tags: | |
| - '[0-9]+.[0-9]+.[0-9]+' | |
| - '[0-9]+.[0-9]+.[0-9]+-*' | |
| pull_request: | |
| branches: | |
| - '*' | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.head_ref || github.sha }} | |
| cancel-in-progress: true | |
| jobs: | |
| build_nuget_dotnet: | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| config: | |
| - { os: "windows-latest", runtime_id: "win-x64" } | |
| - { os: "ubuntu-latest", runtime_id: "linux-x64" } | |
| - { os: "macos-14", runtime_id: "osx-arm64" } | |
| - { os: "macos-15-intel", runtime_id: "osx-x64" } | |
| runs-on: ${{matrix.config.os}} | |
| steps: | |
| # Setup for build | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: false | |
| - name: Init submodules with retry | |
| shell: bash | |
| run: | | |
| git config --global --add safe.directory "$(pwd)" | |
| for attempt in 1 2 3 4 5; do | |
| if git submodule update --init --recursive; then | |
| echo "Submodule init succeeded on attempt $attempt" | |
| exit 0 | |
| fi | |
| echo "Attempt $attempt failed, retrying in 15s..." | |
| sleep 15 | |
| done | |
| echo "Submodule init failed after 5 attempts" | |
| exit 1 | |
| - name: Setup MSVC Developer Command Prompt | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| uses: ilammy/msvc-dev-cmd@v1 | |
| - name: Install Ninja | |
| uses: seanmiddleditch/gha-setup-ninja@master | |
| - name: Install NuGet (Linux) | |
| if: runner.os == 'Linux' | |
| run: | | |
| sudo apt-get update | |
| sudo apt-get install -y mono-complete | |
| wget https://dist.nuget.org/win-x86-commandline/latest/nuget.exe | |
| sudo install -m 755 nuget.exe /usr/local/bin/nuget.exe | |
| echo '#!/bin/bash' | sudo tee /usr/local/bin/nuget | |
| echo 'exec mono /usr/local/bin/nuget.exe "$@"' | sudo tee -a /usr/local/bin/nuget | |
| sudo chmod +x /usr/local/bin/nuget | |
| - name: Install NuGet (macOS) | |
| if: runner.os == 'macOS' | |
| run: brew install nuget | |
| - name: Setup .NET SDK | |
| uses: actions/setup-dotnet@v4 | |
| with: | |
| dotnet-version: '8.0.x' | |
| - name: Install dotnet t4 | |
| run: dotnet tool install --global dotnet-t4 | |
| # Get version number | |
| - name: Update git tags | |
| # Needed because actions/checkout performs a shallow checkout without tags | |
| run: git fetch --unshallow --tags --recurse-submodules=no | |
| - name: Get version number | |
| id: get_version | |
| shell: bash | |
| run: | | |
| version=$(./utl/version_number.py) | |
| version_trimmed=$(echo $version | sed 's/\+.*//') | |
| echo "Generated version number: $version" | |
| echo "version=$version" >> $GITHUB_OUTPUT | |
| echo "version_trimmed=$version_trimmed" >> $GITHUB_OUTPUT | |
| # Build .NET Core, all platforms | |
| - name: Configure .NET Core | |
| run: > | |
| cmake -S . -B build -G Ninja | |
| -Dvw_BUILD_NET_CORE=On | |
| -Dvw_DOTNET_USE_MSPROJECT=Off | |
| -DVW_NUGET_PACKAGE_NAME=VowpalWabbit | |
| -DVW_NUGET_PACKAGE_VERSION="${{ steps.get_version.outputs.version }}" | |
| -DVW_NUGET_PACKAGE_VERSION_TRIMMED="${{ steps.get_version.outputs.version_trimmed }}" | |
| -DVW_FEAT_FLATBUFFERS=Off | |
| -DRAPIDJSON_SYS_DEP=Off | |
| -DFMT_SYS_DEP=Off | |
| -DSPDLOG_SYS_DEP=Off | |
| -DVW_ZLIB_SYS_DEP=${{ runner.os == 'macOS' && 'On' || 'Off' }} | |
| -DVW_BOOST_MATH_SYS_DEP=Off | |
| -DVW_BUILD_VW_C_WRAPPER=Off | |
| -DBUILD_TESTING=Off | |
| -DBUILD_SHARED_LIBS=Off | |
| ${{ runner.os != 'macOS' && '-DCMAKE_POLICY_VERSION_MINIMUM=3.5' || '' }} | |
| - name: Build .NET Core | |
| run: cmake --build build --config Release | |
| - name: Install .NET Core | |
| run: cmake --install build --prefix ./nuget_staging | |
| # Build .NET Framework on Windows | |
| - name: Reset build directory | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| run: Remove-Item -Recurse -Force .\build | |
| - name: Configure .NET Framework | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| run: > | |
| cmake -S . -B build -G "Visual Studio 17 2022" -A x64 | |
| -Dvw_BUILD_NET_FRAMEWORK=On | |
| -DVW_NUGET_PACKAGE_NAME=VowpalWabbit | |
| -DVW_NUGET_PACKAGE_VERSION="${{ steps.get_version.outputs.version }}" | |
| -DVW_NUGET_PACKAGE_VERSION_TRIMMED="${{ steps.get_version.outputs.version_trimmed }}" | |
| -DVW_FEAT_FLATBUFFERS=Off | |
| -DRAPIDJSON_SYS_DEP=Off | |
| -DFMT_SYS_DEP=Off | |
| -DSPDLOG_SYS_DEP=Off | |
| -DVW_ZLIB_SYS_DEP=Off | |
| -DVW_BOOST_MATH_SYS_DEP=Off | |
| -DVW_BUILD_VW_C_WRAPPER=Off | |
| -DBUILD_TESTING=Off | |
| -DBUILD_SHARED_LIBS=Off | |
| -DCMAKE_POLICY_VERSION_MINIMUM=3.5 | |
| - name: Build .NET Framework | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| run: cmake --build build --config Release | |
| - name: Install .NET Framework | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| run: cmake --install build --prefix ./nuget_staging | |
| # Create the combined package on Windows | |
| - name: Package Combined | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| shell: powershell | |
| id: generate-nuget | |
| run: | | |
| cd nuget_staging | |
| nuget pack dotnet.nuspec | |
| $NugetFileName = Get-ChildItem *.nupkg -name | |
| echo "NugetFileName=$NugetFileName" >> $GITHUB_OUTPUT | |
| - name: Upload Combined | |
| if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: VowpalWabbit.${{steps.get_version.outputs.version}}.nupkg | |
| path: nuget_staging/${{ steps.generate-nuget.outputs.NugetFileName }} | |
| overwrite: true | |
| retention-days: ${{ github.event_name == 'pull_request' && 7 || 400 }} | |
| # Create the .NET Core runtime package, all platforms | |
| - name: Package .NET Core Runtime | |
| shell: bash | |
| id: generate-runtime-nuget | |
| run: | | |
| cd nuget_staging | |
| nuget pack dotnetcore_runtime.nuspec | |
| NugetFileName=(*runtime*.nupkg) | |
| echo "NugetFileName=${NugetFileName[0]}" >> $GITHUB_OUTPUT | |
| - name: Upload .NET Core Runtime | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.${{matrix.config.runtime_id}}.${{steps.get_version.outputs.version}}.nupkg | |
| path: nuget_staging/${{ steps.generate-runtime-nuget.outputs.NugetFileName }} | |
| overwrite: true | |
| retention-days: ${{ github.event_name == 'pull_request' && 7 || 400 }} | |
| test_nuget_dotnetcore: | |
| needs: [build_nuget_dotnet] | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| config: | |
| - { os: "windows-latest", runtime_id: "win-x64" } | |
| - { os: "ubuntu-latest", runtime_id: "linux-x64" } | |
| - { os: "macos-14", runtime_id: "osx-arm64" } | |
| - { os: "macos-15-intel", runtime_id: "osx-x64" } | |
| runs-on: ${{matrix.config.os}} | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: false | |
| - name: Init submodules with retry | |
| shell: bash | |
| run: | | |
| git config --global --add safe.directory "$(pwd)" | |
| for attempt in 1 2 3 4 5; do | |
| if git submodule update --init --recursive; then | |
| echo "Submodule init succeeded on attempt $attempt" | |
| exit 0 | |
| fi | |
| echo "Attempt $attempt failed, retrying in 15s..." | |
| sleep 15 | |
| done | |
| echo "Submodule init failed after 5 attempts" | |
| exit 1 | |
| - if: ${{ startsWith(matrix.config.os, 'windows') }} | |
| uses: ilammy/msvc-dev-cmd@v1 | |
| # Get version number | |
| - name: Update git tags | |
| # Needed because actions/checkout performs a shallow checkout without tags | |
| run: git fetch --unshallow --tags --recurse-submodules=no | |
| - name: Get version number | |
| id: get_version | |
| shell: bash | |
| run: | | |
| version=$(./utl/version_number.py) | |
| echo "Generated version number: $version" | |
| echo "version=$version" >> $GITHUB_OUTPUT | |
| # Download the previously built Nuget packages | |
| - name: Clear nuget cache | |
| run: dotnet nuget locals all --clear | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.win-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.linux-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.osx-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.osx-arm64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - name: List downloaded packages | |
| run: ls downloaded_nugets | |
| - name: Install package | |
| run: | | |
| cd nuget/dotnet/test | |
| dotnet add dotnetcore_nuget_test.csproj package VowpalWabbit --version ${{steps.get_version.outputs.version}} --source "${{github.workspace}}/downloaded_nugets" --no-restore | |
| dotnet restore dotnetcore_nuget_test.csproj --runtime ${{matrix.config.runtime_id}} --source "https://api.nuget.org/v3/index.json" --source "${{github.workspace}}/downloaded_nugets" | |
| - name: Build and run test | |
| run: | | |
| cd nuget/dotnet/test | |
| dotnet build dotnetcore_nuget_test.csproj --runtime ${{matrix.config.runtime_id}} --output build --no-restore --self-contained | |
| ./build/dotnetcore_nuget_test | |
| test_nuget_dotnetframework: | |
| needs: [build_nuget_dotnet] | |
| runs-on: "windows-latest" | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: false | |
| - name: Init submodules with retry | |
| shell: bash | |
| run: | | |
| git config --global --add safe.directory "$(pwd)" | |
| for attempt in 1 2 3 4 5; do | |
| if git submodule update --init --recursive; then | |
| echo "Submodule init succeeded on attempt $attempt" | |
| exit 0 | |
| fi | |
| echo "Attempt $attempt failed, retrying in 15s..." | |
| sleep 15 | |
| done | |
| echo "Submodule init failed after 5 attempts" | |
| exit 1 | |
| - uses: ilammy/msvc-dev-cmd@v1 | |
| # Get version number | |
| - name: Update git tags | |
| # Needed because actions/checkout performs a shallow checkout without tags | |
| run: git fetch --unshallow --tags --recurse-submodules=no | |
| - name: Get version number | |
| id: get_version | |
| shell: bash | |
| run: | | |
| version=$(./utl/version_number.py) | |
| echo "Generated version number: $version" | |
| echo "version=$version" >> $GITHUB_OUTPUT | |
| # Download the previously built Nuget packages | |
| - name: Clear nuget cache | |
| run: dotnet nuget locals all --clear | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.win-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.linux-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.osx-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.osx-arm64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - name: List downloaded packages | |
| run: ls downloaded_nugets | |
| - name: Install package | |
| run: | | |
| cd nuget/dotnet/test | |
| dotnet add dotnetframework_nuget_test.csproj package VowpalWabbit --version ${{steps.get_version.outputs.version}} --source "${{github.workspace}}/downloaded_nugets" --no-restore | |
| dotnet restore dotnetframework_nuget_test.csproj --runtime win-x64 --source "https://api.nuget.org/v3/index.json" --source "${{github.workspace}}/downloaded_nugets" | |
| - name: Build and run test | |
| run: | | |
| cd nuget/dotnet/test | |
| dotnet build dotnetframework_nuget_test.csproj --runtime win-x64 --output build --no-restore --self-contained | |
| ./build/dotnetframework_nuget_test | |
| benchmark_nuget: | |
| needs: [build_nuget_dotnet] | |
| runs-on: "windows-latest" | |
| permissions: | |
| contents: write | |
| deployments: write | |
| if: ${{ github.event_name == 'push' && github.ref_name == 'master' }} | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: false | |
| - name: Init submodules with retry | |
| shell: bash | |
| run: | | |
| git config --global --add safe.directory "$(pwd)" | |
| for attempt in 1 2 3 4 5; do | |
| if git submodule update --init --recursive; then | |
| echo "Submodule init succeeded on attempt $attempt" | |
| exit 0 | |
| fi | |
| echo "Attempt $attempt failed, retrying in 15s..." | |
| sleep 15 | |
| done | |
| echo "Submodule init failed after 5 attempts" | |
| exit 1 | |
| - uses: ilammy/msvc-dev-cmd@v1 | |
| # Needed for generating benchmark plots | |
| - uses: r-lib/actions/setup-r@v2 | |
| # Get version number | |
| - name: Update git tags | |
| # Needed because actions/checkout performs a shallow checkout without tags | |
| run: git fetch --unshallow --tags --recurse-submodules=no | |
| - name: Get version number | |
| id: get_version | |
| shell: bash | |
| run: | | |
| version=$(./utl/version_number.py) | |
| echo "Generated version number: $version" | |
| echo "version=$version" >> $GITHUB_OUTPUT | |
| # Download the previously built Nuget packages | |
| - name: Clear nuget cache | |
| run: dotnet nuget locals all --clear | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.win-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.linux-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.osx-x64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - uses: actions/download-artifact@v4 | |
| with: | |
| name: VowpalWabbit.runtime.osx-arm64.${{steps.get_version.outputs.version}}.nupkg | |
| path: downloaded_nugets | |
| - name: List downloaded packages | |
| run: ls downloaded_nugets | |
| - name: Install package | |
| run: | | |
| cd test/benchmarks/dotnet | |
| dotnet add dotnet_benchmark.csproj package VowpalWabbit --version ${{steps.get_version.outputs.version}} --source "${{github.workspace}}/downloaded_nugets" --no-restore | |
| dotnet add dotnet_benchmark.csproj package VowpalWabbit.runtime.win-x64 --version ${{steps.get_version.outputs.version}} --source "${{github.workspace}}/downloaded_nugets" --no-restore | |
| dotnet restore dotnet_benchmark.csproj --runtime win-x64 --source "https://api.nuget.org/v3/index.json" --source "${{github.workspace}}/downloaded_nugets" | |
| - name: Build and run benchmarks | |
| run: | | |
| cd test/benchmarks/dotnet | |
| # Build for both .NET Core and Framework | |
| dotnet build dotnet_benchmark.csproj --framework net8.0 --runtime win-x64 --configuration Release --no-restore --self-contained | |
| dotnet build dotnet_benchmark.csproj --framework net4.8 --runtime win-x64 --configuration Release --no-restore --self-contained | |
| # Run with .NET Core as host process | |
| # Arguments after "--" are for BenchmarkDotNet | |
| dotnet run --project dotnet_benchmark.csproj --framework net8.0 --runtime win-x64 --configuration Release --no-build -- --filter '*' --join | |
| # Generate output for Github workflow artifacts | |
| - name: Print benchmark results | |
| shell: bash | |
| run: | | |
| cd test/benchmarks/dotnet/BenchmarkDotNet.Artifacts/results | |
| echo "## .NET Benchmark Results" >> $GITHUB_STEP_SUMMARY | |
| cat BenchmarkRun-joined-*.md | sed 's/\*\*//g' >> $GITHUB_STEP_SUMMARY | |
| - name: Upload benchmark artifacts | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: benchmark_results | |
| path: test/benchmarks/dotnet/BenchmarkDotNet.Artifacts/results/ | |
| # Generate output for github-action-benchmark | |
| - name: Reset dotnet_benchmark.csproj | |
| run: git restore test/benchmarks/dotnet/dotnet_benchmark.csproj | |
| - name: Filter only .NET Core output for github-action-benchmark | |
| shell: bash | |
| run: | | |
| cd test/benchmarks/dotnet/BenchmarkDotNet.Artifacts/results | |
| echo "=== Debug: Total benchmarks in source file ===" | |
| cat BenchmarkRun-joined-*.json | jq '.Benchmarks | length' | |
| echo "=== Debug: Benchmarks with null Statistics ===" | |
| cat BenchmarkRun-joined-*.json | jq '[.Benchmarks[] | select(.Statistics == null)] | length' | |
| echo "=== Debug: Benchmarks with null Statistics (showing DisplayInfo) ===" | |
| cat BenchmarkRun-joined-*.json | jq '[.Benchmarks[] | select(.Statistics == null) | .DisplayInfo]' | |
| echo "=== Debug: .NET Framework benchmarks count ===" | |
| cat BenchmarkRun-joined-*.json | jq '[.Benchmarks[] | select(.DisplayInfo | contains(".NET Framework"))] | length' | |
| echo "=== Filtering to .NET Core only with valid Statistics ===" | |
| # Filter to .NET Core results with valid Statistics (some entries may have null Statistics if skipped) | |
| cat BenchmarkRun-joined-*.json | jq '.Benchmarks |= map(select((.DisplayInfo | contains(".NET Framework") | not) and .Statistics != null))' > BenchmarkRun.json | |
| echo "Filtered benchmark count: $(jq '.Benchmarks | length' BenchmarkRun.json)" | |
| - uses: benchmark-action/github-action-benchmark@v1 | |
| with: | |
| tool: 'benchmarkdotnet' | |
| output-file-path: test/benchmarks/dotnet/BenchmarkDotNet.Artifacts/results/BenchmarkRun.json | |
| alert-threshold: '200%' | |
| fail-on-alert: true | |
| comment-on-alert: true | |
| auto-push: false | |
| github-token: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Push results to gh-pages branch | |
| run: git push 'https://VowpalWabbit:${{ secrets.GITHUB_TOKEN }}@github.com/VowpalWabbit/vowpal_wabbit.git' gh-pages:gh-pages |