Take the 2-minute tour ×
Server Fault is a question and answer site for system and network administrators. It's 100% free, no registration required.

I'm attempting to insert a block of text into my CA certificate file on CentOS hosts with Puppet. I asked about this before, and it seems CentOS is sorely lacking in certificate management functions...

What I need to do is get a rather large chunk of text representing my CA's certificate (passed through openssl's info command for whatever silly reason) into my /etc/ssl/certs/ca-bundle.crt file and ensure it's always there, even if the host updates its CA file later from repo.

I do not want to manage the ca-bundle file in its entirety with Puppet. This is already being handled by the yum repositories the servers are pointed to.

Difficulty: Puppet doesn't officially have a way to manage chunks of text, only lines, using the file_line resource. Me attempting to be clever, though, thought you could use a newline-escaped "line" of text and manage that.

Well, sort of. It works, in that the text ends up in the file, but the problem is that it keeps getting re-added after each puppet run, like the code can't tell that it already exists.

For detail, the chunk of text looks a lot like this (truncated for obvious reasons :3)

$cacert = "Certificate:\n    Data:\n        Version: 3 (0x2)\n        Serial Number:\n            10:d8:83:91:-redacted-"

The line in my Puppet module looks like this:

class em_cacerts::centos inherits em_cacerts{
    file_line { 'ca-certificate':
            path => '/etc/ssl/certs/ca-bundle.crt',
            line => $cacert,
            #match => "(see below)",
            ensure => present,
    }

I've tried all kinds of shenanigans with the match line (including using an inline_template to set the match regex to the entire contents of the $cacert variable, which works flawlessly in IRB, but not in Puppet) in an attempt to get it to recognize the text block already exists but it keeps getting re-added every time and just stacks up on top of itself..

I'm probably barking up the wrong tree here.. but anyways, that's part of the question.

  • Is there a better way to accomplish this goal?
  • If not, how do I get Puppet to realize the block of text already exists?

Thanks!

share|improve this question

4 Answers 4

up vote 2 down vote accepted

I ended up solving this with an exec line:

class em_cacerts::centos inherits em_cacerts{
        exec { 'cent-ca-certificate':
                command => "/bin/echo '$centcacert' >> '$cabundlepath'",
                onlyif => "test ! `grep (redacted CA name) $cabundlepath`", 
                provider => 'shell',
        }
}

Yeah, it's using exec, which is officially discouraged, but this works reliably and uses absolute basic stuff that any CentOS box will have.

Thanks everyone!

share|improve this answer

Typically I see files managed in their entirety using erb templates. If you won't do that, you could have a script perform a sed command. https://puppetlabs.com/blog/why-puppet-isnt-a-file-management-tool/

share|improve this answer

I think you want the puppet concat module, which builds files from fragments. Or just manage a separate file and have a exec resource sed insert it into the file if not found with grep

share|improve this answer

See also augeas.

http://augeas.net/

It aims to do exactly what you asked for.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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