def test_empty_data(self): method = "get" url = "http://example.com/api/v2/list" data = "" headers = json.loads('{}') curlcommand = CurlCommand(url, method, data, headers) self.assertEqual(curlcommand.get(), "curl -XGET -H \"Content-type: application/json\" " "http://example.com/api/v2/list")
def test_get_method(self): method = "get" url = "http://example.com/api/v2/test" data = "{\"id\": 1, \"name\": \"Foo\"}" headers = json.loads('{}') curlcommand = CurlCommand(url, method, data, headers) self.assertEqual(curlcommand.get(), "curl -XGET -H \"Content-type: application/json\" -d " "'{\"id\": 1, \"name\": \"Foo\"}' http://example.com/api/v2/test")
def test_post_method(self): method = "pOsT" url = "http://example.com/api/post" data = "{\"id\": 2, \"name\": \"Bar\"}" headers = u'{}' curlcommand = CurlCommand(url, method, data, headers) self.assertEquals( curlcommand.get(), "curl -XPOST -H \"Content-type: application/json\" -d " "'{\"id\": 2, \"name\": \"Bar\"}' http://example.com/api/post")
def start(self): print('Fetching open API from: ' + self.url) # Try to find the protocol, host and basePath from the Swagger spec. # host and schemes can be omitted, and the "standard" says you should use the spec's URL to derive them. # https://swagger.io/docs/specification/2-0/api-host-and-base-path/ schemes = [] host = None basePath = None try: spec = self.get_swagger_spec(self.url) specURL = urlparse(self.url) except json.JSONDecodeError: error_cant_connect() if 'swagger' not in spec: self.log_operation(None, self.url, { "status_code": "000", "documented_reason": "Specification: no version string found", "body": "Specification: no version string found in Swagger spec" }, '') raise SchemaException if not spec['swagger'].startswith('2'): self.log_operation(None, self.url, { "status_code": "000", "documented_reason": "Specification: wrong specification version", "body": "Specification: version in swagger spec not supported" }, '') raise SchemaException if 'schemes' in spec: schemes = spec['schemes'] else: # fake the array we'd find in the spec schemes.append(specURL.scheme) self.log_operation(None, self.url, { "status_code": "000", "documented_reason": "Specification: no schemes entry, fallback to spec URL scheme", "body": "Specification: host entry not present in Swagger spec"}, '') if self.host: host = self.host elif 'host' in spec: host = spec['host'] else: host = specURL.netloc self.log_operation(None, self.url, { "status_code": "000", "documented_reason": "Specification: no host entry, fallback to spec URL host", "body": "Specification: schemes entry not present in Swagger spec" }, '') # There is no nice way to derive the basePath from the spec's URL. They *have* to include it if 'basePath' not in spec: self.log_operation(None, self.url, { "status_code": "000", "documented_reason": "Specification: basePath entry missing from Swagger spec", "body": "Specification Error: basePath entry missing from Swagger spec" }, '') raise SchemaException basePath = self.basepath if self.basepath else spec['basePath'] host_basepath = host + basePath paths = spec['paths'] type_definitions = spec['definitions'] # the specifcation can list multiple schemes (http, https, ws, wss) - all should be tested. # Each scheme is a potentially different end point replicator = Replicator(type_definitions, self.use_string_pattern, True, self.max_string_length) html_table_data = [] for protocol in schemes: for path_key in paths.keys(): path = paths[path_key] for op_code in path.keys(): operation = HttpOperation(op_code, protocol + '://' + host_basepath, path_key, replicator=replicator, op_infos=path[op_code], use_fuzzing=True, headers=self.headers, ignore_tls=self.ignore_tls) for _ in range(self.iterations): response = operation.execute() validator = ResultValidator() log = validator.evaluate(response, path[op_code]['responses'], self.log_unexpected_errors_only) curlcommand = CurlCommand(response.url, operation.op_code, operation.request_body, self.headers, self.ignore_tls) # log to screen for now self.log_operation(operation.op_code, response.url, log, curlcommand) # html reports status_code, documented_reason, body = self.html_log(log) obj = {"op_code": op_code, "url": response.url, "status_code": status_code, "response_msg": documented_reason, "body": body, "curl_command": curlcommand.get()} html_table_data.append(obj) generate_html(html_table_data, self.report_dir, self.build_id) files = getListOfFiles(self.report_dir) generate_report(self.report_dir, files) return True