Search code examples
rubychef-infracookbookrecipe

Chef recipe - how to run a resource only if user resource did manage_home


I have two resources in my recipe. The first one is a user resource that sets the user uid/gid/home directory etc. It uses supports :manage_home => true.

My second resource is a bash resource. Currently the script runs on every chef-client run, which is a little unnecessary. I want the script to run only if the manage_home was invoked when running the user resource (eg. run the script if the user's home directory was changed and files were moved over, otherwise do nothing).

I have only been able to find examples of using only_if with some pure Ruby condition (eg. if a certain file exists, if a node has a certain element in its run list, etc), but what I want to do requires the condition to be linked to the result of another chef resource. I know that the user resource just runs usermod (or useradd), which doesn't seem to give any indication of whether the home directory was moved or not. So is this even possible?


Solution

  • Resources have the ability to notify other resources, on any state change.

    user "whatever" do
      action :modify
      notifies :run, "bash[modify user]", :immediately
    end
    

    You can change the default action of your resource to :nothing, then the resource will only run on the notify.

    bash "modify user" do
      command "ls"
      action :nothing
    end
    

    What constitutes a "state change" is controlled inside resources, but it should normally be triggered if any actions at all were taken by the resource (This is set with a flag in the resource called updated_by_last_action). This may not exactly meet your manage_home requirement but it's better than your bash running all the time.