helmfile icon indicating copy to clipboard operation
helmfile copied to clipboard

Quick question about hooks

Open cdunford opened this issue 5 years ago • 18 comments

I am just wondering exactly when presync and postsync hooks are run, specifically:

  1. Are they run if a release is being uninstalled?
  2. Are they run if a release is already uninstalled and installed: false?

If the answer is yes, is there a parameter available to hooks to indicate what exactly is happening (installing/upgrading/uninstalling)?

cdunford avatar Jun 02 '20 11:06 cdunford

Are they run if a release is being uninstalled?

Yes.

https://github.com/roboll/helmfile/blob/68432b1848783640ee8a407edd825f82ca8819fe/pkg/state/state.go#L505

Are they run if a release is already uninstalled and installed: false?

No.

https://github.com/roboll/helmfile/blob/68432b1848783640ee8a407edd825f82ca8819fe/pkg/state/state.go#L419-L426

The general rule is that installed: false doesn't prevent it from being processed, which involves running presync and postsync.

But helmfile has nothing to do for a release that is already installed and is set to installed: false, which means presync and postsync aren't run either.

mumoshu avatar Jun 02 '20 12:06 mumoshu

But helmfile has nothing to do for a release that is already installed and is set to installed: false, which means presync and postsync aren't run either.

I assume you mean a release that is already uninstalled?

Are there any parameters available for hooks to know what is happening?

cdunford avatar Jun 02 '20 12:06 cdunford

I assume you mean a release that is already uninstalled?

Yeah! Sorry for the mistake.

Are there any parameters available for hooks to know what is happening?

Nope. What would you use that for?

mumoshu avatar Jun 02 '20 12:06 mumoshu

I have hooks that I can either skip or make more efficient if I know what is actually happening.

cdunford avatar Jun 02 '20 13:06 cdunford

@cdunford Would it help if I add preuninstall and postuninstall hooks?

mumoshu avatar Jun 02 '20 23:06 mumoshu

@mumoshu - yes that would help. It would also be good to have preinstall/postinstall which only trigger if the release was not previously installed.

cdunford avatar Jun 03 '20 12:06 cdunford

@cdunford Got it!

Btw, what would you use those hooks exactly for? Notifications, creating/deleting extra resources, etc?

The feature is feasible but Im really not sure how people would use it, and if I can recommend that or not.

mumoshu avatar Jun 03 '20 12:06 mumoshu

Sorry for the long delay in getting back to you.

Our application has some somewhat complex requirements around deployment and upgrade; there are certain things (external to kubernetes) that need to happen on initial install, but never again. We can detect these in other ways, but it seems helm/helmfile has the necessary context to know where this is a clean install or an upgrade, so if that context was available to our hooks, we could forgo any sort of other type of detection and just use what helm tells us.

