Sean Hagen
Sean Hagen

Reputation: 752

Puppet running generate function before any classes?

This is one of the manifests that I'm using to set up a Vagrant box.

class company::setup {
  notice("Running initial base setup steps")

  package {
    ["ruby-dev","libxslt-dev","libxml2-dev","libpq-dev","imagemagick","software-properties-common","python-software-properties","python","g++","make"]: ensure => present
  }

  Class['company::setup::user'] -> Class['company::setup::keygen'] -> Class['company::setup::keyuse']

  class { 'company::setup::user': }
  class { 'company::setup::keygen': }
  class { 'company::setup::keyuse': }
}

class company::setup::user {
  file { 'username-home':
    path => '/home/username',
    ensure => 'directory',
  }

  file { 'username-home-ssh':
    path => '/home/username/.ssh',
    ensure => 'directory',
    require => File['/home/username'],
  }

  user { 'username':
    name => 'username',
    ensure => present,
    password => sha1('shopshop'),
    require => File['/home/username/.ssh'],
  }
}

class company::setup::keygen {
  exec { "ssh_keygen_username":
    path => "/bin:/usr/bin",
    command => "ssh-keygen -t dsa -b 1024 -f /home/username/.ssh/id_dsa -N ''",
  }
}

class company::setup::keyuse {
  ssh_authorized_key { "username-access-key":
    name => 'Username Access Key',
    ensure => present,
    key => generate( "/bin/cat", "/home/username/.ssh/id_dsa.pub"),
  }
}

I've tried several different setups, such as using stages, chaining together the different file, user, and other classes using '->', but the result is always the same:

Error: Failed to execute generator /bin/cat: Execution of '/bin/cat
 /home/username/.ssh/id_dsa.pub' returned 1: /bin/cat: /home/username/
.ssh/id_dsa.pub: No such file or directory at /tmp/vagrant-puppet-3/
manifests/manifests/06-setup.pp:47 on node localhost.vn.vagrantbox.net

After a whole day of trying to get this to work, I'm going to move on to a different section of the manifest I'm putting together and hope somemone can help me out with this problem.

Any idea how I can delay the 'generate' function from running until the id_dsa.pub file has been created?

Upvotes: 3

Views: 1657

Answers (1)

rojs
rojs

Reputation: 648

Basically you can't get there from here using this approach.

Puppet is compiling and putting together all the resources before actually doing anything. Since the id_rsa.pub file won't exist until puppet actually does something, you're stuck in a chicken and egg hole.

The work around is to not use ssh_authorized_key and use exec or file resource instead.

exec {'username-access-key':
  command => 'cat /home/username/.ssh/id_dsa.pub > /home/username.ssh/authorized_keys',
  creates => '/home/username/.ssh/authorized_keys',
  require => Exec["ssh_keygen_username"],
}

or (better since you can set the perms on the file)

file {'/home/username/.ssh/authorized_keys':
  ensure  => file,
  source  => '/home/username/.ssh/id_rsa.pub',
  owner   => 'username'
  group   => 'username',
  mode    => '0600',
  require => Exec["ssh_keygen_username"],
}

Upvotes: 3

Related Questions