Reputation: 439
I am trying to create a chef recipe for my Amazon OpsWorks stack. I'd like to pass custom JSON data into the stack, and have the recipe create an .ini file for use with PHP's parse_ini_file() command.
Currently, I can create a flat .ini file with the following:
{
"settings_ini": {
"quantity": 1,
"width": 10,
"height": 20
}
}
quantity = 1
width = 10
height = 20
template "/my/path/here/settings.ini" do
owner "www_data"
group "www_data"
mode "0644"
source "settings.ini.erb"
variables({
:settings_ini => node[:settings_ini]
})
end
<% @settings_ini.each do |name, value| -%>
<%= name %> = <%= value %>
<% end -%>
I'd like to change my JSON data to be this:
{
"settings_ini": {
"quantity": 1,
"attributes": {
"width": 10,
"height": 20
}
}
}
And I want my resulting settings.ini file to be this:
quantity = 1
[attributes]
width = 10
height = 20
Or, it could also be this:
quantity = 1
[attributes]width = 10
[attributes]height = 20
I need help modifying my settings.ini.erb template file to use the nested JSON data correctly.
Upvotes: 0
Views: 1638
Reputation: 2566
You could use a recursive function.
Stick this into libraries/hash_to_ini.rb
:
def hash_to_ini(hash, lines = [])
hash.each do |name, value|
unless value.is_a? Hash
lines << "#{name} = #{value}"
else
lines << "[#{name}]"
lines = hash_to_ini(value, lines)
end
end
return lines
end
Then in your template:
<% hash_to_ini(@settings_ini).each do |line| -%>
<%= line %>
<% end -%>
Upvotes: 1
Reputation: 37640
Why not just a second each
loop?
<% @settings_ini.each do |section, data| -%>
[<%= section %>]
<% data.each do |name, value| -%>
<%= name %> = <%= value %>
<% end -%>
<% end -%>
This code is untested.. but I guess it should work.
You could also add some safety like done e.g. here and here
Upvotes: 0