How to use not_if in a chef recipe

15,257

Solution 1

I had been having the same issue. But, in my case, "not_if" seems executed by different user (root), and failed to check the condition properly. Adding [:user => "postgres"] resolved the issue.

execute "create-database-user" do
    user "postgres"
    exists = <<-EOH
    psql -U postgres -c "select * from pg_user where usename='#{settings[:username]}'" | grep -c #{settings[:username]}
    EOH
    command "createuser -U postgres -sw #{settings[:username]}"
    not_if exists, :user => "postgres"
end

I've referred the following code example.

https://github.com/MarcinKoziuk/chef-postgres-dbsetup/blob/master/recipes/default.rb

Solution 2

You're checking for the existence of:

node[:user]

If it doesn't exist, you create:

node[:postgresql][:user]

Unless these happen to be equal, you'll keep trying to create node[:postgresql][:user] repeatedly.

Share:
15,257
Admin
Author by

Admin

Updated on July 05, 2022

Comments

  • Admin
    Admin almost 2 years

    I am new to chef so I am a little confused in how the conditional not_if works inside a execute resource. I understand that it tells chef not to execute a command if the command returns 0 or true; however, in my code it is apparently still running the command.

    The following code is supposed to create a user (and its password) and a database; however, if the user and database already exist, it should not do anything. The user, database and password are defined in the attributes. The following is the code I have:

    execute "create-user" do
    
            code = <<-EOH
            psql -U postgres -c "select * from pg_user where usename='#{node[:user]}'" | grep -c #{node[:user]}
            EOH
            user "postgres"
            command "createuser -s #{node[:user]}"
            not_if code
    end
    
    
    execute "set-user-password" do
        user "postgres"
        command  "psql -U postgres -d template1 -c \"ALTER USER #{node[:user]} WITH PASSWORD '#{node[:password]}';\""
    end
    
    
    execute "create-database" do
        exists = <<-EOH
        psql -U postgres -c "select * from pg_database WHERE datname='#{node[:database]}'" | grep -c #{node[:database]}}
        EOH
        user "postgres"
        command "createdb #{node[:database]}"
       not_if exists
    
    end
    

    Chef gives me the following error:

    Error executing action run on resource 'execute[create-user]'

    ...

    [2013-01-25T12:24:51-08:00] FATAL: Mixlib::ShellOut::ShellCommandFailed: execute[create-user] (postgresql::initialize line 16) had an error: Mixlib::ShellOut::ShellCommandFailed: Expected process to exit with [0], but received '1'

    STDERR: createuser: creation of new role failed: ERROR: role "user" already exists

    To me it seems that it should work;however, it still running the execute. Am I missing something?

    Thank you

  • Admin
    Admin about 11 years
    Yeah you are right, I had a typo when I copied the code here. Thank you