Skip to content

Commit

Permalink
Reduce logging repeated code in event server
Browse files Browse the repository at this point in the history
Signed-off-by: Matheus Pimenta <matheuscscp@gmail.com>
  • Loading branch information
matheuscscp committed Jun 7, 2023
1 parent 56a77b7 commit a3a7b13
Show file tree
Hide file tree
Showing 2 changed files with 40 additions and 59 deletions.
61 changes: 17 additions & 44 deletions internal/server/event_handlers.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ import (
"time"

"github.com/fluxcd/pkg/runtime/conditions"
"github.com/go-logr/logr"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/labels"
Expand All @@ -43,6 +44,7 @@ import (
func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request) {
return func(w http.ResponseWriter, r *http.Request) {
event := r.Context().Value(eventContextKey{}).(*eventv1.Event)
eventLogger := r.Context().Value(eventLoggerContextKey{}).(logr.Logger)

ctx, cancel := context.WithTimeout(r.Context(), 15*time.Second)
defer cancel()
Expand Down Expand Up @@ -109,18 +111,12 @@ func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request)
}

if len(alerts) == 0 {
s.logger.Info("Discarding event, no alerts found for the involved object",
"reconciler kind", event.InvolvedObject.Kind,
"name", event.InvolvedObject.Name,
"namespace", event.InvolvedObject.Namespace)
eventLogger.Info("Discarding event, no alerts found for the involved object")
w.WriteHeader(http.StatusAccepted)
return
}

s.logger.Info(fmt.Sprintf("Dispatching event: %s", event.Message),
"reconciler kind", event.InvolvedObject.Kind,
"name", event.InvolvedObject.Name,
"namespace", event.InvolvedObject.Namespace)
eventLogger.Info(fmt.Sprintf("Dispatching event: %s", event.Message))

// dispatch notifications
for _, alert := range alerts {
Expand All @@ -135,13 +131,14 @@ func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request)

var provider apiv1beta2.Provider
providerName := types.NamespacedName{Namespace: alert.Namespace, Name: alert.Spec.ProviderRef.Name}
providerLogger := s.logger.WithValues(
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)

err = s.kubeClient.Get(ctx, providerName, &provider)
if err != nil {
s.logger.Error(err, "failed to read provider",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "failed to read provider")
continue
}

Expand All @@ -161,10 +158,7 @@ func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request)

err = s.kubeClient.Get(ctx, secretName, &secret)
if err != nil {
s.logger.Error(err, "failed to read secret",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "failed to read secret")
continue
}

Expand All @@ -191,10 +185,7 @@ func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request)
if h, ok := secret.Data["headers"]; ok {
err := yaml.Unmarshal(h, &headers)
if err != nil {
s.logger.Error(err, "failed to read headers from secret",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "failed to read headers from secret")
continue
}
}
Expand All @@ -207,48 +198,33 @@ func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request)

err = s.kubeClient.Get(ctx, secretName, &secret)
if err != nil {
s.logger.Error(err, "failed to read secret",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "failed to read cert secret")
continue
}

caFile, ok := secret.Data["caFile"]
if !ok {
s.logger.Error(err, "failed to read secret key caFile",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "failed to read secret key caFile")
continue
}

certPool = x509.NewCertPool()
ok = certPool.AppendCertsFromPEM(caFile)
if !ok {
s.logger.Error(err, "could not append to cert pool",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "could not append to cert pool")
continue
}
}

if webhook == "" {
s.logger.Error(nil, "provider has no address",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(nil, "provider has no address")
continue
}

factory := notifier.NewFactory(webhook, proxy, username, provider.Spec.Channel, token, headers, certPool, password, string(provider.UID))
sender, err := factory.Notifier(provider.Spec.Type)
if err != nil {
s.logger.Error(err, "failed to initialize provider",
"reconciler kind", apiv1beta2.ProviderKind,
"name", providerName.Name,
"namespace", providerName.Namespace)
providerLogger.Error(err, "failed to initialize provider")
continue
}

Expand All @@ -265,10 +241,7 @@ func (s *EventServer) handleEvent() func(w http.ResponseWriter, r *http.Request)
} else {
err = errors.New(maskedErrStr)
}
s.logger.Error(err, "failed to send notification",
"reconciler kind", event.InvolvedObject.Kind,
"name", event.InvolvedObject.Name,
"namespace", event.InvolvedObject.Namespace)
eventLogger.Error(err, "failed to send notification")
}
}(sender, notification)
}
Expand Down
38 changes: 23 additions & 15 deletions internal/server/event_server.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,10 @@ import (
eventv1 "github.com/fluxcd/pkg/apis/event/v1beta1"
)

