{"record":{"id":"0ef096afaecd6871","repo":"cilium/cilium","slug":"failed-to-unregister-metric-tcp-flags-total","errorCode":null,"errorMessage":"failed to unregister metric: tcp_flags_total,","messagePattern":"failed to unregister metric: tcp_flags_total,","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"pkg/hubble/metrics/tcp/handler.go","lineNumber":113,"sourceCode":"\t\t\th.tcpFlags.WithLabelValues(labels...).Inc()\n\t\t} else {\n\t\t\tlabels[0] = \"SYN\"\n\t\t\th.tcpFlags.WithLabelValues(labels...).Inc()\n\t\t}\n\t}\n\n\tif tcp.Flags.RST {\n\t\tlabels[0] = \"RST\"\n\t\th.tcpFlags.WithLabelValues(labels...).Inc()\n\t}\n\n\treturn nil\n}\n\nfunc (h *tcpHandler) Deinit(registry *prometheus.Registry) error {\n\tvar errs error\n\tif !registry.Unregister(h.tcpFlags) {\n\t\terrs = errors.Join(errs, fmt.Errorf(\"failed to unregister metric: %v,\", \"tcp_flags_total\"))\n\t}\n\treturn errs\n}\n\nfunc (h *tcpHandler) HandleConfigurationUpdate(cfg *api.MetricConfig) error {\n\treturn h.SetFilters(cfg)\n}\n\nfunc (h *tcpHandler) SetFilters(cfg *api.MetricConfig) error {\n\tvar err error\n\th.AllowList, err = filters.BuildFilterList(context.Background(), cfg.IncludeFilters, filters.DefaultFilters(slog.Default()))\n\tif err != nil {\n\t\treturn err\n\t}\n\th.DenyList, err = filters.BuildFilterList(context.Background(), cfg.ExcludeFilters, filters.DefaultFilters(slog.Default()))\n\tif err != nil {\n\t\treturn err\n\t}","sourceCodeStart":95,"sourceCodeEnd":131,"githubUrl":"https://github.com/cilium/cilium/blob/ac7b90affa4baf0642e6685319d56907b3a73a6d/pkg/hubble/metrics/tcp/handler.go#L95-L131","documentation":"tcpHandler.Deinit returns this error when registry.Unregister(h.tcpFlags) returns false, meaning tcp_flags_total could not be removed from the registry because it is not registered there (or already removed).","triggerScenarios":"Calling Deinit with a registry lacking the tcp_flags_total collector — double Deinit, missing Init, or registry instance mismatch.","commonSituations":"Hubble shutdown paths, repeated config reloads triggering init/deinit cycles, test setups without registration.","solutions":["Ensure Init registered tcpFlags on the same registry before Deinit.","Avoid calling Deinit more than once per handler instance.","Use one shared *prometheus.Registry for the handler's full lifecycle."],"exampleFix":"// before\nh.Deinit(reg)\nh.Deinit(reg)\n// after\nif err := h.Deinit(reg); err != nil { return err } // once per handler","handlingStrategy":"try-catch","validationCode":"// confirm tcpFlags registered on registry before teardown","typeGuard":null,"tryCatchPattern":"if err := h.Deinit(registry); err != nil {\n    log.WithError(err).Warn(\"tcp_flags_total unregister failed\")\n}","preventionTips":["One registry per handler lifecycle","Avoid duplicate Deinit calls","Check Init error paths so registration failures are visible"],"tags":["prometheus","metrics","unregister","lifecycle"],"backgroundTag":"metric-unregister-failed","analyzedSha":"ac7b90affa4baf0642e6685319d56907b3a73a6d","analyzedAt":"2026-08-31T18:27:15.868Z","schemaVersion":2},"datasetVersion":"2026-08-31T19:17:28.585Z"}