Skip to content

Commit 7b41a4b

Browse files
authored
Decode secret (#94)
* use stackitProviderName everywhere Signed-off-by: Felix Breuer <f.breuer94@gmail.com> * extract secret extraction into function Signed-off-by: Felix Breuer <f.breuer94@gmail.com> --------- Signed-off-by: Felix Breuer <f.breuer94@gmail.com>
1 parent db3221c commit 7b41a4b

File tree

6 files changed

+30
-18
lines changed

6 files changed

+30
-18
lines changed

pkg/provider/apis/validation/validation.go

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,11 @@ import (
1010
corev1 "k8s.io/api/core/v1"
1111
)
1212

13+
const (
14+
StackitProjectIDSecretKey = "project-id"
15+
StackitServiceAccountKey = "serviceaccount.json"
16+
)
17+
1318
// uuidRegex is a regex pattern for validating UUID format
1419
var uuidRegex = regexp.MustCompile(`^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$`)
1520

@@ -53,22 +58,22 @@ func ValidateProviderSpecNSecret(spec *api.ProviderSpec, secrets *corev1.Secret)
5358
return errors // Return early if secret is nil
5459
}
5560

56-
projectID, ok := secrets.Data["project-id"]
61+
projectID, ok := secrets.Data[StackitProjectIDSecretKey]
5762
if !ok {
58-
errors = append(errors, fmt.Errorf("secret field 'project-id' is required"))
63+
errors = append(errors, fmt.Errorf("secret field '%s' is required", StackitProjectIDSecretKey))
5964
} else if len(projectID) == 0 {
60-
errors = append(errors, fmt.Errorf("secret field 'project-id' cannot be empty"))
65+
errors = append(errors, fmt.Errorf("secret field '%s' cannot be empty", StackitProjectIDSecretKey))
6166
} else if !isValidUUID(string(projectID)) {
62-
errors = append(errors, fmt.Errorf("secret field 'project-id' must be a valid UUID"))
67+
errors = append(errors, fmt.Errorf("secret field '%s' must be a valid UUID", StackitProjectIDSecretKey))
6368
}
6469

6570
// Validate serviceAccountKey (required for authentication)
6671
// ServiceAccount Key Flow: JSON string containing service account credentials and private key
67-
serviceAccountKey, ok := secrets.Data["serviceaccount.json"]
72+
serviceAccountKey, ok := secrets.Data[StackitServiceAccountKey]
6873
if !ok {
69-
errors = append(errors, fmt.Errorf("secret field 'serviceaccount.json' is required"))
74+
errors = append(errors, fmt.Errorf("secret field '%s' is required", StackitServiceAccountKey))
7075
} else if len(serviceAccountKey) == 0 {
71-
errors = append(errors, fmt.Errorf("secret field 'serviceaccount.json' cannot be empty"))
76+
errors = append(errors, fmt.Errorf("secret field '%s' cannot be empty", StackitServiceAccountKey))
7277
} else if !isValidJSON(string(serviceAccountKey)) {
7378
errors = append(errors, fmt.Errorf("secret field 'serviceAccountKey' must be valid JSON (service account credentials)"))
7479
}

pkg/provider/create.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,8 +52,7 @@ func (p *Provider) CreateMachine(ctx context.Context, req *driver.CreateMachineR
5252
}
5353

5454
// Extract credentials from Secret
55-
projectID := string(req.Secret.Data["project-id"])
56-
serviceAccountKey := string(req.Secret.Data["serviceaccount.json"])
55+
projectID, serviceAccountKey := extractSecretCredentials(req.Secret.Data)
5756