We have some unique requirements around rollbacks in the case of deployment failure as well. It would be useful to have a hook that runs on sync failure that could be used to rollback external items (that helm/helmfile isn't managing declaratively).

I'm basically thinking the set of lifecycle hooks available in helm also make sense in helmfile:

Annotation Value Description
pre-install Executes after templates are rendered, but before any resources are created in Kubernetes
post-install Executes after all resources are loaded into Kubernetes
pre-delete Executes on a deletion request before any resources are deleted from Kubernetes
post-delete Executes on a deletion request after all of the release's resources have been deleted
pre-upgrade Executes on an upgrade request after templates are rendered, but before any resources are updated
post-upgrade Executes on an upgrade after all resources have been upgraded
pre-rollback Executes on a rollback request after templates are rendered, but before any resources are rolled back
post-rollback Executes on a rollback request after all resources have been modified
test Executes when the Helm test subcommand is invoked ( view test docs)

(from https://helm.sh/docs/topics/charts_hooks/)

We may be able to use helm hooks instead of helmfile hooks for our use case(s), but in general the helmfile hooks have been preferable to us as the run in the context of our CD pipeline and don't require crafting templates that deploy resources into our cluster.

cdunford avatar Jun 23 '20 19:06 cdunford

@cdunford Hey! I've managed to come back to this. I've opened #1805 for postinstall.

Equivalents to post-delete and pre-delete has been discussed in #802 and added via #1375

mumoshu avatar Apr 24 '21 22:04 mumoshu

One use-case we had in favor of a post-install and post-uninstall is manually applying CRDs in a specific order. Helm can handle this if the chart is correctly created, but not all charts are created equal. I've found that sometimes we have to take matters into our own hands.

notjames avatar May 02 '21 06:05 notjames

@notjames Hey! Can't you just use incubator/raw with needs in that case, so that you can install CRDs before other releases that depends on the CRDs, and delete CRDs after other releases that depends on the CRDs get deleted?

release:
- name: crds
  chart: incubator/raw
  values:
  - crds/foo.crd.yaml
  - crds/bar.crd.yaml
- name: yourapp
  chart: repo/somechart
  needs:
  - crds

mumoshu avatar May 02 '21 07:05 mumoshu

I'd love to be able to use pre-install to run a script adopting non-helm resources by labelling/annotating them. In particular this would be useful for adopting things the cloud provider (AWS/EKS, in my case) pre-installs; for example, Amazon provides a vpc-cni chart which can be used to install/configure the AWS VPC CNI provider... except the VPC CNI provider is already installed "out of the box" on fresh clusters, and not through Helm. Their documentation recommends running a script to apply the meta.helm.sh annotations and app.kubernetes.io/managed-by label so that Helm 3.2+ can "adopt" the existing resources. If there were a pre-install hook I could just have it run Amazon's provided script (although of course without pre-install I can just use pre-sync and modify the script to check whether the chart is installed before doing anything; or just run the script by hand).

philomory avatar Mar 30 '22 23:03 philomory

@philomory If you want to hook anything before running helm command at all, I guess you can just use prepare hook too we already have today.

mumoshu avatar Mar 31 '22 00:03 mumoshu

Ah, so you want preinstall just to avoid writing your own check for the existence of the helm release, right? 🤔

mumoshu avatar Mar 31 '22 00:03 mumoshu

I think adopting existing resources worth a dedicated issue(and a dedicated Helmfile feature)

mumoshu avatar Mar 31 '22 00:03 mumoshu

Also note that certain kinds of hooks needs extra care to be idempotent. If we were to run e.g. post-uninstall hook after Helmfile uninstalled the release and the hook failed due to a transient error, the next Helmfile run won't rerun the post-uninstall hook as.. it's already uninstalled. That makes me think anything related to cleaning up dangling resources in your cluster needs to be in the cluster itself, or another k8s operator/controller that continuously resyncs your cluster to remove dangling resources, rather than in Helmfile.

mumoshu avatar Mar 31 '22 00:03 mumoshu

@mumoshu I should note, I actually tried today using presync and just adding the logic to check for existence to my script, but it doesn't work. The script never gets executed at all, because before we get to the prescync phase, helmfile calls out to helm diff, and helm diff fails with the same sort of error helm install would when the chart would create resources that already exist. There's even an issue about it in the helm-diff repository.

I might be able to get it to work with a prepare hook where I supply the {{ .HelmfileCommand }} as an argument to the script and then use that to figure out if we're running a command that would have triggered a presync hook such as sync or apply.

philomory avatar Apr 03 '22 21:04 philomory

I would like a pre-install script to install crds before I run helmfile build so that the command does not fail. thanks

my script looks something like this :

helm show crds "$1" > crds.raw.yaml
sed 's/apiVersion\: apiextensions/\-\-\-\napiVersion\: apiextensions/g' crds.raw.yaml > crds.yaml
kubectl apply -f crds.yaml
rm crds.yaml crds.raw.yaml

and I want to run it like this:

  - chart: charts/certs
    name: certs
    namespace: infrastructure
    hooks:
      - pre-install: ./pre-install-crds.sh

woodcockjosh avatar Apr 13 '23 19:04 woodcockjosh