alexharv074.github.io

My blog

View on GitHub
2 September 2018

Pretty-printing Puppet data

by Alex Harvey

Sometimes it is useful to be able to pretty-print Puppet data when debugging. It would be great if there was native support for this, e.g. a built-in function pp() would be nice.

Until then, I found a useful Gist by Github user Cinderhaze a.k.a. Daryl, which is the basis of this method.

Sample code

Consider the following snippet:

# data.pp
$data = {
  "test.ltd" => {
    "ensure" => "present",
    "zone_contact" => "contact.test.ltd",
    "zone_ns"     => ["ns0.test.ltd", "ns1.test.ltd"],
    "zone_serial" => "2018010101",
    "zone_ttl"    => "767200",
    "zone_origin" => "test.ltd",
    "hash_data" => {
      "newyork" => {"owner" => "11.22.33.44"},
      "tokyo"   => {"owner" => "22.33.44.55"},
      "london"  => {"owner" => "33.44.55.66"},
    }
  }
}

notice($data)

If I apply, the output is unreadable:

$ puppet apply data.pp
Notice: Scope(Class[main]): {test.ltd => {ensure => present, zone_contact => contact.test.ltd, zone_ns => [ns0.test.ltd, ns1.test.ltd], zone_serial => 2018010101, zone_ttl => 767200, zone_origin => test.ltd, hash_data => {newyork => {owner => 11.22.33.44}, tokyo => {owner => 22.33.44.55}, london => {owner => 33.44.55.66}}}}
Notice: Compiled catalog for alexs-macbook-pro.local in environment production in 0.02 seconds
Notice: Applied catalog in 0.01 seconds

Pretty-printing

Using the idea suggested by Cinderhaze:

# data.pp
$data = {
  "test.ltd" => {
    "ensure" => "present",
    "zone_contact" => "contact.test.ltd",
    "zone_ns"     => ["ns0.test.ltd", "ns1.test.ltd"],
    "zone_serial" => "2018010101",
    "zone_ttl"    => "767200",
    "zone_origin" => "test.ltd",
    "hash_data" => {
      "newyork" => {"owner" => "11.22.33.44"},
      "tokyo"   => {"owner" => "22.33.44.55"},
      "london"  => {"owner" => "33.44.55.66"},
    }
  }
}

$content = inline_template("
  <%- require 'json' -%>
  <%= JSON.pretty_generate(@data) %>
  ")

I now get nice readable JSON-formatted output:

$ puppet apply data.pp
Notice: Scope(Class[main]):
  {
  "test.ltd": {
    "ensure": "present",
    "zone_contact": "contact.test.ltd",
    "zone_ns": [
      "ns0.test.ltd",
      "ns1.test.ltd"
    ],
    "zone_serial": "2018010101",
    "zone_ttl": "767200",
    "zone_origin": "test.ltd",
    "hash_data": {
      "newyork": {
        "owner": "11.22.33.44"
      },
      "tokyo": {
        "owner": "22.33.44.55"
      },
      "london": {
        "owner": "33.44.55.66"
      }
    }
  }
}

Notice: Compiled catalog for alexs-macbook-pro.local in environment production in 0.04 seconds
Notice: Applied catalog in 0.01 seconds

Using awesome-print instead

Or we could use the Ruby awesome_print library:

$data = {
  "test.ltd" => {
    "ensure" => "present",
    "zone_contact" => "contact.test.ltd",
    "zone_ns"     => ["ns0.test.ltd", "ns1.test.ltd"],
    "zone_serial" => "2018010101",
    "zone_ttl"    => "767200",
    "zone_origin" => "test.ltd",
    "hash_data" => {
      "newyork" => {"owner" => "11.22.33.44"},
      "tokyo"   => {"owner" => "22.33.44.55"},
      "london"  => {"owner" => "33.44.55.66"}
    }
  }
}

$content = inline_template("
  <%- require 'awesome_print' -%>
  <%= ap(@data) %>
  ")
notice($content)

And get:

$ puppet apply data.pp
{
    "test.ltd" => {
              "ensure" => "present",
        "zone_contact" => "contact.test.ltd",
             "zone_ns" => [
            [0] "ns0.test.ltd",
            [1] "ns1.test.ltd"
        ],
         "zone_serial" => "2018010101",
            "zone_ttl" => "767200",
         "zone_origin" => "test.ltd",
           "hash_data" => {
            "newyork" => {
                "owner" => "11.22.33.44"
            },
              "tokyo" => {
                "owner" => "22.33.44.55"
            },
             "london" => {
                "owner" => "33.44.55.66"
            }
        }
    }
}
Notice: Scope(Class[main]):
  {"test.ltd"=>{"ensure"=>"present", "zone_contact"=>"contact.test.ltd", "zone_ns"=>["ns0.test.ltd", "ns1.test.ltd"], "zone_serial"=>"2018010101", "zone_ttl"=>"767200", "zone_origin"=>"test.ltd", "hash_data"=>{"newyork"=>{"owner"=>"11.22.33.44"}, "tokyo"=>{"owner"=>"22.33.44.55"}, "london"=>{"owner"=>"33.44.55.66"}}}}

Notice: Compiled catalog for alexs-macbook-pro.local in environment production in 0.08 seconds
Notice: Applied catalog in 0.01 seconds
tags: puppet