5857
// Initialize client on first use (lazy initialization)
5958
if err := p.ensureClient(serviceAccountKey); err != nil {

pkg/provider/delete.go

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,8 @@ func (p *Provider) DeleteMachine(ctx context.Context, req *driver.DeleteMachineR
2727
defer klog.V(2).Infof("Machine deletion request has been processed for %q", req.Machine.Name)
2828

2929
// Extract credentials from Secret
30-
serviceAccountKey := string(req.Secret.Data["serviceaccount.json"])
30+
projectIDFromSecret, serviceAccountKey := extractSecretCredentials(req.Secret.Data)
31+
3132
// Initialize client on first use (lazy initialization)
3233
if err := p.ensureClient(serviceAccountKey); err != nil {
3334
return nil, status.Error(codes.Internal, fmt.Sprintf("failed to initialize STACKIT client: %v", err))
@@ -48,7 +49,8 @@ func (p *Provider) DeleteMachine(ctx context.Context, req *driver.DeleteMachineR
4849
}
4950

5051
if projectID == "" {
51-
projectID = string(req.Secret.Data["project-id"])
52+
// use the secret as a fallback
53+
projectID = projectIDFromSecret
5254
}
5355

5456
providerSpec, err := decodeProviderSpec(req.MachineClass)

pkg/provider/helpers.go

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77

88
"github.com/gardener/machine-controller-manager/pkg/apis/machine/v1alpha1"
99
api "github.com/stackitcloud/machine-controller-manager-provider-stackit/pkg/provider/apis"
10+
"github.com/stackitcloud/machine-controller-manager-provider-stackit/pkg/provider/apis/validation"
1011
)
1112

1213
// decodeProviderSpec decodes the ProviderSpec from a MachineClass
@@ -31,18 +32,18 @@ func encodeProviderSpecForResponse(spec *api.ProviderSpec) ([]byte, error) {
3132
// parseProviderID parses a STACKIT ProviderID and extracts the projectID and serverID
3233
// Expected format: stackit://<projectId>/<serverId>
3334
func parseProviderID(providerID string) (projectID, serverID string, err error) {
34-
const prefix = "stackit://"
35+
prefix := fmt.Sprintf("%s://", StackitProviderName)
3536

3637
if !strings.HasPrefix(providerID, prefix) {
37-
return "", "", fmt.Errorf("ProviderID must start with 'stackit://'")
38+
return "", "", fmt.Errorf("ProviderID must start with '%s://'", StackitProviderName)
3839
}
3940

4041
// Remove prefix and split by '/'
4142
remainder := strings.TrimPrefix(providerID, prefix)
4243
parts := strings.Split(remainder, "/")
4344

4445
if len(parts) != 2 {
45-
return "", "", fmt.Errorf("ProviderID must have format 'stackit://<projectId>/<serverId>'")
46+
return "", "", fmt.Errorf("ProviderID must have format '%s://<projectId>/<serverId>'", StackitProviderName)
4647
}
4748

4849
if parts[0] == "" || parts[1] == "" {
@@ -51,3 +52,9 @@ func parseProviderID(providerID string) (projectID, serverID string, err error)
5152

5253
return parts[0], parts[1], nil
5354
}
55+
56+
func extractSecretCredentials(secretData map[string][]byte) (projectID, serviceAccountKey string) {
57+
projectID = string(secretData[validation.StackitProjectIDSecretKey])
58+
serviceAccountKey = string(secretData[validation.StackitServiceAccountKey])
59+
return projectID, serviceAccountKey
60+
}

pkg/provider/list.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,8 +27,7 @@ func (p *Provider) ListMachines(ctx context.Context, req *driver.ListMachinesReq
2727
defer klog.V(2).Infof("List machines request has been processed for %q", req.MachineClass.Name)
2828

2929
// Extract credentials from Secret
30-
projectID := string(req.Secret.Data["project-id"])
31-
serviceAccountKey := string(req.Secret.Data["serviceaccount.json"])
30+
projectID, serviceAccountKey := extractSecretCredentials(req.Secret.Data)
3231

3332
// Initialize client on first use (lazy initialization)
3433
if err := p.ensureClient(serviceAccountKey); err != nil {

pkg/provider/status.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ func (p *Provider) GetMachineStatus(ctx context.Context, req *driver.GetMachineS
3939
}
4040

4141
// Extract credentials from Secret
42-
serviceAccountKey := string(req.Secret.Data["serviceaccount.json"])
42+
projectIDFromSecret, serviceAccountKey := extractSecretCredentials(req.Secret.Data)
4343

4444
// Initialize client on first use (lazy initialization)
4545
if err := p.ensureClient(serviceAccountKey); err != nil {
@@ -50,7 +50,7 @@ func (p *Provider) GetMachineStatus(ctx context.Context, req *driver.GetMachineS
5050
// Expected format: stackit://<projectId>/<serverId>
5151
projectID, serverID, err := parseProviderID(req.Machine.Spec.ProviderID)
5252
if projectID == "" {
53-
projectID = string(req.Secret.Data["project-id"])
53+
projectID = projectIDFromSecret
5454
}
5555
if err != nil {
5656
return nil, status.Error(codes.InvalidArgument, fmt.Sprintf("invalid ProviderID format: %v", err))

0 commit comments

Comments
 (0)