Skip to content

Commit 48a5eb8

Browse files
authored
check commands structure with None values (#4451)
1 parent 052dbb2 commit 48a5eb8

File tree

2 files changed

+31
-12
lines changed

2 files changed

+31
-12
lines changed

tools/src/main/python/opengrok_tools/utils/commandsequence.py

Lines changed: 22 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -136,23 +136,34 @@ def check_command_property(command):
136136
w.r.t. individual commands.
137137
:param command: command element
138138
"""
139-
140139
if not isinstance(command, dict):
141140
raise CommandConfigurationException("command '{}' is not a dictionary".format(command))
142141

143-
command_value = command.get(COMMAND_PROPERTY)
144-
call_value = command.get(CALL_PROPERTY)
145-
if command_value is None and call_value is None:
146-
raise CommandConfigurationException(f"command dictionary has unknown key: {command}")
142+
for key in command.keys():
143+
if key not in [COMMAND_PROPERTY, CALL_PROPERTY]:
144+
raise CommandConfigurationException(f"command dictionary has unknown key: {command}")
147145

148-
if command_value and not isinstance(command_value, dict):
149-
raise CommandConfigurationException("command value not a dictionary: {}".
150-
format(command_value))
151-
if call_value:
152-
check_call_config(call_value)
146+
# There is difference between dictionary key that is missing and dictionary key that has None value.
147+
# The get() function cannot distinguish between these two. Given the latter is sometimes a result
148+
# of YAML parsing, use the below code to catch it.
149+
try:
150+
command_value = command[COMMAND_PROPERTY]
151+
if command_value is None:
152+
raise CommandConfigurationException("empty command value")
153153

154-
if command_value:
155154
check_command_config(command_value)
155+
return
156+
except KeyError:
157+
pass
158+
159+
try:
160+
call_value = command[CALL_PROPERTY]
161+
if call_value is None:
162+
raise CommandConfigurationException("empty call value")
163+
164+
check_call_config(call_value)
165+
except KeyError:
166+
pass
156167

157168

158169
class ApiCall:

tools/src/test/python/test_command_sequence.py

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@
3333

3434
from opengrok_tools.utils.commandsequence import CommandSequence, \
3535
CommandSequenceBase, CommandConfigurationException
36-
from opengrok_tools.utils.patterns import PROJECT_SUBST, CALL_PROPERTY
36+
from opengrok_tools.utils.patterns import PROJECT_SUBST, CALL_PROPERTY, COMMAND_PROPERTY
3737

3838

3939
def test_str():
@@ -74,6 +74,14 @@ def test_invalid_configuration_commands_no_dict2():
7474
assert str(exc_info.value).find("is not a dictionary") != -1
7575

7676

77+
@pytest.mark.parametrize('type', [COMMAND_PROPERTY, CALL_PROPERTY])
78+
def test_invalid_configuration_commands_none_value(type):
79+
with pytest.raises(CommandConfigurationException) as exc_info:
80+
CommandSequence(CommandSequenceBase("foo", [{type: None}]))
81+
82+
assert str(exc_info.value).find("empty") != -1
83+
84+
7785
def test_timeout_propagation():
7886
"""
7987
Make sure the timeouts propagate from CommandSequenceBase to CommandSequence.

0 commit comments

Comments
 (0)