fix: initialize ManagedContainers metric with correct count on startup
SyncContainers now reports the delta between actual container count and the UpDownCounter value, so the metric reflects reality after startup and reconnect syncs. Deploy/Remove also track managedCount to keep the counter consistent across the full lifecycle.
- commit
- e7393e2298fa57bd1ed4b05a07f22c92fd32cf27
- author
- brice · · 2026-02-10 08:50 UTC
- parent
- c00708a
- signature
- unsigned
1 file · +13 -0
M internal/usecase/container/service.go +13 -0
| @@ -76,6 +76,7 @@ type Service struct { | |||
| 76 | 76 | metrics *telemetry.Metrics | |
| 77 | 77 | containers map[string]*domain.Container | |
| 78 | 78 | attachments map[string][]string // ownerDomain → []containerIDs | |
| 79 | + | managedCount int64 // tracks UpDownCounter value for delta computation | |
| 79 | 80 | mu sync.RWMutex | |
| 80 | 81 | deployMu sync.Map // per-domain deploy locks (domain → *domainDeployLock) | |
| 81 | 82 | monitor *Monitor | |
| @@ -456,6 +457,9 @@ func (s *Service) activateDeployedContainer(ctx context.Context, domainName stri | |||
| 456 | 457 | s.mu.Lock() | |
| 457 | 458 | _, wasTracked := s.containers[domainName] | |
| 458 | 459 | s.containers[domainName] = container | |
| 460 | + | if !wasTracked { | |
| 461 | + | s.managedCount++ | |
| 462 | + | } | |
| 459 | 463 | s.mu.Unlock() | |
| 460 | 464 | ||
| 461 | 465 | // Track managed container count (only increment for new domains, not replacements) | |
| @@ -679,6 +683,7 @@ func (s *Service) Remove(ctx context.Context, containerID string, force bool) er | |||
| 679 | 683 | if c.ID == containerID { | |
| 680 | 684 | delete(s.containers, d) | |
| 681 | 685 | removedDomain = d | |
| 686 | + | s.managedCount-- | |
| 682 | 687 | log.Info().Str("domain", d).Msg("container removed") | |
| 683 | 688 | break | |
| 684 | 689 | } | |
| @@ -912,8 +917,16 @@ func (s *Service) SyncContainers(ctx context.Context) error { | |||
| 912 | 917 | ||
| 913 | 918 | s.mu.Lock() | |
| 914 | 919 | s.containers = managed | |
| 920 | + | newCount := int64(len(managed)) | |
| 921 | + | delta := newCount - s.managedCount | |
| 922 | + | s.managedCount = newCount | |
| 915 | 923 | s.mu.Unlock() | |
| 916 | 924 | ||
| 925 | + | // Report initial/delta managed container count to OTel UpDownCounter. | |
| 926 | + | if delta != 0 && s.metrics != nil { | |
| 927 | + | s.metrics.ManagedContainers.Add(ctx, delta) | |
| 928 | + | } | |
| 929 | + | ||
| 917 | 930 | log.Info().Int(zerowrap.FieldCount, len(managed)).Msg("container state synchronized") | |
| 918 | 931 | return nil | |
| 919 | 932 | } | |
| @@ -76,6 +76,7 @@ type Service struct { | |||||
| 76 | metrics *telemetry.Metrics | 76 | metrics *telemetry.Metrics | ||
| 77 | containers map[string]*domain.Container | 77 | containers map[string]*domain.Container | ||
| 78 | attachments map[string][]string // ownerDomain → []containerIDs | 78 | attachments map[string][]string // ownerDomain → []containerIDs | ||
| 79 | + | managedCount int64 // tracks UpDownCounter value for delta computation | |||
| 79 | mu sync.RWMutex | 80 | mu sync.RWMutex | ||
| 80 | deployMu sync.Map // per-domain deploy locks (domain → *domainDeployLock) | 81 | deployMu sync.Map // per-domain deploy locks (domain → *domainDeployLock) | ||
| 81 | monitor *Monitor | 82 | monitor *Monitor | ||
| @@ -456,6 +457,9 @@ func (s *Service) activateDeployedContainer(ctx context.Context, domainName stri | |||||
| 456 | s.mu.Lock() | 457 | s.mu.Lock() | ||
| 457 | _, wasTracked := s.containers[domainName] | 458 | _, wasTracked := s.containers[domainName] | ||
| 458 | s.containers[domainName] = container | 459 | s.containers[domainName] = container | ||
| 460 | + | if !wasTracked { | |||
| 461 | + | s.managedCount++ | |||
| 462 | + | } | |||
| 459 | s.mu.Unlock() | 463 | s.mu.Unlock() | ||
| 460 | 464 | ||||
| 461 | // Track managed container count (only increment for new domains, not replacements) | 465 | // Track managed container count (only increment for new domains, not replacements) | ||
| @@ -679,6 +683,7 @@ func (s *Service) Remove(ctx context.Context, containerID string, force bool) er | |||||
| 679 | if c.ID == containerID { | 683 | if c.ID == containerID { | ||
| 680 | delete(s.containers, d) | 684 | delete(s.containers, d) | ||
| 681 | removedDomain = d | 685 | removedDomain = d | ||
| 686 | + | s.managedCount-- | |||
| 682 | log.Info().Str("domain", d).Msg("container removed") | 687 | log.Info().Str("domain", d).Msg("container removed") | ||
| 683 | break | 688 | break | ||
| 684 | } | 689 | } | ||
| @@ -912,8 +917,16 @@ func (s *Service) SyncContainers(ctx context.Context) error { | |||||
| 912 | 917 | ||||
| 913 | s.mu.Lock() | 918 | s.mu.Lock() | ||
| 914 | s.containers = managed | 919 | s.containers = managed | ||
| 920 | + | newCount := int64(len(managed)) | |||
| 921 | + | delta := newCount - s.managedCount | |||
| 922 | + | s.managedCount = newCount | |||
| 915 | s.mu.Unlock() | 923 | s.mu.Unlock() | ||
| 916 | 924 | ||||
| 925 | + | // Report initial/delta managed container count to OTel UpDownCounter. | |||
| 926 | + | if delta != 0 && s.metrics != nil { | |||
| 927 | + | s.metrics.ManagedContainers.Add(ctx, delta) | |||
| 928 | + | } | |||
| 929 | + | ||||
| 917 | log.Info().Int(zerowrap.FieldCount, len(managed)).Msg("container state synchronized") | 930 | log.Info().Int(zerowrap.FieldCount, len(managed)).Msg("container state synchronized") | ||
| 918 | return nil | 931 | return nil | ||
| 919 | } | 932 | } | ||