Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Upgrade to latest mimir-prometheus@main #9844

Draft
wants to merge 15 commits into
base: main
Choose a base branch
from

Conversation

aknuds1
Copy link
Contributor

@aknuds1 aknuds1 commented Nov 6, 2024

What this PR does

Upgrade to latest mimir-prometheus@main, which syncs in Prometheus 3.0 changes.

NB: I add a go-kit/log to slog adapter, since Prometheus now uses the latter.

Which issue(s) this PR fixes or relates to

Checklist

  • Tests updated.
  • Documentation added.
  • CHANGELOG.md updated - the order of entries should be [CHANGE], [FEATURE], [ENHANCEMENT], [BUGFIX].
  • about-versioning.md updated with experimental features.

@aknuds1 aknuds1 force-pushed the arve/upgrade-mimir-prometheus branch 22 times, most recently from cb6d823 to a1b4f48 Compare November 7, 2024 16:53
@aknuds1 aknuds1 changed the title WIP: Upgrade to latest mimir-prometheus@main Upgrade to latest mimir-prometheus@main Nov 8, 2024
@aknuds1 aknuds1 force-pushed the arve/upgrade-mimir-prometheus branch from a1b4f48 to 6a3bfe1 Compare November 8, 2024 10:19
@bboreham
Copy link
Contributor

bboreham commented Nov 8, 2024

To address one small set of test failures: #9854
(The number changes because Prometheus 3.0 changed a window like rate ... [1m] from including both ends to excluding the left-hand end (it is "left-open")).

@aknuds1 aknuds1 force-pushed the arve/upgrade-mimir-prometheus branch 5 times, most recently from 71feed6 to 69c0bd2 Compare November 11, 2024 09:45
Comment on lines +20 to +98
type goKitHandler struct {
logger log.Logger
group string
}

func (h goKitHandler) Enabled(_ context.Context, level slog.Level) bool {
x, ok := h.logger.(leveledLogger)
if !ok {
return true
}

l := x.level()
switch level {
case slog.LevelInfo:
return l <= infoLevel
case slog.LevelWarn:
return l <= warnLevel
case slog.LevelError:
return l <= errorLevel
default:
return l <= debugLevel
}
}

func (h goKitHandler) Handle(_ context.Context, record slog.Record) error {
var logger log.Logger
switch record.Level {
case slog.LevelInfo:
logger = level.Info(h.logger)
case slog.LevelWarn:
logger = level.Warn(h.logger)
case slog.LevelError:
logger = level.Error(h.logger)
default:
logger = level.Debug(h.logger)
}

if h.group == "" {
pairs := make([]any, 0, record.NumAttrs()+2)
pairs = append(pairs, "msg", record.Message)
record.Attrs(func(attr slog.Attr) bool {
pairs = append(pairs, attr.Key, attr.Value)
return true
})
return logger.Log(pairs...)
}

pairs := make([]any, 0, record.NumAttrs())
record.Attrs(func(attr slog.Attr) bool {
pairs = append(pairs, attr.Key, attr.Value)
return true
})
g := slog.Group(h.group, pairs...)
pairs = []any{"msg", record.Message, g.Key, g.Value}
return logger.Log(pairs...)
}

func (h goKitHandler) WithAttrs(attrs []slog.Attr) slog.Handler {
pairs := make([]any, 0, len(attrs))
for _, attr := range attrs {
pairs = append(pairs, attr.Key, attr.Value)
}

if h.group == "" {
return goKitHandler{logger: log.With(h.logger, pairs...)}
}

g := slog.Group(h.group, pairs...)
return goKitHandler{logger: log.With(h.logger, g.Key, g.Value)}
}

func (h goKitHandler) WithGroup(name string) slog.Handler {
if name == "" {
return h
}

h.group = name
return h
}
Copy link

Choose a reason for hiding this comment

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

I'm not sure what kind of tolerances are required for mimir, but I believe the current implementation may be a bit naive. For instance, the WithGroup docs on the slog.Handler state:

// WithGroup returns a new Handler with the given group appended to
// the receiver's existing groups.

It is indeed possible to have more than 1 group; here's output from a contrived example (playground):

time=2009-11-10T23:00:00.000Z level=INFO msg=test g1.g2.hello=world
time=2009-11-10T23:00:00.000Z level=INFO msg=test g1.hello=world g1.hello=world
time=2009-11-10T23:00:00.000Z level=INFO msg=test g1.hello=world g1.g2.hello=world
time=2009-11-10T23:00:00.000Z level=INFO msg=test hello=world hello=world hello=world

However, attempting any similar log calls with a logger produced by SlogFromGoKit() panics in the implementation of Handle()

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@tjhop yeah, admittedly I was uncertain about the WithGroup implementation, thanks for producing a failing example. Are you able to identify any problems with the other goKitHandler methods?

Copy link

Choose a reason for hiding this comment

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

Seems I might've been too hasty in reading the panic message, it actually seems the panic was related to me half-assing the mock logger calls when first playing with this. Better mocking out the same contrived log statements as that playground example, I get this from the handler:

level=info msg=test g2="[hello=world]"
level=info g1="[hello=world]" msg=test hello=world
level=info g1="[hello=world]" msg=test g2="[hello=world]"
level=info hello=world hello=world msg=test hello=world

A few thoughts:

  • slog includes the time by default -- currently the implementation doesn't forward the timestamp from the record along into the kv pairs that get passed to logger.Log()

  • ordering is a bit different, but given the purpose of structured logging, I'd argue it's fine

  • like we already acknowledged, grouping needs some adjustment to properly nest. this patch gets us a bit closer, but still needs further tweaking:

    ~/go/src/github.com/grafana/mimir (arve/upgrade-mimir-prometheus [ U ]) -> gd pkg/util/log/slogadapter.go
    diff --git a/pkg/util/log/slogadapter.go b/pkg/util/log/slogadapter.go
    index 66f084dce3..381a7cdcae 100644
    --- a/pkg/util/log/slogadapter.go
    +++ b/pkg/util/log/slogadapter.go
    @@ -93,6 +93,11 @@ func (h goKitHandler) WithGroup(name string) slog.Handler {
                    return h
            }
    
    -       h.group = name
    +       if h.group == "" {
    +               h.group = name
    +       } else {
    +               h.group = h.group + "." + name
    +       }
    +
            return h
     }
    
    level=info msg=test g1.g2="[hello=world]"
    level=info g1="[hello=world]" msg=test hello=world
    level=info g1="[hello=world]" msg=test g2="[hello=world]"
    level=info hello=world hello=world msg=test hello=world
    

Copy link

Choose a reason for hiding this comment

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

@aknuds1 I think I have something pretty functional -- mind if I PR against this branch?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@tjhop feel free :)

@aknuds1 aknuds1 force-pushed the arve/upgrade-mimir-prometheus branch from 69c0bd2 to a364680 Compare November 12, 2024 07:27
@aknuds1 aknuds1 mentioned this pull request Nov 12, 2024
4 tasks
@aknuds1 aknuds1 force-pushed the arve/upgrade-mimir-prometheus branch 3 times, most recently from dae507f to 78797ed Compare November 15, 2024 10:43
@charleskorn
Copy link
Contributor

charleskorn commented Nov 19, 2024

MQE changes to unblock this are in #9948.

@aknuds1 aknuds1 force-pushed the arve/upgrade-mimir-prometheus branch from 78797ed to d920e20 Compare November 19, 2024 08:49
@aknuds1
Copy link
Contributor Author

aknuds1 commented Nov 19, 2024

MQE changes to unblock this are in #9948.

Thanks @charleskorn - included your changes there into this PR.

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.

4 participants