@@ -3,7 +3,6 @@ package grafana
3
3
import (
4
4
"context"
5
5
"errors"
6
- "strconv"
7
6
8
7
// sha1 is used to generate a hash for the secret name.
9
8
"crypto/sha1" // nolint:gosec
@@ -17,14 +16,14 @@ import (
17
16
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
18
17
"k8s.io/apimachinery/pkg/runtime"
19
18
"sigs.k8s.io/controller-runtime/pkg/client"
20
- "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil"
21
19
logf "sigs.k8s.io/controller-runtime/pkg/log"
22
20
23
21
genapi "github.com/grafana/grafana-openapi-client-go/client"
24
22
"github.com/grafana/grafana-openapi-client-go/client/service_accounts"
25
23
"github.com/grafana/grafana-openapi-client-go/models"
26
24
v1beta1 "github.com/grafana/grafana-operator/v5/api/v1beta1"
27
25
client2 "github.com/grafana/grafana-operator/v5/controllers/client"
26
+ model2 "github.com/grafana/grafana-operator/v5/controllers/model"
28
27
)
29
28
30
29
func isEqualExpirationTime (a , b * metav1.Time ) bool {
@@ -85,6 +84,11 @@ func (r *GrafanaServiceAccountReconciler) reconcileAccounts(
85
84
gClient * genapi.GrafanaHTTPAPI ,
86
85
scheme * runtime.Scheme ,
87
86
) error {
87
+ allSecrets , err := r .listAllTokenSecrets (ctx , cr )
88
+ if err != nil {
89
+ return fmt .Errorf ("listing all token secrets for instance %q: %w" , cr .Name , err )
90
+ }
91
+
88
92
existingSAs , err := listServiceAccounts (ctx , gClient )
89
93
if err != nil {
90
94
return fmt .Errorf ("listing service accounts: %w" , err )
@@ -129,7 +133,10 @@ func (r *GrafanaServiceAccountReconciler) reconcileAccounts(
129
133
}
130
134
131
135
for i := range groups .toSync {
132
- err := r .reconcileAccount (ctx , cr , gClient , groups .toSync [i ].spec , & groups .toSync [i ].status , scheme )
136
+ spec := groups .toSync [i ].spec
137
+ status := & groups .toSync [i ].status
138
+ existingSecrets := allSecrets [spec .ID ]
139
+ err := r .reconcileAccount (ctx , cr , gClient , spec , status , existingSecrets , scheme )
133
140
if err != nil {
134
141
groups .consolidateTo (cr )
135
142
return fmt .Errorf ("reconciling service account %q: %w" , groups .toSync [i ].status .SpecID , err )
@@ -172,6 +179,7 @@ func (r *GrafanaServiceAccountReconciler) reconcileAccount(
172
179
gClient * genapi.GrafanaHTTPAPI ,
173
180
spec v1beta1.GrafanaServiceAccountSpec ,
174
181
status * v1beta1.GrafanaServiceAccountStatus ,
182
+ existingSecrets map [string ]corev1.Secret ,
175
183
scheme * runtime.Scheme ,
176
184
) error {
177
185
var hasDiscrepancy bool
@@ -208,7 +216,7 @@ func (r *GrafanaServiceAccountReconciler) reconcileAccount(
208
216
status .Name = update .Payload .Serviceaccount .Name
209
217
}
210
218
211
- err := r .reconcileTokens (ctx , cr , gClient , spec , status , scheme )
219
+ err := r .reconcileTokens (ctx , cr , gClient , spec , status , existingSecrets , scheme )
212
220
if err != nil {
213
221
return fmt .Errorf ("reconciling tokens for service account %s: %w" , status .Name , err )
214
222
}
@@ -223,16 +231,13 @@ func (r *GrafanaServiceAccountReconciler) reconcileTokens(
223
231
gClient * genapi.GrafanaHTTPAPI ,
224
232
spec v1beta1.GrafanaServiceAccountSpec ,
225
233
sa * v1beta1.GrafanaServiceAccountStatus ,
234
+ existingSecrets map [string ]corev1.Secret ,
226
235
scheme * runtime.Scheme ,
227
236
) error {
228
237
existingTokens , err := listServiceAccountTokens (ctx , gClient , sa .ServiceAccountID )
229
238
if err != nil {
230
239
return fmt .Errorf ("listing tokens for service account: %w" , err )
231
240
}
232
- existingSecrets , err := r .listServiceAccountSecrets (ctx , cr , sa .SpecID )
233
- if err != nil {
234
- return fmt .Errorf ("listing secrets for service account %q: %w" , sa .SpecID , err )
235
- }
236
241
groups := r .classifyTokens (cr , existingTokens , existingSecrets , spec , * sa )
237
242
238
243
for i , tokenStatus := range groups .toDelete {
@@ -327,33 +332,8 @@ func (r *GrafanaServiceAccountReconciler) createToken(
327
332
}
328
333
329
334
// The token was created, let's create a secret for it.
330
- secret := & corev1.Secret {
331
- ObjectMeta : metav1.ObjectMeta {
332
- Name : generateTokenSecretName (cr .Name , sa .SpecID , status .Name ),
333
- Namespace : cr .Namespace ,
334
- Labels : map [string ]string {
335
- "app" : "grafana-serviceaccount-token" ,
336
- "grafana.integreatly.org/sa-spec-id" : sa .SpecID ,
337
- "grafana.integreatly.org/token-name" : status .Name ,
338
- },
339
- Annotations : map [string ]string {
340
- "grafana.integreatly.org/token-id" : strconv .FormatInt (status .ID , 10 ),
341
- },
342
- },
343
- Type : corev1 .SecretTypeOpaque ,
344
- Data : map [string ][]byte {
345
- "token" : []byte (createResp .Payload .Key ),
346
- },
347
- }
348
- if spec .Expires != nil {
349
- secret .Annotations = map [string ]string {
350
- "grafana.integreatly.org/token-expiry" : spec .Expires .Format (time .RFC3339 ),
351
- }
352
- }
353
- err = controllerutil .SetControllerReference (cr , secret , scheme )
354
- if err != nil {
355
- return status , fmt .Errorf ("setting owner reference on token secret %q: %w" , secret .Name , err )
356
- }
335
+ tokenKey := []byte (createResp .Payload .Key )
336
+ secret := model2 .GetInternalServiceAccountSecret (cr , sa , * status , tokenKey , scheme )
357
337
err = r .client .Create (ctx , secret )
358
338
if err != nil {
359
339
return status , fmt .Errorf ("creating token secret %q: %w" , secret .Name , err )
@@ -671,19 +651,33 @@ func listServiceAccountTokens(
671
651
return existingTokens , nil
672
652
}
673
653
674
- func (r * GrafanaServiceAccountReconciler ) listServiceAccountSecrets (
654
+ func (r * GrafanaServiceAccountReconciler ) listAllTokenSecrets (
675
655
ctx context.Context ,
676
656
cr * v1beta1.Grafana ,
677
- serviceAccountSpecID string ,
678
- ) (map [string ]corev1.Secret , error ) {
679
- var secrets corev1.SecretList
680
- err := r .client .List (ctx , & secrets , client .InNamespace (cr .Namespace ), client.MatchingLabels {"grafana.integreatly.org/sa-spec-id" : serviceAccountSpecID })
657
+ ) (map [string ]map [string ]corev1.Secret , error ) {
658
+ var list corev1.SecretList
659
+ err := r .client .List (ctx , & list ,
660
+ client .InNamespace (cr .Namespace ),
661
+ client.MatchingLabels {
662
+ "app" : "grafana-serviceaccount-token" ,
663
+ "grafana.integreatly.org/instance" : cr .Name ,
664
+ },
665
+ )
681
666
if err != nil {
682
- return nil , fmt .Errorf ("listing secrets: %w" , err )
667
+ return nil , fmt .Errorf ("listing token secrets: %w" , err )
683
668
}
684
- existingSecrets := map [string ]corev1.Secret {}
685
- for _ , secret := range secrets .Items {
686
- existingSecrets [secret .Name ] = secret
669
+
670
+ res := map [string ]map [string ]corev1.Secret {}
671
+ for _ , s := range list .Items {
672
+ specID := model2 .GetInternalServiceAccountSpecIDFromSecret (s )
673
+ if specID == "" {
674
+ logf .FromContext (ctx ).V (1 ).Info ("secret doesn't have a spec ID, skipping" , "secret" , s .Name )
675
+ continue
676
+ }
677
+ if res [specID ] == nil {
678
+ res [specID ] = map [string ]corev1.Secret {}
679
+ }
680
+ res [specID ][s.Name ] = s
687
681
}
688
- return existingSecrets , nil
682
+ return res , nil
689
683
}
0 commit comments