Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix purging of resources #220

Merged
merged 1 commit into from
Apr 9, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
43 changes: 38 additions & 5 deletions lib/puppet/type/splunk_config.rb
Original file line number Diff line number Diff line change
Expand Up @@ -127,29 +127,62 @@ def set_provider_paths
end
end

# Returns an array of contexts we want to consider when looking for
# resources of a particular type to purge
def contexts(type_class)
contexts = ['system/local'] # Always consider the default context
catalog_resources = catalog.resources.select { |r| r.is_a?(type_class) }
catalog_resources.each do |res|
contexts << res[:context]
end
contexts.uniq
end

def purge_splunk_resources(type_class)
contexts(type_class).map do |context|
purge_splunk_resources_in_context(type_class, context)
end.flatten
end

def purge_splunk_resources_in_context(type_class, context)
type_name = type_class.name
purge_resources = []
puppet_resources = []

# Search the catalog for resource types matching the provided class
# type and build an array of puppet resources matching the namevar
# as section/setting
# type and context. Then build an array of puppet resources matching
# the namevar as section/setting
#
catalog_resources = catalog.resources.select { |r| r.is_a?(type_class) }
catalog_resources = catalog.resources.select { |r| r.is_a?(type_class) && r[:context] == context }
Puppet.debug "Found #{catalog_resources.size} #{type_class} resources in context #{context}"
catalog_resources.each do |res|
puppet_resources << res[:section] + '/' + res[:setting]
end

# Search the configured instances of the class type and purge them if
# the instance name (setion/setting) isn't found in puppet_resources
#
Puppet::Type.type(type_name).instances.each do |instance|

# ini_setting's `instances` method will only work if the provider is
# configured with the complete file_path (including `context`).
# Temporarily update it before calling `instances`
#
provider = Puppet::Type.type(type_name).provider(:ini_setting)

save_file_path = provider.file_path
provider.file_path = File.join(save_file_path, context, provider.file_name)
instances = Puppet::Type.type(type_name).instances

# Restore the provider's original file_path
provider.file_path = save_file_path

instances.each do |instance|
next if puppet_resources.include?(instance.name)
purge_resources << Puppet::Type.type(type_name).new(
name: instance.name,
name: "Purge #{context} #{instance.name}",
section: instance[:section],
setting: instance[:setting],
context: context,
ensure: :absent
)
end
Expand Down
44 changes: 44 additions & 0 deletions spec/acceptance/splunk_forwarder_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -42,4 +42,48 @@ class { 'splunk::forwarder':
it { is_expected.to be_running }
end
end
context 'purging' do
context 'purge_outputs => false' do
it 'works idempotently with no errors' do
pp = <<-eos
class { 'splunk::params':
}
class { 'splunk::forwarder':
splunkd_port => 8090,
purge_outputs => false,
}
eos

# run it twice and test for idempotency
apply_manifest(pp, catch_failures: true)
apply_manifest(pp, catch_changes: true)
end

describe file('/opt/splunkforwarder/etc/system/local/outputs.conf') do
it { is_expected.to be_file }
its(:content) { is_expected.to match %r{^sslPassword} }
end
end
context 'purge_outputs => true' do
it 'works idempotently with no errors' do
pp = <<-eos
class { 'splunk::params':
}
class { 'splunk::forwarder':
splunkd_port => 8090,
purge_outputs => true,
}
eos

# run it twice and test for idempotency
apply_manifest(pp, catch_failures: true)
apply_manifest(pp, catch_changes: true)
end

describe file('/opt/splunkforwarder/etc/system/local/outputs.conf') do
it { is_expected.to be_file }
its(:content) { is_expected.not_to match %r{^sslPassword} }
end
end
end
end