feat(logs): add log4net integration - #5172
4 issues
High
Structured logs not captured for events below MinimumEventLevel due to early return - `src/Sentry.Log4Net/SentryAppender.cs:97-98`
The CaptureStructuredLog call is placed after the early return at line 97-98, so structured logs are never captured for events below MinimumEventLevel. The test DoAppend_StructuredLoggingWithoutException_LeavesBreadcrumb expects structured logs to be captured even for breadcrumb-only events, but this code path returns before reaching CaptureStructuredLog.
Structured logs not captured when log level is below MinimumEventLevel - `src/Sentry.Log4Net/SentryAppender.cs:98`
When EnableLogs is true and the log level is below MinimumEventLevel, structured logs are not captured due to the early return on line 98. The test DoAppend_StructuredLoggingWithoutException_LeavesBreadcrumb expects structured logs to be captured in this scenario, and Serilog's implementation captures structured logs independently of event/breadcrumb thresholds. Add CaptureStructuredLog call before the early return, or refactor to call it at the end regardless of the event/breadcrumb path.
Also found at:
test/Sentry.Log4Net.Tests/SentryAppenderTests.Structured.cs:216
Low
NullReferenceException when loggingEvent.Level is null in ToSentryLogLevel - `src/Sentry.Log4Net/LevelMapping.cs:38-44`
ToSentryLogLevel uses >= comparisons against log4net Level values. log4net's operator >= dereferences the left operand's numeric field without a null check, so a null loggingEvent.Level throws NullReferenceException (the initial level == Level.Off guard is null-safe and falls through). The sibling ToSentryLevel/ToBreadcrumbLevel methods use only ==, which is null-safe and returns null, so those paths handle null gracefully while the structured-log path does not. The thrown NRE is caught by the try/catch around CaptureStructuredLog in Append, so it does not crash the process — but the structured log is silently dropped and an error diagnostic is logged, giving inconsistent behavior versus the event/breadcrumb paths. Add null => null, as the first switch arm to match the other mappers.
Whitespace-only property keys handled inconsistently between structured logs and events - `src/Sentry.Log4Net/SentryAppender.Structured.cs:35-37`
Use !string.IsNullOrWhiteSpace(key) instead of key.Length != 0 to match the filtering in GetLoggingEventProperties, which filters whitespace-only keys. Currently, a property key like " " would be included in structured logs but filtered from SentryEvent extras.
4 skills analyzed
| Skill | Findings | Duration | Cost |
|---|---|---|---|
| security-review | 0 | 1m 7s | $0.31 |
| code-review | 1 | 3m 58s | $2.38 |
| find-bugs | 3 | 9m 39s | $5.11 |
| gha-security-review | 0 | 6m 41s | $0.50 |
⏱ 21m 26s · 2.8M in / 141.5k out · $8.30