Skip to content

Commit 0f410be

Browse files
committed
Add AC finalizer management
Signed-off-by: Veronika Fisarova <vfisarov@redhat.com>
1 parent 3e1d979 commit 0f410be

9 files changed

Lines changed: 201 additions & 2 deletions

File tree

api/bases/barbican.openstack.org_barbicans.yaml

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -840,6 +840,13 @@ spec:
840840
status:
841841
description: BarbicanStatus defines the observed state of Barbican
842842
properties:
843+
applicationCredentialSecret:
844+
description: |-
845+
ApplicationCredentialSecret - the AC secret barbican is currently
846+
consuming and protecting with the openstack.org/barbican-ac-consumer
847+
finalizer. Tracked so the controller can remove its finalizer from the
848+
old secret when the openstack-operator rotates the reference.
849+
type: string
843850
barbicanAPIReadyCount:
844851
description: ReadyCount of Barbican API instances
845852
format: int32

api/go.mod

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,3 +94,5 @@ replace k8s.io/component-base => k8s.io/component-base v0.31.14 //allow-merging
9494
replace github.com/rabbitmq/cluster-operator/v2 => github.com/openstack-k8s-operators/rabbitmq-cluster-operator/v2 v2.6.1-0.20250929174222-a0d328fa4dec //allow-merging
9595

9696
replace k8s.io/kube-openapi => k8s.io/kube-openapi v0.0.0-20250627150254-e9823e99808e //allow-merging
97+
98+
replace github.com/openstack-k8s-operators/keystone-operator/api => github.com/Deydra71/keystone-operator/api v0.0.0-20260408063234-f70bc06c10d8

