1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117
|
# frozen_string_literal: true
$LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', '..'))
require 'puppet/file_serving/content'
require 'puppet/file_serving/metadata'
require 'puppet_x/elastic/deep_implode'
require 'puppet_x/elastic/deep_to_i'
require 'puppet_x/elastic/deep_to_s'
require 'puppet_x/elastic/elasticsearch_rest_resource'
Puppet::Type.newtype(:elasticsearch_template) do
extend ElasticsearchRESTResource
desc 'Manages Elasticsearch index templates.'
ensurable
newparam(:name, namevar: true) do
desc 'Template name.'
end
newproperty(:content) do
desc 'Structured content of template.'
validate do |value|
raise Puppet::Error, 'hash expected' unless value.is_a? Hash
end
munge do |value|
# The Elasticsearch API will return default empty values for
# order, aliases, and mappings if they aren't defined in the
# user mapping, so we need to set defaults here to keep the
# `in` and `should` states consistent if the user hasn't
# provided any.
#
# The value is first stringified, then integers are parse out as
# necessary, since the Elasticsearch API enforces some fields to be
# integers.
#
# We also need to fully qualify index settings, since users
# can define those with the index json key absent, but the API
# always fully qualifies them.
{ 'order' => 0, 'aliases' => {}, 'mappings' => {} }.merge(
Puppet_X::Elastic.deep_to_i(
Puppet_X::Elastic.deep_to_s(
value.tap do |val|
if val.key? 'settings'
val['settings']['index'] = {} unless val['settings'].key? 'index'
(val['settings'].keys - ['index']).each do |setting|
new_key = if setting.start_with? 'index.'
setting[6..]
else
setting
end
val['settings']['index'][new_key] = \
val['settings'].delete setting
end
end
end
)
)
)
end
def insync?(value)
Puppet_X::Elastic.deep_implode(value) == \
Puppet_X::Elastic.deep_implode(should)
end
end
newparam(:source) do
desc 'Puppet source to file containing template contents.'
validate do |value|
raise Puppet::Error, 'string expected' unless value.is_a? String
end
end
# rubocop:disable Style/SignalException
validate do
# Ensure that at least one source of template content has been provided
if self[:ensure] == :present
fail Puppet::ParseError, '"content" or "source" required' \
if self[:content].nil? && self[:source].nil?
if !self[:content].nil? && !self[:source].nil?
fail(
Puppet::ParseError,
"'content' and 'source' cannot be simultaneously defined"
)
end
end
# If a source was passed, retrieve the source content from Puppet's
# FileServing indirection and set the content property
unless self[:source].nil?
fail(format('Could not retrieve source %s', self[:source])) unless Puppet::FileServing::Metadata.indirection.find(self[:source])
tmp = if !catalog.nil? \
&& catalog.respond_to?(:environment_instance)
Puppet::FileServing::Content.indirection.find(
self[:source],
environment: catalog.environment_instance
)
else
Puppet::FileServing::Content.indirection.find(self[:source])
end
fail(format('Could not find any content at %s', self[:source])) unless tmp
self[:content] = JSON.parse(tmp.content)
end
end
# rubocop:enable Style/SignalException
end
|