I have several cookbooks which include several other cookbooks, depending on each cookbook's needs. The included cookbooks declare services which notify other services.
One of the included cookbook common_actions
is included in all the other cookbooks as it contains actions common to all.
include_recipe 'cookbook1'
include_recipe 'common_actions'
include_recipe 'cookbook2'
# Several cookbooks have such includes, but 'common_actions'
# is included in almost all the cookbooks.
# cookbook specific conditional logic that should be
# executed only if some condition in 'common_actions' is true
Is it a wise idea to include a conditional return statement in the common_actions
cookbook so that it will force the including cookbooks not to be compiled/executed based on that condition? For the purpose of this question, please consider any fake condition like:
if node['IP'] == 'xyz'
# All including cookbooks should execute only IP is xyz
return
end
Can a cookbook with such a return statement cause only certain cookbooks to run? Is it advisable?
Note: I am doing this because I do not want to copy-paste the same code in all the other cookbooks.
If I understood you properly, this won't do what you're after because:
include_recipe A::B
then recipe B of cookbook A will only be compiled once, successive calls will be no-op (won't duplicate the recipe resources).return
statement will end the actual recipe compilation, in your case it will stop the compilation of recipe default
in the cookbook common_actions
.What you can do is using node.run_state
, it's a hash available only during the run.
You can use it to store another hash of conditions from your command_actions
cookbookn for example.
node.run_state['IP_allowed'] = node['IP'] == 'xyz'
# Probabaly a little silly, but that's the easier I can think of
if node.chef_environment == 'Test'
if node['DoDebugLog'] == true
node.run_state['LoggerLevel'] = 'debug'
else
node.run_state['LoggerLevel'] = 'info'
else
node.run_state['LoggerLevel'] = 'warn'
end
Now you can use those values in others recipes to control their behavior while still keeping the conditional definition in a central place.
In a recipe which should not run if node['IP']
is 'xyz'
you'll start the recipe with:
return if node.run_state['IP_allowed']
And on one which should run only if node['IP']
is 'xyz'
you'll start the recipe with:
return unless node.run_state['IP_allowed']
The other value could be used for logging from recipes in different environments like this:
log "Message to log" do
level node.run_state['LoggerLevel']
end