api/v1beta1/barbican_types.go

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -155,6 +155,12 @@ type BarbicanStatus struct {
155155
// Barbican Database Hostname
156156
DatabaseHostname string `json:"databaseHostname,omitempty"`
157157

158+
// ApplicationCredentialSecret - the AC secret barbican is currently
159+
// consuming and protecting with the openstack.org/barbican-ac-consumer
160+
// finalizer. Tracked so the controller can remove its finalizer from the
161+
// old secret when the openstack-operator rotates the reference.
162+
ApplicationCredentialSecret string `json:"applicationCredentialSecret,omitempty"`
163+
158164
// ObservedGeneration - the most recent generation observed for this
159165
// service. If the observed generation is less than the spec generation,
160166
// then the controller has not processed the latest changes injected by

config/crd/bases/barbican.openstack.org_barbicans.yaml

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -840,6 +840,13 @@ spec:
840840
status:
841841
description: BarbicanStatus defines the observed state of Barbican
842842
properties:
843+
applicationCredentialSecret:
844+
description: |-
845+
ApplicationCredentialSecret - the AC secret barbican is currently
846+
consuming and protecting with the openstack.org/barbican-ac-consumer
847+
finalizer. Tracked so the controller can remove its finalizer from the
848+
old secret when the openstack-operator rotates the reference.
849+
type: string
843850
barbicanAPIReadyCount:
844851
description: ReadyCount of Barbican API instances
845852
format: int32

go.mod

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,3 +143,5 @@ replace k8s.io/component-base => k8s.io/component-base v0.31.14 //allow-merging
143143
replace github.com/rabbitmq/cluster-operator/v2 => github.com/openstack-k8s-operators/rabbitmq-cluster-operator/v2 v2.6.1-0.20250929174222-a0d328fa4dec //allow-merging
144144

145145
replace k8s.io/kube-openapi => k8s.io/kube-openapi v0.0.0-20250627150254-e9823e99808e //allow-merging
146+
147+
replace github.com/openstack-k8s-operators/keystone-operator/api => github.com/Deydra71/keystone-operator/api v0.0.0-20260408063234-f70bc06c10d8

go.sum

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
github.com/Deydra71/keystone-operator/api v0.0.0-20260408063234-f70bc06c10d8 h1:BjJXiJDpbD0HS0ehvDTwmlIPLqP0aNjrJY09x0Alprk=
2+
github.com/Deydra71/keystone-operator/api v0.0.0-20260408063234-f70bc06c10d8/go.mod h1:8o6LSPt1VAvvB2ngS2QObGS6HEikSdVpHoKIgmb78KI=
13
github.com/Masterminds/semver/v3 v3.4.0 h1:Zog+i5UMtVoCU8oKka5P7i9q9HgrJeGzI9SA1Xbatp0=
24
github.com/Masterminds/semver/v3 v3.4.0/go.mod h1:4V+yj/TJE1HU9XfppCwVMZq3I84lprf4nC11bSS5beM=
35
github.com/antlr4-go/antlr/v4 v4.13.0 h1:lxCg3LAv+EUK6t1i0y1V6/SLeUi0eKEKdhQAlS8TVTI=
@@ -120,8 +122,6 @@ github.com/openshift/api v0.0.0-20250711200046-c86d80652a9e h1:E1OdwSpqWuDPCedyU
120122
github.com/openshift/api v0.0.0-20250711200046-c86d80652a9e/go.mod h1:Shkl4HanLwDiiBzakv+con/aMGnVE2MAGvoKp5oyYUo=
121123
github.com/openstack-k8s-operators/infra-operator/apis v0.6.1-0.20260316100655-863ae03d41af h1:Ow12j/PVbEtul1bZ7s/ZenVnKPIHK2q+0VgTp+j/wro=
122124
github.com/openstack-k8s-operators/infra-operator/apis v0.6.1-0.20260316100655-863ae03d41af/go.mod h1:nC/Jf3OYJRML8UEzJ/mn/TQcSCv/nhqO6x6LGkdDt60=
123-
github.com/openstack-k8s-operators/keystone-operator/api v0.6.1-0.20260321081256-de45f3b1de4f h1:60I2YLHRznTY2BQXqXWc+ByJ3ipdQgKgW52t9J8C5DY=
124-
github.com/openstack-k8s-operators/keystone-operator/api v0.6.1-0.20260321081256-de45f3b1de4f/go.mod h1:8o6LSPt1VAvvB2ngS2QObGS6HEikSdVpHoKIgmb78KI=
125125
github.com/openstack-k8s-operators/lib-common/modules/common v0.6.1-0.20260326092926-8a2950f0575b h1:0YoXBWZfzax1Em7o1Li/wp9MB2JpcFWXiF7geTQohw0=
126126
github.com/openstack-k8s-operators/lib-common/modules/common v0.6.1-0.20260326092926-8a2950f0575b/go.mod h1:XUUV+h1nZC4kra5oF+cXPkviWYJ3ELhccHxnVO7CvQQ=
127127
github.com/openstack-k8s-operators/lib-common/modules/openstack v0.6.1-0.20260320125710-3a5f82ff0f18 h1:eJDwc8LPJg+H4bHMLh/pDJBk+OezQ+wkjUNpExUFhbM=

internal/barbican/const.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,4 +70,6 @@ const (
7070
BarbicanUID int64 = 42403
7171
// BarbicanGID - based on https://github.com/openstack-k8s-operators/tcib/blob/main/container-images/kolla/base/uid_gid_manage.sh
7272
BarbicanGID int64 = 42403
73+
// ACConsumerFinalizer is added to AC secrets that barbican is actively consuming
74+
ACConsumerFinalizer = "openstack.org/barbican-ac-consumer"
7375
)

internal/controller/barbican_controller.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -391,6 +391,15 @@ func (r *BarbicanReconciler) reconcileNormal(ctx context.Context, instance *barb
391391

392392
instance.Status.Conditions.MarkTrue(condition.ServiceConfigReadyCondition, condition.ServiceConfigReadyMessage)
393393

394+
// Manage consumer finalizer, the AC data was already read and rendered to the service config secret
395+
if err := keystonev1.ManageACSecretFinalizer(ctx, helper, instance.Namespace,
396+
instance.Spec.Auth.ApplicationCredentialSecret,
397+
instance.Status.ApplicationCredentialSecret,
398+
barbican.ACConsumerFinalizer); err != nil {
399+
return ctrl.Result{}, err
400+
}
401+
instance.Status.ApplicationCredentialSecret = instance.Spec.Auth.ApplicationCredentialSecret
402+
394403
// networks to attach to
395404
nadList := []networkv1.NetworkAttachmentDefinition{}
396405
for _, netAtt := range instance.Spec.BarbicanAPI.NetworkAttachments {
@@ -611,6 +620,12 @@ func (r *BarbicanReconciler) reconcileDelete(ctx context.Context, instance *barb
611620
}
612621
}
613622

623+
// Remove consumer finalizer from the AC secret barbican was consuming.
624+
if err := keystonev1.RemoveACSecretConsumerFinalizer(ctx, helper, instance.Namespace,
625+
instance.Status.ApplicationCredentialSecret, barbican.ACConsumerFinalizer); err != nil {
626+
return ctrl.Result{}, err
627+
}
628+
614629
// Service is deleted so remove the finalizer.
615630
controllerutil.RemoveFinalizer(instance, helper.GetFinalizer())
616631
Log.Info(fmt.Sprintf("Reconciled Service '%s' delete successfully", instance.Name))

test/functional/barbican_controller_test.go

Lines changed: 158 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1803,6 +1803,164 @@ var _ = Describe("Barbican controller", func() {
18031803
})
18041804
})
18051805

