Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
81 changes: 12 additions & 69 deletions cmd/operator-controller/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,15 +30,12 @@ import (

"github.com/spf13/cobra"
"go.podman.io/image/v5/types"
corev1 "k8s.io/api/core/v1"
rbacv1 "k8s.io/api/rbac/v1"
apiextensionsv1 "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1"
apiextensionsv1client "k8s.io/apiextensions-apiserver/pkg/client/clientset/clientset/typed/apiextensions/v1"
k8slabels "k8s.io/apimachinery/pkg/labels"
k8stypes "k8s.io/apimachinery/pkg/types"
apimachineryrand "k8s.io/apimachinery/pkg/util/rand"
"k8s.io/client-go/discovery"
"k8s.io/client-go/discovery/cached/memory"
corev1client "k8s.io/client-go/kubernetes/typed/core/v1"
_ "k8s.io/client-go/plugin/pkg/client/auth"
"k8s.io/klog/v2"
Expand All @@ -61,7 +58,6 @@ import (
helmclient "github.com/operator-framework/helm-operator-plugins/pkg/client"

ocv1 "github.com/operator-framework/operator-controller/api/v1"
clusterobjctrl "github.com/operator-framework/operator-controller/internal/object-controller/controllers"
"github.com/operator-framework/operator-controller/internal/operator-controller/action"
"github.com/operator-framework/operator-controller/internal/operator-controller/applier"
"github.com/operator-framework/operator-controller/internal/operator-controller/catalogmetadata/cache"
Expand Down Expand Up @@ -119,7 +115,6 @@ type boxcutterReconcilerConfigurator struct {
imageCache imageutil.Cache
imagePuller imageutil.Puller
finalizers crfinalizer.Finalizers
trackingCache managedcache.TrackingCache
}

type helmReconcilerConfigurator struct {
Expand Down Expand Up @@ -461,26 +456,22 @@ func run() error {
crdupgradesafety.NewPreflight(aeClient.CustomResourceDefinitions()),
}

trackingCache, err := managedcache.NewTrackingCache(
ctrl.Log.WithName("trackingCache"),
mgr.GetConfig(),
crcache.Options{
Scheme: mgr.GetScheme(), Mapper: mgr.GetRESTMapper(),
},
)
if err != nil {
setupLog.Error(err, "unable to create tracking cache")
return err
}
if err := mgr.Add(trackingCache); err != nil {
setupLog.Error(err, "unable to add tracking cache to manager")
return err
}

var trackingCache managedcache.TrackingCache
var ctrlBuilderOpts []controllers.ControllerBuilderOption
if features.OperatorControllerFeatureGate.Enabled(features.BoxcutterRuntime) {
ctrlBuilderOpts = append(ctrlBuilderOpts, controllers.WithOwns(&ocv1.ClusterObjectSet{}))
} else {
trackingCache, err = managedcache.NewTrackingCache(
ctrl.Log.WithName("trackingCache"),
mgr.GetConfig(),
crcache.Options{Scheme: mgr.GetScheme(), Mapper: mgr.GetRESTMapper()},
)
if err != nil {
return fmt.Errorf("unable to create tracking cache: %w", err)
}
if err := mgr.Add(trackingCache); err != nil {
return fmt.Errorf("unable to add tracking cache to manager: %w", err)
}
ctrlBuilderOpts = append(ctrlBuilderOpts, controllers.WithWatchesRawSource(
trackingCache.Source(
crhandler.EnqueueRequestForOwner(mgr.GetScheme(), mgr.GetRESTMapper(), &ocv1.ClusterExtension{}),
Expand Down Expand Up @@ -520,7 +511,6 @@ func run() error {
imageCache: imageCache,
imagePuller: imagePuller,
finalizers: clusterExtensionFinalizers,
trackingCache: trackingCache,
}
} else {
cerCfg = &helmReconcilerConfigurator{
Expand Down Expand Up @@ -665,38 +655,6 @@ func (c *boxcutterReconcilerConfigurator) Configure(ceReconciler *controllers.Cl
controllers.ApplyBundleWithBoxcutter(appl.Apply),
}

baseDiscoveryClient, err := discovery.NewDiscoveryClientForConfig(c.mgr.GetConfig())
if err != nil {
return fmt.Errorf("unable to create discovery client: %w", err)
}

// Wrap the discovery client with caching to reduce memory usage from repeated OpenAPI schema fetches
discoveryClient := memory.NewMemCacheClient(baseDiscoveryClient)

revisionEngineFactory, err := clusterobjctrl.NewDefaultRevisionEngineFactory(
c.mgr.GetScheme(),
c.trackingCache,
discoveryClient,
c.mgr.GetRESTMapper(),
fieldOwnerPrefix,
c.mgr.GetConfig(),
)
if err != nil {
return fmt.Errorf("unable to create revision engine factory: %w", err)
}

cosClient := &secretFallbackClient{
Client: c.mgr.GetClient(),
apiReader: c.mgr.GetAPIReader(),
systemNamespace: cfg.systemNamespace,
}
if err = (&clusterobjctrl.ClusterObjectSetReconciler{
Client: cosClient,
RevisionEngineFactory: revisionEngineFactory,
TrackingCache: c.trackingCache,
}).SetupWithManager(c.mgr); err != nil {
return fmt.Errorf("unable to setup ClusterObjectSet controller: %w", err)
}
return nil
}

Expand Down Expand Up @@ -761,18 +719,3 @@ func main() {
os.Exit(1)
}
}

// secretFallbackClient wraps a cached client.Client and falls back to direct
// API reads for Secrets outside the system namespace, where the cache does not watch.
type secretFallbackClient struct {
client.Client
apiReader client.Reader
systemNamespace string
}

func (c *secretFallbackClient) Get(ctx context.Context, key client.ObjectKey, obj client.Object, opts ...client.GetOption) error {
if _, isSecret := obj.(*corev1.Secret); isSecret && key.Namespace != c.systemNamespace {
return c.apiReader.Get(ctx, key, obj, opts...)
}
return c.Client.Get(ctx, key, obj, opts...)
}
12 changes: 7 additions & 5 deletions helm/experimental.yaml
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
# experimental values for OLMv1.
# This is a YAML-formatted file.
# Declare variables to be passed into your templates.

# List of enabled experimental features for operator-controller
# Use with {{- if has "FeatureGate" .Values.options.operatorController.features.enabled }}
# to pull in resources or additions
options:
objectController:
deployment:
replicas: 2
operatorController:
deployment:
replicas: 2
Expand All @@ -18,9 +20,9 @@ options:
- WebhookProviderCertManager
disabled:
- WebhookProviderOpenshiftServiceCA
# List of enabled experimental features for catalogd
# Use with {{- if has "FeatureGate" .Values.options.catalogd.features.enabled }}
# to pull in resources or additions
# List of enabled experimental features for catalogd
# Use with {{- if has "FeatureGate" .Values.options.catalogd.features.enabled }}
# to pull in resources or additions
catalogd:
deployment:
replicas: 2
Expand All @@ -29,5 +31,5 @@ options:
- APIV1MetasHandler
- GraphQLCatalogQueries
disabled: []
# This can be one of: standard or experimental
# This can be one of: standard or experimental
featureSet: experimental
26 changes: 21 additions & 5 deletions helm/olmv1/templates/_helpers.tpl
Original file line number Diff line number Diff line change
Expand Up @@ -59,14 +59,30 @@ olmv1
{{- end -}}

{{/*
Prepare component resources without enabling a second ClusterObjectSet reconciler.
The deployment and reconciliation handover will replace this activation guard.
Default to a separate object-controller whenever operator-controller uses Boxcutter.
An explicit enabled value also permits installing object-controller on its own.
Disabling it while Boxcutter is active would leave ClusterObjectSets without a controller.
Return an empty string when disabled so the helper can be used in conditionals.
*/}}
{{- define "objectController.enabled" -}}
{{- if hasKey .Values.options "objectController" -}}
{{- if .Values.options.objectController.enabled -}}
{{- fail "object-controller deployment support requires the reconciliation cutover" -}}
{{- $operatorController := .Values.options.operatorController | default dict -}}
{{- $features := $operatorController.features | default dict -}}
{{- if and $operatorController.enabled (has "BoxcutterRuntime" $features.enabled) (has "BoxcutterRuntime" $features.disabled) -}}
{{- fail "BoxcutterRuntime cannot appear in both options.operatorController.features.enabled and options.operatorController.features.disabled" -}}
{{- end -}}
{{- $boxcutterEnabled := and $operatorController.enabled (has "BoxcutterRuntime" $features.enabled) (not (has "BoxcutterRuntime" $features.disabled)) -}}
{{- if and $boxcutterEnabled (eq (toJson .Values.options.objectController.enabled) "false") -}}
{{- fail "options.objectController.enabled=false is incompatible with enabled BoxcutterRuntime" -}}
{{- end -}}
{{- $enabled := .Values.options.objectController.enabled -}}
{{- if eq (toJson $enabled) "null" -}}
{{- $enabled = $boxcutterEnabled -}}
{{- end -}}
{{- if $enabled -}}
{{- if ne .Values.options.featureSet "experimental" -}}
{{- fail "objectController requires options.featureSet=experimental" -}}
{{- end -}}
true
{{- end -}}
{{- end -}}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,3 @@
{{- if .Values.options.operatorController.enabled }}
{{- if (eq .Values.options.featureSet "standard") }}
{{- /* Add when GA: tpl (.Files.Get "base/object-controller/crd/standard/olm.operatorframework.io_clusterobjectsetss.yaml") . */}}
{{- else if (eq .Values.options.featureSet "experimental") }}
{{- if has "BoxcutterRuntime" .Values.options.operatorController.features.enabled }}
{{- if include "objectController.enabled" . }}
Comment thread
coderabbitai[bot] marked this conversation as resolved.
{{ tpl (.Files.Get "base/object-controller/crd/experimental/olm.operatorframework.io_clusterobjectsets.yaml") . }}
{{- end }}
{{- else }}
{{- fail "options.featureSet must be set to one of: {standard,experimental}" }}
{{- end }}
{{- end }}
2 changes: 1 addition & 1 deletion helm/olmv1/values.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
# List of components to include
options:
objectController:
# Activation is reserved until the deployment and reconciliation cutover.
# null follows operatorController's BoxcutterRuntime gate. Set true to deploy independently.
enabled: null
deployment:
image: quay.io/operator-framework/object-controller:devel
Expand Down
Loading
Loading