From 4657b35f30d8cedde9e486ee10339e816fb11ca8 Mon Sep 17 00:00:00 2001 From: molon <3739161+molon@users.noreply.github.com> Date: Sat, 3 Jan 2026 06:50:44 +0800 Subject: [PATCH 1/2] Add naming support to readiness probes for better logging --- lifecycle/func.go | 6 +++++- lifecycle/lifecycle.go | 12 +++++++++++- lifecycle/readiness.go | 12 ++++++++++++ 3 files changed, 28 insertions(+), 2 deletions(-) diff --git a/lifecycle/func.go b/lifecycle/func.go index 01cc960..3f8b9db 100644 --- a/lifecycle/func.go +++ b/lifecycle/func.go @@ -31,8 +31,12 @@ func NewFuncActor(start, stop func(ctx context.Context) error) *FuncActor { } // WithName sets the name of the actor. +// If a readiness probe is enabled, its name is also updated. func (f *FuncActor) WithName(name string) *FuncActor { f.name = name + if f.readinessProbe != nil { + f.readinessProbe.WithName(name) + } return f } @@ -73,7 +77,7 @@ func (f *FuncActor) RequiresStop() bool { // Returns the actor for method chaining. func (f *FuncActor) WithReadiness() *FuncActor { if f.readinessProbe == nil { - f.readinessProbe = NewReadinessProbe() + f.readinessProbe = NewReadinessProbe().WithName(f.name) } return f } diff --git a/lifecycle/lifecycle.go b/lifecycle/lifecycle.go index d21695e..634aca6 100644 --- a/lifecycle/lifecycle.go +++ b/lifecycle/lifecycle.go @@ -142,6 +142,7 @@ func (lc *Lifecycle) Start(ctx context.Context) (xerr error) { lc.mu.RLock() actors := slices.Clone(lc.actors) + logger := lc.logger lc.mu.RUnlock() // Check for long-running services before starting actors @@ -177,7 +178,12 @@ func (lc *Lifecycle) Start(ctx context.Context) (xerr error) { } // Wait for all probes to signal ready - for _, probe := range allProbes { + for i, probe := range allProbes { + probeName := probe.GetName() + if probeName == "" { + probeName = fmt.Sprintf("probe[%d]", i) + } + logger.DebugContext(ctx, "Waiting for readiness probe", "probe", probeName) select { case <-lc.Done(): return lc.Err() @@ -185,8 +191,10 @@ func (lc *Lifecycle) Start(ctx context.Context) (xerr error) { return errors.WithStack(ctx.Err()) case <-probe.Done(): if err := probe.Error(); err != nil { + logger.ErrorContext(ctx, "Readiness probe failed", "probe", probeName, "error", err) return err } + logger.DebugContext(ctx, "Readiness probe signaled ready", "probe", probeName) } } @@ -194,8 +202,10 @@ func (lc *Lifecycle) Start(ctx context.Context) (xerr error) { } // WithName sets the name for the lifecycle. +// Also updates the readiness probe name. func (lc *Lifecycle) WithName(name string) *Lifecycle { lc.FuncService.WithName(name) + lc.readinessProbe.WithName(name) return lc } diff --git a/lifecycle/readiness.go b/lifecycle/readiness.go index 6721785..1fffb38 100644 --- a/lifecycle/readiness.go +++ b/lifecycle/readiness.go @@ -15,6 +15,7 @@ type ReadinessProbe struct { doneC chan struct{} // Completion signal channel mu sync.RWMutex // Protects err field err error // Error if failed, nil if successful + name string // Name for logging and debugging } // NewReadinessProbe creates a new readiness probe. @@ -46,3 +47,14 @@ func (rp *ReadinessProbe) Error() error { defer rp.mu.RUnlock() return rp.err } + +// WithName sets the name of the readiness probe for logging and debugging. +func (rp *ReadinessProbe) WithName(name string) *ReadinessProbe { + rp.name = name + return rp +} + +// GetName returns the name of the readiness probe. +func (rp *ReadinessProbe) GetName() string { + return rp.name +} From 983d656195f36678c24be912bce19bcbfc1b2894 Mon Sep 17 00:00:00 2001 From: molon <3739161+molon@users.noreply.github.com> Date: Sat, 3 Jan 2026 07:17:54 +0800 Subject: [PATCH 2/2] Add debug log for actor startup in Serve method --- lifecycle/lifecycle.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lifecycle/lifecycle.go b/lifecycle/lifecycle.go index 634aca6..97f1498 100644 --- a/lifecycle/lifecycle.go +++ b/lifecycle/lifecycle.go @@ -343,6 +343,8 @@ func (lc *Lifecycle) Serve(ctx context.Context, ctors ...any) (xerr error) { actorType = "Service" } + logger.DebugContext(ctx, fmt.Sprintf("%s starting", actorType), "actor", actorName) + if err := actor.Start(ctx); err != nil { logger.ErrorContext(ctx, fmt.Sprintf("Failed to start %s", strings.ToLower(actorType)), "actor", actorName, "error", err) return err