type eventContextKey struct{}
type (
eventContextKey struct{}
eventLoggerContextKey struct{}
)

// EventServer handles event POST requests
type EventServer struct {
Expand Down Expand Up @@ -68,8 +71,8 @@ func (s *EventServer) ListenAndServe(stopCh <-chan struct{}, mdlw middleware.Mid
var handler http.Handler = http.HandlerFunc(s.handleEvent())
for _, middleware := range []func(http.Handler) http.Handler{
limitMiddleware.Handle,
s.logRateLimitMiddleware,
s.cleanupMetadataMiddleware,
logRateLimitMiddleware,
s.eventMiddleware,
} {
handler = middleware(handler)
}
Expand Down Expand Up @@ -100,10 +103,12 @@ func (s *EventServer) ListenAndServe(stopCh <-chan struct{}, mdlw middleware.Mid
}
}

// cleanupMetadataMiddleware cleans up the metadata using cleanupMetadata() and
// eventMiddleware cleans up the event metadata using cleanupMetadata() and
// adds the cleaned event in the request context which can then be queried and
// used directly by the other http handlers.
func (s *EventServer) cleanupMetadataMiddleware(h http.Handler) http.Handler {
// used directly by the other http handlers. This middleware also adds a
// logger with the event's involved object's kind, name and namespace to the
// request context.
func (s *EventServer) eventMiddleware(h http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
body, err := io.ReadAll(r.Body)
if err != nil {
Expand All @@ -124,10 +129,16 @@ func (s *EventServer) cleanupMetadataMiddleware(h http.Handler) http.Handler {

cleanupMetadata(event)

ctxWithEvent := context.WithValue(r.Context(), eventContextKey{}, event)
reqWithEvent := r.WithContext(ctxWithEvent)
logger := s.logger.WithValues(
"reconciler kind", event.InvolvedObject.Kind,
"name", event.InvolvedObject.Name,
"namespace", event.InvolvedObject.Namespace)

enhancedCtx := context.WithValue(r.Context(), eventContextKey{}, event)
enhancedCtx = context.WithValue(enhancedCtx, eventLoggerContextKey{}, logger)
enhancedReq := r.WithContext(enhancedCtx)

h.ServeHTTP(w, reqWithEvent)
h.ServeHTTP(w, enhancedReq)
})
}

Expand Down Expand Up @@ -172,7 +183,7 @@ func (r *statusRecorder) WriteHeader(status int) {
r.ResponseWriter.WriteHeader(status)
}

func (s *EventServer) logRateLimitMiddleware(h http.Handler) http.Handler {
func logRateLimitMiddleware(h http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
recorder := &statusRecorder{
ResponseWriter: w,
Expand All @@ -181,11 +192,8 @@ func (s *EventServer) logRateLimitMiddleware(h http.Handler) http.Handler {
h.ServeHTTP(recorder, r)

if recorder.Status == http.StatusTooManyRequests {
event := r.Context().Value(eventContextKey{}).(*eventv1.Event)
s.logger.V(1).Info("Discarding event, rate limiting duplicate events",
"reconciler kind", event.InvolvedObject.Kind,
"name", event.InvolvedObject.Name,
"namespace", event.InvolvedObject.Namespace)
r.Context().Value(eventLoggerContextKey{}).(logr.Logger).V(1).
Info("Discarding event, rate limiting duplicate events")
}
})
}
Expand Down

0 comments on commit a3a7b13

Please sign in to comment.