Skip to content

Cherry-pick: LogLevel bug fixes#3524

Merged
RubenCerna2079 merged 5 commits intorelease/2.0from
dev/rubencerna/cherry-pick-fix-loglevel-bugs-3
May 7, 2026
Merged

Cherry-pick: LogLevel bug fixes#3524
RubenCerna2079 merged 5 commits intorelease/2.0from
dev/rubencerna/cherry-pick-fix-loglevel-bugs-3

Conversation

@RubenCerna2079
Copy link
Copy Markdown
Contributor

@RubenCerna2079 RubenCerna2079 commented May 6, 2026

Why make this change?

This change cherry-picks the PRs that fix the LogLevel bugs

What is this change?

How was this tested?

Existing tests in cherry-pick cover new changes.

Sample Request(s)

N/A

@RubenCerna2079 RubenCerna2079 changed the title Dev/rubencerna/cherry pick fix loglevel bugs 3 Cherry-pick: LogLevel bug fixes May 6, 2026
RubenCerna2079 and others added 2 commits May 6, 2026 17:30
- Closes issue #3262
The logger for the Startup class is not initialized properly, since this
logger is special due to the nature of the Startup class it needs to be
continuously updated as DAB initializes. This causes two problems:
- Some logs appear even when LogLevel is set to some value that would
impede those logs to appear.
- Some logs don't appear at all, even when LogLevel is set to a value
that should allow them to be logged.

- Closes issue #3256 & #3255
The CLI logger still outputs some logs even when the LogLevel is set to
`none`. It is expected that if the LogLevel set is `none` or some other
level that shouldn't output the `information` level, the logs will not
appear.

Important Note: These changes currently only allow us to change the
LogLevel from the CLI with the `default` namespace in the config file.
An task was created to solve this issue:
#3451

In order to solve issue #3262:
- We removed the LogBuffer from the services inside of `Startup.cs`,
this is necessary since we wanted each class to have its own LogBuffer
so that we are able to tell from which logger the logs are being
outputted.
- Then, we also correctly initialized the `Startup` logger by changing
the method that it was using to initialize the logger, it now uses
`CreateLoggerFactoryForHostedAndNonHostedScenario` which checks if there
are any LogLevel namespaces from the config file that can be applicable
for the specific logger. It is important to note that there are multiple
places where the logs are flushed in order to cover for the cases in
which an exception is found and causes DAB to end abruptly, and when we
there is an IsLateConfigured scenario.
- We also changed the logger for the LogBuffer in all the missing places
where it creates logs before the logger is able to properly initialize
to add those logs to the LogBuffer and only flush them after the loggers
are initialized.

In order to solve issue #3256 & #3255:
- We changed the CLI so that we add all the logs go to a single global
LogBuffer that is created inside the `StartOptions.cs` until it is able
to deserialize the RuntimeConfig and find which level to set the
`LogLevel` in order to flush all the logs.
- This is something that we only want to happen when we use the `dab
start` command, which is why we only make this change in the
`StartOptions.cs` file, on the function `TryStartEngineWithOptions`
inside of `ConfigGenerator.cs`, and a few functions from `Utils.cs` and
`ConfigMerger.cs` that are used inside the `TryStartEngine` function.

- [ ] Integration Tests
- [x] Unit Tests

- dab start --LogLevel none
- dab start --LogLevel error

---------

Co-authored-by: Aniruddh Munde <anmunde@microsoft.com>
## Why make this change?

Enables MCP clients (like MCP Inspector, Claude Desktop, VS Code
Copilot) to receive real-time log output via MCP
`notifications/message`.

Related: #3274 (depends on PR #3419)

## What is this change?

When `logging/setLevel` is called with a level other than "none", logs
are sent to MCP clients as JSON-RPC notifications:

```json
{
  "jsonrpc": "2.0",
  "method": "notifications/message",
  "params": {
    "level": "info",
    "logger": "Azure.DataApiBuilder.Service.Startup",
    "data": "Starting Data API builder..."
  }
}
```

### New files:
- `McpLogNotificationWriter.cs` - Writes logs as MCP notifications to
stdout
- `McpLogger.cs` / `McpLoggerProvider.cs` - ILogger implementation for
.NET logging pipeline
- `McpLogNotificationTests.cs` - Unit tests (8 tests)

### Modified files:
- `Program.cs` - Registers `McpNotificationWriter` and
`McpLoggerProvider` for MCP mode
- `McpStdioServer.cs` - Enables notifications when `logging/setLevel` is
called

## How was this tested?

- Unit tests: 6 tests covering level mapping, enable/disable, JSON
format
- Manual testing with MCP Inspector: verified notifications appear when
`logging/setLevel` is sent

## Note