1806+
When("ApplicationCredential consumer finalizer is managed", func() {
1807+
var (
1808+
acSecretName string
1809+
servicePasswordSecret string
1810+
)
1811+
1812+
BeforeEach(func() {
1813+
servicePasswordSecret = "ac-test-osp-secret" //nolint:gosec // G101
1814+
1815+
DeferCleanup(k8sClient.Delete, ctx,
1816+
CreateBarbicanMessageBusSecret(
1817+
barbicanTest.Instance.Namespace,
1818+
barbicanTest.RabbitmqSecretName,
1819+
),
1820+
)
1821+
DeferCleanup(k8sClient.Delete, ctx,
1822+
CreateBarbicanSecret(
1823+
barbicanTest.Instance.Namespace, servicePasswordSecret))
1824+
1825+
acSecretName = "ac-barbican-a1b2c-secret" //nolint:gosec // G101
1826+
secret := &corev1.Secret{
1827+
ObjectMeta: metav1.ObjectMeta{
1828+
Namespace: barbicanTest.Instance.Namespace,
1829+
Name: acSecretName,
1830+
},
1831+
Data: map[string][]byte{
1832+
keystonev1.ACIDSecretKey: []byte("a1b2ctest-ac-id"),
1833+
keystonev1.ACSecretSecretKey: []byte("test-ac-secret"),
1834+
},
1835+
}
1836+
DeferCleanup(k8sClient.Delete, ctx, secret)
1837+
Expect(k8sClient.Create(ctx, secret)).To(Succeed())
1838+
1839+
spec := GetDefaultBarbicanSpec()
1840+
spec["secret"] = servicePasswordSecret
1841+
spec["simpleCryptoBackendSecret"] = servicePasswordSecret
1842+
spec["auth"] = map[string]any{
1843+
"applicationCredentialSecret": acSecretName,
1844+
}
1845+
DeferCleanup(th.DeleteInstance,
1846+
CreateBarbican(barbicanTest.Instance, spec))
1847+
DeferCleanup(
1848+
mariadb.DeleteDBService,
1849+
mariadb.CreateDBService(
1850+
barbicanTest.Instance.Namespace,
1851+
GetBarbican(barbicanTest.Instance).Spec.DatabaseInstance,
1852+
corev1.ServiceSpec{
1853+
Ports: []corev1.ServicePort{{Port: 3306}}}))
1854+
1855+
DeferCleanup(keystone.DeleteKeystoneAPI,
1856+
keystone.CreateKeystoneAPI(barbicanTest.Instance.Namespace))
1857+
1858+
infra.SimulateTransportURLReady(barbicanTest.BarbicanTransportURL)
1859+
mariadb.SimulateMariaDBAccountCompleted(barbicanTest.BarbicanDatabaseAccount)
1860+
mariadb.SimulateMariaDBDatabaseCompleted(barbicanTest.BarbicanDatabaseName)
1861+
th.SimulateJobSuccess(barbicanTest.BarbicanDBSync)
1862+
keystone.SimulateKeystoneEndpointReady(barbicanTest.BarbicanKeystoneEndpoint)
1863+
})
1864+
1865+
It("should add the consumer finalizer to the AC secret", func() {
1866+
Eventually(func(g Gomega) {
1867+
secret := th.GetSecret(types.NamespacedName{
1868+
Namespace: barbicanTest.Instance.Namespace,
1869+
Name: acSecretName,
1870+
})
1871+
g.Expect(secret.Finalizers).To(
1872+
ContainElement(barbican.ACConsumerFinalizer))
1873+
}, timeout, interval).Should(Succeed())
1874+
})
1875+
1876+
It("should track the consumed AC secret in status", func() {
1877+
Eventually(func(g Gomega) {
1878+
b := GetBarbican(barbicanTest.Instance)
1879+
g.Expect(b.Status.ApplicationCredentialSecret).To(Equal(acSecretName))
1880+
}, timeout, interval).Should(Succeed())
1881+
})
1882+
1883+
It("should move the finalizer from the old to the new secret on rotation", func() {
1884+
// Wait for the initial finalizer to appear
1885+
Eventually(func(g Gomega) {
1886+
secret := th.GetSecret(types.NamespacedName{
1887+
Namespace: barbicanTest.Instance.Namespace,
1888+
Name: acSecretName,
1889+
})
1890+
g.Expect(secret.Finalizers).To(
1891+
ContainElement(barbican.ACConsumerFinalizer))
1892+
}, timeout, interval).Should(Succeed())
1893+
1894+
// Create a new AC secret
1895+
newACSecretName := "ac-barbican-x9y8z-secret" //nolint:gosec // G101
1896+
newSecret := &corev1.Secret{
1897+
ObjectMeta: metav1.ObjectMeta{
1898+
Namespace: barbicanTest.Instance.Namespace,
1899+
Name: newACSecretName,
1900+
},
1901+
Data: map[string][]byte{
1902+
keystonev1.ACIDSecretKey: []byte("x9y8zrotated-ac-id"),
1903+
keystonev1.ACSecretSecretKey: []byte("rotated-ac-secret"),
1904+
},
1905+
}
1906+
DeferCleanup(k8sClient.Delete, ctx, newSecret)
1907+
Expect(k8sClient.Create(ctx, newSecret)).To(Succeed())
1908+
1909+
// Update the Barbican CR to reference the new AC secret
1910+
Eventually(func(g Gomega) {
1911+
b := GetBarbican(barbicanTest.Instance)
1912+
b.Spec.Auth.ApplicationCredentialSecret = newACSecretName
1913+
g.Expect(k8sClient.Update(ctx, b)).Should(Succeed())
1914+
}, timeout, interval).Should(Succeed())
1915+
1916+
// New secret should gain the consumer finalizer
1917+
Eventually(func(g Gomega) {
1918+
secret := th.GetSecret(types.NamespacedName{
1919+
Namespace: barbicanTest.Instance.Namespace,
1920+
Name: newACSecretName,
1921+
})
1922+
g.Expect(secret.Finalizers).To(
1923+
ContainElement(barbican.ACConsumerFinalizer))
1924+
}, timeout, interval).Should(Succeed())
1925+
1926+
// Old secret should lose the consumer finalizer
1927+
Eventually(func(g Gomega) {
1928+
secret := th.GetSecret(types.NamespacedName{
1929+
Namespace: barbicanTest.Instance.Namespace,
1930+
Name: acSecretName,
1931+
})
1932+
g.Expect(secret.Finalizers).NotTo(
1933+
ContainElement(barbican.ACConsumerFinalizer))
1934+
}, timeout, interval).Should(Succeed())
1935+
1936+
// Status should reflect the new secret
1937+
Eventually(func(g Gomega) {
1938+
b := GetBarbican(barbicanTest.Instance)
1939+
g.Expect(b.Status.ApplicationCredentialSecret).To(Equal(newACSecretName))
1940+
}, timeout, interval).Should(Succeed())
1941+
})
1942+
1943+
It("should remove the consumer finalizer from AC secret on CR deletion", func() {
1944+
Eventually(func(g Gomega) {
1945+
secret := th.GetSecret(types.NamespacedName{
1946+
Namespace: barbicanTest.Instance.Namespace,
1947+
Name: acSecretName,
1948+
})
1949+
g.Expect(secret.Finalizers).To(
1950+
ContainElement(barbican.ACConsumerFinalizer))
1951+
}, timeout, interval).Should(Succeed())
1952+
1953+
th.DeleteInstance(GetBarbican(barbicanTest.Instance))
1954+
1955+
secret := th.GetSecret(types.NamespacedName{
1956+
Namespace: barbicanTest.Instance.Namespace,
1957+
Name: acSecretName,
1958+
})
1959+
Expect(secret.Finalizers).NotTo(
1960+
ContainElement(barbican.ACConsumerFinalizer))
1961+
})
1962+
})
1963+
18061964
// Run MariaDBAccount suite tests. these are pre-packaged ginkgo tests
18071965
// that exercise standard account create / update patterns that should be
18081966
// common to all controllers that ensure MariaDBAccount CRs.

0 commit comments

Comments
 (0)