Skip to content

feat(catalog): route cache-save warning through ctx-scoped logger#31

Merged
kevinelliott merged 1 commit intomainfrom
feat/catalog-ctx-logger
Apr 21, 2026
Merged

feat(catalog): route cache-save warning through ctx-scoped logger#31
kevinelliott merged 1 commit intomainfrom
feat/catalog-ctx-logger

Conversation

@kevinelliott
Copy link
Copy Markdown
Owner

Summary

`doRefresh` now emits its cache-save warn via `logging.FromContext(ctx).Warn(...)` instead of the package-level `slog.Warn`. This lets callers:

  • Attach a request-scoped logger via `logging.WithContext` to tag events with trigger source.
  • Correlate cache-save failures with an outer request or background tick.
  • Inject a test logger to assert events fired (as the updated test now does).

Behavior in production

Unchanged. Without an attached logger, `FromContext` falls back to `slog.Default`, which `logging.Install(logging.New(cfg))` in each `main` has already pointed at the configured handler.

Test

`TestManagerRefresh_LogsCacheSaveErrorButSucceeds` now attaches a test logger via `logging.WithContext` and asserts the warn event reaches it — previously we only tested that the cache-error path didn't fail the refresh.

Not changed

`mustMarshal`'s `slog.Warn` is untouched: its signature has no ctx and that path is a should-never-fire marshal of a struct we control.

Test plan

  • `go test ./pkg/catalog/... -race` green
  • `make lint` clean
  • `go test ./... -race -short` green

🤖 Generated with Claude Code

doRefresh's cache-write failure path now uses
logging.FromContext(ctx).Warn(...) instead of the package-level
slog.Warn. Callers can attach a request-scoped logger via
logging.WithContext to tag events with trigger source, correlate
with an outer request, or inject a test logger to assert events
fired — exactly the pattern pkg/logging was designed for.

Behavior unchanged in production: without an attached logger,
FromContext falls back to slog.Default, which logging.Install
has already pointed at the configured handler.

Updates TestManagerRefresh_LogsCacheSaveErrorButSucceeds to attach
a test logger via logging.WithContext and assert the warn event
reaches it — previously we only tested that the cache-error path
didn't fail the refresh.

mustMarshal's slog.Warn is untouched: its signature has no ctx
and that path is a should-never-fire marshal of a struct we
control.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings April 21, 2026 12:56
Copy link
Copy Markdown

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

Routes the catalog cache-save warning through a context-attached *slog.Logger so callers can inject/request-scope logging (and tests can assert on emitted events) while keeping production behavior unchanged via fallback to slog.Default().

Changes:

  • Replace slog.Warn(...) in Manager.doRefresh with logging.FromContext(ctx).Warn(...).
  • Update TestManagerRefresh_LogsCacheSaveErrorButSucceeds to attach a context-scoped test logger and assert the warn event is emitted to it.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.

File Description
pkg/catalog/manager.go Emits cache-save warning via ctx-scoped logger (logging.FromContext(ctx)) instead of package-level slog.Warn.
pkg/catalog/manager_test.go Injects a test logger into context and asserts the warn log is produced on the ctx-scoped logger.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread pkg/catalog/manager.go
Comment on lines +171 to +174
// Non-fatal: we still have the catalog in memory. Use the
// request-scoped logger so operators can tag refresh events
// (e.g. with a trigger source) at the call site.
logging.FromContext(ctx).Warn("catalog: failed to persist cache",
Copy link

Copilot AI Apr 21, 2026

Choose a reason for hiding this comment

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

Because Refresh() coalesces concurrent calls via singleflight, the ctx passed into doRefresh (and therefore logging.FromContext(ctx)) will come from whichever caller entered the singleflight first. If the intent is to reliably tag refresh events by trigger source at the call site, this can misattribute the warning when different callers refresh concurrently; consider documenting this limitation here or adjusting the logging to include an explicit trigger field rather than relying solely on the context logger.

Suggested change
// Non-fatal: we still have the catalog in memory. Use the
// request-scoped logger so operators can tag refresh events
// (e.g. with a trigger source) at the call site.
logging.FromContext(ctx).Warn("catalog: failed to persist cache",
// Non-fatal: we still have the catalog in memory. Avoid relying on
// the request-scoped logger here because Refresh() coalesces callers
// via singleflight, so the context may belong to a different trigger.
slog.Warn("catalog: failed to persist cache",

Copilot uses AI. Check for mistakes.
@kevinelliott kevinelliott merged commit dc35f25 into main Apr 21, 2026
19 checks passed
@kevinelliott kevinelliott deleted the feat/catalog-ctx-logger branch April 21, 2026 13:05
kevinelliott added a commit that referenced this pull request Apr 24, 2026
Toolchain + dependency refresh. Minimum Go bumped to 1.25 (forced by
x/sync v0.20.0), golangci-lint migrated to v2.11.4, 5 deps bumped
plus 3 patch-level ones from v1.2.0-era. Also captures post-v1.2.0
polish: TUI storage reuse perf win (#33), doctor catalog-source
breakdown (#32), catalog ctx-scoped logger (#31), README refresh (#30).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants