De onde vem o ambiente do Puppet?

2

Autoformação em puppet e escreveu o seguinte manifesto:

class bratch::test {

  file { '/var/cache/tempFile':
    owner  => 'root',
    group  => 'root',
    mode   => '0644',
    source => "puppet://${puppetserver}/modules/bratch/tempFile"
  }

  exec { "create_file":
    command => "/bin/echo boop >> /tmp/outputFile",
  }

Funciona como eu esperava, mas não pensava na linha exec até depois do fato.

Se puppet entendeu o redirecionamento de saída, isso significa que invoca um shell? Se sim, de onde vem o ambiente? Ele inicializa o ambiente a cada vez ou herda diretamente do agente fantoche?

    
por Bratchley 22.12.2014 / 17:11

1 resposta

1

A documentação é um pouco confusa neste ponto:

Providers

posix

Executes external binaries directly, without passing through a shell or performing any interpolation. This is a safer and more predictable way to execute most commands, but prevents the use of globbing and shell built-ins (including control logic like “for” and “if” statements).

Default for feature == posix.

shell

Passes the provided command through /bin/sh; only available on POSIX systems. This allows the use of shell globbing and built-ins, and does not require that the path to a command be fully-qualified. Although this can be more convenient than the posix provider, it also means that you need to be more careful with escaping; as ever, with great power comes etc. etc.

This provider closely resembles the behavior of the exec type in Puppet 0.25.x.

Portanto, se você usar o provedor shell , poderá usar o redirecionamento, mas o padrão é posix , que é execução direta, portanto, a menos que você tenha especificado shell , o que você não fez .. .

Em ambos os casos, a documentação não diz muito sobre o ambiente. É preciso examinar o código :

begin
  # Do our chdir
  Dir.chdir(dir) do
    environment = {}

    environment[:PATH] = resource[:path].join(File::PATH_SEPARATOR) if resource[:path]

Parece que está definido para vazio e preenchido com as configurações que fornecemos usando o campo environment e, portanto, é reinicializado a cada vez.

No entanto, se seguirmos as migalhas de pão, chegaremos à função chamar que faz a execução:

      output = Puppet::Util::Execution.execute(command, :failonfail => false, :combine => true,
                              :uid => resource[:user], :gid => resource[:group],
                              :override_locale => false,
                              :custom_environment => environment)

Execution.execute chama execute_posix , que por sua vez, faz :

  command = [command].flatten
  ...
    options[:custom_environment] ||= {}
    Puppet::Util.withenv(options[:custom_environment]) do
      Kernel.exec(*command)

Eu não sei Ruby, eu diria que a menos que você especifique um comando e seus argumentos como uma matriz explicitamente, e apenas forneça uma string como "/bin/echo boop >> /tmp/outputFile" , então a linha de comando é passada como é para Kernel.exec , para o qual:

the string is taken as a command line that is subject to shell expansion before being executed.

É por isso que você pode usar o redirecionamento sem definir shell como o provedor. Além disso, olhando para withenv , o conjunto de conjuntos environment acima é simplesmente usado como um conjunto de substituições. Se o campo environment não for especificado, nada será sobrescrito. Portanto, o ambiente deve ser herdado do Puppet. Agora que ambiente o Puppet tem, não tenho certeza, mas se for executado como um serviço em um sistema Upstart-as-init como o Ubuntu, então pelo menos TERM e PATH estão disponíveis.

    
por 26.12.2014 / 12:52

Tags