Continuing work on Azure framework tasks - #837
Conversation
Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
| var appDirectory = Environment.GetEnvironmentVariable("ARK_AZF_FUNCTION_APP_DIR") | ||
| ?? FindFunctionAppDirectory(); | ||
| var port = GetAvailablePort(); | ||
| var logPath = Path.Combine(Path.GetTempPath(), $"ark-azf-{Guid.NewGuid():N}.log"); |
| var candidate = Path.Combine( | ||
| directory.FullName, | ||
| "samples/Ark.MediatorFramework.Sample/src/Ark.MediatorFramework.Sample.AzureFunctions/bin/Debug/net10.0"); | ||
| if (File.Exists(Path.Combine(candidate, "host.json"))) |
There was a problem hiding this comment.
Pull request overview
Adds an Azure Functions (isolated worker) boundary test suite for the mediator framework sample, plus documentation and CI coverage to ensure Azure Functions trigger generation and selected endpoint parity stay stable over time.
Changes:
- Added
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Teststo launch the built sample via Azure Functions Core Tools and validate readiness + endpoint inventory. - Documented Azure Functions transport usage and recorded a parity matrix for the boundary-tested contract set.
- Integrated the boundary suite into CI with Core Tools installation and log artifact upload on failures.
Reviewed changes
Copilot reviewed 10 out of 10 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
| tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/README.md | Documents how to build/run the new boundary suite locally and how logs are handled. |
| tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/packages.lock.json | Adds lockfile for the new boundary test project to support locked restore in CI. |
| tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/AzureFunctionsBoundaryTests.cs | Implements Core Tools process hosting, readiness probing, and endpoint parity inventory assertion. |
| tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests.csproj | Introduces the new boundary test project and references the Azure Functions sample host. |
| samples/Ark.MediatorFramework.Sample/README.md | Links the Azure Functions sample host entry to the new guide page. |
| docs/mediator-framework/progress/tasks/README.md | Marks AZF-10 as completed in progress tracking. |
| docs/mediator-framework/progress/tasks/azure-functions/AZF-10-boundary-parity.md | Adds the parity matrix documenting the boundary-tested contract inventory. |
| docs/mediator-framework/guide/README.md | Adds the Azure Functions guide entry to the mediator framework guide index. |
| docs/mediator-framework/guide/azure-functions.md | New guide explaining Azure Functions isolated worker integration and boundary testing strategy. |
| .github/workflows/ci.yml | Adds a CI job to install Core Tools and run the new boundary tests, uploading sanitized logs on failure. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| private async Task WaitForReadinessAsync(CancellationToken cancellationToken) | ||
| { | ||
| using var client = new HttpClient { BaseAddress = BaseAddress }; | ||
| var deadline = Stopwatch.GetTimestamp() + StartupTimeout.Ticks * (Stopwatch.Frequency / TimeSpan.TicksPerSecond); |
| process.StartInfo.Environment["AzureServiceBus__ConnectionString"] = | ||
| "boundary.invalid"; |
| _ = CaptureAsync(process.StandardOutput, log); | ||
| _ = CaptureAsync(process.StandardError, log); |
| if (!process.Start()) | ||
| throw new InvalidOperationException("Azure Functions Core Tools did not start."); |
|
@copilot Fix the code for all comments in this review thread. Fix also all open code quality comments. Do not make changes beyond what is described in the linked review thread. Review the findings before fixing as may be false positives. Addtionally integrate master and ensure build and tests succeeds |
…framework-task-again Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 10 out of 10 changed files in this pull request and generated 1 comment.
Suppressed comments (2)
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/AzureFunctionsBoundaryTests.cs:87
SecretPatternsetsRegexOptions.ExplicitCapturebut the replacement uses$1, expecting the first group to be captured. WithExplicitCapture, unnamed groups aren't captured, so the prefix won't be preserved in the sanitized log output.
private static readonly Regex SecretPattern = new(
"(?i)(authorization\\s*:\\s*|connectionstring\\s*[=:]\\s*)[^\\s,;]+",
RegexOptions.Compiled
| RegexOptions.CultureInvariant
| RegexOptions.ExplicitCapture
| RegexOptions.NonBacktracking);
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/AzureFunctionsBoundaryTests.cs:153
PumpLogsAsyncis started with the test cancellation token. If that token is canceled (timeout/abort),_logPumpTaskcan throwOperationCanceledExceptionand preventDisposeAsyncfrom flushing/disposing logs and the process. The log pump should not be canceled by the test token; completion should be driven by_logLines.Writer.TryComplete().
var logLines = Channel.CreateUnbounded<string>();
#pragma warning disable CA2025
var logPumpTask = PumpLogsAsync(log, logLines.Reader, cancellationToken);
#pragma warning restore CA2025
|
@copilot fix ci failure |
…zurite to boundary CI Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
Fixed in the latest commit. The
Changes:
All four review comments addressed (commit
CI fix (latest commit): added |
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 10 out of 10 changed files in this pull request and generated 1 comment.
Suppressed comments (1)
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/AzureFunctionsBoundaryTests.cs:211
- PumpLogsAsync can throw OperationCanceledException when the test cancellation token is signaled (e.g., on timeout), causing DisposeAsync to throw while cleaning up the host and potentially masking the real failure. Swallow cancellation inside the log pump so disposal remains reliable.
{
await foreach (var line in logLines.ReadAllAsync(cancellationToken).ConfigureAwait(false))
await log.WriteLineAsync(SecretPattern.Replace(line, "$1[REDACTED]"), cancellationToken).ConfigureAwait(false);
}
…oped authorization services Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 11 out of 11 changed files in this pull request and generated no new comments.
Suppressed comments (1)
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/AzureFunctionsBoundaryTests.cs:87
- Secret redaction currently stops at
,or;because of[^\s,;]+, so a typical connection string (semicolon-delimited) will only be partially redacted and may leakSharedAccessKey=...or similar segments into the uploaded log artifact. Since these logs are uploaded on CI failure, the sanitizer should redact the whole value through end-of-line.
private static readonly Regex SecretPattern = new(
"(?i)(authorization\\s*:\\s*|connectionstring\\s*[=:]\\s*)[^\\s,;]+",
RegexOptions.Compiled
| RegexOptions.CultureInvariant
| RegexOptions.ExplicitCapture
| RegexOptions.NonBacktracking);
|
@copilot the CI workflow for the boundary test of azure function keeps failing in CI. check design for mediator-framework and its azure function extension in docs/mediator-framework/
|
Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
… generator review in AGENTS.md Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
…feature coverage Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
…ed test host Co-authored-by: AndreaCuneo <5227688+AndreaCuneo@users.noreply.github.com>
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 39 out of 39 changed files in this pull request and generated 1 comment.
Suppressed comments (3)
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Tests/AzureFunctionsBoundaryTests.cs:259
- The log pump is tied to the test cancellation token (and CA2025 is suppressed). If the test token is canceled (timeout/abort),
PumpLogsAsynccan stop early andDisposeAsynccan throw when awaiting_logPumpTask, potentially hiding the real failure and dropping host logs. Prefer running the pump without cancellation and letting_logLines.Writer.TryComplete()end the loop.
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.TestHost/EchoContracts.cs:93 - Parameter name
Requestis PascalCase, which is inconsistent with the codebase naming convention for parameters (camelCase). It also makes the null-check and property access read like type names. Rename it torequest.
docs/mediator-framework/progress/tasks/azure-functions/AZF-10-boundary-parity.md:99 - This doc references a test method
AzureFunctionsBoundaryTests.SelectedApplicationEndpointsMatchTheParityMatrix, but no such method exists in the repo. As written, it implies the parity matrix is enforced by a test when it currently isn’t (or the method was renamed and the doc wasn’t updated).
The inventory guard in `AzureFunctionsBoundaryTests.SelectedApplicationEndpointsMatchTheParityMatrix`
fails when a selected application endpoint is added without a row here. MessagePack contracts
`CreateGreetingRequest` and `DescribeShapeRequest` are intentionally excluded by the sample host.
| source.Append(" ").Append(endpoint.FullyQualifiedType).AppendLine("? _bodyNullable;"); | ||
| source.AppendLine(" try"); | ||
| source.AppendLine(" {"); | ||
| source.Append(" _bodyNullable = await request.ReadFromJsonAsync<").Append(endpoint.FullyQualifiedType).AppendLine(">(cancellationToken).ConfigureAwait(false);"); | ||
| source.Append(" _bodyNullable = await global::Microsoft.AspNetCore.Http.HttpRequestJsonExtensions.ReadFromJsonAsync<").Append(endpoint.FullyQualifiedType).AppendLine(">(request, cancellationToken).ConfigureAwait(false);"); | ||
| source.AppendLine(" }"); |
This pull request introduces Azure Functions isolated worker support for the Mediator Framework sample, including a new end-to-end boundary test suite, improved CI integration, and supporting documentation. The main themes are: Azure Functions host and authentication setup, new testing infrastructure, build and CI improvements, and comprehensive documentation and parity records.
Azure Functions isolated worker and authentication:
Ark.Tools.MediatorFramework.AzureFunctionsandMicrosoft.AspNetCore.Authentication.JwtBearerto the sample Function app, and configured the isolated worker host with proper authentication, including a dedicated integration test scheme for CI/test environments (Program.cs,AzureFunctionsRebusComposition.cs, project files, lock files) [1] [2] [3] [4] [5] [6] [7].Boundary test suite and parity matrix:
Ark.Tools.slnx, new test project files) [1] [2] [3].docs/mediator-framework/guide/azure-functions.md,docs/mediator-framework/progress/tasks/azure-functions/AZF-10-boundary-parity.md) [1] [2].Build, source generation, and CI improvements:
Directory.Build.props,samples/Ark.MediatorFramework.Sample/Directory.Build.props) [1] [2]..github/workflows/ci.yml) [1] [2].Documentation and project structure:
docs/mediator-framework/guide/azure-functions.md,samples/Ark.MediatorFramework.Sample/README.md,docs/mediator-framework/guide/README.md,AGENTS.md) [1] [2] [3] [4].docs/mediator-framework/progress/tasks/README.md).These changes collectively add robust Azure Functions support, with strong test and CI coverage and clear documentation for future maintainers and adopters.This pull request introduces a comprehensive Azure Functions isolated worker boundary test suite for the mediator framework, along with supporting documentation and CI integration. It adds a new test project that launches the built sample host using Azure Functions Core Tools, verifies endpoint readiness and contract parity, and ensures correct behavior at the transport boundary. Documentation is updated to describe Azure Functions support, boundary testing, and the tested contract inventory. CI now runs these boundary tests on every pull request.
Azure Functions boundary test suite:
tests/Ark.Tools.MediatorFramework.AzureFunctions.Boundary.Teststhat launches the built sample host with Azure Functions Core Tools, verifies the/healthCheckendpoint, and checks that all expected HTTP endpoints are generated and available. Host logs are sanitized and uploaded on failure. [1] [2] [3] [4]Documentation updates:
Test coverage and parity tracking:
Project and progress tracking: