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

AlertStore: implementation using thanos objstore bucket client #3888

Conversation

pracucci
Copy link
Contributor

@pracucci pracucci commented Feb 26, 2021

What this PR does:
Similarly to #3805, in this PR I'm introducing the Thanos object store client support to the alertmanager backend clients. The config structure follows the same pattern used for the ruler in #3805.

Important: the BucketAlertStore is not using UserBucketClient yet (so it's not supporting S3 SSE per-tenant overrides) because it will need some changes, due to the structure of the alertmanager config in the bucket. I prefer to do it in a separate PR to keep the diff easier to review.

The ListAlertConfigs is not optimised (configs are loaded 1-by-1). I plan to optimise it in a follow up PR. The problem is that the caller is not optimised (we load all tenants configs and then we filter by shard's ownership). I will fix this in a separate PR.

I suggest to review changes with "Hide whitespace changes" enabled.

Which issue(s) this PR fixes:
N/A

Checklist

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

@pracucci pracucci marked this pull request as draft February 26, 2021 17:18

cfg, err := s.getAlertConfig(ctx, userID)
if err != nil {
return errors.Wrapf(nil, "failed to fetch alertmanager config for user %s", userID)
Copy link
Contributor

Choose a reason for hiding this comment

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

I think Wrapf(nil, ...) will always return nil here - https://pkg.go.dev/github.com/pkg/errors#Wrapf

Did you mean Errorf() here?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Damn, good job spotting it! I meant Wrapf(err, ...).


// NewLegacyAlertStore returns a new alertmanager storage backend poller and store
func NewLegacyAlertStore(cfg LegacyConfig, logger log.Logger) (AlertStore, error) {
if cfg.Type == "configdb" {
Copy link
Contributor

Choose a reason for hiding this comment

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

Use the ConfigDB constant here?

// Config configures the alertmanager backend
type Config struct {
const (
ConfigDB = "configdb"
Copy link
Contributor

Choose a reason for hiding this comment

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

Does this need to be exposed?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

No, it doesn't.

return objectclient.NewAlertStore(client), nil

store := bucketclient.NewBucketAlertStore(bucketClient, cfgProvider, logger)
if err != nil {
Copy link
Contributor

Choose a reason for hiding this comment

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

NewBucketAlertStore doesn't return an error - no need to check err.

Can just return bucketclient.NewBucketAlertStore(...), nil

@pracucci pracucci force-pushed the add-thanos-bucket-client-support-to-alertmanager branch from 61fcd78 to 67ea9f7 Compare March 1, 2021 13:39
@@ -43,38 +47,6 @@ receivers:
- name: dummy`
)

// basic easily configurable mock
type mockAlertStore struct {
Copy link
Contributor Author

Choose a reason for hiding this comment

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

Removed in favour of using a real implementation (the one backed by filesystem) or the bucket.ClientMock when we need to mock the backend (eg. simulate a failure).

Copy link
Contributor

Choose a reason for hiding this comment

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

👍

…Config

Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
Signed-off-by: Marco Pracucci <marco@pracucci.com>
@pracucci pracucci force-pushed the add-thanos-bucket-client-support-to-alertmanager branch from 4a47c3f to c0e225f Compare March 1, 2021 14:41
@pracucci pracucci marked this pull request as ready for review March 1, 2021 14:41
Copy link
Contributor

@stevesg stevesg left a comment

Choose a reason for hiding this comment

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

LGTM!

Copy link
Contributor

@jtlisi jtlisi left a comment

Choose a reason for hiding this comment

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

LGTM, great work

@@ -43,38 +47,6 @@ receivers:
- name: dummy`
)

// basic easily configurable mock
type mockAlertStore struct {
Copy link
Contributor

Choose a reason for hiding this comment

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

👍

Comment on lines +82 to +84
if cfg.Backend == local.Name {
return local.NewStore(cfg.Local)
}
Copy link
Contributor

Choose a reason for hiding this comment

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

thought: When I updated the ruler client, I didn't port over the local implementation, just the configdb. My main thought was that it is readonly and mainly used for testing and the new client will already have a filesystem/inmem implementation out of the box. I figured I'd leave it in the legacy config for the time being to avoid confusions with the filesystem backend. However, I'm fine keeping it since there are some desirable properties to a statically configured read-only Alertmanager/RuleStorage backend. Up to you if you think it's worth porting over to the config style or if we should deprecate it when we remove the old config in the future.

If we add it here, we should also port it over to the new ruler config backend as well.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Good point. My point was to deprecate the old config as soon as we complete the rollout in prod (and we confirm the new config works fine). Unless we want to completely remove the local support, then I think the new config should support local too so that we can completely remove the old config in 2 releases.

Copy link
Contributor

Choose a reason for hiding this comment

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

👍

Copy link
Contributor

@pstibrany pstibrany left a comment

Choose a reason for hiding this comment

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

Very nice, thanks!

@pracucci pracucci merged commit 003eb33 into cortexproject:master Mar 2, 2021
@pracucci pracucci deleted the add-thanos-bucket-client-support-to-alertmanager branch March 2, 2021 16:50
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants