def test_disabling_spec_validation(self): body = file(self.NOT_VALID_SPEC).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() self.assertEqual(len(api_calls), 0) parser = OpenAPI(response, no_validation=True) parser.parse() api_calls = parser.get_api_calls() self.assertEqual(len(api_calls), 1) api_call = api_calls[0] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = [] e_headers = Headers([('Content-Type', 'application/json')]) e_body = '{"pet": {"age": 42}}' self.assertEqual(api_call.get_method(), 'POST') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEqual(api_call.get_data(), e_body)
def _extract_api_calls_from_response(self, spec_url, http_response): """ Try to parse an API specification from an HTTP response. Send all the newly found fuzzable requests to the core after adding any authentication data that might have been configured. :parm spec_url: A URL to API specification :param http_response: An HTTP response :return: None """ if not OpenAPI.can_parse(http_response): return om.out.debug('OpenAPI parser is about to parse %s' % spec_url) parser = OpenAPI(http_response, self._no_spec_validation, self._discover_fuzzable_headers, self._discover_fuzzable_url_parts) parser.parse() self._report_to_kb_if_needed(http_response, parser) self._send_spec_to_core(spec_url) om.out.debug('OpenAPI parser identified %s API calls' % len(parser.get_api_calls())) for api_call in parser.get_api_calls(): if not self._is_target_domain(api_call): continue api_call = self._set_authentication_data(api_call) self.output_queue.put(api_call)
def test_disabling_spec_validation(self): body = file(self.NOT_VALID_SPEC).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() self.assertEqual(len(api_calls), 0) parser = OpenAPI(response, no_validation=True) parser.parse() api_calls = parser.get_api_calls() self.assertEqual(len(api_calls), 1) api_call = api_calls[0] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = [] e_headers = Headers([('Content-Type', 'application/json')]) e_body = '{"pet": {"age": 42}}' self.assertEqual(api_call.get_method(), 'POST') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEqual(api_call.get_data(), e_body)
def test_issue_210(self): body = file(self.ISSUE_210_API_YAML).read() headers = Headers({'Content-Type': 'application/yaml'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.yaml'), URL('http://moth/swagger.yaml'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() expected_api_calls = 19 self.assertEqual(expected_api_calls, len(api_calls)) first_api_call = api_calls[0] uri = first_api_call.get_uri().url_string expected_uri = 'https://api.domain.com/domain/tokens' self.assertEqual(expected_uri, uri)
def test_custom_content_type(self): body = file(self.CUSTOM_CONTENT_TYPE).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() api_calls.sort(by_path) self.assertEqual(len(api_calls), 2) # # Assertions on call #1 # api_call = api_calls[0] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = [] e_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) e_post_data_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) e_all_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) self.assertIsInstance(api_call.get_raw_data(), JSONContainer) self.assertEquals(api_call.get_method(), 'PUT') self.assertEquals(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEquals(api_call.get_post_data_headers(), e_post_data_headers) self.assertEquals(api_call.get_all_headers(), e_all_headers) self.assertEquals(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEquals(str(api_call.get_raw_data()), '{"info": {"tag": "7", "name": "John", "id": 42}}') # # Assertions on call #2 # api_call = api_calls[1] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = ['X-Foo-Header'] e_headers = Headers([('Content-Type', 'application/vnd.w3af+json'), ('X-Foo-Header', '42')]) e_post_data_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) e_all_headers = Headers([('Content-Type', 'application/vnd.w3af+json'), ('X-Foo-Header', '42')]) self.assertIsInstance(api_call.get_raw_data(), JSONContainer) self.assertEquals(api_call.get_method(), 'POST') self.assertEquals(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEquals(api_call.get_post_data_headers(), e_post_data_headers) self.assertEquals(api_call.get_all_headers(), e_all_headers) self.assertEquals(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEquals(str(api_call.get_raw_data()), '{"info": {"tag": "7", "name": "John"}}')
def test_custom_content_type(self): body = file(self.CUSTOM_CONTENT_TYPE).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() api_calls.sort(by_path) self.assertEqual(len(api_calls), 2) # # Assertions on call #1 # api_call = api_calls[0] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = [] e_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) e_post_data_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) e_all_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) self.assertIsInstance(api_call.get_raw_data(), JSONContainer) self.assertEquals(api_call.get_method(), 'PUT') self.assertEquals(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEquals(api_call.get_post_data_headers(), e_post_data_headers) self.assertEquals(api_call.get_all_headers(), e_all_headers) self.assertEquals(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEquals(str(api_call.get_raw_data()), '{"info": {"tag": "7", "name": "John", "id": 42}}') # # Assertions on call #2 # api_call = api_calls[1] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = ['X-Foo-Header'] e_headers = Headers([('Content-Type', 'application/vnd.w3af+json'), ('X-Foo-Header', '42')]) e_post_data_headers = Headers([('Content-Type', 'application/vnd.w3af+json')]) e_all_headers = Headers([('Content-Type', 'application/vnd.w3af+json'), ('X-Foo-Header', '42')]) self.assertIsInstance(api_call.get_raw_data(), JSONContainer) self.assertEquals(api_call.get_method(), 'POST') self.assertEquals(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEquals(api_call.get_post_data_headers(), e_post_data_headers) self.assertEquals(api_call.get_all_headers(), e_all_headers) self.assertEquals(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEquals(str(api_call.get_raw_data()), '{"info": {"tag": "7", "name": "John"}}')
def test_disabling_spec_validation(self): body = file(self.NOT_VALID_SPEC).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) # # By default we don't validate the swagger spec, which allows us to # parse some invalid specs and extract information # parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() self.assertEqual(len(api_calls), 1) api_call = api_calls[0] e_url = 'http://w3af.org/api/pets' e_force_fuzzing_headers = [] e_headers = Headers([('Content-Type', 'application/json')]) e_body = '{"pet": {"age": 42}}' self.assertEqual(api_call.get_method(), 'POST') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) self.assertEqual(api_call.get_data(), e_body) # # With validation enabled the parsing fails because there is a mising # required attribute # parser = OpenAPI(response, validate_swagger_spec=True) parser.parse() api_calls = parser.get_api_calls() self.assertEqual(len(api_calls), 0)
def test_unknown_content_type(self): body = file(self.UNKNOWN_CONTENT_TYPE).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() self.assertEquals(api_calls, [])
def test_unknown_content_type(self): body = file(self.UNKNOWN_CONTENT_TYPE).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() self.assertEquals(api_calls, [])
def test_large_many_endpoints(self): body = file(self.LARGE_MANY_ENDPOINTS).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) # # In some cases with validation enabled (not the default) we find a set # of endpoints: # parser = OpenAPI(response, validate_swagger_spec=True) parser.parse() api_calls = parser.get_api_calls() expected_api_calls = 161 self.assertEqual(expected_api_calls, len(api_calls)) # # And without spec validation there is a different set of endpoints: # parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() expected_api_calls = 165 self.assertEqual(expected_api_calls, len(api_calls)) first_api_call = api_calls[0] uri = first_api_call.get_uri().url_string expected_uri = 'https://target.com/api/Partners/3419/Agreement?performedBy=56' self.assertEqual(expected_uri, uri)
def test_large_many_endpoints(self): body = file(self.LARGE_MANY_ENDPOINTS).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() expected_api_calls = 161 self.assertEqual(expected_api_calls, len(api_calls)) first_api_call = api_calls[0] uri = first_api_call.get_uri().url_string expected_uri = 'https://target.com/api/Partners/3419/Agreement?performedBy=56' self.assertEqual(expected_uri, uri)
def test_missing_license_name(self): body = file(self.MISSING_LICENSE).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() expected_api_calls = 5 self.assertEqual(expected_api_calls, len(api_calls)) first_api_call = api_calls[0] uri = first_api_call.get_uri().url_string expected_uri = 'http://1.2.3.4/api/prod/2.0/employees/3419' self.assertEqual(expected_uri, uri)
def test_fuzing_on_invalid_token_path(self): body = file(self.INVALID_TOKEN_PATH).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() for api_call in api_calls: fake_mutants = create_mutants(api_call, ['']) for mutant in fake_mutants: create_mutants(mutant.get_fuzzable_request(), [''], fuzzable_param_list=[mutant.get_token_name()])
def test_json_pet_store(self): # http://petstore.swagger.io/v2/swagger.json body = file(self.SWAGGER_JSON).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() json_headers = Headers([('Content-Type', 'application/json')]) multipart_headers = Headers([('Content-Type', 'multipart/form-data')]) url_encoded_headers = Headers([('Content-Type', 'application/x-www-form-urlencoded')]) json_api_headers = Headers([('api_key', 'FrAmE30.'), ('Content-Type', 'application/json')]) url_root = 'http://petstore.swagger.io/v2' expected_body_1 = ('{"body": {"category": {"id": 42, "name": "John"},' ' "status": "available", "name": "doggie",' ' "tags": [{"id": 42, "name": "John"}],' ' "photoUrls": ["56"], "id": 42}}') expected_body_2 = ( '{"body": {"username": "******", "firstName": "John",' ' "lastName": "Smith", "userStatus": 42,' ' "email": "*****@*****.**", "phone": "55550178",' ' "password": "******", "id": 42}}') expected_body_3 = ( '{"body": [{"username": "******", "firstName": "John",' ' "lastName": "Smith", "userStatus": 42,' ' "email": "*****@*****.**", "phone": "55550178",' ' "password": "******", "id": 42}]}') expected_body_4 = ( '{"body": {"status": "placed",' ' "shipDate": "2017-06-30T23:59:45",' ' "complete": false, "petId": 42, "id": 42, "quantity": 42}}') e_api_calls = [ ('GET', '/pet/findByStatus?status=available', json_headers, ''), ('POST', '/pet/42/uploadImage', multipart_headers, ''), ('POST', '/pet/42', url_encoded_headers, ''), ('POST', '/pet', json_headers, expected_body_1), ('GET', '/pet/42', json_headers, ''), ('GET', '/pet/42', json_api_headers, ''), ('GET', '/pet/findByTags?tags=56', json_headers, ''), ('PUT', '/pet', json_headers, expected_body_1), ('PUT', '/user/John8212', json_headers, expected_body_2), ('POST', '/user/createWithList', json_headers, expected_body_3), ('POST', '/user', json_headers, expected_body_2), ('GET', '/user/John8212', json_headers, ''), ('GET', '/user/login?username=John8212&password=FrAmE30.', json_headers, ''), ('GET', '/user/logout', Headers(), ''), ('POST', '/user/createWithArray', json_headers, expected_body_3), ('GET', '/store/order/2', json_headers, ''), ('GET', '/store/inventory', json_headers, ''), ('GET', '/store/inventory', json_api_headers, ''), ('POST', '/store/order', json_headers, expected_body_4), ] self.assertEqual(21, len(api_calls)) for api_call in api_calls: method = api_call.get_method() headers = api_call.get_headers() data = api_call.get_data() uri = api_call.get_uri().url_string uri = uri.replace(url_root, '') data = (method, uri, headers, data) self.assertIn(data, e_api_calls)
def test_real_api_yaml(self): body = file(self.REAL_API_YAML).read() headers = Headers({'Content-Type': 'application/yaml'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.yaml'), URL('http://moth/swagger.yaml'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() e_api_calls = [ ('GET', u'https://w3af.org/bankid/tokens/4271a25e-7211-4306-b527-46196eb2af28', Headers([(u'Content-Type', u'application/json')]), ''), ('POST', u'https://w3af.org/bankid/tokens', Headers([(u'Content-Type', u'application/json')]), '{"body": null}'), ('POST', u'https://w3af.org/bankid/tokens', Headers([(u'Content-Type', u'application/json'), (u'Authorization', u'FrAmE30.')]), '{"body": {"orderRef": "e475f288-4e9b-43ea-966c-d3912e7a25b2"}}'), ('POST', u'https://w3af.org/bankid/orders', Headers([(u'Content-Type', u'application/json')]), '{"body": null}'), ('POST', u'https://w3af.org/bankid/orders', Headers([(u'Content-Type', u'application/json')]), '{"body": {"pid": "191212121212"}}'), ('GET', u'https://w3af.org/persons/3419/partners', Headers([(u'Content-Type', u'application/json')]), ''), ('GET', u'https://w3af.org/persons/3419/partners', Headers([(u'Authorization', u'FrAmE30.'), (u'Content-Type', u'application/json')]), ''), ('GET', u'https://w3af.org/persons/3419/partners/3419', Headers([(u'Content-Type', u'application/json')]), ''), ('GET', u'https://w3af.org/persons/3419/partners/3419', Headers([(u'Authorization', u'FrAmE30.'), (u'Content-Type', u'application/json')]), ''), ('GET', u'https://w3af.org/persons/3419', Headers([(u'Content-Type', u'application/json')]), ''), ('GET', u'https://w3af.org/persons/3419', Headers([(u'Authorization', u'FrAmE30.'), (u'Content-Type', u'application/json')]), ''), ('POST', u'https://w3af.org/persons/3419/partners', Headers([(u'Content-Type', u'application/json')]), '{"body": null}'), ('POST', u'https://w3af.org/persons/3419/partners', Headers([(u'Content-Type', u'application/json'), (u'Authorization', u'FrAmE30.')]), '{"body": {"partner": "19101010****", "termsAccepted": false}}'), ('PATCH', u'https://w3af.org/persons/3419', Headers([(u'Content-Type', u'application/json')]), '{"body": null}'), ('PATCH', u'https://w3af.org/persons/3419', Headers([(u'Content-Type', u'application/json'), (u'Authorization', u'FrAmE30.')]), '{"body": {"termsAccepted": false}}'), ('PUT', u'https://w3af.org/persons/3419/partners/3419', Headers([(u'Content-Type', u'application/json')]), '{"body": null}'), ('PUT', u'https://w3af.org/persons/3419/partners/3419', Headers([(u'Content-Type', u'application/json'), (u'Authorization', u'FrAmE30.')]), '{"body": {"partner": "19101010****", "termsAccepted": false}}'), ('POST', u'https://w3af.org/events', Headers([(u'Content-Type', u'application/json')]), '{"body": null}'), ('POST', u'https://w3af.org/events', Headers([(u'Content-Type', u'application/json'), (u'Authorization', u'FrAmE30.')]), '{"body": {"event": "start doktor24"}}') ] self.assertEqual(19, len(api_calls)) for api_call in api_calls: method = api_call.get_method() headers = api_call.get_headers() data = api_call.get_data() uri = api_call.get_uri().url_string _tuple = (method, uri, headers, data) self.assertIn(_tuple, e_api_calls)
def test_disabling_headers_discovery(self): body = file(self.MULTIPLE_PATHS_AND_HEADERS).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) self.assertTrue(OpenAPI.can_parse(response)) parser = OpenAPI(response, discover_fuzzable_headers=False) parser.parse() api_calls = parser.get_api_calls() api_calls.sort(by_path) self.assertEqual(len(api_calls), 4) e_force_fuzzing_headers = [] # # Assertions on call #1 # api_call = api_calls[0] e_url = 'http://w3af.org/api/cats' e_headers = Headers([('X-Awesome-Header', '2018'), ('X-Foo-Header', 'foo'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) # # Assertions on call #2 # api_call = api_calls[1] e_url = 'http://w3af.org/api/cats?limit=42' e_headers = Headers([('X-Awesome-Header', '2018'), ('X-Foo-Header', 'foo'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) # # Assertions on call #3 # api_call = api_calls[2] e_url = 'http://w3af.org/api/pets' e_headers = Headers([('X-Foo-Header', '42'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) # # Assertions on call #4 # api_call = api_calls[3] e_url = 'http://w3af.org/api/pets' e_headers = Headers([('X-Bar-Header', '56'), ('X-Foo-Header', '42'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers)
from w3af.core.data.parsers.doc.open_api import OpenAPI from w3af.core.data.url.HTTPResponse import HTTPResponse spec_filename = sys.argv[1] _, extension = os.path.splitext(spec_filename) body = file(spec_filename).read() headers = Headers({'Content-Type': 'application/%s' % extension}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.%s' % extension), URL('http://moth/swagger.%s' % extension), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() for api_call in api_calls: method = api_call.get_method() headers = api_call.get_headers() data = api_call.get_data() uri = api_call.get_uri().url_string data = (method, uri, headers, data) pprint.pprint(data)
def test_json_pet_store(self): # http://petstore.swagger.io/v2/swagger.json body = file(self.SWAGGER_JSON).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response) parser.parse() api_calls = parser.get_api_calls() json_headers = Headers([('Content-Type', 'application/json')]) multipart_headers = Headers([('Content-Type', 'multipart/form-data')]) url_encoded_headers = Headers([('Content-Type', 'application/x-www-form-urlencoded')]) json_api_headers = Headers([('api_key', 'FrAmE30.'), ('Content-Type', 'application/json')]) url_root = 'http://petstore.swagger.io/v2' expected_body_1 = ('{"body": {"category": {"id": 42, "name": "John"},' ' "status": "available", "name": "John",' ' "tags": [{"id": 42, "name": "John"}],' ' "photoUrls": ["56"], "id": 42}}') expected_body_2 = ('{"body": {"username": "******", "firstName": "John",' ' "lastName": "Smith", "userStatus": 42,' ' "email": "*****@*****.**", "phone": "55550178",' ' "password": "******", "id": 42}}') expected_body_3 = ('{"body": [{"username": "******", "firstName": "John",' ' "lastName": "Smith", "userStatus": 42,' ' "email": "*****@*****.**", "phone": "55550178",' ' "password": "******", "id": 42}]}') expected_body_4 = ('{"body": {"status": "placed",' ' "shipDate": "2017-06-30T23:59:45",' ' "complete": true, "petId": 42, "id": 42, "quantity": 42}}') e_api_calls = [ ('GET', '/pet/findByStatus?status=available', json_headers, ''), ('POST', '/pet/42/uploadImage', multipart_headers, ''), ('POST', '/pet/42', url_encoded_headers, ''), ('POST', '/pet', json_headers, expected_body_1), ('GET', '/pet/42', json_headers, ''), ('GET', '/pet/42', json_api_headers, ''), ('GET', '/pet/findByTags?tags=56', json_headers, ''), ('PUT', '/pet', json_headers, expected_body_1), ('PUT', '/user/John8212', json_headers, expected_body_2), ('POST', '/user/createWithList', json_headers, expected_body_3), ('POST', '/user', json_headers, expected_body_2), ('GET', '/user/John8212', json_headers, ''), ('GET', '/user/login?username=John8212&password=FrAmE30.', json_headers, ''), ('GET', '/user/logout', Headers(), ''), ('POST', '/user/createWithArray', json_headers, expected_body_3), ('GET', '/store/order/2', json_headers, ''), ('GET', '/store/inventory', json_headers, ''), ('GET', '/store/inventory', json_api_headers, ''), ('POST', '/store/order', json_headers, expected_body_4), ] for api_call in api_calls: method = api_call.get_method() headers = api_call.get_headers() data = api_call.get_data() uri = api_call.get_uri().url_string uri = uri.replace(url_root, '') data = (method, uri, headers, data) self.assertIn(data, e_api_calls)
def test_disabling_headers_discovery(self): body = file(self.MULTIPLE_PATHS_AND_HEADERS).read() headers = Headers({'Content-Type': 'application/json'}.items()) response = HTTPResponse(200, body, headers, URL('http://moth/swagger.json'), URL('http://moth/swagger.json'), _id=1) parser = OpenAPI(response, discover_fuzzable_headers=False) parser.parse() api_calls = parser.get_api_calls() api_calls.sort(by_path) self.assertEqual(len(api_calls), 4) e_force_fuzzing_headers = [] # # Assertions on call #1 # api_call = api_calls[0] e_url = 'http://w3af.org/api/cats' e_headers = Headers([ ('X-Awesome-Header', '2018'), ('X-Foo-Header', 'foo'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) # # Assertions on call #2 # api_call = api_calls[1] e_url = 'http://w3af.org/api/cats?limit=42' e_headers = Headers([ ('X-Awesome-Header', '2018'), ('X-Foo-Header', 'foo'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) # # Assertions on call #3 # api_call = api_calls[2] e_url = 'http://w3af.org/api/pets' e_headers = Headers([ ('X-Foo-Header', '42'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers) # # Assertions on call #4 # api_call = api_calls[3] e_url = 'http://w3af.org/api/pets' e_headers = Headers([ ('X-Bar-Header', '56'), ('X-Foo-Header', '42'), ('Content-Type', 'application/json')]) self.assertEqual(api_call.get_method(), 'GET') self.assertEqual(api_call.get_uri().url_string, e_url) self.assertEquals(api_call.get_headers(), e_headers) self.assertEqual(api_call.get_force_fuzzing_headers(), e_force_fuzzing_headers)