-
Notifications
You must be signed in to change notification settings - Fork 3.4k
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
fix(operator): Fix structured logs common fields #11700
Conversation
ab5f494
to
1c86d62
Compare
1c86d62
to
9b21a7c
Compare
1d00997
to
9c236f8
Compare
operator/controllers/loki/internal/lokistack/ruler_config_discovery.go
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Food for thought, IIUC our logs will benefit from these event values, but if an error occurs in a handler they will not have event values. Should we add event
values when we throw an error?
efac682
to
9b460da
Compare
9b460da
to
bdd3d54
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
lgtm
AlertingRuleCtrlName = "alertingrule" | ||
CertRotationCtrlName = "certrotation" | ||
DashboardsCtrlName = "dashboard" | ||
LokiStackCtrlName = "lokistack" | ||
LokiStackZoneLabelsCtrlName = "lokistack-zone-labels" | ||
RecordingRuleCtrlName = "recordingrule" | ||
RulerConfigCtrlName = "rulerconfig" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We usually use prefixes to group similar constants together. Does this make sense here as well? (calling them ControllerNameAlertingRule
, etc., for example)
RulerConfigCtrlName = "rulerconfig" | ||
) | ||
|
||
type LogContructorType func(request *reconcile.Request) logr.Logger |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Small typo and suggestion for renaming (don't know if we did a similar thing already):
type LogContructorType func(request *reconcile.Request) logr.Logger | |
type LogConstructorFunc func(request *reconcile.Request) logr.Logger |
Also this type does not need to be public, as far as I can see...
} | ||
} | ||
|
||
func logWithLokiStackRef(log logr.Logger, req ctrl.Request, name string) logr.Logger { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wonder why we need this, when we have the lokiStackLogConstructor
above which should already produce a lokistack
field. Do we maybe just need to get our logger from the Context
(there's a helper ctrl.LoggerFrom(ctx)
)?
l = l.WithValues( | ||
"controllerGroup", lokiv1.GroupVersion.Group, | ||
"controllerKind", "LokiStack", | ||
"lokistack", klog.KRef(req.Namespace, req.Name), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wonder if we can avoid the extra dependency to klog
just for getting an ObjectRef
to produce a string representation of namespace/name
.
--edit: Oh, wait it's not producing namespace/name
but an object with namespace
and name
attributes in it. Is that what we want?
@@ -55,27 +57,26 @@ func (r *CertRotationReconciler) Reconcile(ctx context.Context, req ctrl.Request | |||
} | |||
|
|||
checkExpiryAfter := expiryRetryAfter(rt.TargetCertRefresh) | |||
r.Log.Info("Checking if LokiStack certificates expired", "name", req.String(), "interval", checkExpiryAfter.String()) | |||
ll.Info("checking if certificates expired", "interval", checkExpiryAfter.String()) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I recently wondered if we should remove a few of these outputs that happen every reconciliation and only print output if there's anything "noteworthy". Don't know if this should also happen in this PR though.
Closing for a later stage to review this |
What this PR does / why we need it:
The Loki Operator is using the
logr.Logger
interface extensively to emit structured logs per controller and handler. In addition the controller-runtime is leveraging theBuilder
factory to link reconciliation errors (i.e. any kind of error that is bubbled up and returned by the controllers'Reconcile()
method) to the managing controller. However the present implementation makes it hard to link top-bottom logs for a specific combo of a controller, a handler and a LokiStack name due to the following issues:Builder.For()
andBuilder.Named
methods. This approach works when linking reconciler errors to the orginating controller/LokiStack if and only if the controller is built withBuilder.For(lokiv1.LokiStack{}
as the source type. However this is not the case for controllers like theAlertingRuleReconciler
,RecordingRuleReconciler
and more critical for theCertRotationReconciler
rendering searching for errors per LokiStack impossible.main.go
the resulting logger instance (used for info/warning logging/non-reconciliation-error logging) needs to be manually augmented with similar fields (controller
,lokistack.name
,lokistack.namespace
) per controller, handler and incoming request. This manual augmentation happens vialogr.Logger.WithValues()
and has been not consistent.With the following PR the implementation is streamlined to:
Builder.For(lokiv1.LokiStack{}
) setup will use consistently the same fields for lokistack (name and namespace) wherever applicable, i.e.AlertingRuleReconciler
,RecordingRuleReconciler
andRulerConfigReconciler
are manually mimicking the same fields to link annotation error with the target LokiStack.Examples (for the sake of simplicity modeled with
jq
):jq -c 'select(.lokistack.name=="lokistack-dev" and .event=="createOrRotateCertificates")'
jq -c 'select(.controller=="lokistack" and .event=="createOrUpdateLokiStack")'
jq -c 'select(.controller=="certrotation" and ._message=="Reconciler error" and .lokistack.name=="lokistack-dev")'
Which issue(s) this PR fixes:
Fixes #
Special notes for your reviewer:
This PR leaves out the duplicates cleanup of usage references of✔️kverrors.Wrap
,log.Info
andlog.Error
across the code base where the Lokistack identifiers (name, namespace) might be logger under an additional key (e.g. sometimeskey
,ref
,name
, etc.). This is left as future work in a separate PR.Checklist
CONTRIBUTING.md
guide (required)CHANGELOG.md
updatedadd-to-release-notes
labeldocs/sources/setup/upgrade/_index.md
production/helm/loki/Chart.yaml
and updateproduction/helm/loki/CHANGELOG.md
andproduction/helm/loki/README.md
. Example PRdeprecated-config.yaml
anddeleted-config.yaml
files respectively in thetools/deprecated-config-checker
directory. Example PR