diff --git a/.github/workflows/itests.yml b/.github/workflows/itests.yml index 3521124dc..80226da70 100644 --- a/.github/workflows/itests.yml +++ b/.github/workflows/itests.yml @@ -10,26 +10,36 @@ jobs: strategy: fail-fast: false matrix: - dotnet-version: ['8.0', '9.0', '10.0'] + dotnet-version: ['8.0', '9.0', '10.0', '11.0'] include: - dotnet-version: '8.0' display-name: '.NET 8.0' framework: 'net8.0' prefix: 'net8' install-version: '8.0.x' + quality: 'ga' upload_coverage: false - dotnet-version: '9.0' display-name: '.NET 9.0' framework: 'net9.0' prefix: 'net9' install-version: '9.0.x' + quality: 'ga' upload_coverage: false - dotnet-version: '10.0' display-name: '.NET 10.0' framework: 'net10.0' prefix: 'net10' install-version: '10.0.x' + quality: 'ga' upload_coverage: true + - dotnet-version: '11.0' + display-name: '.NET 11.0' + framework: 'net11.0' + prefix: 'net11' + install-version: '11.0.x' + quality: 'preview' + upload_coverage: false env: NUPKG_OUTDIR: bin/Release/nugets GOVER: 1.20.3 @@ -40,6 +50,7 @@ jobs: DAPR_RUNTIME_VER: 1.16.6 DAPR_INSTALL_URL: https://raw.githubusercontent.com/dapr/cli/release-1.16/install/install.sh DAPR_CLI_REF: '' + DaprEnableNet11: ${{ matrix.framework == 'net11.0' }} steps: - name: Set up Dapr CLI run: wget -q ${{ env.DAPR_INSTALL_URL }} -O - | /bin/bash -s ${{ env.DAPR_CLI_VER }} @@ -95,11 +106,14 @@ jobs: - uses: actions/checkout@v1 - name: Parse release version run: python ./.github/scripts/get_release_version.py + - name: Remove global.json (use .NET 11 preview SDK) + if: ${{ matrix.framework == 'net11.0' }} + run: rm global.json - name: Setup ${{ matrix.display-name }} uses: actions/setup-dotnet@v3 with: dotnet-version: ${{ matrix.install-version }} - dotnet-quality: 'ga' # Prefer a GA release, but use the RC if not available + dotnet-quality: ${{ matrix.quality }} - name: Setup .NET 8 (required) uses: actions/setup-dotnet@v3 if: ${{ matrix.install-version != '8.0.x' }} @@ -141,33 +155,47 @@ jobs: id: tests continue-on-error: true # proceed if tests fail, the report step will report the failure with more details. run: | + test_args=( + --logger "trx;LogFilePrefix=${{ matrix.prefix }}" + --logger "console;verbosity=detailed" + ) + if [[ "${{ matrix.framework }}" != "net11.0" ]]; then + test_args+=( + --logger "GitHubActions;report-warnings=false" + /p:CollectCoverage=true + /p:CoverletOutputFormat=opencover + ) + fi dotnet test ${{ github.workspace }}/test/Dapr.E2E.Test/Dapr.E2E.Test.csproj \ --configuration Release \ --framework ${{ matrix.framework }} \ --no-build \ --no-restore \ - --logger "trx;LogFilePrefix=${{ matrix.prefix }}" \ - --logger "GitHubActions;report-warnings=false" \ - --logger "console;verbosity=detailed" \ --results-directory "${{ github.workspace }}/TestResults" \ - /p:CollectCoverage=true \ - /p:CoverletOutputFormat=opencover \ + "${test_args[@]}" \ /p:GITHUB_ACTIONS=false - name: Run Generators Integration Tests id: generator-tests continue-on-error: true # proceed if tests fail, the report step will report the failure with more details. run: | + test_args=( + --logger "trx;LogFilePrefix=${{ matrix.prefix }}" + --logger "console;verbosity=detailed" + ) + if [[ "${{ matrix.framework }}" != "net11.0" ]]; then + test_args+=( + --logger "GitHubActions;report-warnings=false" + /p:CollectCoverage=true + /p:CoverletOutputFormat=opencover + ) + fi dotnet test ${{ github.workspace }}/test/Dapr.E2E.Test.Actors.Generators/Dapr.E2E.Test.Actors.Generators.csproj \ --configuration Release \ --framework ${{ matrix.framework }} \ --no-build \ --no-restore \ - --logger "trx;LogFilePrefix=${{ matrix.prefix }}" \ - --logger "GitHubActions;report-warnings=false" \ - --logger "console;verbosity=detailed" \ --results-directory "${{ github.workspace }}/TestResults" \ - /p:CollectCoverage=true \ - /p:CoverletOutputFormat=opencover \ + "${test_args[@]}" \ /p:GITHUB_ACTIONS=false - name: Check test failure in PR if: github.event_name == 'pull_request' && (steps.tests.outcome != 'success' || steps.generator-tests.outcome != 'success') diff --git a/.github/workflows/sdk_build.yml b/.github/workflows/sdk_build.yml index 0e9bc14c8..6775f831a 100644 --- a/.github/workflows/sdk_build.yml +++ b/.github/workflows/sdk_build.yml @@ -216,6 +216,77 @@ jobs: printf 'matrix=%s\n' "$matrix_json" >> "$GITHUB_OUTPUT" + compute-integration-matrix-net11: + runs-on: ubuntu-latest + permissions: + contents: read + needs: [ discover-integration-v2-tests, get-dapr-versions ] + outputs: + matrix: ${{ steps.build.outputs.matrix }} + steps: + - id: build + shell: bash + run: | + set -euo pipefail + + projects_raw='${{ needs.discover-integration-v2-tests.outputs.projects }}' + dapr_raw='${{ needs.get-dapr-versions.outputs.matrix_json }}' + + if [ -z "${projects_raw}" ] || [ "${projects_raw}" = "null" ]; then + projects_raw='[]' + fi + if [ -z "${dapr_raw}" ] || [ "${dapr_raw}" = "null" ]; then + dapr_raw='[]' + fi + + dotnets='[ + {"dotnet-version":"11.0", "display-name":".NET 11.0", "framework":"net11.0", "prefix":"net11", "install-version":"11.0.x"} + ]' + oss='["ubuntu-latest"]' + + dapr_array=$( + jq -cn --argjson d "$dapr_raw" ' + if ($d|type) == "array" then + $d + elif ($d|type) == "object" and ($d|has("include")) then + $d.include + elif ($d|type) == "object" then + [$d] + else + [] + end + ' + ) + + matrix_json=$( + jq -cn \ + --argjson projects "$projects_raw" \ + --argjson dotnets "$dotnets" \ + --argjson oss "$oss" \ + --argjson dapr "$dapr_array" ' + [ + $projects[] as $p + | $dotnets[] as $d + | $oss[] as $o + | $dapr[] as $dv + | { + project: $p.project, + projectName: $p.projectName, + "dotnet-version": $d["dotnet-version"], + "display-name": $d["display-name"], + framework: $d.framework, + prefix: $d.prefix, + "install-version":$d["install-version"], + os: $o, + "dapr-runtime-versions": $dv + } + ] + | { include: . } + ' + ) + + printf 'matrix=%s\n' "$matrix_json" >> "$GITHUB_OUTPUT" + integration-tests-v2: name: ${{ matrix.prefix }}-${{ matrix['dapr-runtime-versions'].version }}-${{ matrix.projectName }} needs: [ compute-integration-matrix ] @@ -264,9 +335,52 @@ jobs: with: TRX_PATH: ${{ github.workspace }}/TestResults REPO_TOKEN: ${{ secrets.GITHUB_TOKEN }} + integration-tests-net11: + name: ${{ matrix.prefix }}-${{ matrix['dapr-runtime-versions'].version }}-${{ matrix.projectName }} + needs: [ compute-integration-matrix-net11 ] + runs-on: ${{ matrix.os }} + permissions: + checks: write + contents: read + timeout-minutes: 60 + strategy: + fail-fast: false + matrix: ${{ fromJson(needs.compute-integration-matrix-net11.outputs.matrix) }} + steps: + - uses: actions/checkout@v6 + - name: Remove global.json (use .NET 11 preview SDK) + run: rm global.json + - name: Setup ${{ matrix.display-name }} + uses: actions/setup-dotnet@v5 + with: + dotnet-version: ${{ matrix.install-version }} + dotnet-quality: 'preview' + - name: Integration Tests + id: integration-tests-net11 + continue-on-error: false + env: + DAPR_RUNTIME_VERSION: ${{ matrix.dapr-runtime-versions.version }} + DaprEnableNet11: 'true' + run: | + dotnet test "${{ matrix.project }}" \ + --configuration release \ + --framework ${{ matrix.framework }} \ + --logger "trx;LogFilePrefix=${{ matrix.prefix }}" \ + --logger "console;verbosity=detailed" \ + --results-directory "${{ github.workspace }}/TestResults" \ + /p:RuntimeIdentifier=linux-x64 \ + /p:GITHUB_ACTIONS=false + timeout-minutes: 60 + - name: Parse Trx files + uses: NasAmin/trx-parser@v0.2.0 + id: trx-parser + if: github.event_name != 'pull_request' || github.event.pull_request.head.repo.full_name == github.repository # does not work on PRs from forks + with: + TRX_PATH: ${{ github.workspace }}/TestResults + REPO_TOKEN: ${{ secrets.GITHUB_TOKEN }} ci-integration-tests-gate: runs-on: ubuntu-latest - needs: [integration-tests-v2, integration-test] + needs: [integration-tests-v2, integration-test, integration-tests-net11] steps: - name: "All integration tests passed" run: echo "All unit tests passed" @@ -339,9 +453,51 @@ jobs: with: TRX_PATH: ${{ github.workspace }}/TestResults REPO_TOKEN: ${{ secrets.GITHUB_TOKEN }} + unit-tests-net11: + name: Unit Tests .NET 11.0 / ${{ matrix.project }} + needs: discover-unit-test-projects + runs-on: ubuntu-latest + permissions: + checks: write + contents: read + strategy: + fail-fast: false + matrix: + project: ${{ fromJson(needs.discover-unit-test-projects.outputs.matrix) }} + steps: + - uses: actions/checkout@v6 + - name: Remove global.json (use .NET 11 preview SDK) + run: rm global.json + - name: Setup .NET 11.0 + uses: actions/setup-dotnet@v5 + with: + dotnet-version: '11.0.x' + dotnet-quality: 'preview' + - name: Test + env: + DaprEnableNet11: 'true' + id: tests + continue-on-error: false + run: | + dotnet test "${{ matrix.project }}" \ + --configuration release \ + --framework net11.0 \ + --logger "trx;LogFilePrefix=net11" \ + --logger "console;verbosity=detailed" \ + --results-directory "${{ github.workspace }}/TestResults" \ + /p:RuntimeIdentifier=linux-x64 \ + /p:GITHUB_ACTIONS=false + timeout-minutes: 60 + - name: Parse Trx files + uses: NasAmin/trx-parser@v0.2.0 + id: trx-parser + if: github.event_name != 'pull_request' || github.event.pull_request.head.repo.full_name == github.repository # does not work on PRs from forks + with: + TRX_PATH: ${{ github.workspace }}/TestResults + REPO_TOKEN: ${{ secrets.GITHUB_TOKEN }} ci-unit-tests-gate: runs-on: ubuntu-latest - needs: [unit-tests] + needs: [unit-tests, unit-tests-net11] steps: - name: "All unit tests passed" run: echo "All unit tests passed" diff --git a/Directory.Packages.props b/Directory.Packages.props index 92789459a..b1008c17b 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -22,9 +22,11 @@ + + @@ -36,19 +38,27 @@ - - - - - - - - + + + + + + + + + + + + + + + + - + diff --git a/examples/Directory.Build.props b/examples/Directory.Build.props index 3c92edf6c..30840b961 100644 --- a/examples/Directory.Build.props +++ b/examples/Directory.Build.props @@ -3,6 +3,7 @@ net8.0;net9.0;net10.0 + $(TargetFrameworks);net11.0 $(RepoRoot)bin\$(Configuration)\examples\$(MSBuildProjectName)\ diff --git a/src/Directory.Build.props b/src/Directory.Build.props index b8fda5632..955ca5a38 100644 --- a/src/Directory.Build.props +++ b/src/Directory.Build.props @@ -5,6 +5,7 @@ net8.0;net9.0;net10.0 + $(TargetFrameworks);net11.0 $(RepoRoot)bin\$(Configuration)\prod\$(MSBuildProjectName)\ $(DefaultItemExcludes);**\obj\**;**\bin\** diff --git a/test/Dapr.Actors.Analyzers.Test/TimerCallbackMethodPresentAnalyzerTests.cs b/test/Dapr.Actors.Analyzers.Test/TimerCallbackMethodPresentAnalyzerTests.cs index 0def07285..4663843ad 100644 --- a/test/Dapr.Actors.Analyzers.Test/TimerCallbackMethodPresentAnalyzerTests.cs +++ b/test/Dapr.Actors.Analyzers.Test/TimerCallbackMethodPresentAnalyzerTests.cs @@ -25,6 +25,11 @@ public class TimerCallbackMethodPresentAnalyzerTests private static readonly ReferenceAssemblies assemblies = ReferenceAssemblies.Net.Net90; #elif NET10_0 private static readonly ReferenceAssemblies assemblies = ReferenceAssemblies.Net.Net100; + #elif NET11_0 + private static readonly ReferenceAssemblies assemblies = new ReferenceAssemblies( + "net11.0", + new PackageIdentity("Microsoft.NETCore.App.Ref", "11.0.0-preview.7.26381.103"), + Path.Combine("ref", "net11.0")); #endif [Fact] @@ -146,4 +151,3 @@ public async Task DoSomethingAsync() - diff --git a/test/Dapr.Actors.Generators.Test/CSharpSourceGeneratorVerifier.cs b/test/Dapr.Actors.Generators.Test/CSharpSourceGeneratorVerifier.cs index 828426818..7c179453a 100644 --- a/test/Dapr.Actors.Generators.Test/CSharpSourceGeneratorVerifier.cs +++ b/test/Dapr.Actors.Generators.Test/CSharpSourceGeneratorVerifier.cs @@ -38,6 +38,8 @@ public Test() 9; #elif NET10_0 10; +#elif NET11_0 + 11; #endif // @@ -53,7 +55,11 @@ public Test() $"net{frameworkVersion}.0", new PackageIdentity( "Microsoft.NETCore.App.Ref", +#if NET11_0 + "11.0.0-preview.7.26381.103"), +#else $"{frameworkVersion}.0.0"), +#endif Path.Combine("ref", $"net{frameworkVersion}.0")); } diff --git a/test/Dapr.Actors.Next.Analyzers.Test/AnalyzerTest.cs b/test/Dapr.Actors.Next.Analyzers.Test/AnalyzerTest.cs index 85eb0be6e..e35fa0554 100644 --- a/test/Dapr.Actors.Next.Analyzers.Test/AnalyzerTest.cs +++ b/test/Dapr.Actors.Next.Analyzers.Test/AnalyzerTest.cs @@ -108,6 +108,11 @@ private static void AddReferences(Microsoft.CodeAnalysis.Testing.Anal test.ReferenceAssemblies = ReferenceAssemblies.Net.Net90; #elif NET10_0 test.ReferenceAssemblies = ReferenceAssemblies.Net.Net100; +#elif NET11_0 + test.ReferenceAssemblies = new ReferenceAssemblies( + "net11.0", + new PackageIdentity("Microsoft.NETCore.App.Ref", "11.0.0-preview.7.26381.103"), + Path.Combine("ref", "net11.0")); #endif test.TestState.AdditionalReferences.Add(MetadataReference.CreateFromFile(typeof(Actor).Assembly.Location)); test.TestState.AdditionalReferences.Add(MetadataReference.CreateFromFile(typeof(DaprActorAttribute).Assembly.Location)); @@ -124,6 +129,11 @@ private static void AddReferences(Microsoft.CodeAnalysis.Testing.Code test.ReferenceAssemblies = ReferenceAssemblies.Net.Net90; #elif NET10_0 test.ReferenceAssemblies = ReferenceAssemblies.Net.Net100; +#elif NET11_0 + test.ReferenceAssemblies = new ReferenceAssemblies( + "net11.0", + new PackageIdentity("Microsoft.NETCore.App.Ref", "11.0.0-preview.7.26381.103"), + Path.Combine("ref", "net11.0")); #endif test.TestState.AdditionalReferences.Add(MetadataReference.CreateFromFile(typeof(Actor).Assembly.Location)); test.TestState.AdditionalReferences.Add(MetadataReference.CreateFromFile(typeof(DaprActorAttribute).Assembly.Location)); diff --git a/test/Dapr.Analyzers.Common/TestUtilities.cs b/test/Dapr.Analyzers.Common/TestUtilities.cs index 92d569974..c5936ded9 100644 --- a/test/Dapr.Analyzers.Common/TestUtilities.cs +++ b/test/Dapr.Analyzers.Common/TestUtilities.cs @@ -37,6 +37,11 @@ internal static class TestUtilities var referenceAssemblies = ReferenceAssemblies.Net.Net90; #elif NET10_0 var referenceAssemblies = ReferenceAssemblies.Net.Net100; +#elif NET11_0 + var referenceAssemblies = new ReferenceAssemblies( + "net11.0", + new PackageIdentity("Microsoft.NETCore.App.Ref", "11.0.0-preview.7.26381.103"), + Path.Combine("ref", "net11.0")); #endif // Create a new project with necessary references diff --git a/test/Dapr.Analyzers.Common/VerifyAnalyzer.cs b/test/Dapr.Analyzers.Common/VerifyAnalyzer.cs index baeeec4b3..c3f35ecc2 100644 --- a/test/Dapr.Analyzers.Common/VerifyAnalyzer.cs +++ b/test/Dapr.Analyzers.Common/VerifyAnalyzer.cs @@ -39,6 +39,11 @@ public async Task VerifyAnalyzerAsync(string source, string? program, test.ReferenceAssemblies = ReferenceAssemblies.Net.Net90; #elif NET10_0 test.ReferenceAssemblies = ReferenceAssemblies.Net.Net100; +#elif NET11_0 + test.ReferenceAssemblies = new ReferenceAssemblies( + "net11.0", + new PackageIdentity("Microsoft.NETCore.App.Ref", "11.0.0-preview.7.26381.103"), + Path.Combine("ref", "net11.0")); #endif if (program != null) @@ -78,4 +83,3 @@ public Test() } } } - diff --git a/test/Dapr.E2E.Test/DaprTestApp.cs b/test/Dapr.E2E.Test/DaprTestApp.cs index ecab50d89..83b009227 100644 --- a/test/Dapr.E2E.Test/DaprTestApp.cs +++ b/test/Dapr.E2E.Test/DaprTestApp.cs @@ -144,6 +144,7 @@ private static string GetTargetFrameworkName() ".NETCoreApp,Version=v8.0" => "net8.0", ".NETCoreApp,Version=v9.0" => "net9.0", ".NETCoreApp,Version=v10.0" => "net10.0", + ".NETCoreApp,Version=v11.0" => "net11.0", _ => throw new InvalidOperationException($"Unsupported target framework: {targetFrameworkName}") }; } diff --git a/test/Dapr.Extensions.Configuration.Test/DaprSecretStoreConfigurationProviderTest.cs b/test/Dapr.Extensions.Configuration.Test/DaprSecretStoreConfigurationProviderTest.cs index 54536896e..4dcdd402b 100644 --- a/test/Dapr.Extensions.Configuration.Test/DaprSecretStoreConfigurationProviderTest.cs +++ b/test/Dapr.Extensions.Configuration.Test/DaprSecretStoreConfigurationProviderTest.cs @@ -963,6 +963,7 @@ public async Task LoadSecrets_OptionalWithDescriptors_PopulatesConfig() var storeName = "store"; var secretKey = "mySecret"; var secretValue = "myValue"; + var continueSecretFetch = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); var daprClient = new Mock(); // Sidecar ready immediately @@ -972,7 +973,11 @@ public async Task LoadSecrets_OptionalWithDescriptors_PopulatesConfig() daprClient .Setup(c => c.GetSecretAsync(storeName, secretKey, It.IsAny>(), It.IsAny())) - .ReturnsAsync(new Dictionary { { secretKey, secretValue } }); + .Returns(async () => + { + await continueSecretFetch.Task; + return new Dictionary { { secretKey, secretValue } }; + }); var secretDescriptors = new[] { new DaprSecretDescriptor(secretKey) }; @@ -983,6 +988,7 @@ public async Task LoadSecrets_OptionalWithDescriptors_PopulatesConfig() // Wait for the reload token to fire, indicating background load completed var reloaded = new TaskCompletionSource(); config.GetReloadToken().RegisterChangeCallback(_ => reloaded.TrySetResult(true), null); + continueSecretFetch.SetResult(true); await reloaded.Task.WaitAsync(TimeSpan.FromSeconds(5), TestContext.Current.CancellationToken); config[secretKey].ShouldBe(secretValue); diff --git a/test/Dapr.IntegrationTest.Workflow.Versioning/RegistrationOrderRegressionIntegrationTests.cs b/test/Dapr.IntegrationTest.Workflow.Versioning/RegistrationOrderRegressionIntegrationTests.cs index 8d59db4b4..360948c27 100644 --- a/test/Dapr.IntegrationTest.Workflow.Versioning/RegistrationOrderRegressionIntegrationTests.cs +++ b/test/Dapr.IntegrationTest.Workflow.Versioning/RegistrationOrderRegressionIntegrationTests.cs @@ -23,7 +23,7 @@ using Grpc.Core; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; -#if NET10_0 +#if NET10_0_OR_GREATER using System.Diagnostics; using System.IO.Compression; using System.Xml.Linq; @@ -90,7 +90,7 @@ public async Task SchedulingCanonicalWorkflowNameShouldRunLatestGeneratedVersion Assert.Equal("v3:runtime", state.ReadOutputAs()); } -#if NET10_0 +#if NET10_0_OR_GREATER [Fact] public void PackedDaprWorkflowPackageShouldExposeVersioningAndRouteCanonicalNameToLatest() { @@ -274,7 +274,7 @@ private static async Task WaitForSidecarAsync(DaprTestApplication app, TimeSpan private static bool IsTransientRpc(RpcException ex) => ex.StatusCode is StatusCode.Unavailable or StatusCode.DeadlineExceeded; -#if NET10_0 +#if NET10_0_OR_GREATER private static string FindRepoRoot() { var current = new DirectoryInfo(AppContext.BaseDirectory); diff --git a/test/Dapr.Jobs.Analyzer.Test/MapDaprScheduledJobHandlerTest.cs b/test/Dapr.Jobs.Analyzer.Test/MapDaprScheduledJobHandlerTest.cs index eaa49c9ad..f57097f05 100644 --- a/test/Dapr.Jobs.Analyzer.Test/MapDaprScheduledJobHandlerTest.cs +++ b/test/Dapr.Jobs.Analyzer.Test/MapDaprScheduledJobHandlerTest.cs @@ -12,6 +12,11 @@ public class DaprJobsAnalyzerAnalyzerTests private static readonly ReferenceAssemblies referenceAssemblies = ReferenceAssemblies.Net.Net90; #elif NET10_0 private static readonly ReferenceAssemblies referenceAssemblies = ReferenceAssemblies.Net.Net100; +#elif NET11_0 + private static readonly ReferenceAssemblies referenceAssemblies = new ReferenceAssemblies( + "net11.0", + new PackageIdentity("Microsoft.NETCore.App.Ref", "11.0.0-preview.7.26381.103"), + Path.Combine("ref", "net11.0")); #endif [Fact] diff --git a/test/Dapr.Packaging.Test/AggregatorPackageTests.cs b/test/Dapr.Packaging.Test/AggregatorPackageTests.cs index b1bdc23c2..287e1f2f1 100644 --- a/test/Dapr.Packaging.Test/AggregatorPackageTests.cs +++ b/test/Dapr.Packaging.Test/AggregatorPackageTests.cs @@ -8,7 +8,7 @@ namespace Dapr.Packaging.Test; -#if NET10_0 +#if NET10_0_OR_GREATER public sealed class AggregatorPackageTests { public static TheoryData PackagesWithBundledAssets => new() diff --git a/test/Directory.Build.props b/test/Directory.Build.props index 0e07a0a47..083f62923 100644 --- a/test/Directory.Build.props +++ b/test/Directory.Build.props @@ -4,6 +4,7 @@ net8.0;net9.0;net10.0 + $(TargetFrameworks);net11.0 $(RepoRoot)bin\$(Configuration)\test\$(MSBuildProjectName)\ @@ -18,7 +19,7 @@ - +