/
managed_clusters_agent_pool_extensions.go
92 lines (77 loc) · 3.26 KB
/
managed_clusters_agent_pool_extensions.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
/*
* Copyright (c) Microsoft Corporation.
* Licensed under the MIT license.
*/
package customizations
import (
"context"
"fmt"
"strings"
"github.com/go-logr/logr"
"github.com/pkg/errors"
"sigs.k8s.io/controller-runtime/pkg/conversion"
containerservice "github.com/Azure/azure-service-operator/v2/api/containerservice/v1api20231001/storage"
"github.com/Azure/azure-service-operator/v2/internal/genericarmclient"
"github.com/Azure/azure-service-operator/v2/internal/resolver"
"github.com/Azure/azure-service-operator/v2/internal/set"
"github.com/Azure/azure-service-operator/v2/pkg/genruntime"
"github.com/Azure/azure-service-operator/v2/pkg/genruntime/extensions"
)
var _ extensions.PreReconciliationChecker = &ManagedClustersAgentPoolExtension{}
// If an agent pool has a provisioningState not in this set, it will reject any attempt to PUT a new state out of
// hand; so there's no point in even trying. This is true even if the PUT we're doing will have no effect on the state
// of the agent pool.
// These are all listed lowercase, so we can do a case-insensitive match.
var nonBlockingManagedClustersAgentPoolProvisioningStates = set.Make(
"succeeded",
"failed",
"canceled",
)
func (ext *ManagedClustersAgentPoolExtension) PreReconcileCheck(
_ context.Context,
obj genruntime.MetaObject,
owner genruntime.MetaObject,
_ *resolver.Resolver,
_ *genericarmclient.GenericClient,
_ logr.Logger,
_ extensions.PreReconcileCheckFunc,
) (extensions.PreReconcileCheckResult, error) {
// This has to be the current hub storage version. It will need to be updated
// if the hub storage version changes.
agentPool, ok := obj.(*containerservice.ManagedClustersAgentPool)
if !ok {
return extensions.PreReconcileCheckResult{},
errors.Errorf("cannot run on unknown resource type %T, expected *containerservice.ManagedCluster", obj)
}
// Type assert that we are the hub type. This will fail to compile if
// the hub type has been changed but this extension has not
var _ conversion.Hub = agentPool
// Check to see if the owning cluster is in a state that will block us from reconciling
if owner != nil {
if managedCluster, ok := owner.(*containerservice.ManagedCluster); ok {
state := managedCluster.Status.ProvisioningState
if state != nil && clusterProvisioningStateBlocksReconciliation(state) {
return extensions.BlockReconcile(
fmt.Sprintf("Managed cluster %q is in provisioning state %q", owner.GetName(), *state)),
nil
}
}
}
// If the agent pool is in a state that will reject any PUT, then we should skip reconciliation
// as there's no point in even trying.
// This allows us to "play nice with others" and not use up request quota attempting to make changes when we
// already know those attempts will fail.
state := agentPool.Status.ProvisioningState
if state != nil && agentPoolProvisioningStateBlocksReconciliation(state) {
return extensions.BlockReconcile(
fmt.Sprintf("Managed cluster agent pool is in provisioning state %q", *state)),
nil
}
return extensions.ProceedWithReconcile(), nil
}
func agentPoolProvisioningStateBlocksReconciliation(provisioningState *string) bool {
if provisioningState == nil {
return false
}
return !nonBlockingManagedClustersAgentPoolProvisioningStates.Contains(strings.ToLower(*provisioningState))
}