Skip to content

Commit 4883277

Browse files
authored
Merge pull request #28 from puppetlabs/ensure_get_title_tokens_func_only_gets_resource_titles
(CONT-333) Ensure get_title_tokens func only gets resource titles
2 parents 0d36068 + 121c195 commit 4883277

File tree

2 files changed

+48
-37
lines changed

2 files changed

+48
-37
lines changed

lib/puppet-lint/plugins/check_unsafe_interpolations.rb

Lines changed: 26 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,17 @@
11
PuppetLint.new_check(:check_unsafe_interpolations) do
22
COMMANDS = Array['command', 'onlyif', 'unless']
33
INTERPOLATED_STRINGS = Array[:DQPRE, :DQMID]
4+
USELESS_CHARS = Array[:WHITESPACE, :COMMA]
45
def check
56
# Gather any exec commands' resources into an array
67
exec_resources = resource_indexes.map { |resource|
78
resource_parameters = resource[:param_tokens].map(&:value)
89
resource if resource[:type].value == 'exec' && !(COMMANDS & resource_parameters).empty?
910
}.compact
1011

11-
# Filter the list of titles returned by get_title_tokens for those contained in an exec
12-
exec_title_tokens = get_title_tokens.select { |title|
13-
title if title[:resource_type].value == 'exec'
14-
}.compact
15-
1612
# Iterate over title tokens and raise a warning if any are variables
17-
unless exec_title_tokens.empty?
18-
exec_title_tokens.each do |title|
13+
unless get_exec_titles.empty?
14+
get_exec_titles.each do |title|
1915
check_unsafe_title(title)
2016
end
2117
end
@@ -28,7 +24,7 @@ def check
2824

2925
# Iterate over the tokens in a title and raise a warning if an interpolated variable is found
3026
def check_unsafe_title(title)
31-
title[:tokens].each do |token|
27+
title.each do |token|
3228
notify_warning(token.next_code_token) if interpolated?(token)
3329
end
3430
end
@@ -83,43 +79,36 @@ def parameterised?(token)
8379

8480
# This function is a replacement for puppet_lint's title_tokens function which assumes titles have single quotes
8581
# This function adds a check for titles in double quotes where there could be interpolated variables
86-
def get_title_tokens
82+
def get_exec_titles
8783
result = []
8884
tokens.each_index do |token_idx|
89-
next unless tokens[token_idx].type == :COLON
85+
next unless ['exec'].include?(tokens[token_idx].value)
86+
# We have a resource declaration. Now find the title
9087
tokens_array = []
9188
# Check if title is an array
92-
if tokens[token_idx - 1].type == :RBRACK
93-
array_start_idx = tokens.rindex do |r|
94-
r.type == :LBRACK
95-
end
96-
title_array_tokens = tokens[(array_start_idx + 1)..(token_idx - 2)]
97-
tokens_array.concat(title_array_tokens.select do |token|
98-
{ STRING: true, NAME: true }.include?(token.type)
89+
if tokens[token_idx].next_code_token.next_code_token.type == :LBRACK
90+
# Get the start and end indices of the array of titles
91+
array_start_idx = tokens.rindex { |r| r.type == :LBRACK }
92+
array_end_idx = tokens.rindex { |r| r.type == :RBRACK }
93+
94+
# Grab everything within the array
95+
title_array_tokens = tokens[(array_start_idx + 1)..(array_end_idx - 1)]
96+
tokens_array.concat(title_array_tokens.reject do |token|
97+
USELESS_CHARS.include?(token.type)
9998
end)
100-
result << {
101-
tokens: tokens_array,
102-
resource_type: tokens[array_start_idx].prev_code_token.prev_code_token
103-
}
99+
result << tokens_array
104100
# Check if title is double quotes string
105-
elsif tokens[token_idx - 1].type == :DQPOST
106-
# Find index of the start of the title
107-
title_start_idx = tokens.rindex do |r|
108-
r.type == :DQPRE
109-
end
110-
result << {
111-
# Title is tokens from :DQPRE to the index before :COLON
112-
tokens: tokens[title_start_idx..(token_idx - 1)],
113-
resource_type: tokens[title_start_idx].prev_code_token.prev_code_token
114-
}
101+
elsif tokens[token_idx].next_code_token.next_code_token.type == :DQPRE
102+
# Find the start and end of the title
103+
title_start_idx = tokens.rindex { |r| r.type == :DQPRE }
104+
title_end_idx = tokens.rindex { |r| r.type == :DQPOST }
105+
106+
result << tokens[title_start_idx..title_end_idx]
115107
# Title is in single quotes
116108
else
117-
next_token = tokens[token_idx].next_code_token
118-
tokens_array.concat([tokens[token_idx - 1]]) unless next_token.type == :LBRACE
119-
result << {
120-
tokens: tokens_array,
121-
resource_type: tokens[token_idx - 1].prev_code_token.prev_code_token
122-
}
109+
tokens_array.concat([tokens[token_idx].next_code_token.next_code_token])
110+
111+
result << tokens_array
123112
end
124113
end
125114
result

spec/puppet-lint/plugins/check_unsafe_interpolations_spec.rb

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -160,5 +160,27 @@ class foo {
160160
expect(problems).to have(1).problems
161161
end
162162
end
163+
164+
context 'case statement and an exec' do
165+
let(:code) do
166+
<<-PUPPET
167+
class foo {
168+
case bar {
169+
baz : {
170+
echo qux
171+
}
172+
}
173+
174+
exec { 'foo':
175+
command => "echo bar",
176+
}
177+
}
178+
PUPPET
179+
end
180+
181+
it 'detects zero problems' do
182+
expect(problems).to have(0).problems
183+
end
184+
end
163185
end
164186
end

0 commit comments

Comments
 (0)