diff --git a/src/ES.Kubernetes.Reflector/Mirroring/Core/ResourceMirror.cs b/src/ES.Kubernetes.Reflector/Mirroring/Core/ResourceMirror.cs index 69dff9e..bf5c5f6 100644 --- a/src/ES.Kubernetes.Reflector/Mirroring/Core/ResourceMirror.cs +++ b/src/ES.Kubernetes.Reflector/Mirroring/Core/ResourceMirror.cs @@ -512,7 +512,17 @@ private async Task ResourceReflect(NamespacedName sourceNsName, NamespacedName r foreach (var patchAnnotation in patchAnnotations) annotations[patchAnnotation.Key] = patchAnnotation.Value; patchDoc.Replace(e => e.Metadata.Annotations, annotations); - + + // Merge labels: preserve any existing labels on the reflection but ensure labels from the source + // are present (source labels take precedence). + var labels = reflectionObj.Metadata.Labels is null + ? new Dictionary() + : new Dictionary(reflectionObj.Metadata.Labels); + if (source.Metadata?.Labels is not null) + foreach (var kv in source.Metadata.Labels) + labels[kv.Key] = kv.Value; + patchDoc.Replace(e => e.Metadata.Labels, labels); + await OnResourceConfigurePatch(source, patchDoc); var patch = JsonConvert.SerializeObject(patchDoc, Formatting.Indented); diff --git a/src/ES.Kubernetes.Reflector/Mirroring/SecretMirror.cs b/src/ES.Kubernetes.Reflector/Mirroring/SecretMirror.cs index 64e7413..2a802f6 100644 --- a/src/ES.Kubernetes.Reflector/Mirroring/SecretMirror.cs +++ b/src/ES.Kubernetes.Reflector/Mirroring/SecretMirror.cs @@ -24,6 +24,10 @@ protected override async Task OnResourceApplyPatch(V1Patch patch, NamespacedName protected override Task OnResourceConfigurePatch(V1Secret source, JsonPatchDocument patchDoc) { patchDoc.Replace(e => e.Data, source.Data); + + // Ensure any labels on the source secret are reflected as well + patchDoc.Replace(e => e.Metadata.Labels, source.Metadata?.Labels ?? new Dictionary()); + return Task.CompletedTask; } @@ -38,7 +42,16 @@ protected override Task OnResourceClone(V1Secret sourceResource) => ApiVersion = sourceResource.ApiVersion, Kind = sourceResource.Kind, Type = sourceResource.Type, - Data = sourceResource.Data + Data = sourceResource.Data, + + // Preserve labels from the source so tools that rely on labels can discover mirrored secrets + Metadata = new k8s.Models.V1ObjectMeta + { + Labels = sourceResource.Metadata?.Labels is null + ? null + : new Dictionary(sourceResource.Metadata.Labels) + } + }); protected override async Task OnResourceDelete(NamespacedName resourceId)