Skip to content

Commit 4a133ce

Browse files
authored
fix: limit number of resources in appset status (#24690) (#24694)
Signed-off-by: Alexander Matyushentsev <[email protected]>
1 parent 376525e commit 4a133ce

15 files changed

+157
-11
lines changed

applicationset/controllers/applicationset_controller.go

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,7 @@ type ApplicationSetReconciler struct {
9191
GlobalPreservedAnnotations []string
9292
GlobalPreservedLabels []string
9393
Metrics *metrics.ApplicationsetMetrics
94+
MaxResourcesStatusCount int
9495
}
9596

9697
// +kubebuilder:rbac:groups=argoproj.io,resources=applicationsets,verbs=get;list;watch;create;update;patch;delete
@@ -1314,6 +1315,11 @@ func (r *ApplicationSetReconciler) updateResourcesStatus(ctx context.Context, lo
13141315
sort.Slice(statuses, func(i, j int) bool {
13151316
return statuses[i].Name < statuses[j].Name
13161317
})
1318+
1319+
if r.MaxResourcesStatusCount > 0 && len(statuses) > r.MaxResourcesStatusCount {
1320+
logCtx.Warnf("Truncating ApplicationSet %s resource status from %d to max allowed %d entries", appset.Name, len(statuses), r.MaxResourcesStatusCount)
1321+
statuses = statuses[:r.MaxResourcesStatusCount]
1322+
}
13171323
appset.Status.Resources = statuses
13181324
// DefaultRetry will retry 5 times with a backoff factor of 1, jitter of 0.1 and a duration of 10ms
13191325
err := retry.RetryOnConflict(retry.DefaultRetry, func() error {

applicationset/controllers/applicationset_controller_test.go

Lines changed: 80 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -6097,10 +6097,11 @@ func TestUpdateResourceStatus(t *testing.T) {
60976097
require.NoError(t, err)
60986098

60996099
for _, cc := range []struct {
6100-
name string
6101-
appSet v1alpha1.ApplicationSet
6102-
apps []v1alpha1.Application
6103-
expectedResources []v1alpha1.ResourceStatus
6100+
name string
6101+
appSet v1alpha1.ApplicationSet
6102+
apps []v1alpha1.Application
6103+
expectedResources []v1alpha1.ResourceStatus
6104+
maxResourcesStatusCount int
61046105
}{
61056106
{
61066107
name: "handles an empty application list",
@@ -6271,6 +6272,73 @@ func TestUpdateResourceStatus(t *testing.T) {
62716272
apps: []v1alpha1.Application{},
62726273
expectedResources: nil,
62736274
},
6275+
{
6276+
name: "truncates resources status list to",
6277+
appSet: v1alpha1.ApplicationSet{
6278+
ObjectMeta: metav1.ObjectMeta{
6279+
Name: "name",
6280+
Namespace: "argocd",
6281+
},
6282+
Status: v1alpha1.ApplicationSetStatus{
6283+
Resources: []v1alpha1.ResourceStatus{
6284+
{
6285+
Name: "app1",
6286+
Status: v1alpha1.SyncStatusCodeOutOfSync,
6287+
Health: &v1alpha1.HealthStatus{
6288+
Status: health.HealthStatusProgressing,
6289+
Message: "this is progressing",
6290+
},
6291+
},
6292+
{
6293+
Name: "app2",
6294+
Status: v1alpha1.SyncStatusCodeOutOfSync,
6295+
Health: &v1alpha1.HealthStatus{
6296+
Status: health.HealthStatusProgressing,
6297+
Message: "this is progressing",
6298+
},
6299+
},
6300+
},
6301+
},
6302+
},
6303+
apps: []v1alpha1.Application{
6304+
{
6305+
ObjectMeta: metav1.ObjectMeta{
6306+
Name: "app1",
6307+
},
6308+
Status: v1alpha1.ApplicationStatus{
6309+
Sync: v1alpha1.SyncStatus{
6310+
Status: v1alpha1.SyncStatusCodeSynced,
6311+
},
6312+
Health: v1alpha1.HealthStatus{
6313+
Status: health.HealthStatusHealthy,
6314+
},
6315+
},
6316+
},
6317+
{
6318+
ObjectMeta: metav1.ObjectMeta{
6319+
Name: "app2",
6320+
},
6321+
Status: v1alpha1.ApplicationStatus{
6322+
Sync: v1alpha1.SyncStatus{
6323+
Status: v1alpha1.SyncStatusCodeSynced,
6324+
},
6325+
Health: v1alpha1.HealthStatus{
6326+
Status: health.HealthStatusHealthy,
6327+
},
6328+
},
6329+
},
6330+
},
6331+
expectedResources: []v1alpha1.ResourceStatus{
6332+
{
6333+
Name: "app1",
6334+
Status: v1alpha1.SyncStatusCodeSynced,
6335+
Health: &v1alpha1.HealthStatus{
6336+
Status: health.HealthStatusHealthy,
6337+
},
6338+
},
6339+
},
6340+
maxResourcesStatusCount: 1,
6341+
},
62746342
} {
62756343
t.Run(cc.name, func(t *testing.T) {
62766344
kubeclientset := kubefake.NewSimpleClientset([]runtime.Object{}...)
@@ -6279,13 +6347,14 @@ func TestUpdateResourceStatus(t *testing.T) {
62796347
metrics := appsetmetrics.NewFakeAppsetMetrics(client)
62806348

62816349
r := ApplicationSetReconciler{
6282-
Client: client,
6283-
Scheme: scheme,
6284-
Recorder: record.NewFakeRecorder(1),
6285-
Generators: map[string]generators.Generator{},
6286-
ArgoDB: &dbmocks.ArgoDB{},
6287-
KubeClientset: kubeclientset,
6288-
Metrics: metrics,
6350+
Client: client,
6351+
Scheme: scheme,
6352+
Recorder: record.NewFakeRecorder(1),
6353+
Generators: map[string]generators.Generator{},
6354+
ArgoDB: &dbmocks.ArgoDB{},
6355+
KubeClientset: kubeclientset,
6356+
Metrics: metrics,
6357+
MaxResourcesStatusCount: cc.maxResourcesStatusCount,
62896358
}
62906359

62916360
err := r.updateResourcesStatus(context.TODO(), log.NewEntry(log.StandardLogger()), &cc.appSet, cc.apps)

cmd/argocd-applicationset-controller/commands/applicationset_controller.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,7 @@ func NewCommand() *cobra.Command {
7474
enableScmProviders bool
7575
webhookParallelism int
7676
tokenRefStrictMode bool
77+
maxResourcesStatusCount int
7778
)
7879
scheme := runtime.NewScheme()
7980
_ = clientgoscheme.AddToScheme(scheme)
@@ -227,6 +228,7 @@ func NewCommand() *cobra.Command {
227228
GlobalPreservedAnnotations: globalPreservedAnnotations,
228229
GlobalPreservedLabels: globalPreservedLabels,
229230
Metrics: &metrics,
231+
MaxResourcesStatusCount: maxResourcesStatusCount,
230232
}).SetupWithManager(mgr, enableProgressiveSyncs, maxConcurrentReconciliations); err != nil {
231233
log.Error(err, "unable to create controller", "controller", "ApplicationSet")
232234
os.Exit(1)
@@ -270,6 +272,7 @@ func NewCommand() *cobra.Command {
270272
command.Flags().StringSliceVar(&globalPreservedLabels, "preserved-labels", env.StringsFromEnv("ARGOCD_APPLICATIONSET_CONTROLLER_GLOBAL_PRESERVED_LABELS", []string{}, ","), "Sets global preserved field values for labels")
271273
command.Flags().IntVar(&webhookParallelism, "webhook-parallelism-limit", env.ParseNumFromEnv("ARGOCD_APPLICATIONSET_CONTROLLER_WEBHOOK_PARALLELISM_LIMIT", 50, 1, 1000), "Number of webhook requests processed concurrently")
272274
command.Flags().StringSliceVar(&metricsAplicationsetLabels, "metrics-applicationset-labels", []string{}, "List of Application labels that will be added to the argocd_applicationset_labels metric")
275+
command.Flags().IntVar(&maxResourcesStatusCount, "max-resources-status-count", env.ParseNumFromEnv("ARGOCD_APPLICATIONSET_CONTROLLER_MAX_RESOURCES_STATUS_COUNT", 0, 0, math.MaxInt), "Max number of resources stored in appset status.")
273276
return &command
274277
}
275278

docs/operator-manual/argocd-cmd-params-cm.yaml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -272,6 +272,8 @@ data:
272272
applicationsetcontroller.requeue.after: "3m"
273273
# Enable strict mode for tokenRef in ApplicationSet resources. When enabled, the referenced secret must have a label `argocd.argoproj.io/secret-type` with value `scm-creds`.
274274
applicationsetcontroller.enable.tokenref.strict.mode: "false"
275+
# The maximum number of resources stored in the status of an ApplicationSet. This is a safeguard to prevent the status from growing too large.
276+
applicationsetcontroller.status.max.resources.count: "5000"
275277

276278
## Argo CD Notifications Controller Properties
277279
# Set the logging level. One of: debug|info|warn|error (default "info")

manifests/base/applicationset-controller/argocd-applicationset-controller-deployment.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -175,6 +175,12 @@ spec:
175175
name: argocd-cmd-params-cm
176176
key: applicationsetcontroller.requeue.after
177177
optional: true
178+
- name: ARGOCD_APPLICATIONSET_CONTROLLER_MAX_RESOURCES_STATUS_COUNT
179+
valueFrom:
180+
configMapKeyRef:
181+
name: argocd-cmd-params-cm
182+
key: applicationsetcontroller.status.max.resources.count
183+
optional: true
178184
volumeMounts:
179185
- mountPath: /app/config/ssh
180186
name: ssh-known-hosts

manifests/core-install-with-hydrator.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24165,6 +24165,12 @@ spec:
2416524165
key: applicationsetcontroller.requeue.after
2416624166
name: argocd-cmd-params-cm
2416724167
optional: true
24168+
- name: ARGOCD_APPLICATIONSET_CONTROLLER_MAX_RESOURCES_STATUS_COUNT
24169+
valueFrom:
24170+
configMapKeyRef:
24171+
key: applicationsetcontroller.status.max.resources.count
24172+
name: argocd-cmd-params-cm
24173+
optional: true
2416824174
image: quay.io/argoproj/argocd:v2.14.18
2416924175
imagePullPolicy: Always
2417024176
name: argocd-applicationset-controller

manifests/core-install.yaml

Lines changed: 6 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

manifests/ha/install-with-hydrator.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25506,6 +25506,12 @@ spec:
2550625506
key: applicationsetcontroller.requeue.after
2550725507
name: argocd-cmd-params-cm
2550825508
optional: true
25509+
- name: ARGOCD_APPLICATIONSET_CONTROLLER_MAX_RESOURCES_STATUS_COUNT
25510+
valueFrom:
25511+
configMapKeyRef:
25512+
key: applicationsetcontroller.status.max.resources.count
25513+
name: argocd-cmd-params-cm
25514+
optional: true
2550925515
image: quay.io/argoproj/argocd:v2.14.18
2551025516
imagePullPolicy: Always
2551125517
name: argocd-applicationset-controller

manifests/ha/install.yaml

Lines changed: 6 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

manifests/ha/namespace-install-with-hydrator.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1736,6 +1736,12 @@ spec:
17361736
key: applicationsetcontroller.requeue.after
17371737
name: argocd-cmd-params-cm
17381738
optional: true
1739+
- name: ARGOCD_APPLICATIONSET_CONTROLLER_MAX_RESOURCES_STATUS_COUNT
1740+
valueFrom:
1741+
configMapKeyRef:
1742+
key: applicationsetcontroller.status.max.resources.count
1743+
name: argocd-cmd-params-cm
1744+
optional: true
17391745
image: quay.io/argoproj/argocd:v2.14.18
17401746
imagePullPolicy: Always
17411747
name: argocd-applicationset-controller

0 commit comments

Comments
 (0)