Skip to content

Commit

Permalink
Consider Updating Bravado_core to 5.15.0 to fix Open API Bugs #18218
Browse files Browse the repository at this point in the history
  • Loading branch information
andresriancho committed Nov 25, 2019
1 parent ac83ce7 commit 73ef285
Show file tree
Hide file tree
Showing 3 changed files with 29 additions and 8 deletions.
2 changes: 1 addition & 1 deletion w3af/core/controllers/dependency_check/requirements.py
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@
PIPDependency('diff_match_patch', 'diff-match-patch', '20121119'),

# OpenAPI documentation parser
PIPDependency('bravado_core', 'bravado-core', '5.12.1'),
PIPDependency('bravado_core', 'bravado-core', '5.15.0'),

# Fast compression library
PIPDependency('lz4', 'lz4', '1.1.0'),
Expand Down
20 changes: 16 additions & 4 deletions w3af/core/data/parsers/doc/open_api/parameters.py
Original file line number Diff line number Diff line change
Expand Up @@ -475,7 +475,7 @@ def _get_object_definition(self, param_spec):
"""
return self._get_object_definition_impl(param_spec)

def _merge_all_parts(self, all_parts):
def _merge_all_parts(self, all_parts, already_defined_objects=None):
"""
https://swagger.io/docs/specification/data-models/oneof-anyof-allof-not/
Expand All @@ -494,12 +494,22 @@ def _merge_all_parts(self, all_parts):
:param all_parts: A list containing the `allOf`
:return: The definition as shown above
"""
already_defined_objects = already_defined_objects or []

merged = {'required': [],
'properties': {},
'type': 'object'}

for part in all_parts:
object_definition = self._get_object_definition_impl(part)

# The following lines prevent infinite recursion when there are model
# definition loops like the one seen in `nested_loop_model.json`
if part in already_defined_objects:
continue

already_defined_objects.append(part)

object_definition = self._get_object_definition_impl(part, already_defined_objects)

if 'required' in object_definition:
for required in object_definition['required']:
Expand All @@ -511,18 +521,20 @@ def _merge_all_parts(self, all_parts):

return merged

def _get_object_definition_impl(self, param_spec):
def _get_object_definition_impl(self, param_spec, already_defined_objects=None):
"""
:param param_spec: The parameter specification instance
:return: The object definition which needs to be created
"""
already_defined_objects = already_defined_objects or []

if '$ref' in param_spec:
ref = {'$ref': param_spec['$ref']}
param_spec = self.spec.deref(ref)

if 'allOf' in param_spec:
all_parts = param_spec['allOf']
param_spec = self._merge_all_parts(all_parts)
param_spec = self._merge_all_parts(all_parts, already_defined_objects)

if 'schema' in param_spec:
if '$ref' in param_spec['schema']:
Expand Down
15 changes: 12 additions & 3 deletions w3af/core/data/parsers/doc/open_api/tests/test_specification.py
Original file line number Diff line number Diff line change
Expand Up @@ -467,9 +467,18 @@ def test_model_param_nested_loop_in_json(self):

data = [d for d in handler.get_api_information()]

# `_parse_spec_from_dict` raises max recursion while trying to resolve
# references for this (broken) model.
self.assertEqual(len(data), 0)
self.assertEqual(len(data), 1, data)

#
# Assertions on call #1
#
spec, api_resource_name, resource, operation_name, operation, parameters = data[0]

self.assertEqual(api_resource_name, 'pets')
self.assertEqual(operation_name, 'findPets')
self.assertEqual(operation.consumes, [u'application/json'])
self.assertEqual(operation.produces, [u'application/json', u'application/xml', u'text/xml', u'text/html'])
self.assertEqual(operation.path_name, '/pets')

def test_dereferenced_pet_store(self):
# See: dereferenced_pet_store.json , which was generated using
Expand Down

0 comments on commit 73ef285

Please sign in to comment.