Fix control tags fetching logic which was breaking profiles with tags used

Signed-off-by: Nikita Mathur <nikita.mathur@chef.io>
This commit is contained in:
Nikita Mathur 2021-08-31 17:17:24 +05:30
parent 601238ca81
commit ddcb096666
3 changed files with 30 additions and 8 deletions

View file

@ -53,19 +53,24 @@ module Inspec
def control(id, opts = {}, &block)
opts[:skip_only_if_eval] = @skip_only_if_eval
tag_ids = control_tags(&block)
if (controls_list_empty? && tags_list_empty?) || control_exist_in_controls_list?(id) || tag_exist_in_control_tags?(tag_ids)
if (controls_list_empty? && tags_list_empty?) || control_exist_in_controls_list?(id)
register_control(Inspec::Rule.new(id, profile_id, resources_dsl, opts, &block))
elsif !tags_list_empty?
# Inside elsif rule is initialised before registering it because it enables fetching of control tags
inspec_rule = Inspec::Rule.new(id, profile_id, resources_dsl, opts, &block)
tag_ids = control_tags(inspec_rule)
register_control(inspec_rule) if tag_exist_in_control_tags?(tag_ids)
end
end
alias rule control
def control_tags(&block)
tag_source = block.source.split("\n").select { |src| src.split.first.eql?("tag") }
tag_source = tag_source.map { |src| src.sub("tag", "").strip }.map { |src| src.split(",").map { |final_src| final_src.sub(/([^:]*):/, "") } }.flatten
output = tag_source.map { |src| src.sub(/\[|\]/, "") }.map { |src| instance_eval(src) }
output.compact.uniq
def control_tags(inspec_rule)
all_tags = []
inspec_rule.tag.each do |key, value|
value.nil? ? all_tags.push(key) : all_tags.push(value)
end
all_tags.flatten.compact.uniq.map(&:to_s)
rescue
[]
end

View file

@ -1,8 +1,16 @@
control "basic" do
tag "tag1"
tag :special, :special1
tag severity: nil
tag data: "tag2"
tag data_arr: ["tag3", "tag4"]
tag error1: "Line with a line-feed
error"
tag error2: "Line with a comma,error"
tag cci: ['CCI-000366']
tag legacy: []
tag nist: ["AU-9", "AU-9 (3)", "AC-3 (4)", "AC-6 (10)"]
tag ref: "http:example.html:CIS CSC v6.0 #5.1;"
describe(true) { it { should eq true } }
end

View file

@ -258,7 +258,7 @@ Test Summary: 0 successful, 0 failures, 0 skipped
it "executes only specified controls when selecting the controls by using regex on tags" do
inspec("exec " + File.join(profile_path, "control-tags") + " --no-create-lockfile --tags '/\s+/'")
_(stdout).must_include "true is expected to eq true\n"
_(stdout).must_include "Test Summary: 1 successful, 0 failures, 0 skipped\n"
_(stdout).must_include "Test Summary: 2 successful, 0 failures, 0 skipped\n"
_(stderr).must_equal ""
assert_exit_code 0, out
@ -282,6 +282,15 @@ Test Summary: 0 successful, 0 failures, 0 skipped
assert_exit_code 100, out
end
it "executes profile successfully when tags are used with single element array, punctuations and linefeeds" do
inspec("exec " + File.join(profile_path, "control-tags") + " --no-create-lockfile --tags tag1 'Line with a comma,error' CCI-000366")
_(stdout).must_include "true is expected to eq true\n"
_(stdout).must_include "Test Summary: 1 successful, 0 failures, 0 skipped\n"
_(stderr).must_equal ""
assert_exit_code 0, out
end
it "reports whan a profile cannot be loaded" do
inspec("exec " + File.join(profile_path, "raise_outside_control") + " --no-create-lockfile")
_(stdout).must_match(/Profile:[\W]+InSpec Profile \(raise_outside_control\)/)