From what I understand, puppetd runs as root. As root, I launch

 puppetd --onetime --no-daemonize --verbose

So I don't understand why this doesn't work:

exec { "useradd -m testuser":
       path => "/bin:/usr/bin",

I just get:

...Exec[useradd -m testuser]/returns: change from notrun to 0 failed:useradd -m testuser returned 1 instead of one of [0] at...

If I execute the command directly, it works just fine.

Any ideas?

PS: exec { "touch /root/a.test":} is successful, so it is indeed executing as root.

PS2: I get the exact same problem when executing "apt-get autoremove"

  • What OS is this on? – Tacticus Nov 29 '11 at 12:14
  • It's on Ubuntu 10.04 – chris Nov 30 '11 at 1:09
  • Have you moved useradd? Puppet execs will not inherit the default path values from a host – Tacticus Nov 30 '11 at 3:25

Well in most systems useradd will be in one of the sbin folders rather than /bin or /usr/bin. your path should be "/bin:/usr/bin:/sbin:/usr/sbin",. though this solution is rather horible i would use the user type rather than an exec it will give you much better management of users on a host (checks on pw and existance requires etc)

@user {
    uid => ,
    gid =>,
    password => #hash of password,
    home => ,
    groups => ,

this is a virtual resource and can be added to your host by realize ( User[testuser]) allowing it to be referenced multiple times

it's a nice simple solution

| improve this answer | |
  • The path unfortunately isn't the problem. And regarding the user type, you are right... see above. – chris Nov 29 '11 at 14:45
  • After a lot of investigation it appears that the path was indeed the problem! Thanks! – chris Dec 1 '11 at 7:11

Try running the command with:

exec { "useradd -m testuser":
  path => "/bin:/usr/bin",
  logoutput => true,

And see what it says. It should give you error on the command line now. Also 'on_failure' is another option which only outputs when the command fails. I usually do:

Exec {
  logoutput => on_failure,

As a default so all my commands output something meaningful globally if they fail.

But normally - you would use the 'user' resource instead:

user { "myusername":
  ensure => present,
  managehome => true,

Well documented here alone with other resource types:


| improve this answer | |
  • I can't seem to find the output log. Although it's set as /var/log/puppet/ in puppet.conf, that directory is empty. Am I missing something? – chris Nov 29 '11 at 14:40
  • If you run puppet on the command line you should see it in the report 'puppet agent -t' ... test it works by just using 'echo foo' in another exec resource. – Ken Barber Nov 29 '11 at 16:00
  • -t is not a valid option... By running puppetd --onetime --no-daemonize --verbose --logdest /var/log/puppet/log --debug I get some more info but nothing useful about why useradd is failing. – chris Nov 30 '11 at 0:57

It works but does it return 1 instead of 0 ? Try running echo $? after that useradd command.

You tend to get better error messages by using the built in Puppet types rather than exec like this:

user { "foo":
  ensure => present,
  uid => 1001,
  password => '<some password hash>',
  shell => "/bin/bash",
  home => "/home/foo",
  groups =>  ["foogroup"],
  managehome => true,

Is there any reason you're using exec instead of doing that ?

| improve this answer | |
  • No it doesn't work. The useradd part is actually part of a larger script that syncs users with a sql table. I'd love to do the sync through puppet but I wouldn't know where to start... – chris Nov 29 '11 at 14:44

You need to make sure you have the Ruby Shadow gem in order to work with /etc/shadow

sudo apt-get install libshadow-ruby1.8

or in redhat/fedora

sudo yum install ruby-shadow
| improve this answer | |
  • it is already installed, latest version. – chris Nov 30 '11 at 0:56

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.