This PR targets `dev/anushakolan/set-log-level` (PR #3419) as it depends
on the `logging/setLevel` implementation.
@RubenCerna2079 RubenCerna2079 force-pushed the dev/rubencerna/cherry-pick-fix-loglevel-bugs-3 branch from c8019ba to ee75c86 Compare May 7, 2026 00:32
@RubenCerna2079 RubenCerna2079 marked this pull request as ready for review May 7, 2026 00:32
Copilot AI review requested due to automatic review settings May 7, 2026 00:32
@RubenCerna2079 RubenCerna2079 added this to the May 2026 milestone May 7, 2026
@RubenCerna2079 RubenCerna2079 moved this from Todo to Review In Progress in Data API builder May 7, 2026
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This cherry-pick brings in the LogLevel-related fixes (from #3318) to ensure DAB’s Service + CLI + MCP stdio modes respect configured/CLI log levels (including none) and to support dynamic log-level changes and MCP log notifications without corrupting the stdio JSON-RPC channel.

Changes:

  • Adds MCP stdio-safe logging by introducing a lock-protected shared stdout writer and an MCP ILoggerProvider that emits notifications/message.
  • Refactors startup/config-load logging to buffer early logs and apply runtime-config log level resolution (including logger namespace filtering).
  • Updates CLI logging to honor the resolved minimum log level and adjusts/extends unit tests to validate suppression behavior.

Reviewed changes

Copilot reviewed 31 out of 31 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
src/Service/Telemetry/DynamicLogLevelProvider.cs Uses centralized MCP↔.NET log level conversion and supports logger-filtered config log level resolution.
src/Service/Startup.cs Refactors startup log buffering, telemetry logger initialization, and late-config handling; adds a unified flush helper.
src/Service/Program.cs Adds MCP stdio logging setup (provider clearing, dynamic filtering, MCP notification provider wiring).
src/Service.Tests/UnitTests/SqlMetadataProviderUnitTests.cs Stabilizes assertion by waiting for stderr capture and improves failure message.
src/Service.Tests/UnitTests/McpStdoutWriterTests.cs Adds concurrency/disposal tests for the MCP stdout writer.
src/Service.Tests/UnitTests/McpLogNotificationTests.cs Adds tests for MCP log notification writer/provider behavior and JSON framing.
src/Service.Tests/UnitTests/DynamicLogLevelProviderTests.cs Adds concurrency/precedence tests for MCP updates vs CLI override.
src/Service.Tests/TestHelper.cs Ensures runtime config loader has a logger in tests; adds delay/retry helper.
src/Service.Tests/Configuration/RuntimeConfigLoaderTests.cs Updates config loader failure test to use loader logger and new parse-error emission behavior.
src/Service.Tests/Configuration/ConfigurationTests.cs Exposes retry constants for shared use in new delay helper.
src/Core/Telemetry/McpLogLevelConverter.cs Centralizes MCP↔.NET log-level mapping used by multiple components.
src/Config/RuntimeConfigLoader.cs Introduces a shared log buffer for early config-loader logging.
src/Config/LogBuffer.cs Generalizes the prior startup buffer into a reusable buffer that can carry exceptions.
src/Config/FileSystemRuntimeConfigLoader.cs Removes per-instance buffer injection and routes early logs through the shared buffer; adds parse-error emission state.
src/Cli/Utils.cs Adds optional CLI log buffering for early-phase CLI logs; adjusts CLI logger factory creation.
src/Cli/Exporter.cs Updates call-site to the updated config-file precedence helper signature.
src/Cli/CustomLoggerProvider.cs Adds configurable minimum log level and routes Error/Critical to stderr.
src/Cli/ConfigMerger.cs Adds optional CLI buffering for merge logs and errors during dab start.
src/Cli/ConfigGenerator.cs Buffers CLI-phase logs until the effective minimum log level is resolved, then flushes and reconfigures loggers.
src/Cli/Commands/StartOptions.cs Adds a CLI log buffer for dab start and flushes on failure paths.
src/Cli.Tests/ValidateConfigTests.cs Captures stderr (instead of stdout) for validation error messaging; initializes CLI logger factory in env-var test.
src/Cli.Tests/UtilsTests.cs Updates merge-config tests to pass a CLI log buffer.
src/Cli.Tests/EnvironmentTests.cs Adjusts stderr assertions to match new “clean error message” behavior.
src/Cli.Tests/EndToEndTests.cs Adds/adjusts tests for high LogLevel and LogLevel None startup behavior; resets CLI logger factory between tests.
src/Cli.Tests/CustomLoggerTests.cs Splits stdout/stderr expectations and validates Error/Critical go to stderr with correct labels.
src/Azure.DataApiBuilder.Mcp/Telemetry/McpLogNotificationWriter.cs Implements MCP notifications/message emission via shared stdout writer; exposes an enable gate.
src/Azure.DataApiBuilder.Mcp/Telemetry/McpLoggerProvider.cs Adds an MCP ILoggerProvider that caches category loggers and enforces disposal semantics.
src/Azure.DataApiBuilder.Mcp/Telemetry/McpLogger.cs Implements an MCP ILogger that emits notifications and appends exception details.
src/Azure.DataApiBuilder.Mcp/Model/McpStdioJsonRpcErrorCodes.cs Centralizes JSON-RPC version constant.
src/Azure.DataApiBuilder.Mcp/Core/McpStdoutWriter.cs Adds a process-wide, lock-protected stdout owner to prevent JSON-RPC frame interleaving.
src/Azure.DataApiBuilder.Mcp/Core/McpStdioServer.cs Routes JSON-RPC responses through the shared stdout writer and toggles MCP notification gating on logging/setLevel.

Comment thread src/Config/FileSystemRuntimeConfigLoader.cs
Comment thread src/Azure.DataApiBuilder.Mcp/Core/McpStdoutWriter.cs
Comment thread src/Service/Startup.cs
Comment thread src/Service/Startup.cs
Comment thread src/Config/RuntimeConfigLoader.cs
Comment thread src/Cli/Utils.cs
@RubenCerna2079 RubenCerna2079 enabled auto-merge (squash) May 7, 2026 02:22
@RubenCerna2079 RubenCerna2079 merged commit 5c97b5c into release/2.0 May 7, 2026
12 checks passed
@RubenCerna2079 RubenCerna2079 deleted the dev/rubencerna/cherry-pick-fix-loglevel-bugs-3 branch May 7, 2026 03:29
@github-project-automation github-project-automation Bot moved this from Review In Progress to Done in Data API builder May 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

5 participants