Skip to content

Commit 27195c0

Browse files
authored
Merge pull request #8850 from killianmuldoon/pr-stop-caching-pods
🐛 ClusterCacheTracker: Stop pod caching when checking workload cluster
2 parents 06d5b86 + ed31880 commit 27195c0

File tree

1 file changed

+25
-14
lines changed

1 file changed

+25
-14
lines changed

controllers/remote/cluster_cache_tracker.go

Lines changed: 25 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -278,13 +278,14 @@ func (t *ClusterCacheTracker) newClusterAccessor(ctx context.Context, cluster cl
278278
}
279279

280280
// Create a client and a cache for the cluster.
281-
c, cache, err := t.createClient(ctx, config, cluster, indexes)
281+
c, uncachedClient, cache, err := t.createClient(ctx, config, cluster, indexes)
282282
if err != nil {
283283
return nil, err
284284
}
285285

286286
// Detect if the controller is running on the workload cluster.
287-
runningOnCluster, err := t.runningOnWorkloadCluster(ctx, c, cluster)
287+
// This function uses an uncached client to ensure pods aren't cached by the long-lived client.
288+
runningOnCluster, err := t.runningOnWorkloadCluster(ctx, uncachedClient, cluster)
288289
if err != nil {
289290
return nil, err
290291
}
@@ -303,7 +304,7 @@ func (t *ClusterCacheTracker) newClusterAccessor(ctx context.Context, cluster cl
303304
config.Host = inClusterConfig.Host
304305

305306
// Create a new client and overwrite the previously created client.
306-
c, cache, err = t.createClient(ctx, config, cluster, indexes)
307+
c, _, cache, err = t.createClient(ctx, config, cluster, indexes)
307308
if err != nil {
308309
return nil, errors.Wrap(err, "error creating client for self-hosted cluster")
309310
}
@@ -355,26 +356,26 @@ func (t *ClusterCacheTracker) runningOnWorkloadCluster(ctx context.Context, c cl
355356
return t.controllerPodMetadata.UID == pod.UID, nil
356357
}
357358

358-
// createClient creates a client and a mapper based on a rest.Config.
359-
func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Config, cluster client.ObjectKey, indexes []Index) (client.Client, *stoppableCache, error) {
359+
// createClient creates a cached client, and uncached client and a mapper based on a rest.Config.
360+
func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Config, cluster client.ObjectKey, indexes []Index) (client.Client, client.Client, *stoppableCache, error) {
360361
// Create a http client for the cluster.
361362
httpClient, err := rest.HTTPClientFor(config)
362363
if err != nil {
363-
return nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error creating http client", cluster.String())
364+
return nil, nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error creating http client", cluster.String())
364365
}
365366

366367
// Create a mapper for it
367368
mapper, err := apiutil.NewDynamicRESTMapper(config, httpClient)
368369
if err != nil {
369-
return nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error creating dynamic rest mapper", cluster.String())
370+
return nil, nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error creating dynamic rest mapper", cluster.String())
370371
}
371372

372373
// Verify if we can get a rest mapping from the workload cluster apiserver.
373374
// Note: This also checks if the apiserver is up in general. We do this already here
374375
// to avoid further effort creating a cache and a client and to produce a clearer error message.
375376
_, err = mapper.RESTMapping(corev1.SchemeGroupVersion.WithKind("Node").GroupKind(), corev1.SchemeGroupVersion.Version)
376377
if err != nil {
377-
return nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error getting rest mapping", cluster.String())
378+
return nil, nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error getting rest mapping", cluster.String())
378379
}
379380

380381
// Create the cache for the remote cluster
@@ -385,7 +386,7 @@ func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Con
385386
}
386387
remoteCache, err := cache.New(config, cacheOptions)
387388
if err != nil {
388-
return nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error creating cache", cluster.String())
389+
return nil, nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q: error creating cache", cluster.String())
389390
}
390391

391392
cacheCtx, cacheCtxCancel := context.WithCancel(ctx)
@@ -398,12 +399,12 @@ func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Con
398399

399400
for _, index := range indexes {
400401
if err := cache.IndexField(ctx, index.Object, index.Field, index.ExtractValue); err != nil {
401-
return nil, nil, errors.Wrapf(err, "error adding index for field %q to cache for remote cluster %q", index.Field, cluster.String())
402+
return nil, nil, nil, errors.Wrapf(err, "error adding index for field %q to cache for remote cluster %q", index.Field, cluster.String())
402403
}
403404
}
404405

405406
// Create the client for the remote cluster
406-
c, err := client.New(config, client.Options{
407+
cachedClient, err := client.New(config, client.Options{
407408
Scheme: t.scheme,
408409
Mapper: mapper,
409410
HTTPClient: httpClient,
@@ -414,9 +415,19 @@ func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Con
414415
},
415416
})
416417
if err != nil {
417-
return nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q", cluster.String())
418+
return nil, nil, nil, errors.Wrapf(err, "error creating client for remote cluster %q", cluster.String())
418419
}
419420

421+
// Create an uncached client. This is used in `runningOnWorkloadCluster` to ensure we don't continuously cache
422+
// pods in the client.
423+
uncachedClient, err := client.New(config, client.Options{
424+
Scheme: t.scheme,
425+
Mapper: mapper,
426+
HTTPClient: httpClient,
427+
})
428+
if err != nil {
429+
return nil, nil, nil, errors.Wrapf(err, "error creating uncached client for remote cluster %q", cluster.String())
430+
}
420431
// Start the cache!!!
421432
go cache.Start(cacheCtx) //nolint:errcheck
422433

@@ -425,7 +436,7 @@ func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Con
425436
defer cacheSyncCtxCancel()
426437
if !cache.WaitForCacheSync(cacheSyncCtx) {
427438
cache.Stop()
428-
return nil, nil, fmt.Errorf("failed waiting for cache for remote cluster %v to sync: %w", cluster, cacheCtx.Err())
439+
return nil, nil, nil, fmt.Errorf("failed waiting for cache for remote cluster %v to sync: %w", cluster, cacheCtx.Err())
429440
}
430441

431442
// Start cluster healthcheck!!!
@@ -435,7 +446,7 @@ func (t *ClusterCacheTracker) createClient(ctx context.Context, config *rest.Con
435446
httpClient: httpClient,
436447
})
437448

438-
return c, cache, nil
449+
return cachedClient, uncachedClient, cache, nil
439450
}
440451

441452
// deleteAccessor stops a clusterAccessor's cache and removes the clusterAccessor from the tracker.

0 commit comments

Comments
 (0)