Skip to content

Commit

Permalink
fix: move awsacfg resource creation from Helm chart to controller (#61)
Browse files Browse the repository at this point in the history
Co-authored-by: Parikshit Samant <[email protected]>
  • Loading branch information
kbeniwal and pns-nirmata authored Mar 16, 2023
1 parent 73e6517 commit 42221ff
Show file tree
Hide file tree
Showing 5 changed files with 142 additions and 16 deletions.
9 changes: 9 additions & 0 deletions charts/kyverno-aws-adapter/templates/deployment.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,15 @@ spec:
image: {{ include "kyverno-aws-adapter.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy }}
name: manager
env:
- name: ADAPTER_NAME
value: {{ include "kyverno-aws-adapter.fullname" . }}
- name: ADAPTER_NAMESPACE
value: {{ .Release.Namespace }}
- name: CLUSTER_NAME
value: {{ required "EKS cluster name is required" .Values.eksCluster.name }}
- name: CLUSTER_REGION
value: {{ required "EKS cluster region is required" .Values.eksCluster.region }}
{{- if .Values.pollInterval }}
args:
- --sync-period={{ .Values.pollInterval }}
Expand Down
9 changes: 0 additions & 9 deletions charts/kyverno-aws-adapter/templates/resource.yaml

This file was deleted.

35 changes: 31 additions & 4 deletions controllers/awsadapterconfig_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,10 @@ import (

"github.com/go-logr/logr"
"github.com/google/go-cmp/cmp"
"k8s.io/apimachinery/pkg/api/errors"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
apimachineryTypes "k8s.io/apimachinery/pkg/types"
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/client"
"sigs.k8s.io/controller-runtime/pkg/log"
Expand Down Expand Up @@ -86,13 +88,13 @@ func (r *AWSAdapterConfigReconciler) Reconcile(ctx context.Context, req ctrl.Req
}
l.Info("Reconciling", "req", req)

l.Info("Loading AWS SDK config")
l.Info("Loading AWS Adapter config")
cfg, err := config.LoadDefaultConfig(context.TODO(), config.WithRegion(*objOld.Spec.Region))
if err != nil {
l.Error(err, "error occurred while loading aws sdk config")
return r.updateLastPollStatusFailure(ctx, objOld, "error occurred while loading aws sdk config", err, &l, time.Now())
l.Error(err, "error occurred while loading aws adapter config")
return r.updateLastPollStatusFailure(ctx, objOld, "error occurred while loading aws adapter config", err, &l, time.Now())
}
l.Info("AWS SDK config loaded successfully")
l.Info("AWS Adapter config loaded successfully")

stsClient := sts.NewFromConfig(cfg)
ec2Client := ec2.NewFromConfig(cfg)
Expand Down Expand Up @@ -464,6 +466,31 @@ func (r *AWSAdapterConfigReconciler) updateLastPollStatusFailure(ctx context.Con
return ctrl.Result{RequeueAfter: r.RequeueInterval}, nil
}

func (r *AWSAdapterConfigReconciler) IsAWSAdapterConfigPresent(adapterName, adapterNamespace string) (bool, error) {
obj := &securityv1alpha1.AWSAdapterConfig{}
err := r.Get(context.TODO(), apimachineryTypes.NamespacedName{Namespace: adapterNamespace, Name: adapterName}, obj)
if err == nil {
return true, nil
}
if errors.IsNotFound(err) {
return false, nil
}
return false, err
}

func (r *AWSAdapterConfigReconciler) CreateAWSAdapterConfig(clusterName, clusterRegion, adapterName, adapterNamespace string) error {
return r.Create(context.TODO(), &securityv1alpha1.AWSAdapterConfig{
ObjectMeta: metav1.ObjectMeta{
Name: adapterName,
Namespace: adapterNamespace,
},
Spec: securityv1alpha1.AWSAdapterConfigSpec{
Name: &clusterName,
Region: &clusterRegion,
},
})
}

func getAmi(ctx context.Context, ec2Client *ec2.Client, imageId *string) (*types.Image, error) {
amis, err := ec2Client.DescribeImages(ctx, &ec2.DescribeImagesInput{
DryRun: aws.Bool(false),
Expand Down
24 changes: 24 additions & 0 deletions docs/getting_started.md
Original file line number Diff line number Diff line change
Expand Up @@ -163,3 +163,27 @@ kubectl get awsacfg -n nirmata-aws-adapter
NAME ... CLUSTER NAME ... LAST POLLED STATUS
kyverno-aws-adapter ... cluster-name ... success
```
### Uninstalling the AWS Adapter Helm chart
To uninstall the AWS Adapter Helm chart, use the following command.
```bash
helm uninstall kyverno-aws-adapter --namespace nirmata-aws-adapter
```
This removes all the Kubernetes components associated with the chart and deletes the release.
The `awsadapterconfigs.security.nirmata.io` CRD created by this chart is not removed by default and should be manually cleaned up. So, after uninstalling helm chart the following command can be used to remove the CRD.
```bash
kubectl delete crd awsadapterconfigs.security.nirmata.io
```
### Deleting the AWSAdapterConfig
The `AWSAdapterConfig` CR is not deleted by `helm uninstall` or by deleting the pod, and must be manually cleaned up.
```bash
kubectl delete awsacfg kyverno-aws-adapter -n nirmata-aws-adapter
```
81 changes: 78 additions & 3 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ import (
utilruntime "k8s.io/apimachinery/pkg/util/runtime"
clientgoscheme "k8s.io/client-go/kubernetes/scheme"
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/client"
"sigs.k8s.io/controller-runtime/pkg/healthz"
"sigs.k8s.io/controller-runtime/pkg/log/zap"

Expand Down Expand Up @@ -92,11 +93,12 @@ func main() {
os.Exit(1)
}

if err = (&controllers.AWSAdapterConfigReconciler{
Client: mgr.GetClient(),
r := &controllers.AWSAdapterConfigReconciler{
Client: getClient(),
Scheme: mgr.GetScheme(),
RequeueInterval: time.Duration(syncPeriod) * time.Minute,
}).SetupWithManager(mgr); err != nil {
}
if err = r.SetupWithManager(mgr); err != nil {
setupLog.Error(err, "unable to create controller", "controller", "AWSAdapterConfig")
os.Exit(1)
}
Expand All @@ -111,9 +113,82 @@ func main() {
os.Exit(1)
}

createAWSAdapterConfigIfNotPresent(r)

setupLog.Info("starting manager")
if err := mgr.Start(ctrl.SetupSignalHandler()); err != nil {
setupLog.Error(err, "problem running manager")
os.Exit(1)
}
}

func getClient() client.Client {
cl, err := client.New(ctrl.GetConfigOrDie(), client.Options{Scheme: scheme})
if err != nil {
setupLog.Error(err, "unable to create client")
os.Exit(1)
}
return cl
}

type requiredParams struct {
clusterName string
clusterRegion string
adapterName string
adapterNamespace string
}

func (rp *requiredParams) areAllPresent() bool {
return rp.clusterName != "" && rp.clusterRegion != "" && rp.adapterName != "" && rp.adapterNamespace != ""
}

func createAWSAdapterConfigIfNotPresent(r *controllers.AWSAdapterConfigReconciler) {
rp := requiredParams{
clusterName: getClusterName(),
clusterRegion: getClusterRegion(),
adapterName: getAdapterName(),
adapterNamespace: getAdapterNamespace(),
}

if rp.areAllPresent() {
setupLog.Info("One or more of the required parameters could not be found: clusterName='%s' clusterRegion='%s' adapterName='%s' adapterNamespace='%s'", rp.clusterName, rp.clusterRegion, rp.adapterName, rp.adapterNamespace)
return
}

if isAWSAdapterConfigPresent, err := r.IsAWSAdapterConfigPresent(rp.adapterName, rp.adapterNamespace); err != nil {
setupLog.Error(err, "problem checking if AWS Adapter config exists")
os.Exit(1)
} else if isAWSAdapterConfigPresent {
setupLog.Info("AWS Adapter config already exists. Skipping resource creation.")
} else {
setupLog.Info("creating AWS Adapter config")
if err := r.CreateAWSAdapterConfig(rp.clusterName, rp.clusterRegion, rp.adapterName, rp.adapterNamespace); err != nil {
setupLog.Error(err, "unable to create AWS Adapter config")
os.Exit(1)
}
setupLog.Info("AWS Adapter config created successfully")
}
}

const (
ADAPTER_NAME_ENV_VAR = "ADAPTER_NAME"
ADAPTER_NAMESPACE_ENV_VAR = "ADAPTER_NAMESPACE"
CLUSTER_NAME_ENV_VAR = "CLUSTER_NAME"
CLUSTER_REGION_ENV_VAR = "CLUSTER_REGION"
)

func getAdapterName() string {
return os.Getenv(ADAPTER_NAME_ENV_VAR)
}

func getAdapterNamespace() string {
return os.Getenv(ADAPTER_NAMESPACE_ENV_VAR)
}

func getClusterName() string {
return os.Getenv(CLUSTER_NAME_ENV_VAR)
}

func getClusterRegion() string {
return os.Getenv(CLUSTER_REGION_ENV_VAR)
}

0 comments on commit 42221ff

Please sign in to comment.