diff --git a/.gitignore b/.gitignore index 48a3e5daa..34aef3b17 100644 --- a/.gitignore +++ b/.gitignore @@ -11,3 +11,4 @@ htmlcov/ *.swp .tox/ .idea/ +.pytest_cache/ diff --git a/README.rst b/README.rst index 0f1dad7e2..307dba498 100644 --- a/README.rst +++ b/README.rst @@ -397,8 +397,10 @@ parameters to the underlying `werkzeug`_ server. The Swagger UI Console ---------------------- -The Swagger UI for an API is available, by default, in -``{base_path}/ui/`` where ``base_path`` is the base path of the API. +The Swagger UI for an API is available through pip extras. +You can install it with ``pip install connexion[swagger-ui]``. +It will be served up at ``{base_path}/ui/`` where ``base_path`` is the +base path of the API. You can disable the Swagger UI at the application level: @@ -417,7 +419,7 @@ You can also disable it at the API level: app.add_api('my_api.yaml', swagger_ui=False) If necessary, you can explicitly specify the path to the directory with -swagger-ui to not use the connexion-embedded swagger-ui distro. +swagger-ui to not use the connexion[swagger-ui] distro. In order to do this, you should specify the following option: .. code-block:: python @@ -425,12 +427,24 @@ In order to do this, you should specify the following option: options = {'swagger_path': '/path/to/swagger_ui/'} app = connexion.App(__name__, specification_dir='swagger/', options=options) -Make sure that ``swagger_ui/index.html`` loads by default local swagger json. -You can use the ``api_url`` jinja variable for this purpose: +If you wish to provide your own swagger-ui distro, note that connextion +expects a jinja2 file called ``swagger_ui/index.j2`` in order to load the +correct ``swagger.json`` by default. Your ``index.j2`` file can use the +``openapi_spec_url`` jinja variable for this purpose: .. code-block:: - const ui = SwaggerUIBundle({ url: "{{ api_url }}/swagger.json"}) + const ui = SwaggerUIBundle({ url: "{{ openapi_spec_url }}"}) + +Additionally, if you wish to use swagger-ui-3.x.x, it is also provided by +installing connexion[swagger-ui], and can be enabled like this: + +.. code-block:: python + + from swagger_ui_bundle import swagger_ui_3_path + options = {'swagger_path': swagger_ui_3_path} + app = connexion.App(__name__, specification_dir='swagger/', options=options) + Server Backend -------------- diff --git a/connexion/apis/abstract.py b/connexion/apis/abstract.py index 96303a1c3..665f5c24a 100644 --- a/connexion/apis/abstract.py +++ b/connexion/apis/abstract.py @@ -8,20 +8,17 @@ import jinja2 import six import yaml -from swagger_spec_validator.validator20 import validate_spec +from six.moves.urllib.parse import urlparse -from ..exceptions import ResolverError -from ..operation import Operation +from ..exceptions import InvalidSpecification, ResolverError +from ..operations import OpenAPIOperation, Swagger2Operation from ..options import ConnexionOptions from ..resolver import Resolver from ..utils import Jsonifier MODULE_PATH = pathlib.Path(__file__).absolute().parent.parent -SWAGGER_UI_PATH = MODULE_PATH / 'vendor' / 'swagger-ui' SWAGGER_UI_URL = 'ui' -RESOLVER_ERROR_ENDPOINT_RANDOM_DIGITS = 6 - logger = logging.getLogger('connexion.apis.abstract') @@ -68,22 +65,10 @@ def __init__(self, specification, base_path=None, arguments=None, self.validator_map = validator_map self.resolver_error_handler = resolver_error_handler - self.options = ConnexionOptions(old_style_options) - # options is added last to preserve the highest priority - self.options = self.options.extend(options) - - # TODO: Remove this in later versions (Current version is 1.1.9) - if base_path is None and 'base_url' in old_style_options: - base_path = old_style_options['base_url'] - logger.warning("Parameter base_url should be no longer used. Use base_path instead.") - logger.debug('Loading specification: %s', specification, extra={'swagger_yaml': specification, 'base_path': base_path, 'arguments': arguments, - 'swagger_ui': self.options.openapi_console_ui_available, - 'swagger_path': self.options.openapi_console_ui_from_dir, - 'swagger_url': self.options.openapi_console_ui_path, 'auth_all_paths': auth_all_paths}) if isinstance(specification, dict): @@ -95,6 +80,22 @@ def __init__(self, specification, base_path=None, arguments=None, self.specification = compatibility_layer(self.specification) logger.debug('Read specification', extra={'spec': self.specification}) + self.spec_version = self._get_spec_version(self.specification) + + self.options = ConnexionOptions(old_style_options, oas_version=self.spec_version) + # options is added last to preserve the highest priority + self.options = self.options.extend(options) + + # TODO: Remove this in later versions (Current version is 1.1.9) + if base_path is None and 'base_url' in old_style_options: + base_path = old_style_options['base_url'] + logger.warning("Parameter base_url should be no longer used. Use base_path instead.") + + logger.debug('Options Loaded', + extra={'swagger_ui': self.options.openapi_console_ui_available, + 'swagger_path': self.options.openapi_console_ui_from_dir, + 'swagger_url': self.options.openapi_console_ui_path}) + # Avoid validator having ability to modify specification spec = copy.deepcopy(self.specification) self._validate_spec(spec) @@ -116,6 +117,7 @@ def __init__(self, specification, base_path=None, arguments=None, logger.debug('Security Definitions: %s', self.security_definitions) self.definitions = self.specification.get('definitions', {}) + self.components = self.specification.get('components', {}) self.parameter_definitions = self.specification.get('parameters', {}) self.response_definitions = self.specification.get('responses', {}) @@ -131,7 +133,7 @@ def __init__(self, specification, base_path=None, arguments=None, self.pythonic_params = pythonic_params if self.options.openapi_spec_available: - self.add_swagger_json() + self.add_openapi_json() if self.options.openapi_console_ui_available: self.add_swagger_ui() @@ -142,20 +144,34 @@ def __init__(self, specification, base_path=None, arguments=None, self.add_auth_on_not_found(self.security, self.security_definitions) def _validate_spec(self, spec): + if self.spec_version < (3, 0, 0): + logger.info('Using Swagger 2.0 specification') + from openapi_spec_validator import validate_v2_spec as validate_spec + else: + logger.info('Using OpenApi %d.%d.%d specification' % self.spec_version) + from openapi_spec_validator import validate_v3_spec as validate_spec validate_spec(spec) def _set_base_path(self, base_path): # type: (AnyStr) -> None if base_path is None: self.base_path = canonical_base_path(self.specification.get('basePath', '')) + if self.spec_version >= (3, 0, 0): + # TODO variable subsitution in urls for oas3 + servers = self.specification.get('servers', []) + for server in servers: + # TODO how to handle multiple servers in an oas3 spec with different paths? + self.base_path = canonical_base_path(urlparse(server['url']).path) + break else: self.base_path = canonical_base_path(base_path) self.specification['basePath'] = base_path @abc.abstractmethod - def add_swagger_json(self): + def add_openapi_json(self): """ - Adds swagger json to {base_path}/swagger.json + Adds openapi spec to {base_path}/openapi.json + (or {base_path}/swagger.json for swagger2) """ @abc.abstractmethod @@ -187,24 +203,40 @@ def add_operation(self, method, path, swagger_operation, path_parameters): :type path: str :type swagger_operation: dict """ - operation = Operation(self, - method=method, - path=path, - path_parameters=path_parameters, - operation=swagger_operation, - app_produces=self.produces, - app_consumes=self.consumes, - app_security=self.security, - security_definitions=self.security_definitions, - definitions=self.definitions, - parameter_definitions=self.parameter_definitions, - response_definitions=self.response_definitions, - validate_responses=self.validate_responses, - validator_map=self.validator_map, - strict_validation=self.strict_validation, - resolver=self.resolver, - pythonic_params=self.pythonic_params, - uri_parser_class=self.options.uri_parser_class) + if self.spec_version < (3, 0, 0): + operation = Swagger2Operation(self, + method=method, + path=path, + path_parameters=path_parameters, + operation=swagger_operation, + app_produces=self.produces, + app_consumes=self.consumes, + app_security=self.security, + security_definitions=self.security_definitions, + definitions=self.definitions, + parameter_definitions=self.parameter_definitions, + response_definitions=self.response_definitions, + validate_responses=self.validate_responses, + validator_map=self.validator_map, + strict_validation=self.strict_validation, + resolver=self.resolver, + pythonic_params=self.pythonic_params, + uri_parser_class=self.options.uri_parser_class) + else: + operation = OpenAPIOperation(self, + method=method, + path=path, + operation=swagger_operation, + path_parameters=path_parameters, + app_security=self.security, + components=self.components, + validate_responses=self.validate_responses, + validator_map=self.validator_map, + strict_validation=self.strict_validation, + resolver=self.resolver, + pythonic_params=self.pythonic_params, + uri_parser_class=self.options.uri_parser_class) + self._add_operation_internal(method, path, operation) @abc.abstractmethod @@ -219,18 +251,8 @@ def _add_resolver_error_handler(self, method, path, err): Adds a handler for ResolverError for the given method and path. """ operation = self.resolver_error_handler(err, - method=method, - path=path, - app_produces=self.produces, - app_security=self.security, - security_definitions=self.security_definitions, - definitions=self.definitions, - parameter_definitions=self.parameter_definitions, - response_definitions=self.response_definitions, - validate_responses=self.validate_responses, - strict_validation=self.strict_validation, - resolver=self.resolver, - randomize_endpoint=RESOLVER_ERROR_ENDPOINT_RANDOM_DIGITS) + security=self.security, + security_definitions=self.security_definitions) self._add_operation_internal(method, path, operation) def add_paths(self, paths=None): @@ -287,6 +309,20 @@ def load_spec_from_file(self, arguments, specification): swagger_string = jinja2.Template(swagger_template).render(**arguments) return yaml.safe_load(swagger_string) # type: dict + def _get_spec_version(self, spec): + try: + version_string = spec.get('openapi') or spec.get('swagger') + except AttributeError: + raise InvalidSpecification('Unable to get spec version') + if version_string is None: + raise InvalidSpecification('Unable to get spec version') + try: + version_tuple = tuple(map(int, version_string.split("."))) + except TypeError: + # unable to convert to semver tuple + raise InvalidSpecification('Invalid Spec Version') + return version_tuple + @classmethod @abc.abstractmethod def get_request(self, *args, **kwargs): diff --git a/connexion/apis/aiohttp_api.py b/connexion/apis/aiohttp_api.py index 1c25d1dbe..ec49609b6 100644 --- a/connexion/apis/aiohttp_api.py +++ b/connexion/apis/aiohttp_api.py @@ -64,19 +64,21 @@ def _set_base_path(self, base_path): def normalize_string(string): return re.sub(r'[^a-zA-Z0-9]', '_', string.strip('/')) - def add_swagger_json(self): + def add_openapi_json(self): """ - Adds swagger json to {base_path}/swagger.json + Adds openapi json to {base_path}/openapi.json + (or {base_path}/swagger.json for swagger2) """ - logger.debug('Adding swagger.json: %s/swagger.json', self.base_path) + logger.debug('Adding spec json: %s/%s', self.base_path, + self.options.openapi_spec_path) self.subapp.router.add_route( 'GET', - '/swagger.json', - self._get_swagger_json + self.options.openapi_spec_path, + self._get_openapi_json ) @asyncio.coroutine - def _get_swagger_json(self, req): + def _get_openapi_json(self, req): return web.Response( status=200, content_type='application/json', @@ -109,10 +111,11 @@ def add_swagger_ui(self): name='swagger_ui_static' ) - @aiohttp_jinja2.template('index.html') + @aiohttp_jinja2.template('index.j2') @asyncio.coroutine def _get_swagger_ui_home(self, req): - return {'api_url': self.base_path} + return {'openapi_spec_url': (self.base_path + + self.options.openapi_spec_path)} def add_auth_on_not_found(self, security, security_definitions): """ diff --git a/connexion/apis/flask_api.py b/connexion/apis/flask_api.py index 87b8682d3..0fa877996 100644 --- a/connexion/apis/flask_api.py +++ b/connexion/apis/flask_api.py @@ -26,13 +26,15 @@ def _set_blueprint(self): self.blueprint = flask.Blueprint(endpoint, __name__, url_prefix=self.base_path, template_folder=str(self.options.openapi_console_ui_from_dir)) - def add_swagger_json(self): + def add_openapi_json(self): """ - Adds swagger json to {base_path}/swagger.json + Adds spec json to {base_path}/swagger.json + or {base_path}/openapi.json (for oas3) """ - logger.debug('Adding swagger.json: %s/swagger.json', self.base_path) - endpoint_name = "{name}_swagger_json".format(name=self.blueprint.name) - self.blueprint.add_url_rule('/swagger.json', + logger.debug('Adding spec json: %s/%s', self.base_path, + self.options.openapi_spec_path) + endpoint_name = "{name}_openapi_json".format(name=self.blueprint.name) + self.blueprint.add_url_rule(self.options.openapi_spec_path, endpoint_name, lambda: flask.jsonify(self.specification)) @@ -279,7 +281,10 @@ def console_ui_home(self): :return: """ - return flask.render_template('index.html', api_url=self.base_path) + return flask.render_template( + 'index.j2', + openapi_spec_url=(self.base_path + self.options.openapi_spec_path) + ) def console_ui_static_files(self, filename): """ diff --git a/connexion/apps/abstract.py b/connexion/apps/abstract.py index d58cd3dc1..538ce969e 100644 --- a/connexion/apps/abstract.py +++ b/connexion/apps/abstract.py @@ -161,10 +161,6 @@ def add_api(self, specification, base_path=None, arguments=None, def _resolver_error_handler(self, *args, **kwargs): from connexion.handlers import ResolverErrorHandler - kwargs['operation'] = { - 'operationId': 'connexion.handlers.ResolverErrorHandler', - } - kwargs.setdefault('app_consumes', ['application/json']) return ResolverErrorHandler(self.api_cls, self.resolver_error, *args, **kwargs) def add_url_rule(self, rule, endpoint=None, view_func=None, **options): diff --git a/connexion/decorators/parameter.py b/connexion/decorators/parameter.py index aad997e8a..5a33da631 100644 --- a/connexion/decorators/parameter.py +++ b/connexion/decorators/parameter.py @@ -1,4 +1,3 @@ -import copy import functools import inspect import logging @@ -7,8 +6,9 @@ import inflection import six +from ..http_facts import FORM_CONTENT_TYPES from ..lifecycle import ConnexionRequest # NOQA -from ..utils import all_json, boolean, is_null, is_nullable +from ..utils import all_json try: import builtins @@ -24,14 +24,6 @@ except NameError: # pragma: no cover py_string = str # pragma: no cover -# https://github.com/swagger-api/swagger-spec/blob/master/versions/2.0.md#data-types -TYPE_MAP = {'integer': int, - 'number': float, - 'string': py_string, - 'boolean': boolean, - 'array': list, - 'object': dict} # map of swagger types to python types - def inspect_function_arguments(function): # pragma: no cover """ @@ -52,21 +44,6 @@ def inspect_function_arguments(function): # pragma: no cover return argspec.args, bool(argspec.keywords) -def make_type(value, type): - type_func = TYPE_MAP[type] # convert value to right type - return type_func(value) - - -def get_val_from_param(value, query_param): - if is_nullable(query_param) and is_null(value): - return None - - if query_param["type"] == "array": - return [make_type(v, query_param["items"]["type"]) for v in value] - else: - return make_type(value, query_param["type"]) - - def snake_and_shadow(name): """ Converts the given name into Pythonic form. Firstly it converts CamelCase names to snake_case. Secondly it looks to @@ -81,40 +58,29 @@ def snake_and_shadow(name): return snake -def parameter_to_arg(parameters, consumes, function, pythonic_params=False): +def parameter_to_arg(operation, function, pythonic_params=False): """ Pass query and body parameters as keyword arguments to handler function. See (https://github.com/zalando/connexion/issues/59) - :param parameters: All the parameters of the handler functions - :type parameters: dict|None - :param consumes: The list of content types the operation consumes - :type consumes: list - :param function: The handler function for the REST endpoint. + :param operation: The operation being called + :type operation: connexion.operations.AbstractOperation :param pythonic_params: When True CamelCase parameters are converted to snake_case and an underscore is appended to any shadowed built-ins :type pythonic_params: bool :type function: function|None """ - def sanitize_param(name): - if name and pythonic_params: - name = snake_and_shadow(name) + consumes = operation.consumes + + def pythonic(name): + name = name and snake_and_shadow(name) return name and re.sub('^[^a-zA-Z_]+', '', re.sub('[^0-9a-zA-Z_]', '', name)) - body_parameters = [parameter for parameter in parameters if parameter['in'] == 'body'] or [{}] - body_name = sanitize_param(body_parameters[0].get('name')) - default_body = body_parameters[0].get('schema', {}).get('default') - query_types = {sanitize_param(parameter['name']): parameter - for parameter in parameters if parameter['in'] == 'query'} # type: dict[str, str] - form_types = {sanitize_param(parameter['name']): parameter - for parameter in parameters if parameter['in'] == 'formData'} - path_types = {parameter['name']: parameter - for parameter in parameters if parameter['in'] == 'path'} + def sanitized(name): + return name and re.sub('^[^a-zA-Z_]+', '', re.sub('[^0-9a-zA-Z_]', '', name)) + + sanitize = pythonic if pythonic_params else sanitized arguments, has_kwargs = inspect_function_arguments(function) - default_query_params = {sanitize_param(param['name']): param['default'] - for param in parameters if param['in'] == 'query' and 'default' in param} - default_form_params = {sanitize_param(param['name']): param['default'] - for param in parameters if param['in'] == 'formData' and 'default' in param} @functools.wraps(function) def wrapper(request): @@ -124,67 +90,24 @@ def wrapper(request): if all_json(consumes): request_body = request.json + elif consumes[0] in FORM_CONTENT_TYPES: + request_body = {sanitize(k): v for k, v in request.form.items()} else: request_body = request.body - if default_body and not request_body: - request_body = default_body + # accept formData even even if mimetype is wrong for backwards + # compatability :/ + request_body = request_body or {sanitize(k): v for k, v in request.form.items()} - # Parse path parameters - path_params = request.path_params - for key, value in path_params.items(): - if key in path_types: - kwargs[key] = get_val_from_param(value, path_types[key]) - else: # Assume path params mechanism used for injection - kwargs[key] = value + try: + query = request.query.to_dict(flat=False) + except AttributeError: + query = dict(request.query.items()) - # Add body parameters - if not has_kwargs and body_name not in arguments: - logger.debug("Body parameter '%s' not in function arguments", body_name) - elif body_name: - logger.debug("Body parameter '%s' in function arguments", body_name) - kwargs[body_name] = request_body - - # Add query parameters - query_arguments = copy.deepcopy(default_query_params) - query_arguments.update(request.query) - for key, value in query_arguments.items(): - key = sanitize_param(key) - if not has_kwargs and key not in arguments: - logger.debug("Query Parameter '%s' not in function arguments", key) - else: - logger.debug("Query Parameter '%s' in function arguments", key) - try: - query_param = query_types[key] - except KeyError: # pragma: no cover - logger.error("Function argument '{}' not defined in specification".format(key)) - else: - logger.debug('%s is a %s', key, query_param) - kwargs[key] = get_val_from_param(value, query_param) - - # Add formData parameters - form_arguments = copy.deepcopy(default_form_params) - form_arguments.update({sanitize_param(k): v for k, v in request.form.items()}) - for key, value in form_arguments.items(): - if not has_kwargs and key not in arguments: - logger.debug("FormData parameter '%s' not in function arguments", key) - else: - logger.debug("FormData parameter '%s' in function arguments", key) - try: - form_param = form_types[key] - except KeyError: # pragma: no cover - logger.error("Function argument '{}' not defined in specification".format(key)) - else: - kwargs[key] = get_val_from_param(value, form_param) - - # Add file parameters - file_arguments = request.files - for key, value in file_arguments.items(): - if not has_kwargs and key not in arguments: - logger.debug("File parameter (formData) '%s' not in function arguments", key) - else: - logger.debug("File parameter (formData) '%s' in function arguments", key) - kwargs[key] = value + kwargs.update( + operation.get_arguments(request.path_params, query, request_body, + request.files, arguments, has_kwargs, sanitize) + ) # optionally convert parameter variable names to un-shadowed, snake_case form if pythonic_params: diff --git a/connexion/decorators/response.py b/connexion/decorators/response.py index 137f438a4..9ecbef83d 100644 --- a/connexion/decorators/response.py +++ b/connexion/decorators/response.py @@ -15,7 +15,7 @@ class ResponseValidator(BaseDecorator): - def __init__(self, operation, mimetype): + def __init__(self, operation, mimetype): """ :type operation: Operation :type mimetype: str @@ -32,13 +32,16 @@ def validate_response(self, data, status_code, headers, url): :type headers: dict :rtype bool | None """ - response_definitions = self.operation.operation["responses"] - response_definition = response_definitions.get(str(status_code), response_definitions.get("default", {})) - response_definition = self.operation.resolve_reference(response_definition) + # check against returned header, fall back to expected mimetype + content_type = headers.get("Content-Type", self.mimetype) + content_type = content_type.rsplit(";", 1)[0] # remove things like utf8 metadata - if self.is_json_schema_compatible(response_definition): - schema = response_definition.get("schema") - v = ResponseBodyValidator(schema) + response_definition = self.operation.response_definition(str(status_code), content_type) + response_schema = self.operation.response_schema(str(status_code), content_type) + + if self.is_json_schema_compatible(response_schema): + logger.debug(response_schema) + v = ResponseBodyValidator(response_schema) try: data = self.operation.json_loads(data) v.validate_schema(data, url) @@ -57,7 +60,7 @@ def validate_response(self, data, status_code, headers, url): raise NonConformingResponseHeaders(message=msg) return True - def is_json_schema_compatible(self, response_definition): + def is_json_schema_compatible(self, response_schema): """ Verify if the specified operation responses are JSON schema compatible. @@ -66,13 +69,12 @@ def is_json_schema_compatible(self, response_definition): type "application/json" or "text/plain" can be validated using json_schema package. - :type response_definition: dict + :type response_schema: dict :rtype bool """ - if not response_definition: + if not response_schema: return False - return ('schema' in response_definition and - (all_json([self.mimetype]) or self.mimetype == 'text/plain')) + return all_json([self.mimetype]) or self.mimetype == 'text/plain' def __call__(self, function): """ diff --git a/connexion/decorators/uri_parsing.py b/connexion/decorators/uri_parsing.py index c81eb3134..a67ec20ae 100644 --- a/connexion/decorators/uri_parsing.py +++ b/connexion/decorators/uri_parsing.py @@ -9,6 +9,13 @@ logger = logging.getLogger('connexion.decorators.uri_parsing') +QUERY_STRING_DELIMITERS = { + 'spaceDelimited': ' ', + 'pipeDelimited': '|', + 'simple': ',', + 'form': ',' +} + @six.add_metaclass(abc.ABCMeta) class AbstractURIParser(BaseDecorator): @@ -116,6 +123,48 @@ def wrapper(request): return wrapper +class OpenAPIURIParser(AbstractURIParser): + + @property + def param_defns(self): + return self._param_defns + + @property + def param_schemas(self): + return {k: v.get("schema", {}) for k, v in self.param_defns.items()} + + @staticmethod + def _resolve_param_duplicates(values, param_defn): + """ Resolve cases where query parameters are provided multiple times. + The default behavior is to use the first-defined value. + For example, if the query string is '?a=1,2,3&a=4,5,6' the value of + `a` would be "4,5,6". + However, if 'explode' is 'True' then the duplicate values + are concatenated together and `a` would be "1,2,3,4,5,6". + """ + try: + style = param_defn['style'] + delimiter = QUERY_STRING_DELIMITERS.get(style, ',') + is_form = (style == 'form') + explode = param_defn.get('explode', is_form) + if explode: + return delimiter.join(values) + except KeyError: + pass + + # default to last defined value + return values[-1] + + @staticmethod + def _split(value, param_defn): + try: + style = param_defn['style'] + delimiter = QUERY_STRING_DELIMITERS.get(style, ',') + return value.split(delimiter) + except KeyError: + return value.split(',') + + class Swagger2URIParser(AbstractURIParser): """ Adheres to the Swagger2 spec, diff --git a/connexion/decorators/validation.py b/connexion/decorators/validation.py index 1a2e2d27b..00b96dc80 100644 --- a/connexion/decorators/validation.py +++ b/connexion/decorators/validation.py @@ -9,6 +9,7 @@ from werkzeug import FileStorage from ..exceptions import ExtraParameterProblem +from ..http_facts import FORM_CONTENT_TYPES from ..problem import problem from ..utils import all_json, boolean, is_json_mimetype, is_null, is_nullable @@ -46,13 +47,14 @@ def __str__(self): def validate_type(param, value, parameter_type, parameter_name=None): - param_type = param.get('type') + param_schema = param.get("schema", param) + param_type = param_schema.get('type') parameter_name = parameter_name if parameter_name else param['name'] if param_type == "array": converted_params = [] for v in value: try: - converted = make_type(v, param["items"]["type"]) + converted = make_type(v, param_schema["items"]["type"]) except (ValueError, TypeError): converted = v converted_params.append(converted) @@ -74,7 +76,8 @@ def validate_parameter_list(request_params, spec_params): class RequestBodyValidator(object): - def __init__(self, schema, consumes, api, is_null_value_valid=False, validator=None): + def __init__(self, schema, consumes, api, is_null_value_valid=False, validator=None, + strict_validation=False): """ :param schema: The schema of the request body :param consumes: The list of content types the operation consumes @@ -82,13 +85,20 @@ def __init__(self, schema, consumes, api, is_null_value_valid=False, validator=N :param validator: Validator class that should be used to validate passed data against API schema. Default is jsonschema.Draft4Validator. :type validator: jsonschema.IValidator + :param strict_validation: Flag indicating if parameters not in spec are allowed """ self.consumes = consumes + self.schema = schema self.has_default = schema.get('default', False) self.is_null_value_valid = is_null_value_valid validatorClass = validator or Draft4Validator self.validator = validatorClass(schema, format_checker=draft4_format_checker) self.api = api + self.strict_validation = strict_validation + + def validate_requestbody_property_list(self, data): + spec_params = self.schema.get('properties', {}).keys() + return validate_parameter_list(data, spec_params) def __call__(self, function): """ @@ -100,7 +110,6 @@ def __call__(self, function): def wrapper(request): if all_json(self.consumes): data = request.json - if data is None and len(request.body) > 0 and not self.is_null_value_valid: try: ctype_is_json = is_json_mimetype(request.headers.get("Content-Type", "")) @@ -121,7 +130,22 @@ def wrapper(request): content_type=request.headers.get("Content-Type", "") )) - logger.debug("%s validating schema...", request.url) + logger.debug('%s validating schema...', request.url) + error = self.validate_schema(data, request.url) + if error and not self.has_default: + return error + elif self.consumes[0] in FORM_CONTENT_TYPES: + data = dict(request.form.items()) or (request.body if len(request.body) > 0 else {}) + if data is None and len(request.body) > 0 and not self.is_null_value_valid: + # complain about no data? + pass + data.update(dict.fromkeys(request.files, '')) # validator expects string.. + logger.debug('%s validating schema...', request.url) + if self.strict_validation: + formdata_errors = self.validate_requestbody_property_list(data) + if formdata_errors: + raise ExtraParameterProblem(formdata_errors, []) + error = self.validate_schema(data, request.url) if error and not self.has_default: return error @@ -173,6 +197,7 @@ class ParameterValidator(object): def __init__(self, parameters, api, strict_validation=False): """ :param parameters: List of request parameter dictionaries + :param api: api that the validator is attached to :param strict_validation: Flag indicating if parameters not in spec are allowed """ self.parameters = collections.defaultdict(list) @@ -182,8 +207,8 @@ def __init__(self, parameters, api, strict_validation=False): self.api = api self.strict_validation = strict_validation - @staticmethod - def validate_parameter(parameter_type, value, param): + @classmethod + def validate_parameter(cls, parameter_type, value, param): if value is not None: if is_nullable(param) and is_null(value): return @@ -249,7 +274,7 @@ def validate_header_parameter(self, param, request): return self.validate_parameter('header', val, param) def validate_formdata_parameter(self, param, request): - if param.get('type') == 'file': + if param.get('type') == 'file' or param.get('format') == 'binary': val = request.files.get(param['name']) else: val = request.form.get(param['name']) diff --git a/connexion/handlers.py b/connexion/handlers.py index 87093b48f..85d40ea0a 100644 --- a/connexion/handlers.py +++ b/connexion/handlers.py @@ -1,10 +1,12 @@ import logging -from .operation import Operation, SecureOperation +from .operations.secure import SecureOperation from .problem import problem logger = logging.getLogger('connexion.handlers') +RESOLVER_ERROR_ENDPOINT_RANDOM_DIGITS = 6 + class AuthErrorHandler(SecureOperation): """ @@ -25,7 +27,7 @@ def __init__(self, api, exception, security, security_definitions): :type security_definitions: dict """ self.exception = exception - SecureOperation.__init__(self, api, security, security_definitions) + super(AuthErrorHandler, self).__init__(api, security, security_definitions) @property def function(self): @@ -52,15 +54,15 @@ def handle(self, *args, **kwargs): return self.api.get_response(response) -class ResolverErrorHandler(Operation): +class ResolverErrorHandler(SecureOperation): """ Handler for responding to ResolverError. """ - def __init__(self, api, status_code, exception, *args, **kwargs): + def __init__(self, api, status_code, exception, security, security_definitions): self.status_code = status_code self.exception = exception - Operation.__init__(self, api, *args, **kwargs) + super(ResolverErrorHandler, self).__init__(api, security, security_definitions) @property def function(self): @@ -73,3 +75,18 @@ def handle(self, *args, **kwargs): status=self.status_code ) return self.api.get_response(response) + + @property + def operation_id(self): + return "noop" + + @property + def router_controller(self): + return None + + @property + def randomize_endpoint(self): + return RESOLVER_ERROR_ENDPOINT_RANDOM_DIGITS + + def get_path_parameter_types(self): + return [] diff --git a/connexion/http_facts.py b/connexion/http_facts.py new file mode 100644 index 000000000..be7756c04 --- /dev/null +++ b/connexion/http_facts.py @@ -0,0 +1,4 @@ +FORM_CONTENT_TYPES = [ + 'application/x-www-form-urlencoded', + 'multipart/form-data' +] diff --git a/connexion/mock.py b/connexion/mock.py index c123e7e6f..7c5f23436 100644 --- a/connexion/mock.py +++ b/connexion/mock.py @@ -27,7 +27,7 @@ def resolve(self, operation): """ Mock operation resolver - :type operation: connexion.operation.Operation + :type operation: connexion.operations.AbstractOperation """ operation_id = self.resolve_operation_id(operation) if not operation_id: @@ -51,33 +51,7 @@ def resolve(self, operation): return Resolution(func, operation_id) def mock_operation(self, operation, *args, **kwargs): - response_definitions = operation.operation["responses"] - # simply use the first/lowest status code, this is probably 200 or 201 - status_code = sorted(response_definitions.keys())[0] - response_definition = response_definitions.get(status_code, {}) - try: - status_code = int(status_code) - except ValueError: - status_code = 200 - response_definition = operation.resolve_reference(response_definition) - examples = response_definition.get('examples') - if examples: - return list(examples.values())[0], status_code - else: - # No response example, check for schema example - response_schema = response_definition.get('schema', {}) - definitions = response_schema.get('definitions', {}) - schema_example = None - ref = response_schema.get('$ref') - if ref: - # Referenced schema - ref = ref[ref.rfind('/')+1:] or '' - ref_schema = definitions.get(ref, {}) - schema_example = ref_schema.get('example') - else: - # Inline schema - schema_example = response_schema.get('example') - if schema_example: - return schema_example, status_code - else: - return 'No example response was defined.', status_code + resp, code = operation.example_response() + if resp is not None: + return resp, code + return 'No example response was defined.', code diff --git a/connexion/operation.py b/connexion/operation.py deleted file mode 100644 index b4b80deb7..000000000 --- a/connexion/operation.py +++ /dev/null @@ -1,487 +0,0 @@ -import functools -import logging -from copy import deepcopy - -from jsonschema import ValidationError - -from .decorators import validation -from .decorators.decorator import (BeginOfRequestLifecycleDecorator, - EndOfRequestLifecycleDecorator) -from .decorators.metrics import UWSGIMetricsCollector -from .decorators.parameter import parameter_to_arg -from .decorators.produces import BaseSerializer, Produces -from .decorators.response import ResponseValidator -from .decorators.security import (get_tokeninfo_func, get_tokeninfo_url, - security_passthrough, verify_oauth_local, - verify_oauth_remote) -from .decorators.uri_parsing import AlwaysMultiURIParser -from .decorators.validation import (ParameterValidator, RequestBodyValidator, - TypeValidationError) -from .exceptions import InvalidSpecification -from .utils import all_json, is_nullable - -logger = logging.getLogger('connexion.operation') - -DEFAULT_MIMETYPE = 'application/json' - - -VALIDATOR_MAP = { - 'parameter': ParameterValidator, - 'body': RequestBodyValidator, - 'response': ResponseValidator, -} - - -class SecureOperation(object): - - def __init__(self, api, security, security_definitions): - """ - :param security: list of security rules the application uses by default - :type security: list - :param security_definitions: `Security Definitions Object - `_ - :type security_definitions: dict - """ - self.api = api - self.security = security - self.security_definitions = security_definitions - - @property - def security_decorator(self): - """ - Gets the security decorator for operation - - From Swagger Specification: - - **Security Definitions Object** - - A declaration of the security schemes available to be used in the specification. - - This does not enforce the security schemes on the operations and only serves to provide the relevant details - for each scheme. - - - **Security Requirement Object** - - Lists the required security schemes to execute this operation. The object can have multiple security schemes - declared in it which are all required (that is, there is a logical AND between the schemes). - - The name used for each property **MUST** correspond to a security scheme declared in the Security Definitions. - - :rtype: types.FunctionType - """ - logger.debug('... Security: %s', self.security, extra=vars(self)) - if self.security: - if len(self.security) > 1: - logger.debug("... More than one security requirement defined. **IGNORING SECURITY REQUIREMENTS**", - extra=vars(self)) - return security_passthrough - - security = self.security[0] # type: dict - # the following line gets the first (and because of the previous condition only) scheme and scopes - # from the operation's security requirements - - scheme_name, scopes = next(iter(security.items())) # type: str, list - security_definition = self.security_definitions[scheme_name] - if security_definition['type'] == 'oauth2': - token_info_url = get_tokeninfo_url(security_definition) - token_info_func = get_tokeninfo_func(security_definition) - scopes = set(scopes) # convert scopes to set because this is needed for verify_oauth_remote - - if token_info_url and token_info_func: - logger.warning("... Both x-tokenInfoUrl and x-tokenInfoFunc are defined, using x-tokenInfoFunc", - extra=vars(self)) - if token_info_func: - return functools.partial(verify_oauth_local, token_info_func, scopes) - if token_info_url: - return functools.partial(verify_oauth_remote, token_info_url, scopes) - else: - logger.warning("... OAuth2 token info URL missing. **IGNORING SECURITY REQUIREMENTS**", - extra=vars(self)) - elif security_definition['type'] in ('apiKey', 'basic'): - logger.debug( - "... Security type '%s' not natively supported by Connexion; you should handle it yourself", - security_definition['type'], extra=vars(self)) - - # if we don't know how to handle the security or it's not defined we will usa a passthrough decorator - return security_passthrough - - def get_mimetype(self): - return DEFAULT_MIMETYPE - - @property - def _request_begin_lifecycle_decorator(self): - """ - Transforms the result of the operation handler in a internal - representation (connexion.lifecycle.ConnexionRequest) to be - used by internal Connexion decorators. - - :rtype: types.FunctionType - """ - return BeginOfRequestLifecycleDecorator(self.api, self.get_mimetype()) - - @property - def _request_end_lifecycle_decorator(self): - """ - Guarantees that instead of the internal representation of the - operation handler response - (connexion.lifecycle.ConnexionRequest) a framework specific - object is returned. - :rtype: types.FunctionType - """ - return EndOfRequestLifecycleDecorator(self.api, self.get_mimetype()) - - -class Operation(SecureOperation): - - """ - A single API operation on a path. - """ - - def __init__(self, api, method, path, operation, resolver, app_produces, app_consumes, - path_parameters=None, app_security=None, security_definitions=None, - definitions=None, parameter_definitions=None, response_definitions=None, - validate_responses=False, strict_validation=False, randomize_endpoint=None, - validator_map=None, pythonic_params=False, uri_parser_class=None): - """ - This class uses the OperationID identify the module and function that will handle the operation - - From Swagger Specification: - - **OperationID** - - A friendly name for the operation. The id MUST be unique among all operations described in the API. - Tools and libraries MAY use the operation id to uniquely identify an operation. - - :param method: HTTP method - :type method: str - :param path: - :type path: str - :param operation: swagger operation object - :type operation: dict - :param resolver: Callable that maps operationID to a function - :param app_produces: list of content types the application can return by default - :type app_produces: list - :param app_consumes: list of content types the application consumes by default - :type app_consumes: list - :param validator_map: map of validators - :type validator_map: dict - :param path_parameters: Parameters defined in the path level - :type path_parameters: list - :param app_security: list of security rules the application uses by default - :type app_security: list - :param security_definitions: `Security Definitions Object - `_ - :type security_definitions: dict - :param definitions: `Definitions Object - `_ - :type definitions: dict - :param parameter_definitions: Global parameter definitions - :type parameter_definitions: dict - :param response_definitions: Global response definitions - :type response_definitions: dict - :param validator_map: Custom validators for the types "parameter", "body" and "response". - :type validator_map: dict - :param validate_responses: True enables validation. Validation errors generate HTTP 500 responses. - :type validate_responses: bool - :param strict_validation: True enables validation on invalid request parameters - :type strict_validation: bool - :param pythonic_params: When True CamelCase parameters are converted to snake_case and an underscore is appended - to any shadowed built-ins - :type pythonic_params: bool - :param uri_parser_class: A URI parser class that inherits from AbstractURIParser - :type uri_parser_class: AbstractURIParser - """ - - self.api = api - self.method = method - self.path = path - self.validator_map = dict(VALIDATOR_MAP) - self.validator_map.update(validator_map or {}) - self.security_definitions = security_definitions or {} - self.definitions = definitions or {} - self.parameter_definitions = parameter_definitions or {} - self.response_definitions = response_definitions or {} - self.definitions_map = { - 'definitions': self.definitions, - 'parameters': self.parameter_definitions, - 'responses': self.response_definitions - } - self.validate_responses = validate_responses - self.strict_validation = strict_validation - self.operation = operation - self.randomize_endpoint = randomize_endpoint - self.pythonic_params = pythonic_params - self.uri_parser_class = uri_parser_class or AlwaysMultiURIParser - - # todo support definition references - # todo support references to application level parameters - self.parameters = list(self.resolve_parameters(operation.get('parameters', []))) - if path_parameters: - self.parameters += list(self.resolve_parameters(path_parameters)) - - self.security = operation.get('security', app_security) - self.produces = operation.get('produces', app_produces) - self.consumes = operation.get('consumes', app_consumes) - - resolution = resolver.resolve(self) - self.operation_id = resolution.operation_id - self.__undecorated_function = resolution.function - - self.validate_defaults() - - def validate_defaults(self): - for param in self.parameters: - try: - if param['in'] == 'query' and 'default' in param: - validation.validate_type(param, param['default'], 'query', param['name']) - except (TypeValidationError, ValidationError): - raise InvalidSpecification('The parameter \'{param_name}\' has a default value which is not of' - ' type \'{param_type}\''.format(param_name=param['name'], - param_type=param['type'])) - - def resolve_reference(self, schema): - schema = deepcopy(schema) # avoid changing the original schema - self.check_references(schema) - - # find the object we need to resolve/update if this is not a proper SchemaObject - # e.g a response or parameter object - for obj in schema, schema.get('items'): - reference = obj and obj.get('$ref') # type: str - if reference: - break - if reference: - definition = deepcopy(self._retrieve_reference(reference)) - # Update schema - obj.update(definition) - del obj['$ref'] - - # if there is a schema object on this param or response, then we just - # need to include the defs and it can be validated by jsonschema - if 'schema' in schema: - schema['schema']['definitions'] = self.definitions - return schema - - return schema - - def check_references(self, schema): - """ - Searches the keys and values of a schema object for json references. - If it finds one, it attempts to locate it and will thrown an exception - if the reference can't be found in the definitions dictionary. - - :param schema: The schema object to check - :type schema: dict - :raises InvalidSpecification: raised when a reference isn't found - """ - - stack = [schema] - visited = set() - while stack: - schema = stack.pop() - for k, v in schema.items(): - if k == "$ref": - if v in visited: - continue - visited.add(v) - stack.append(self._retrieve_reference(v)) - elif isinstance(v, (list, tuple)): - continue - elif hasattr(v, "items"): - stack.append(v) - - def _retrieve_reference(self, reference): - if not reference.startswith('#/'): - raise InvalidSpecification( - "{method} {path} '$ref' needs to start with '#/'".format(**vars(self))) - path = reference.split('/') - definition_type = path[1] - try: - definitions = self.definitions_map[definition_type] - except KeyError: - ref_possible = ', '.join(self.definitions_map.keys()) - raise InvalidSpecification( - "{method} {path} $ref \"{reference}\" needs to point to one of: " - "{ref_possible}".format( - method=self.method, - path=self.path, - reference=reference, - ref_possible=ref_possible - )) - definition_name = path[-1] - try: - # Get sub definition - definition = deepcopy(definitions[definition_name]) - except KeyError: - raise InvalidSpecification( - "{method} {path} Definition '{definition_name}' not found".format( - definition_name=definition_name, method=self.method, path=self.path)) - - return definition - - def get_mimetype(self): - """ - If the endpoint has no 'produces' then the default is - 'application/json'. - - :rtype str - """ - if all_json(self.produces): - try: - return self.produces[0] - except IndexError: - return DEFAULT_MIMETYPE - elif len(self.produces) == 1: - return self.produces[0] - else: - return DEFAULT_MIMETYPE - - def resolve_parameters(self, parameters): - for param in parameters: - param = self.resolve_reference(param) - yield param - - def get_path_parameter_types(self): - return {p['name']: 'path' if p.get('type') == 'string' and p.get('format') == 'path' else p.get('type') - for p in self.parameters if p['in'] == 'path'} - - @property - def body_schema(self): - """ - The body schema definition for this operation. - """ - return self.body_definition.get('schema') - - @property - def body_definition(self): - """ - The body complete definition for this operation. - - **There can be one "body" parameter at most.** - - :rtype: dict - """ - body_parameters = [parameter for parameter in self.parameters if parameter['in'] == 'body'] - if len(body_parameters) > 1: - raise InvalidSpecification( - "{method} {path} There can be one 'body' parameter at most".format(**vars(self))) - - return body_parameters[0] if body_parameters else {} - - @property - def function(self): - """ - Operation function with decorators - - :rtype: types.FunctionType - """ - - function = parameter_to_arg( - self.parameters, self.consumes, self.__undecorated_function, self.pythonic_params) - function = self._request_begin_lifecycle_decorator(function) - - if self.validate_responses: - logger.debug('... Response validation enabled.') - response_decorator = self.__response_validation_decorator - logger.debug('... Adding response decorator (%r)', response_decorator) - function = response_decorator(function) - - produces_decorator = self.__content_type_decorator - logger.debug('... Adding produces decorator (%r)', produces_decorator) - function = produces_decorator(function) - - for validation_decorator in self.__validation_decorators: - function = validation_decorator(function) - - uri_parsing_decorator = self.__uri_parsing_decorator - logging.debug('... Adding uri parsing decorator (%r)', uri_parsing_decorator) - function = uri_parsing_decorator(function) - - # NOTE: the security decorator should be applied last to check auth before anything else :-) - security_decorator = self.security_decorator - logger.debug('... Adding security decorator (%r)', security_decorator) - function = security_decorator(function) - - if UWSGIMetricsCollector.is_available(): # pragma: no cover - decorator = UWSGIMetricsCollector(self.path, self.method) - function = decorator(function) - - function = self._request_end_lifecycle_decorator(function) - - return function - - @property - def __uri_parsing_decorator(self): - """ - Get uri parsing decorator - - This decorator handles query and path parameter deduplication and - array types. - """ - return self.uri_parser_class(self.parameters) - - @property - def __content_type_decorator(self): - """ - Get produces decorator. - - If the operation mimetype format is json then the function return value is jsonified - - From Swagger Specification: - - **Produces** - - A list of MIME types the operation can produce. This overrides the produces definition at the Swagger Object. - An empty value MAY be used to clear the global definition. - - :rtype: types.FunctionType - """ - - logger.debug('... Produces: %s', self.produces, extra=vars(self)) - - mimetype = self.get_mimetype() - if all_json(self.produces): # endpoint will return json - logger.debug('... Produces json', extra=vars(self)) - # TODO: Refactor this. - return lambda f: f - - elif len(self.produces) == 1: - logger.debug('... Produces %s', mimetype, extra=vars(self)) - decorator = Produces(mimetype) - return decorator - - else: - return BaseSerializer() - - @property - def __validation_decorators(self): - """ - :rtype: types.FunctionType - """ - ParameterValidator = self.validator_map['parameter'] - RequestBodyValidator = self.validator_map['body'] - if self.parameters: - yield ParameterValidator(self.parameters, - self.api, - strict_validation=self.strict_validation) - if self.body_schema: - yield RequestBodyValidator(self.body_schema, self.consumes, self.api, - is_nullable(self.body_definition)) - - @property - def __response_validation_decorator(self): - """ - Get a decorator for validating the generated Response. - :rtype: types.FunctionType - """ - ResponseValidator = self.validator_map['response'] - return ResponseValidator(self, self.get_mimetype()) - - def json_loads(self, data): - """ - A wrapper for calling the API specific JSON loader. - - :param data: The JSON data in textual form. - :type data: bytes - """ - return self.api.json_loads(data) diff --git a/connexion/operations/__init__.py b/connexion/operations/__init__.py new file mode 100644 index 000000000..70080490d --- /dev/null +++ b/connexion/operations/__init__.py @@ -0,0 +1,4 @@ +from .abstract import AbstractOperation # noqa +from .openapi import OpenAPIOperation # noqa +from .swagger2 import Swagger2Operation # noqa +from .secure import SecureOperation # noqa diff --git a/connexion/operations/abstract.py b/connexion/operations/abstract.py new file mode 100644 index 000000000..0eefc2be1 --- /dev/null +++ b/connexion/operations/abstract.py @@ -0,0 +1,433 @@ +import abc +import logging + +import six + +from connexion.operations.secure import SecureOperation + +from ..decorators.metrics import UWSGIMetricsCollector +from ..decorators.parameter import parameter_to_arg +from ..decorators.produces import BaseSerializer, Produces +from ..decorators.response import ResponseValidator +from ..decorators.validation import ParameterValidator, RequestBodyValidator +from ..exceptions import InvalidSpecification +from ..utils import all_json, deep_get, is_nullable + +logger = logging.getLogger('connexion.operations.abstract') + +DEFAULT_MIMETYPE = 'application/json' + +VALIDATOR_MAP = { + 'parameter': ParameterValidator, + 'body': RequestBodyValidator, + 'response': ResponseValidator, +} + + +@six.add_metaclass(abc.ABCMeta) +class AbstractOperation(SecureOperation): + + """ What is an Operation? + An API routes requests to the operation by a (path, method) pair. + The operation uses a resolver to resolve its handler function. + We use the provided spec to do a bunch of heavy lifting before + (and after) we call security_schemes handler. + What heavy lifting? + - on creation: + - validate defaults + - resolve references to components / definitions + - at runtime: + - secure endpoint + - validate inputs + - convert "web inputs" (request bodies, query parameters, etc) into _function inputs_ + - convert "funtion outputs" into _web outputs_ + - validate outputs + This leaves the handler function to implement the business logic, and do away with the + boilerplate. + + An operation needs a way to: + - wrap a handler function + - a security wrapper + + """ + def __init__(self, api, method, path, operation, resolver, + app_security=None, security_schemes=None, + validate_responses=False, strict_validation=False, + randomize_endpoint=None, validator_map=None, + pythonic_params=False, uri_parser_class=None): + """ + """ + self._api = api + self._method = method + self._path = path + self._operation = operation + self._resolver = resolver + self._security = app_security + self._security_schemes = security_schemes + self._validate_responses = validate_responses + self._strict_validation = strict_validation + self._pythonic_params = pythonic_params + self._uri_parser_class = uri_parser_class + self._randomize_endpoint = randomize_endpoint + + self._router_controller = self._operation.get('x-swagger-router-controller') + + self._operation_id = self._operation.get("operationId") + self._resolution = resolver.resolve(self) + self._operation_id = self._resolution.operation_id + + self._validator_map = dict(VALIDATOR_MAP) + self._validator_map.update(validator_map or {}) + + @property + def method(self): + """ + The HTTP method for this operation (ex. GET, POST) + """ + return self._method + + @property + def path(self): + """ + The path of the operation, relative to the API base path + """ + return self._path + + @property + def validator_map(self): + """ + Validators to use for parameter, body, and response validation + """ + return self._validator_map + + @property + def operation_id(self): + """ + The operation id used to indentify the operation internally to the app + """ + return self._operation_id + + @property + def randomize_endpoint(self): + """ + number of random digits to generate and append to the operation_id. + """ + return self._randomize_endpoint + + @property + def router_controller(self): + """ + The router controller to use (python module where handler functions live) + """ + return self._router_controller + + @property + def strict_validation(self): + """ + If True, validate all requests against the spec + """ + return self._strict_validation + + @property + def pythonic_params(self): + """ + """ + return self._pythonic_params + + @property + def validate_responses(self): + """ + """ + return self._validate_responses + + def _get_file_arguments(self, files, arguments, has_kwargs=False): + return {k: v for k, v in files.items() if not has_kwargs and k in arguments} + + @abc.abstractmethod + def _get_val_from_param(self, value, query_defn): + """ + """ + + @abc.abstractmethod + def _get_query_arguments(self, query, arguments, has_kwargs, sanitize): + """ + """ + + def _get_path_arguments(self, path_params, sanitize): + kwargs = {} + path_defns = {p["name"]: p for p in self.parameters if p["in"] == "path"} + for key, value in path_params.items(): + key = sanitize(key) + if key in path_defns: + kwargs[key] = self._get_val_from_param(value, path_defns[key]) + else: # Assume path params mechanism used for injection + kwargs[key] = value + return kwargs + + def _get_body_argument(self, body, arguments, has_kwargs): + body_schema = self.body_schema + if body_schema: + x_body_name = body_schema.get('x-body-name', 'body') + logger.debug('x-body-name is %s' % x_body_name) + if x_body_name in arguments or has_kwargs: + return {x_body_name: body} + return {} + + @abc.abstractproperty + def produces(self): + """ + Content-Types that the operation produces + """ + return [] + + @abc.abstractproperty + def consumes(self): + """ + Content-Types that the operation consumes + """ + return [] + + @abc.abstractproperty + def _spec_definitions(self): + """ + a nested dictionary that is used by _resolve_reference. + It contains the definitions referenced in the spec. + + for example, a spec with "#/components/schemas/Banana" + would have a definitions map that looked like: + {"components": {"schemas": {"Banana": {...}}}} + """ + return {} + + @abc.abstractproperty + def body_schema(self): + """ + The body schema definition for this operation. + """ + + @abc.abstractproperty + def body_definition(self): + """ + The body complete definition for this operation. + + **There can be one "body" parameter at most.** + + :rtype: dict + """ + + @abc.abstractmethod + def get_arguments(self, path_params, query_params, body, files, arguments, + has_kwargs, sanitize): + """ + get arguments for handler function + """ + + @abc.abstractmethod + def response_definition(self, code=None, mimetype=None): + """ + response definition for this endpoint + """ + + @abc.abstractmethod + def response_schema(self, code=None, mimetype=None): + """ + response schema for this endpoint + """ + + @abc.abstractmethod + def example_response(self, code=None, mimetype=None): + """ + Returns an example from the spec + """ + + @abc.abstractmethod + def get_path_parameter_types(self): + """ + Returns the types for parameters in the path + """ + + @abc.abstractmethod + def _validate_defaults(self): + """ + validate the openapi operation defaults using the openapi schema + """ + + @abc.abstractmethod + def _resolve_reference(self, schema): + """ + replaces schema references like "#/components/schemas/MySchema" + with the contents of that reference. + + relies on self._components to be a nested dictionary with the + definitions for all of the components. + + See helper methods _check_references and _retrieve_reference + """ + + def _check_references(self, schema): + """ + Searches the keys and values of a schema object for json references. + If it finds one, it attempts to locate it and will thrown an exception + if the reference can't be found in the definitions dictionary. + + :param schema: The schema object to check + :type schema: dict + :raises InvalidSpecification: raised when a reference isn't found + """ + stack = [schema] + visited = set() + while stack: + schema = stack.pop() + for k, v in schema.items(): + if k == "$ref": + if v in visited: + continue + visited.add(v) + stack.append(self._retrieve_reference(v)) + elif isinstance(v, (list, tuple)): + continue + elif hasattr(v, "items"): + stack.append(v) + + def _retrieve_reference(self, reference): + if not reference.startswith('#/'): + raise InvalidSpecification( + "{method} {path} '$ref' needs to start with '#/'".format( + method=self.method, + path=self.path)) + path = reference[2:].split('/') + try: + definition = deep_get(self._spec_definitions, path) + except KeyError: + raise InvalidSpecification( + "{method} {path} $ref '{reference}' not found".format( + reference=reference, method=self.method, path=self.path)) + + return definition + + def get_mimetype(self): + """ + If the endpoint has no 'produces' then the default is + 'application/json'. + + :rtype str + """ + if all_json(self.produces): + try: + return self.produces[0] + except IndexError: + return DEFAULT_MIMETYPE + elif len(self.produces) == 1: + return self.produces[0] + else: + return DEFAULT_MIMETYPE + + @property + def _uri_parsing_decorator(self): + return self._uri_parser_class(self.parameters) + + @property + def function(self): + """ + Operation function with decorators + + :rtype: types.FunctionType + """ + function = parameter_to_arg(self, self._resolution.function, self.pythonic_params) + function = self._request_begin_lifecycle_decorator(function) + + if self.validate_responses: + logger.debug('... Response validation enabled.') + response_decorator = self.__response_validation_decorator + logger.debug('... Adding response decorator (%r)', response_decorator) + function = response_decorator(function) + + produces_decorator = self.__content_type_decorator + logger.debug('... Adding produces decorator (%r)', produces_decorator) + function = produces_decorator(function) + + for validation_decorator in self.__validation_decorators: + function = validation_decorator(function) + + uri_parsing_decorator = self._uri_parsing_decorator + function = uri_parsing_decorator(function) + + # NOTE: the security decorator should be applied last to check auth before anything else :-) + security_decorator = self.security_decorator + logger.debug('... Adding security decorator (%r)', security_decorator) + function = security_decorator(function) + + if UWSGIMetricsCollector.is_available(): # pragma: no cover + decorator = UWSGIMetricsCollector(self.path, self.method) + function = decorator(function) + + function = self._request_end_lifecycle_decorator(function) + + return function + + @property + def __content_type_decorator(self): + """ + Get produces decorator. + + If the operation mimetype format is json then the function return value is jsonified + + From Swagger Specification: + + **Produces** + + A list of MIME types the operation can produce. This overrides the produces definition at the Swagger Object. + An empty value MAY be used to clear the global definition. + + :rtype: types.FunctionType + """ + + logger.debug('... Produces: %s', self.produces, extra=vars(self)) + + mimetype = self.get_mimetype() + if all_json(self.produces): # endpoint will return json + logger.debug('... Produces json', extra=vars(self)) + # TODO: Refactor this. + return lambda f: f + + elif len(self.produces) == 1: + logger.debug('... Produces %s', mimetype, extra=vars(self)) + decorator = Produces(mimetype) + return decorator + + else: + return BaseSerializer() + + @property + def __validation_decorators(self): + """ + :rtype: types.FunctionType + """ + ParameterValidator = self.validator_map['parameter'] + RequestBodyValidator = self.validator_map['body'] + if self.parameters: + yield ParameterValidator(self.parameters, + self.api, + strict_validation=self.strict_validation) + if self.body_schema: + yield RequestBodyValidator(self.body_schema, self.consumes, self.api, + is_nullable(self.body_definition), + strict_validation=self.strict_validation) + + @property + def __response_validation_decorator(self): + """ + Get a decorator for validating the generated Response. + :rtype: types.FunctionType + """ + ResponseValidator = self.validator_map['response'] + return ResponseValidator(self, self.get_mimetype()) + + def json_loads(self, data): + """ + A wrapper for calling the API specific JSON loader. + + :param data: The JSON data in textual form. + :type data: bytes + """ + return self.api.json_loads(data) diff --git a/connexion/operations/openapi.py b/connexion/operations/openapi.py new file mode 100644 index 000000000..08ff37f8b --- /dev/null +++ b/connexion/operations/openapi.py @@ -0,0 +1,381 @@ +import logging +from copy import deepcopy + +from jsonschema import ValidationError + +from connexion.operations.abstract import AbstractOperation + +from ..decorators.uri_parsing import OpenAPIURIParser +from ..decorators.validation import TypeValidationError, validate_type +from ..exceptions import InvalidSpecification +from ..utils import deep_get, is_null, is_nullable, make_type + +logger = logging.getLogger("connexion.operations.openapi3") + +QUERY_STRING_DELIMITERS = { + 'spaceDelimited': ' ', + 'pipeDelimited': '|', + 'simple': ',', + 'form': ',' +} + + +class OpenAPIOperation(AbstractOperation): + + """ + A single API operation on a path. + """ + + def __init__(self, api, method, path, operation, resolver, path_parameters=None, + app_security=None, components=None, validate_responses=False, + strict_validation=False, randomize_endpoint=None, validator_map=None, + pythonic_params=False, uri_parser_class=None): + """ + This class uses the OperationID identify the module and function that will handle the operation + + From Swagger Specification: + + **OperationID** + + A friendly name for the operation. The id MUST be unique among all operations described in the API. + Tools and libraries MAY use the operation id to uniquely identify an operation. + + :param method: HTTP method + :type method: str + :param path: + :type path: str + :param operation: swagger operation object + :type operation: dict + :param resolver: Callable that maps operationID to a function + :param path_parameters: Parameters defined in the path level + :type path_parameters: list + :param app_security: list of security rules the application uses by default + :type app_security: list + :param components: `Components Object + `_ + :type components: dict + :param validate_responses: True enables validation. Validation errors generate HTTP 500 responses. + :type validate_responses: bool + :param strict_validation: True enables validation on invalid request parameters + :type strict_validation: bool + :param randomize_endpoint: number of random characters to append to operation name + :type randomize_endpoint: integer + :param validator_map: Custom validators for the types "parameter", "body" and "response". + :type validator_map: dict + :param pythonic_params: When True CamelCase parameters are converted to snake_case and an underscore is appended + to any shadowed built-ins + :type pythonic_params: bool + :param uri_parser_class: class to use for uri parseing + :type uri_parser_class: AbstractURIParser + """ + self.components = components or {} + + def component_get(oas3_name): + return self.components.get(oas3_name, {}) + + # operation overrides globals + security_schemes = component_get('securitySchemes') + app_security = operation.get('security', app_security) + uri_parser_class = uri_parser_class or OpenAPIURIParser + + super(OpenAPIOperation, self).__init__( + api=api, + method=method, + path=path, + operation=operation, + resolver=resolver, + app_security=app_security, + security_schemes=security_schemes, + validate_responses=validate_responses, + strict_validation=strict_validation, + randomize_endpoint=randomize_endpoint, + validator_map=validator_map, + pythonic_params=pythonic_params, + uri_parser_class=uri_parser_class + ) + + self._definitions_map = { + 'components': { + 'schemas': component_get('schemas'), + 'requestBodies': component_get('requestBodies'), + 'parameters': component_get('parameters'), + 'securitySchemes': component_get('securitySchemes'), + 'responses': component_get('responses'), + 'headers': component_get('headers'), + } + } + + # todo support definition references + # todo support references to application level parameters + self._request_body = operation.get('requestBody') + if self._request_body: + self._request_body = self._resolve_reference(self._request_body) + + def resolve_parameters(parameters): + return [self._resolve_reference(p) for p in parameters] + + self.parameters = resolve_parameters(operation.get('parameters', [])) + if path_parameters: + self.parameters += resolve_parameters(path_parameters) + + def resolve_responses(responses): + if not responses: + return responses + responses = deepcopy(responses) + for status_code, resp in responses.items(): + # check components/responses + if '$ref' in resp: + ref = self._resolve_reference(resp) + del resp['$ref'] + resp = ref + + content = resp.get("content", {}) + for mimetype, resp in content.items(): + # check components/examples + examples = resp.get("examples", {}) + for _, example in examples.items(): + example = self._resolve_reference(example) + + example = resp.get("example", {}) + ref = self._resolve_reference(example) + if ref: + resp["example"] = ref + + schema = resp.get("schema", {}) + ref = self._resolve_reference(schema) + if ref: + resp["schema"] = ref + + return responses + + self._responses = resolve_responses(operation.get('responses', {})) + + # TODO figure out how to support multiple mimetypes + # NOTE we currently just combine all of the possible mimetypes, + # but we need to refactor to support mimetypes by response code + response_codes = operation.get('responses', {}) + response_content_types = [] + for _, defn in response_codes.items(): + response_content_types += defn.get('content', {}).keys() + self._produces = response_content_types or ['application/json'] + + request_content = operation.get('requestBody', {}).get('content', {}) + self._consumes = list(request_content.keys()) or ['application/json'] + + logger.debug('consumes: %s' % self.consumes) + logger.debug('produces: %s' % self.produces) + + self._validate_defaults() + + @property + def request_body(self): + return self._request_body + + @property + def consumes(self): + return self._consumes + + @property + def produces(self): + return self._produces + + @property + def _spec_definitions(self): + return self._definitions_map + + def _validate_defaults(self): + for param_defn in self.parameters: + try: + param_schema = param_defn["schema"] + if param_defn['in'] == 'query' and 'default' in param_schema: + validate_type(param_defn, param_schema['default'], + 'query', param_defn['name']) + except (TypeValidationError, ValidationError): + raise InvalidSpecification('The parameter \'{param_name}\' has a default value which is not of' + ' type \'{param_type}\''.format(param_name=param_defn['name'], + param_type=param_schema['type'])) + + def _resolve_reference(self, schema): + schema = deepcopy(schema) # avoid changing the original schema + self._check_references(schema) + + # find the object we need to resolve/update if this is not a proper SchemaObject + # e.g a response or parameter object + for obj in schema, schema.get('items'): + reference = obj and obj.get('$ref') # type: str + if reference: + break + if reference: + definition = deepcopy(self._retrieve_reference(reference)) + # Update schema + obj.update(definition) + del obj['$ref'] + + # if the schema includes allOf or oneOf or anyOf + for multi in ['allOf', 'anyOf', 'oneOf']: + upd = [] + for s in schema.get(multi, []): + upd.append(self._resolve_reference(s)) + if upd: + schema[multi] = upd + + # additionalProperties + try: + ap = schema['additionalProperties'] + if ap: + schema['additionalProperties'] = self._resolve_reference(ap) + except KeyError: + pass + + # if there is a schema object on this param or response, then we just + # need to include the defs and it can be validated by jsonschema + if "$ref" in schema.get("schema", {}): + if self.components: + schema['schema']['components'] = self.components + return schema + + return schema + + def response_definition(self, status_code=None, content_type=None): + content_type = content_type or self.get_mimetype() + response_definitions = self._responses + response_definition = response_definitions.get(str(status_code), response_definitions.get("default", {})) + response_definition = self._resolve_reference(response_definition) + return response_definition + + def response_schema(self, status_code=None, content_type=None): + response_definition = self.response_definition(status_code, content_type) + content_definition = response_definition.get("content", response_definition) + content_definition = content_definition.get(content_type, content_definition) + return self._resolve_reference(content_definition.get("schema", {})) + + def example_response(self, code=None, content_type=None): + """ + Returns example response from spec + """ + # simply use the first/lowest status code, this is probably 200 or 201 + try: + code = code or sorted(self._responses.keys())[0] + except IndexError: + code = 200 + + content_type = content_type or self.get_mimetype() + examples_path = [str(code), 'content', content_type, 'examples'] + example_path = [str(code), 'content', content_type, 'example'] + schema_example_path = [str(code), 'content', content_type, 'schema', 'example'] + + try: + code = int(code) + except ValueError: + code = 200 + try: + # TODO also use example header? + return (list(deep_get(self._responses, examples_path).values())[0], code) + except (KeyError, IndexError): + pass + try: + return (deep_get(self._responses, example_path), code) + except KeyError: + pass + try: + return (deep_get(self._responses, schema_example_path), code) + except KeyError: + return (None, code) + + def get_path_parameter_types(self): + types = {} + path_parameters = (p for p in self.parameters if p["in"] == "path") + for path_defn in path_parameters: + path_schema = path_defn["schema"] + if path_schema.get('type') == 'string' and path_schema.get('format') == 'path': + # path is special case for type 'string' + path_type = 'path' + else: + path_type = path_schema.get('type') + types[path_defn['name']] = path_type + return types + + @property + def body_schema(self): + """ + The body schema definition for this operation. + """ + return self._resolve_reference(self.body_definition.get('schema', {})) + + @property + def body_definition(self): + """ + The body complete definition for this operation. + + **There can be one "body" parameter at most.** + + :rtype: dict + """ + if self._request_body: + if len(self.consumes) > 1: + logger.warning( + 'this operation accepts multiple content types, using %s', + self.consumes[0]) + res = self._request_body.get('content', {}).get(self.consumes[0], {}) + return self._resolve_reference(res) + return {} + + def _get_body_argument(self, body, arguments, has_kwargs): + body_schema = self.body_schema + default_body = body_schema.get('default') + body = body or default_body + if body_schema: + x_body_name = body_schema.get('x-body-name', 'body') + logger.debug('x-body-name is %s' % x_body_name) + if x_body_name in arguments or has_kwargs: + return {x_body_name: body} + return {} + + def get_arguments(self, path_params, query_params, body, files, arguments, + has_kwargs, sanitize): + """ + get arguments for handler function + """ + ret = {} + ret.update(self._get_path_arguments(path_params, sanitize)) + ret.update(self._get_query_arguments(query_params, arguments, has_kwargs, sanitize)) + ret.update(self._get_body_argument(body, arguments, has_kwargs)) + ret.update(self._get_file_arguments(files, arguments, has_kwargs)) + return ret + + def _get_query_arguments(self, query, arguments, has_kwargs, sanitize): + query_defns = {sanitize(p["name"]): p + for p in self.parameters + if p["in"] == "query"} + default_query_params = {k: v["schema"]['default'] + for k, v in query_defns.items() + if 'default' in v["schema"]} + query_arguments = deepcopy(default_query_params) + + query_arguments.update(query) + res = {} + for key, value in query_arguments.items(): + key = sanitize(key) + if not has_kwargs and key not in arguments: + logger.debug("Query Parameter '%s' not in function arguments", key) + else: + logger.debug("Query Parameter '%s' in function arguments", key) + try: + query_defn = query_defns[key] + except KeyError: # pragma: no cover + logger.error("Function argument '{}' not defined in specification".format(key)) + else: + logger.debug('%s is a %s', key, query_defn) + res[key] = self._get_val_from_param(value, query_defn) + return res + + def _get_val_from_param(self, value, query_defn): + if is_nullable(query_defn) and is_null(value): + return None + + query_schema = query_defn["schema"] + + if query_schema["type"] == "array": + return [make_type(part, query_schema["items"]["type"]) for part in value] + else: + return make_type(value, query_schema["type"]) diff --git a/connexion/operations/secure.py b/connexion/operations/secure.py new file mode 100644 index 000000000..bdbe8f451 --- /dev/null +++ b/connexion/operations/secure.py @@ -0,0 +1,124 @@ +import functools +import logging + +from ..decorators.decorator import (BeginOfRequestLifecycleDecorator, + EndOfRequestLifecycleDecorator) +from ..decorators.security import (get_tokeninfo_func, get_tokeninfo_url, + security_passthrough, verify_oauth_local, + verify_oauth_remote) + +logger = logging.getLogger("connexion.operations.secure") + +DEFAULT_MIMETYPE = 'application/json' + + +class SecureOperation(object): + + def __init__(self, api, security, security_schemes): + """ + :param security: list of security rules the application uses by default + :type security: list + :param security_definitions: `Security Definitions Object + `_ + :type security_definitions: dict + """ + self._api = api + self._security = security + self._security_schemes = security_schemes + + @property + def api(self): + return self._api + + @property + def security(self): + return self._security + + @property + def security_schemes(self): + return self._security_schemes + + @property + def security_decorator(self): + """ + Gets the security decorator for operation + + From Swagger Specification: + + **Security Definitions Object** + + A declaration of the security schemes available to be used in the specification. + + This does not enforce the security schemes on the operations and only serves to provide the relevant details + for each scheme. + + + **Security Requirement Object** + + Lists the required security schemes to execute this operation. The object can have multiple security schemes + declared in it which are all required (that is, there is a logical AND between the schemes). + + The name used for each property **MUST** correspond to a security scheme declared in the Security Definitions. + + :rtype: types.FunctionType + """ + logger.debug('... Security: %s', self.security, extra=vars(self)) + if self.security: + if len(self.security) > 1: + logger.debug("... More than one security requirement defined. **IGNORING SECURITY REQUIREMENTS**", + extra=vars(self)) + return security_passthrough + + security = self.security[0] # type: dict + # the following line gets the first (and because of the previous condition only) scheme and scopes + # from the operation's security requirements + + scheme_name, scopes = next(iter(security.items())) # type: str, list + security_definition = self.security_schemes[scheme_name] + if security_definition['type'] == 'oauth2': + token_info_url = get_tokeninfo_url(security_definition) + token_info_func = get_tokeninfo_func(security_definition) + scopes = set(scopes) # convert scopes to set because this is needed for verify_oauth_remote + + if token_info_url and token_info_func: + logger.warning("... Both x-tokenInfoUrl and x-tokenInfoFunc are defined, using x-tokenInfoFunc", + extra=vars(self)) + if token_info_func: + return functools.partial(verify_oauth_local, token_info_func, scopes) + if token_info_url: + return functools.partial(verify_oauth_remote, token_info_url, scopes) + else: + logger.warning("... OAuth2 token info URL missing. **IGNORING SECURITY REQUIREMENTS**", + extra=vars(self)) + elif security_definition['type'] in ('apiKey', 'basic'): + logger.debug( + "... Security type '%s' not natively supported by Connexion; you should handle it yourself", + security_definition['type'], extra=vars(self)) + + # if we don't know how to handle the security or it's not defined we will usa a passthrough decorator + return security_passthrough + + def get_mimetype(self): + return DEFAULT_MIMETYPE + + @property + def _request_begin_lifecycle_decorator(self): + """ + Transforms the result of the operation handler in a internal + representation (connexion.lifecycle.ConnexionRequest) to be + used by internal Connexion decorators. + + :rtype: types.FunctionType + """ + return BeginOfRequestLifecycleDecorator(self.api, self.get_mimetype()) + + @property + def _request_end_lifecycle_decorator(self): + """ + Guarantees that instead of the internal representation of the + operation handler response + (connexion.lifecycle.ConnexionRequest) a framework specific + object is returned. + :rtype: types.FunctionType + """ + return EndOfRequestLifecycleDecorator(self.api, self.get_mimetype()) diff --git a/connexion/operations/swagger2.py b/connexion/operations/swagger2.py new file mode 100644 index 000000000..892a37958 --- /dev/null +++ b/connexion/operations/swagger2.py @@ -0,0 +1,348 @@ +import logging +from copy import deepcopy + +from jsonschema import ValidationError + +from connexion.operations.abstract import AbstractOperation + +from ..decorators.uri_parsing import Swagger2URIParser +from ..decorators.validation import TypeValidationError, validate_type +from ..exceptions import InvalidSpecification +from ..utils import deep_get, is_null, is_nullable, make_type + +logger = logging.getLogger("connexion.operations.swagger2") + + +class Swagger2Operation(AbstractOperation): + + def __init__(self, api, method, path, operation, resolver, app_produces, app_consumes, + path_parameters=None, app_security=None, security_definitions=None, + definitions=None, parameter_definitions=None, + response_definitions=None, validate_responses=False, strict_validation=False, + randomize_endpoint=None, validator_map=None, pythonic_params=False, + uri_parser_class=None): + """ + This class uses the OperationID identify the module and function that will handle the operation + + From Swagger Specification: + + **OperationID** + + A friendly name for the operation. The id MUST be unique among all operations described in the API. + Tools and libraries MAY use the operation id to uniquely identify an operation. + + :param method: HTTP method + :type method: str + :param path: + :type path: str + :param operation: swagger operation object + :type operation: dict + :param resolver: Callable that maps operationID to a function + :param app_produces: list of content types the application can return by default + :type app_produces: list + :param app_consumes: list of content types the application consumes by default + :type app_consumes: list + :param path_parameters: Parameters defined in the path level + :type path_parameters: list + :param app_security: list of security rules the application uses by default + :type app_security: list + :param security_definitions: `Security Definitions Object + `_ + :type security_definitions: dict + :param definitions: `Definitions Object + `_ + :type definitions: dict + :param parameter_definitions: Global parameter definitions + :type parameter_definitions: dict + :param response_definitions: Global response definitions + :type response_definitions: dict + :param validator_map: Custom validators for the types "parameter", "body" and "response". + :type validator_map: dict + :param validate_responses: True enables validation. Validation errors generate HTTP 500 responses. + :type validate_responses: bool + :param strict_validation: True enables validation on invalid request parameters + :type strict_validation: bool + :param randomize_endpoint: number of random characters to append to operation name + :type randomize_endpoint: integer + :param pythonic_params: When True CamelCase parameters are converted to snake_case and an underscore is appended + to any shadowed built-ins + :type pythonic_params: bool + :param uri_parser_class: class to use for uri parseing + :type uri_parser_class: AbstractURIParser + """ + app_security = operation.get('security', app_security) + uri_parser_class = uri_parser_class or Swagger2URIParser + + super(Swagger2Operation, self).__init__( + api=api, + method=method, + path=path, + operation=operation, + resolver=resolver, + app_security=app_security, + security_schemes=security_definitions, + validate_responses=validate_responses, + strict_validation=strict_validation, + randomize_endpoint=randomize_endpoint, + validator_map=validator_map, + pythonic_params=pythonic_params, + uri_parser_class=uri_parser_class + ) + + self._produces = operation.get('produces', app_produces) + self._consumes = operation.get('consumes', app_consumes) + + self.definitions = definitions or {} + + self.definitions_map = { + 'definitions': self.definitions, + 'parameters': parameter_definitions, + 'responses': response_definitions + } + + def resolve_parameters(parameters): + return [self._resolve_reference(p) for p in parameters] + + self.parameters = resolve_parameters(operation.get('parameters', [])) + if path_parameters: + self.parameters += resolve_parameters(path_parameters) + + def resolve_responses(responses): + if not responses: + return {} + for status_code, resp in responses.items(): + if not resp: + continue + + # check definitions + if '$ref' in resp: + ref = self._resolve_reference(resp) + del resp['$ref'] + resp = ref + + examples = resp.get("examples", {}) + ref = self._resolve_reference(examples) + if ref: + resp["examples"] = ref + + schema = resp.get("schema", {}) + ref = self._resolve_reference(schema) + if ref: + resp["schema"] = ref + + return responses + + self._responses = resolve_responses(operation.get('responses', {})) + logger.debug(self._responses) + + logger.debug('consumes: %s', self.consumes) + logger.debug('produces: %s', self.produces) + + self._validate_defaults() + + @property + def _spec_definitions(self): + return self.definitions_map + + @property + def consumes(self): + return self._consumes + + @property + def produces(self): + return self._produces + + def _validate_defaults(self): + for param_defn in self.parameters: + try: + if param_defn['in'] == 'query' and 'default' in param_defn: + validate_type(param_defn, param_defn['default'], + 'query', param_defn['name']) + except (TypeValidationError, ValidationError): + raise InvalidSpecification('The parameter \'{param_name}\' has a default value which is not of' + ' type \'{param_type}\''.format(param_name=param_defn['name'], + param_type=param_defn['type'])) + + def get_path_parameter_types(self): + types = {} + path_parameters = (p for p in self.parameters if p["in"] == "path") + for path_defn in path_parameters: + if path_defn.get('type') == 'string' and path_defn.get('format') == 'path': + # path is special case for type 'string' + path_type = 'path' + else: + path_type = path_defn.get('type') + types[path_defn['name']] = path_type + return types + + def _resolve_reference(self, schema): + schema = deepcopy(schema) # avoid changing the original schema + self._check_references(schema) + + # find the object we need to resolve/update if this is not a proper SchemaObject + # e.g a response or parameter object + for obj in schema, schema.get('items'): + reference = obj and obj.get('$ref') # type: str + if reference: + break + if reference: + definition = deepcopy(self._retrieve_reference(reference)) + # Update schema + obj.update(definition) + del obj['$ref'] + + # if there is a schema object on this param or response, then we just + # need to include the defs and it can be validated by jsonschema + if "schema" in schema: + schema['schema']['definitions'] = self.definitions + + return schema + + def response_definition(self, status_code=None, content_type=None): + content_type = content_type or self.get_mimetype() + response_definitions = self._responses + response_definition = response_definitions.get(str(status_code), response_definitions.get("default", {})) + response_definition = self._resolve_reference(response_definition) + return response_definition + + def response_schema(self, status_code=None, content_type=None): + response_definition = self.response_definition(status_code, content_type) + return self._resolve_reference(response_definition.get("schema", {})) + + def example_response(self, code=None, *args, **kwargs): + """ + Returns example response from spec + """ + # simply use the first/lowest status code, this is probably 200 or 201 + try: + code = code or sorted(self._responses.keys())[0] + except IndexError: + code = 200 + examples_path = [str(code), 'examples'] + schema_example_path = [str(code), 'schema', 'example'] + try: + code = int(code) + except ValueError: + code = 200 + try: + return (list(deep_get(self._responses, examples_path).values())[0], code) + except KeyError: + pass + try: + return (deep_get(self._responses, schema_example_path), code) + except KeyError: + return (None, code) + + @property + def body_schema(self): + """ + The body schema definition for this operation. + """ + return self._resolve_reference(self.body_definition.get('schema', {})) + + @property + def body_definition(self): + """ + The body complete definition for this operation. + + **There can be one "body" parameter at most.** + + :rtype: dict + """ + body_parameters = [p for p in self.parameters if p['in'] == 'body'] + if len(body_parameters) > 1: + raise InvalidSpecification( + "{method} {path} There can be one 'body' parameter at most".format( + method=self.method, + path=self.path)) + return body_parameters[0] if body_parameters else {} + + def get_arguments(self, path_params, query_params, body, files, arguments, + has_kwargs, sanitize): + """ + get arguments for handler function + """ + ret = {} + ret.update(self._get_path_arguments(path_params, sanitize)) + ret.update(self._get_query_arguments(query_params, arguments, has_kwargs, sanitize)) + ret.update(self._get_body_argument(body, arguments, has_kwargs, sanitize)) + ret.update(self._get_file_arguments(files, arguments, has_kwargs)) + return ret + + def _get_query_arguments(self, query, arguments, has_kwargs, sanitize): + query_defns = {sanitize(p["name"]): p + for p in self.parameters + if p["in"] == "query"} + default_query_params = {k: v['default'] + for k, v in query_defns.items() + if 'default' in v} + query_arguments = deepcopy(default_query_params) + + query_arguments.update(query) + res = {} + for key, value in query_arguments.items(): + key = sanitize(key) + if not has_kwargs and key not in arguments: + logger.debug("Query Parameter '%s' not in function arguments", key) + else: + logger.debug("Query Parameter '%s' in function arguments", key) + try: + query_defn = query_defns[key] + except KeyError: # pragma: no cover + logger.error("Function argument '{}' not defined in specification".format(key)) + else: + logger.debug('%s is a %s', key, query_defn) + res[key] = self._get_val_from_param(value, query_defn) + return res + + def _get_body_argument(self, body, arguments, has_kwargs, sanitize): + kwargs = {} + body_parameters = [p for p in self.parameters if p['in'] == 'body'] or [{}] + default_body = body_parameters[0].get('schema', {}).get('default') + body_name = sanitize(body_parameters[0].get('name')) + + body = body or default_body + + form_defns = {sanitize(p['name']): p + for p in self.parameters + if p['in'] == 'formData'} + + default_form_params = {sanitize(p['name']): p['default'] + for p in form_defns + if 'default' in p} + + # Add body parameters + if body_name: + if not has_kwargs and body_name not in arguments: + logger.debug("Body parameter '%s' not in function arguments", body_name) + else: + logger.debug("Body parameter '%s' in function arguments", body_name) + kwargs[body_name] = body + + # Add formData parameters + form_arguments = deepcopy(default_form_params) + if form_defns and body: + form_arguments.update(body) + for key, value in form_arguments.items(): + if not has_kwargs and key not in arguments: + logger.debug("FormData parameter '%s' not in function arguments", key) + else: + logger.debug("FormData parameter '%s' in function arguments", key) + try: + form_defn = form_defns[key] + except KeyError: # pragma: no cover + logger.error("Function argument '{}' not defined in specification".format(key)) + else: + kwargs[key] = self._get_val_from_param(value, form_defn) + return kwargs + + def _get_val_from_param(self, value, query_defn): + if is_nullable(query_defn) and is_null(value): + return None + + query_schema = query_defn + + if query_schema["type"] == "array": + return [make_type(part, query_defn["items"]["type"]) for part in value] + else: + return make_type(value, query_defn["type"]) diff --git a/connexion/options.py b/connexion/options.py index 77cb32166..32c2ba000 100644 --- a/connexion/options.py +++ b/connexion/options.py @@ -1,13 +1,40 @@ +import logging import pathlib from typing import Optional # NOQA +try: + from swagger_ui_bundle import (swagger_ui_2_path, + swagger_ui_3_path) +except ImportError: + swagger_ui_2_path = swagger_ui_3_path = None + +try: + from swagger_ui_bundle import swagger_ui_2_path + INTERNAL_CONSOLE_UI_PATH = swagger_ui_2_path +except ImportError: + INTERNAL_CONSOLE_UI_PATH = None + MODULE_PATH = pathlib.Path(__file__).absolute().parent -INTERNAL_CONSOLE_UI_PATH = MODULE_PATH / 'vendor' / 'swagger-ui' +NO_UI_MSG = """The swagger_ui directory could not be found. + Please install connexion with extra install: pip install connexion[swagger-ui] + or provide the path to your local installation by passing swagger_path= +""" + +logger = logging.getLogger("connexion.options") class ConnexionOptions(object): - def __init__(self, options=None): + + def __init__(self, options=None, oas_version=(2,)): self._options = {} + self.oas_version = oas_version + if self.oas_version >= (3, 0, 0): + self.openapi_spec_name = '/openapi.json' + self.swagger_ui_local_path = swagger_ui_3_path + else: + self.openapi_spec_name = '/swagger.json' + self.swagger_ui_local_path = swagger_ui_2_path + if options: self._options.update(filter_values(options)) @@ -22,7 +49,7 @@ def extend(self, new_values=None): options = dict(self._options) options.update(filter_values(new_values)) - return ConnexionOptions(options) + return ConnexionOptions(options, self.oas_version) def as_dict(self): return self._options @@ -32,11 +59,10 @@ def openapi_spec_available(self): # type: () -> bool """ Whether to make available the OpenAPI Specification under - `openapi_console_ui_path`/swagger.json path. + `openapi_spec_path`. Default: True """ - # NOTE: Under OpenAPI v3 this should change to "/openapi.json" return self._options.get('swagger_json', True) @property @@ -50,8 +76,22 @@ def openapi_console_ui_available(self): Default: True """ + if (self._options.get('swagger_ui', True) and + self.openapi_console_ui_from_dir is None): + logger.warning(NO_UI_MSG) + return False return self._options.get('swagger_ui', True) + @property + def openapi_spec_path(self): + # type: () -> str + """ + Path to mount the OpenAPI Console UI and make it accessible via a browser. + + Default: /openapi.json for openapi3, otherwise /swagger.json + """ + return self._options.get('openapi_spec_path', self.openapi_spec_name) + @property def openapi_console_ui_path(self): # type: () -> str @@ -71,11 +111,11 @@ def openapi_console_ui_from_dir(self): Default: Connexion's vendored version of the OpenAPI Console UI. """ - return self._options.get('swagger_path', INTERNAL_CONSOLE_UI_PATH) + return self._options.get('swagger_path', self.swagger_ui_local_path) @property def uri_parser_class(self): - # type: () -> str + # type: () -> AbstractURIParser """ The class to use for parsing URIs into path and query parameters. Default: None diff --git a/connexion/resolver.py b/connexion/resolver.py index eacabafec..5fe1434f5 100644 --- a/connexion/resolver.py +++ b/connexion/resolver.py @@ -34,7 +34,7 @@ def resolve(self, operation): """ Default operation resolver - :type operation: connexion.operation.Operation + :type operation: connexion.operations.AbstractOperation """ operation_id = self.resolve_operation_id(operation) return Resolution(self.resolve_function_from_operation_id(operation_id), operation_id) @@ -43,14 +43,13 @@ def resolve_operation_id(self, operation): """ Default operationId resolver - :type operation: connexion.operation.Operation + :type operation: connexion.operations.AbstractOperation """ - spec = operation.operation - operation_id = spec.get('operationId', '') - x_router_controller = spec.get('x-swagger-router-controller') - if x_router_controller is None: + operation_id = operation.operation_id + router_controller = operation.router_controller + if operation.router_controller is None: return operation_id - return '{}.{}'.format(x_router_controller, operation_id) + return '{}.{}'.format(router_controller, operation_id) def resolve_function_from_operation_id(self, operation_id): """ @@ -85,9 +84,9 @@ def resolve_operation_id(self, operation): """ Resolves the operationId using REST semantics unless explicitly configured in the spec - :type operation: connexion.operation.Operation + :type operation: connexion.operations.AbstractOperation """ - if operation.operation.get('operationId'): + if operation.operation_id: return Resolver.resolve_operation_id(self, operation) return self.resolve_operation_id_using_rest_semantics(operation) @@ -96,14 +95,14 @@ def resolve_operation_id_using_rest_semantics(self, operation): """ Resolves the operationId using REST semantics - :type operation: connexion.operation.Operation + :type operation: connexion.operations.AbstractOperation """ path_match = re.search( '^/?(?P([\w\-](?/*)(?P.*)$', operation.path ) def get_controller_name(): - x_router_controller = operation.operation.get('x-swagger-router-controller') + x_router_controller = operation.router_controller name = self.default_module_name resource_name = path_match.group('resource_name') diff --git a/connexion/utils.py b/connexion/utils.py index 9190710e9..8b4c71f01 100644 --- a/connexion/utils.py +++ b/connexion/utils.py @@ -3,6 +3,48 @@ import six +# Python 2/3 compatibility: +try: + py_string = unicode +except NameError: # pragma: no cover + py_string = str # pragma: no cover + + +def boolean(s): + ''' + Convert JSON/Swagger boolean value to Python, raise ValueError otherwise + + >>> boolean('true') + True + + >>> boolean('false') + False + ''' + if isinstance(s, bool): + return s + elif not hasattr(s, 'lower'): + raise ValueError('Invalid boolean value') + elif s.lower() == 'true': + return True + elif s.lower() == 'false': + return False + else: + raise ValueError('Invalid boolean value') + + +# https://github.com/swagger-api/swagger-spec/blob/master/versions/2.0.md#data-types +TYPE_MAP = {'integer': int, + 'number': float, + 'string': py_string, + 'boolean': boolean, + 'array': list, + 'object': dict} # map of swagger types to python types + + +def make_type(value, type): + type_func = TYPE_MAP[type] # convert value to right type + return type_func(value) + def deep_getattr(obj, attr): """ @@ -13,6 +55,15 @@ def deep_getattr(obj, attr): return functools.reduce(getattr, attr.split('.'), obj) +def deep_get(obj, keys): + """ + Recurses through a nested object get a leaf value. + """ + if not keys: + return obj + return deep_get(obj[keys[0]], keys[1:]) + + def get_function_from_name(function_name): """ Tries to get function by fully qualified name (e.g. "mymodule.myobj.myfunc") @@ -85,30 +136,12 @@ def all_json(mimetypes): return all(is_json_mimetype(mimetype) for mimetype in mimetypes) -def boolean(s): - ''' - Convert JSON/Swagger boolean value to Python, raise ValueError otherwise - - >>> boolean('true') - True - - >>> boolean('false') - False - ''' - if isinstance(s, bool): - return s - elif not hasattr(s, 'lower'): - raise ValueError('Invalid boolean value') - elif s.lower() == 'true': - return True - elif s.lower() == 'false': - return False - else: - raise ValueError('Invalid boolean value') - - def is_nullable(param_def): - return param_def.get('x-nullable', False) + # XXX DGK - masks oas3/swagger2 differences + return ( + param_def.get("schema", param_def).get('nullable', False) or + param_def.get('x-nullable', False) # swagger2 + ) def is_null(value): diff --git a/connexion/vendor/swagger-ui/css/print.css b/connexion/vendor/swagger-ui/css/print.css deleted file mode 100644 index f9cb0439f..000000000 --- a/connexion/vendor/swagger-ui/css/print.css +++ /dev/null @@ -1,1367 +0,0 @@ -/* Original style from softwaremaniacs.org (c) Ivan Sagalaev */ -.swagger-section pre code { - display: block; - padding: 0.5em; - background: #F0F0F0; -} -.swagger-section pre code, -.swagger-section pre .subst, -.swagger-section pre .tag .title, -.swagger-section pre .lisp .title, -.swagger-section pre .clojure .built_in, -.swagger-section pre .nginx .title { - color: black; -} -.swagger-section pre .string, -.swagger-section pre .title, -.swagger-section pre .constant, -.swagger-section pre .parent, -.swagger-section pre .tag .value, -.swagger-section pre .rules .value, -.swagger-section pre .rules .value .number, -.swagger-section pre .preprocessor, -.swagger-section pre .ruby .symbol, -.swagger-section pre .ruby .symbol .string, -.swagger-section pre .aggregate, -.swagger-section pre .template_tag, -.swagger-section pre .django .variable, -.swagger-section pre .smalltalk .class, -.swagger-section pre .addition, -.swagger-section pre .flow, -.swagger-section pre .stream, -.swagger-section pre .bash .variable, -.swagger-section pre .apache .tag, -.swagger-section pre .apache .cbracket, -.swagger-section pre .tex .command, -.swagger-section pre .tex .special, -.swagger-section pre .erlang_repl .function_or_atom, -.swagger-section pre .markdown .header { - color: #800; -} -.swagger-section pre .comment, -.swagger-section pre .annotation, -.swagger-section pre .template_comment, -.swagger-section pre .diff .header, -.swagger-section pre .chunk, -.swagger-section pre .markdown .blockquote { - color: #888; -} -.swagger-section pre .number, -.swagger-section pre .date, -.swagger-section pre .regexp, -.swagger-section pre .literal, -.swagger-section pre .smalltalk .symbol, -.swagger-section pre .smalltalk .char, -.swagger-section pre .go .constant, -.swagger-section pre .change, -.swagger-section pre .markdown .bullet, -.swagger-section pre .markdown .link_url { - color: #080; -} -.swagger-section pre .label, -.swagger-section pre .javadoc, -.swagger-section pre .ruby .string, -.swagger-section pre .decorator, -.swagger-section pre .filter .argument, -.swagger-section pre .localvars, -.swagger-section pre .array, -.swagger-section pre .attr_selector, -.swagger-section pre .important, -.swagger-section pre .pseudo, -.swagger-section pre .pi, -.swagger-section pre .doctype, -.swagger-section pre .deletion, -.swagger-section pre .envvar, -.swagger-section pre .shebang, -.swagger-section pre .apache .sqbracket, -.swagger-section pre .nginx .built_in, -.swagger-section pre .tex .formula, -.swagger-section pre .erlang_repl .reserved, -.swagger-section pre .prompt, -.swagger-section pre .markdown .link_label, -.swagger-section pre .vhdl .attribute, -.swagger-section pre .clojure .attribute, -.swagger-section pre .coffeescript .property { - color: #88F; -} -.swagger-section pre .keyword, -.swagger-section pre .id, -.swagger-section pre .phpdoc, -.swagger-section pre .title, -.swagger-section pre .built_in, -.swagger-section pre .aggregate, -.swagger-section pre .css .tag, -.swagger-section pre .javadoctag, -.swagger-section pre .phpdoc, -.swagger-section pre .yardoctag, -.swagger-section pre .smalltalk .class, -.swagger-section pre .winutils, -.swagger-section pre .bash .variable, -.swagger-section pre .apache .tag, -.swagger-section pre .go .typename, -.swagger-section pre .tex .command, -.swagger-section pre .markdown .strong, -.swagger-section pre .request, -.swagger-section pre .status { - font-weight: bold; -} -.swagger-section pre .markdown .emphasis { - font-style: italic; -} -.swagger-section pre .nginx .built_in { - font-weight: normal; -} -.swagger-section pre .coffeescript .javascript, -.swagger-section pre .javascript .xml, -.swagger-section pre .tex .formula, -.swagger-section pre .xml .javascript, -.swagger-section pre .xml .vbscript, -.swagger-section pre .xml .css, -.swagger-section pre .xml .cdata { - opacity: 0.5; -} -.swagger-section .hljs { - display: block; - overflow-x: auto; - padding: 0.5em; - background: #F0F0F0; -} -.swagger-section .hljs, -.swagger-section .hljs-subst { - color: #444; -} -.swagger-section .hljs-keyword, -.swagger-section .hljs-attribute, -.swagger-section .hljs-selector-tag, -.swagger-section .hljs-meta-keyword, -.swagger-section .hljs-doctag, -.swagger-section .hljs-name { - font-weight: bold; -} -.swagger-section .hljs-built_in, -.swagger-section .hljs-literal, -.swagger-section .hljs-bullet, -.swagger-section .hljs-code, -.swagger-section .hljs-addition { - color: #1F811F; -} -.swagger-section .hljs-regexp, -.swagger-section .hljs-symbol, -.swagger-section .hljs-variable, -.swagger-section .hljs-template-variable, -.swagger-section .hljs-link, -.swagger-section .hljs-selector-attr, -.swagger-section .hljs-selector-pseudo { - color: #BC6060; -} -.swagger-section .hljs-type, -.swagger-section .hljs-string, -.swagger-section .hljs-number, -.swagger-section .hljs-selector-id, -.swagger-section .hljs-selector-class, -.swagger-section .hljs-quote, -.swagger-section .hljs-template-tag, -.swagger-section .hljs-deletion { - color: #880000; -} -.swagger-section .hljs-title, -.swagger-section .hljs-section { - color: #880000; - font-weight: bold; -} -.swagger-section .hljs-comment { - color: #888888; -} -.swagger-section .hljs-meta { - color: #2B6EA1; -} -.swagger-section .hljs-emphasis { - font-style: italic; -} -.swagger-section .hljs-strong { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap { - line-height: 1; - font-family: "Droid Sans", sans-serif; - min-width: 760px; - max-width: 960px; - margin-left: auto; - margin-right: auto; - /* JSONEditor specific styling */ -} -.swagger-section .swagger-ui-wrap b, -.swagger-section .swagger-ui-wrap strong { - font-family: "Droid Sans", sans-serif; - font-weight: bold; -} -.swagger-section .swagger-ui-wrap q, -.swagger-section .swagger-ui-wrap blockquote { - quotes: none; -} -.swagger-section .swagger-ui-wrap p { - line-height: 1.4em; - padding: 0 0 10px; - color: #333333; -} -.swagger-section .swagger-ui-wrap q:before, -.swagger-section .swagger-ui-wrap q:after, -.swagger-section .swagger-ui-wrap blockquote:before, -.swagger-section .swagger-ui-wrap blockquote:after { - content: none; -} -.swagger-section .swagger-ui-wrap .heading_with_menu h1, -.swagger-section .swagger-ui-wrap .heading_with_menu h2, -.swagger-section .swagger-ui-wrap .heading_with_menu h3, -.swagger-section .swagger-ui-wrap .heading_with_menu h4, -.swagger-section .swagger-ui-wrap .heading_with_menu h5, -.swagger-section .swagger-ui-wrap .heading_with_menu h6 { - display: block; - clear: none; - float: left; - -moz-box-sizing: border-box; - -webkit-box-sizing: border-box; - -ms-box-sizing: border-box; - box-sizing: border-box; - width: 60%; -} -.swagger-section .swagger-ui-wrap table { - border-collapse: collapse; - border-spacing: 0; -} -.swagger-section .swagger-ui-wrap table thead tr th { - padding: 5px; - font-size: 0.9em; - color: #666666; - border-bottom: 1px solid #999999; -} -.swagger-section .swagger-ui-wrap table tbody tr:last-child td { - border-bottom: none; -} -.swagger-section .swagger-ui-wrap table tbody tr.offset { - background-color: #f0f0f0; -} -.swagger-section .swagger-ui-wrap table tbody tr td { - padding: 6px; - font-size: 0.9em; - border-bottom: 1px solid #cccccc; - vertical-align: top; - line-height: 1.3em; -} -.swagger-section .swagger-ui-wrap ol { - margin: 0px 0 10px; - padding: 0 0 0 18px; - list-style-type: decimal; -} -.swagger-section .swagger-ui-wrap ol li { - padding: 5px 0px; - font-size: 0.9em; - color: #333333; -} -.swagger-section .swagger-ui-wrap ol, -.swagger-section .swagger-ui-wrap ul { - list-style: none; -} -.swagger-section .swagger-ui-wrap h1 a, -.swagger-section .swagger-ui-wrap h2 a, -.swagger-section .swagger-ui-wrap h3 a, -.swagger-section .swagger-ui-wrap h4 a, -.swagger-section .swagger-ui-wrap h5 a, -.swagger-section .swagger-ui-wrap h6 a { - text-decoration: none; -} -.swagger-section .swagger-ui-wrap h1 a:hover, -.swagger-section .swagger-ui-wrap h2 a:hover, -.swagger-section .swagger-ui-wrap h3 a:hover, -.swagger-section .swagger-ui-wrap h4 a:hover, -.swagger-section .swagger-ui-wrap h5 a:hover, -.swagger-section .swagger-ui-wrap h6 a:hover { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap h1 span.divider, -.swagger-section .swagger-ui-wrap h2 span.divider, -.swagger-section .swagger-ui-wrap h3 span.divider, -.swagger-section .swagger-ui-wrap h4 span.divider, -.swagger-section .swagger-ui-wrap h5 span.divider, -.swagger-section .swagger-ui-wrap h6 span.divider { - color: #aaaaaa; -} -.swagger-section .swagger-ui-wrap a { - color: #547f00; -} -.swagger-section .swagger-ui-wrap a img { - border: none; -} -.swagger-section .swagger-ui-wrap article, -.swagger-section .swagger-ui-wrap aside, -.swagger-section .swagger-ui-wrap details, -.swagger-section .swagger-ui-wrap figcaption, -.swagger-section .swagger-ui-wrap figure, -.swagger-section .swagger-ui-wrap footer, -.swagger-section .swagger-ui-wrap header, -.swagger-section .swagger-ui-wrap hgroup, -.swagger-section .swagger-ui-wrap menu, -.swagger-section .swagger-ui-wrap nav, -.swagger-section .swagger-ui-wrap section, -.swagger-section .swagger-ui-wrap summary { - display: block; -} -.swagger-section .swagger-ui-wrap pre { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - background-color: #fcf6db; - border: 1px solid #e5e0c6; - padding: 10px; -} -.swagger-section .swagger-ui-wrap pre code { - line-height: 1.6em; - background: none; -} -.swagger-section .swagger-ui-wrap .content > .content-type > div > label { - clear: both; - display: block; - color: #0F6AB4; - font-size: 1.1em; - margin: 0; - padding: 15px 0 5px; -} -.swagger-section .swagger-ui-wrap .content pre { - font-size: 12px; - margin-top: 5px; - padding: 5px; -} -.swagger-section .swagger-ui-wrap .icon-btn { - cursor: pointer; -} -.swagger-section .swagger-ui-wrap .info_title { - padding-bottom: 10px; - font-weight: bold; - font-size: 25px; -} -.swagger-section .swagger-ui-wrap .footer { - margin-top: 20px; -} -.swagger-section .swagger-ui-wrap p.big, -.swagger-section .swagger-ui-wrap div.big p { - font-size: 1em; - margin-bottom: 10px; -} -.swagger-section .swagger-ui-wrap form.fullwidth ol li.string input, -.swagger-section .swagger-ui-wrap form.fullwidth ol li.url input, -.swagger-section .swagger-ui-wrap form.fullwidth ol li.text textarea, -.swagger-section .swagger-ui-wrap form.fullwidth ol li.numeric input { - width: 500px !important; -} -.swagger-section .swagger-ui-wrap .info_license { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_tos { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .message-fail { - color: #cc0000; -} -.swagger-section .swagger-ui-wrap .info_url { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_email { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_name { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_description { - padding-bottom: 10px; - font-size: 15px; -} -.swagger-section .swagger-ui-wrap .markdown ol li, -.swagger-section .swagger-ui-wrap .markdown ul li { - padding: 3px 0px; - line-height: 1.4em; - color: #333333; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.string input, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.url input, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.numeric input { - display: block; - padding: 4px; - width: auto; - clear: both; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.string input.title, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.url input.title, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.numeric input.title { - font-size: 1.3em; -} -.swagger-section .swagger-ui-wrap table.fullwidth { - width: 100%; -} -.swagger-section .swagger-ui-wrap .model-signature { - font-family: "Droid Sans", sans-serif; - font-size: 1em; - line-height: 1.5em; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-nav a { - text-decoration: none; - color: #AAA; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-nav a:hover { - text-decoration: underline; - color: black; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-nav .selected { - color: black; - text-decoration: none; -} -.swagger-section .swagger-ui-wrap .model-signature .propType { - color: #5555aa; -} -.swagger-section .swagger-ui-wrap .model-signature pre:hover { - background-color: #ffffdd; -} -.swagger-section .swagger-ui-wrap .model-signature pre { - font-size: .85em; - line-height: 1.2em; - overflow: auto; - max-height: 200px; - cursor: pointer; -} -.swagger-section .swagger-ui-wrap .model-signature ul.signature-nav { - display: block; - min-width: 230px; - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap .model-signature ul.signature-nav li:last-child { - padding-right: 0; - border-right: none; -} -.swagger-section .swagger-ui-wrap .model-signature ul.signature-nav li { - float: left; - margin: 0 5px 5px 0; - padding: 2px 5px 2px 0; - border-right: 1px solid #ddd; -} -.swagger-section .swagger-ui-wrap .model-signature .propOpt { - color: #555; -} -.swagger-section .swagger-ui-wrap .model-signature .snippet small { - font-size: 0.75em; -} -.swagger-section .swagger-ui-wrap .model-signature .propOptKey { - font-style: italic; -} -.swagger-section .swagger-ui-wrap .model-signature .description .strong { - font-weight: bold; - color: #000; - font-size: .9em; -} -.swagger-section .swagger-ui-wrap .model-signature .description div { - font-size: 0.9em; - line-height: 1.5em; - margin-left: 1em; -} -.swagger-section .swagger-ui-wrap .model-signature .description .stronger { - font-weight: bold; - color: #000; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propWrap .optionsWrapper { - border-spacing: 0; - position: absolute; - background-color: #ffffff; - border: 1px solid #bbbbbb; - display: none; - font-size: 11px; - max-width: 400px; - line-height: 30px; - color: black; - padding: 5px; - margin-left: 10px; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propWrap .optionsWrapper th { - text-align: center; - background-color: #eeeeee; - border: 1px solid #bbbbbb; - font-size: 11px; - color: #666666; - font-weight: bold; - padding: 5px; - line-height: 15px; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propWrap .optionsWrapper .optionName { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propDesc.markdown > p:first-child, -.swagger-section .swagger-ui-wrap .model-signature .description .propDesc.markdown > p:last-child { - display: inline; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propDesc.markdown > p:not(:first-child):before { - display: block; - content: ''; -} -.swagger-section .swagger-ui-wrap .model-signature .description span:last-of-type.propDesc.markdown > p:only-child { - margin-right: -3px; -} -.swagger-section .swagger-ui-wrap .model-signature .propName { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-container { - clear: both; -} -.swagger-section .swagger-ui-wrap .body-textarea { - width: 300px; - height: 100px; - border: 1px solid #aaa; -} -.swagger-section .swagger-ui-wrap .markdown p code, -.swagger-section .swagger-ui-wrap .markdown li code { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - background-color: #f0f0f0; - color: black; - padding: 1px 3px; -} -.swagger-section .swagger-ui-wrap .required { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .editor_holder { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap .editor_holder label { - font-weight: normal!important; - /* JSONEditor uses bold by default for all labels, we revert that back to normal to not give the impression that by default fields are required */ -} -.swagger-section .swagger-ui-wrap .editor_holder label.required { - font-weight: bold!important; -} -.swagger-section .swagger-ui-wrap input.parameter { - width: 300px; - border: 1px solid #aaa; -} -.swagger-section .swagger-ui-wrap h1 { - color: black; - font-size: 1.5em; - line-height: 1.3em; - padding: 10px 0 10px 0; - font-family: "Droid Sans", sans-serif; - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .heading_with_menu { - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap .heading_with_menu ul { - display: block; - clear: none; - float: right; - -moz-box-sizing: border-box; - -webkit-box-sizing: border-box; - -ms-box-sizing: border-box; - box-sizing: border-box; - margin-top: 10px; -} -.swagger-section .swagger-ui-wrap h2 { - color: black; - font-size: 1.3em; - padding: 10px 0 10px 0; -} -.swagger-section .swagger-ui-wrap h2 a { - color: black; -} -.swagger-section .swagger-ui-wrap h2 span.sub { - font-size: 0.7em; - color: #999999; - font-style: italic; -} -.swagger-section .swagger-ui-wrap h2 span.sub a { - color: #777777; -} -.swagger-section .swagger-ui-wrap span.weak { - color: #666666; -} -.swagger-section .swagger-ui-wrap .message-success { - color: #89BF04; -} -.swagger-section .swagger-ui-wrap caption, -.swagger-section .swagger-ui-wrap th, -.swagger-section .swagger-ui-wrap td { - text-align: left; - font-weight: normal; - vertical-align: middle; -} -.swagger-section .swagger-ui-wrap .code { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.text textarea { - font-family: "Droid Sans", sans-serif; - height: 250px; - padding: 4px; - display: block; - clear: both; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.select select { - display: block; - clear: both; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.boolean { - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.boolean label { - display: block; - float: left; - clear: none; - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.boolean input { - display: block; - float: left; - clear: none; - margin: 0 5px 0 0; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.required label { - color: black; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li label { - display: block; - clear: both; - width: auto; - padding: 0 0 3px; - color: #666666; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li label abbr { - padding-left: 3px; - color: #888888; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li p.inline-hints { - margin-left: 0; - font-style: italic; - font-size: 0.9em; - margin: 0; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.buttons { - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap span.blank, -.swagger-section .swagger-ui-wrap span.empty { - color: #888888; - font-style: italic; -} -.swagger-section .swagger-ui-wrap .markdown h3 { - color: #547f00; -} -.swagger-section .swagger-ui-wrap .markdown h4 { - color: #666666; -} -.swagger-section .swagger-ui-wrap .markdown pre { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - background-color: #fcf6db; - border: 1px solid #e5e0c6; - padding: 10px; - margin: 0 0 10px 0; -} -.swagger-section .swagger-ui-wrap .markdown pre code { - line-height: 1.6em; - overflow: auto; -} -.swagger-section .swagger-ui-wrap div.gist { - margin: 20px 0 25px 0 !important; -} -.swagger-section .swagger-ui-wrap ul#resources { - font-family: "Droid Sans", sans-serif; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource { - border-bottom: 1px solid #dddddd; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource:hover div.heading h2 a, -.swagger-section .swagger-ui-wrap ul#resources li.resource.active div.heading h2 a { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource:hover div.heading ul.options li a, -.swagger-section .swagger-ui-wrap ul#resources li.resource.active div.heading ul.options li a { - color: #555555; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource:last-child { - border-bottom: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading { - border: 1px solid transparent; - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options { - overflow: hidden; - padding: 0; - display: block; - clear: none; - float: right; - margin: 14px 10px 0 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li { - float: left; - clear: none; - margin: 0; - padding: 2px 10px; - border-right: 1px solid #dddddd; - color: #666666; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a { - color: #aaaaaa; - text-decoration: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a:hover { - text-decoration: underline; - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a:hover, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a:active, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a.active { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li.last { - padding-right: 0; - border-right: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 { - color: #999999; - padding-left: 0; - display: block; - clear: none; - float: left; - font-family: "Droid Sans", sans-serif; - font-weight: bold; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 a { - color: #999999; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 a:hover { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation { - float: none; - clear: both; - overflow: hidden; - display: block; - margin: 0 0 10px; - padding: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading { - float: none; - clear: both; - overflow: hidden; - display: block; - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 { - display: block; - clear: none; - float: left; - width: auto; - margin: 0; - padding: 0; - line-height: 1.1em; - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path { - padding-left: 10px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path a { - color: black; - text-decoration: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path a.toggleOperation.deprecated { - text-decoration: line-through; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path a:hover { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.http_method a { - text-transform: uppercase; - text-decoration: none; - color: white; - display: inline-block; - width: 50px; - font-size: 0.7em; - text-align: center; - padding: 7px 0 4px; - -moz-border-radius: 2px; - -webkit-border-radius: 2px; - -o-border-radius: 2px; - -ms-border-radius: 2px; - -khtml-border-radius: 2px; - border-radius: 2px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span { - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options { - overflow: hidden; - padding: 0; - display: block; - clear: none; - float: right; - margin: 6px 10px 0 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li { - float: left; - clear: none; - margin: 0; - padding: 2px 10px; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li a { - text-decoration: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li a .markdown p { - color: inherit; - padding: 0; - line-height: inherit; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li.access { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content { - border-top: none; - padding: 10px; - -moz-border-radius-bottomleft: 6px; - -webkit-border-bottom-left-radius: 6px; - -o-border-bottom-left-radius: 6px; - -ms-border-bottom-left-radius: 6px; - -khtml-border-bottom-left-radius: 6px; - border-bottom-left-radius: 6px; - -moz-border-radius-bottomright: 6px; - -webkit-border-bottom-right-radius: 6px; - -o-border-bottom-right-radius: 6px; - -ms-border-bottom-right-radius: 6px; - -khtml-border-bottom-right-radius: 6px; - border-bottom-right-radius: 6px; - margin: 0 0 20px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content h4 { - font-size: 1.1em; - margin: 0; - padding: 15px 0 5px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header { - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header a { - padding: 4px 0 0 10px; - display: inline-block; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header input.submit { - display: block; - clear: none; - float: left; - padding: 6px 8px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header span.response_throbber { - background-image: url('../images/throbber.gif'); - width: 128px; - height: 16px; - display: block; - clear: none; - float: right; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content form input[type='text'].error { - outline: 2px solid black; - outline-color: #cc0000; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content form select[name='parameterContentType'] { - max-width: 300px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.response div.block pre { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - padding: 10px; - font-size: 0.9em; - max-height: 400px; - overflow-y: auto; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading { - background-color: #f9f2e9; - border: 1px solid #f0e0ca; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading h3 span.http_method a { - background-color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #f0e0ca; - color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li a { - color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content { - background-color: #faf5ee; - border: 1px solid #f0e0ca; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content h4 { - color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content div.sandbox_header a { - color: #dcb67f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading { - background-color: #fcffcd; - border: 1px solid black; - border-color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading h3 span.http_method a { - text-transform: uppercase; - background-color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #ffd20f; - color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li a { - color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content { - background-color: #fcffcd; - border: 1px solid black; - border-color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content h4 { - color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content div.sandbox_header a { - color: #6fc992; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading { - background-color: #f5e8e8; - border: 1px solid #e8c6c7; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading h3 span.http_method a { - text-transform: uppercase; - background-color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #e8c6c7; - color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li a { - color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content { - background-color: #f7eded; - border: 1px solid #e8c6c7; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content h4 { - color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content div.sandbox_header a { - color: #c8787a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading { - background-color: #e7f6ec; - border: 1px solid #c3e8d1; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading h3 span.http_method a { - background-color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #c3e8d1; - color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li a { - color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content { - background-color: #ebf7f0; - border: 1px solid #c3e8d1; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content h4 { - color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content div.sandbox_header a { - color: #6fc992; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading { - background-color: #FCE9E3; - border: 1px solid #F5D5C3; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading h3 span.http_method a { - background-color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #f0cecb; - color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li a { - color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content { - background-color: #faf0ef; - border: 1px solid #f0cecb; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content h4 { - color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content div.sandbox_header a { - color: #dcb67f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading { - background-color: #e7f0f7; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading h3 span.http_method a { - background-color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #c3d9ec; - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li a { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content { - background-color: #ebf3f9; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content h4 { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content div.sandbox_header a { - color: #6fa5d2; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading { - background-color: #e7f0f7; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading h3 span.http_method a { - background-color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #c3d9ec; - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading ul.options li a { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.content { - background-color: #ebf3f9; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.content h4 { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.content div.sandbox_header a { - color: #6fa5d2; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content { - border-top: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li.last { - padding-right: 0; - border-right: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li a:hover, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li a:active, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li a.active { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap p#colophon { - margin: 0 15px 40px 15px; - padding: 10px 0; - font-size: 0.8em; - border-top: 1px solid #dddddd; - font-family: "Droid Sans", sans-serif; - color: #999999; - font-style: italic; -} -.swagger-section .swagger-ui-wrap p#colophon a { - text-decoration: none; - color: #547f00; -} -.swagger-section .swagger-ui-wrap h3 { - color: black; - font-size: 1.1em; - padding: 10px 0 10px 0; -} -.swagger-section .swagger-ui-wrap .markdown ol, -.swagger-section .swagger-ui-wrap .markdown ul { - font-family: "Droid Sans", sans-serif; - margin: 5px 0 10px; - padding: 0 0 0 18px; - list-style-type: disc; -} -.swagger-section .swagger-ui-wrap form.form_box { - background-color: #ebf3f9; - border: 1px solid #c3d9ec; - padding: 10px; -} -.swagger-section .swagger-ui-wrap form.form_box label { - color: #0f6ab4 !important; -} -.swagger-section .swagger-ui-wrap form.form_box input[type=submit] { - display: block; - padding: 10px; -} -.swagger-section .swagger-ui-wrap form.form_box p.weak { - font-size: 0.8em; -} -.swagger-section .swagger-ui-wrap form.form_box p { - font-size: 0.9em; - padding: 0 0 15px; - color: #7e7b6d; -} -.swagger-section .swagger-ui-wrap form.form_box p a { - color: #646257; -} -.swagger-section .swagger-ui-wrap form.form_box p strong { - color: black; -} -.swagger-section .swagger-ui-wrap .operation-status td.markdown > p:last-child { - padding-bottom: 0; -} -.swagger-section .title { - font-style: bold; -} -.swagger-section .secondary_form { - display: none; -} -.swagger-section .main_image { - display: block; - margin-left: auto; - margin-right: auto; -} -.swagger-section .oauth_body { - margin-left: 100px; - margin-right: 100px; -} -.swagger-section .oauth_submit { - text-align: center; - display: inline-block; -} -.swagger-section .authorize-wrapper { - margin: 15px 0 10px; -} -.swagger-section .authorize-wrapper_operation { - float: right; -} -.swagger-section .authorize__btn:hover { - text-decoration: underline; - cursor: pointer; -} -.swagger-section .authorize__btn_operation:hover .authorize-scopes { - display: block; -} -.swagger-section .authorize-scopes { - position: absolute; - margin-top: 20px; - background: #FFF; - border: 1px solid #ccc; - border-radius: 5px; - display: none; - font-size: 13px; - max-width: 300px; - line-height: 30px; - color: black; - padding: 5px; -} -.swagger-section .authorize-scopes .authorize__scope { - text-decoration: none; -} -.swagger-section .authorize__btn_operation { - height: 18px; - vertical-align: middle; - display: inline-block; - background: url(../images/explorer_icons.png) no-repeat; -} -.swagger-section .authorize__btn_operation_login { - background-position: 0 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section .authorize__btn_operation_logout { - background-position: -30px 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section #auth_container { - color: #fff; - display: inline-block; - border: none; - padding: 5px; - width: 87px; - height: 13px; -} -.swagger-section #auth_container .authorize__btn { - color: #fff; -} -.swagger-section .auth_container { - padding: 0 0 10px; - margin-bottom: 5px; - border-bottom: solid 1px #CCC; - font-size: 0.9em; -} -.swagger-section .auth_container .auth__title { - color: #547f00; - font-size: 1.2em; -} -.swagger-section .auth_container .basic_auth__label { - display: inline-block; - width: 60px; -} -.swagger-section .auth_container .auth__description { - color: #999999; - margin-bottom: 5px; -} -.swagger-section .auth_container .auth__button { - margin-top: 10px; - height: 30px; -} -.swagger-section .auth_container .key_auth__field { - margin: 5px 0; -} -.swagger-section .auth_container .key_auth__label { - display: inline-block; - width: 60px; -} -.swagger-section .api-popup-dialog { - position: absolute; - display: none; -} -.swagger-section .api-popup-dialog-wrapper { - z-index: 1000; - width: 500px; - background: #FFF; - padding: 20px; - border: 1px solid #ccc; - border-radius: 5px; - font-size: 13px; - color: #777; - position: fixed; - top: 50%; - left: 50%; - transform: translate(-50%, -50%); -} -.swagger-section .api-popup-dialog-shadow { - position: fixed; - top: 0; - left: 0; - width: 100%; - height: 100%; - opacity: 0.2; - background-color: gray; - z-index: 900; -} -.swagger-section .api-popup-dialog .api-popup-title { - font-size: 24px; - padding: 10px 0; -} -.swagger-section .api-popup-dialog .api-popup-title { - font-size: 24px; - padding: 10px 0; -} -.swagger-section .api-popup-dialog .error-msg { - padding-left: 5px; - padding-bottom: 5px; -} -.swagger-section .api-popup-dialog .api-popup-content { - max-height: 500px; - overflow-y: auto; -} -.swagger-section .api-popup-dialog .api-popup-authbtn { - height: 30px; -} -.swagger-section .api-popup-dialog .api-popup-cancel { - height: 30px; -} -.swagger-section .api-popup-scopes { - padding: 10px 20px; -} -.swagger-section .api-popup-scopes li { - padding: 5px 0; - line-height: 20px; -} -.swagger-section .api-popup-scopes li input { - position: relative; - top: 2px; -} -.swagger-section .api-popup-scopes .api-scope-desc { - padding-left: 20px; - font-style: italic; -} -.swagger-section .api-popup-actions { - padding-top: 10px; -} -#header { - display: none; -} -.swagger-section .swagger-ui-wrap .model-signature pre { - max-height: none; -} -.swagger-section .swagger-ui-wrap .body-textarea { - width: 100px; -} -.swagger-section .swagger-ui-wrap input.parameter { - width: 100px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options { - display: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints { - display: block !important; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content { - display: block !important; -} diff --git a/connexion/vendor/swagger-ui/css/reset.css b/connexion/vendor/swagger-ui/css/reset.css deleted file mode 100644 index b2b078943..000000000 --- a/connexion/vendor/swagger-ui/css/reset.css +++ /dev/null @@ -1,125 +0,0 @@ -/* http://meyerweb.com/eric/tools/css/reset/ v2.0 | 20110126 */ -html, -body, -div, -span, -applet, -object, -iframe, -h1, -h2, -h3, -h4, -h5, -h6, -p, -blockquote, -pre, -a, -abbr, -acronym, -address, -big, -cite, -code, -del, -dfn, -em, -img, -ins, -kbd, -q, -s, -samp, -small, -strike, -strong, -sub, -sup, -tt, -var, -b, -u, -i, -center, -dl, -dt, -dd, -ol, -ul, -li, -fieldset, -form, -label, -legend, -table, -caption, -tbody, -tfoot, -thead, -tr, -th, -td, -article, -aside, -canvas, -details, -embed, -figure, -figcaption, -footer, -header, -hgroup, -menu, -nav, -output, -ruby, -section, -summary, -time, -mark, -audio, -video { - margin: 0; - padding: 0; - border: 0; - font-size: 100%; - font: inherit; - vertical-align: baseline; -} -/* HTML5 display-role reset for older browsers */ -article, -aside, -details, -figcaption, -figure, -footer, -header, -hgroup, -menu, -nav, -section { - display: block; -} -body { - line-height: 1; -} -ol, -ul { - list-style: none; -} -blockquote, -q { - quotes: none; -} -blockquote:before, -blockquote:after, -q:before, -q:after { - content: ''; - content: none; -} -table { - border-collapse: collapse; - border-spacing: 0; -} diff --git a/connexion/vendor/swagger-ui/css/screen.css b/connexion/vendor/swagger-ui/css/screen.css deleted file mode 100644 index 39ff583e8..000000000 --- a/connexion/vendor/swagger-ui/css/screen.css +++ /dev/null @@ -1,1494 +0,0 @@ -/* Original style from softwaremaniacs.org (c) Ivan Sagalaev */ -.swagger-section pre code { - display: block; - padding: 0.5em; - background: #F0F0F0; -} -.swagger-section pre code, -.swagger-section pre .subst, -.swagger-section pre .tag .title, -.swagger-section pre .lisp .title, -.swagger-section pre .clojure .built_in, -.swagger-section pre .nginx .title { - color: black; -} -.swagger-section pre .string, -.swagger-section pre .title, -.swagger-section pre .constant, -.swagger-section pre .parent, -.swagger-section pre .tag .value, -.swagger-section pre .rules .value, -.swagger-section pre .rules .value .number, -.swagger-section pre .preprocessor, -.swagger-section pre .ruby .symbol, -.swagger-section pre .ruby .symbol .string, -.swagger-section pre .aggregate, -.swagger-section pre .template_tag, -.swagger-section pre .django .variable, -.swagger-section pre .smalltalk .class, -.swagger-section pre .addition, -.swagger-section pre .flow, -.swagger-section pre .stream, -.swagger-section pre .bash .variable, -.swagger-section pre .apache .tag, -.swagger-section pre .apache .cbracket, -.swagger-section pre .tex .command, -.swagger-section pre .tex .special, -.swagger-section pre .erlang_repl .function_or_atom, -.swagger-section pre .markdown .header { - color: #800; -} -.swagger-section pre .comment, -.swagger-section pre .annotation, -.swagger-section pre .template_comment, -.swagger-section pre .diff .header, -.swagger-section pre .chunk, -.swagger-section pre .markdown .blockquote { - color: #888; -} -.swagger-section pre .number, -.swagger-section pre .date, -.swagger-section pre .regexp, -.swagger-section pre .literal, -.swagger-section pre .smalltalk .symbol, -.swagger-section pre .smalltalk .char, -.swagger-section pre .go .constant, -.swagger-section pre .change, -.swagger-section pre .markdown .bullet, -.swagger-section pre .markdown .link_url { - color: #080; -} -.swagger-section pre .label, -.swagger-section pre .javadoc, -.swagger-section pre .ruby .string, -.swagger-section pre .decorator, -.swagger-section pre .filter .argument, -.swagger-section pre .localvars, -.swagger-section pre .array, -.swagger-section pre .attr_selector, -.swagger-section pre .important, -.swagger-section pre .pseudo, -.swagger-section pre .pi, -.swagger-section pre .doctype, -.swagger-section pre .deletion, -.swagger-section pre .envvar, -.swagger-section pre .shebang, -.swagger-section pre .apache .sqbracket, -.swagger-section pre .nginx .built_in, -.swagger-section pre .tex .formula, -.swagger-section pre .erlang_repl .reserved, -.swagger-section pre .prompt, -.swagger-section pre .markdown .link_label, -.swagger-section pre .vhdl .attribute, -.swagger-section pre .clojure .attribute, -.swagger-section pre .coffeescript .property { - color: #88F; -} -.swagger-section pre .keyword, -.swagger-section pre .id, -.swagger-section pre .phpdoc, -.swagger-section pre .title, -.swagger-section pre .built_in, -.swagger-section pre .aggregate, -.swagger-section pre .css .tag, -.swagger-section pre .javadoctag, -.swagger-section pre .phpdoc, -.swagger-section pre .yardoctag, -.swagger-section pre .smalltalk .class, -.swagger-section pre .winutils, -.swagger-section pre .bash .variable, -.swagger-section pre .apache .tag, -.swagger-section pre .go .typename, -.swagger-section pre .tex .command, -.swagger-section pre .markdown .strong, -.swagger-section pre .request, -.swagger-section pre .status { - font-weight: bold; -} -.swagger-section pre .markdown .emphasis { - font-style: italic; -} -.swagger-section pre .nginx .built_in { - font-weight: normal; -} -.swagger-section pre .coffeescript .javascript, -.swagger-section pre .javascript .xml, -.swagger-section pre .tex .formula, -.swagger-section pre .xml .javascript, -.swagger-section pre .xml .vbscript, -.swagger-section pre .xml .css, -.swagger-section pre .xml .cdata { - opacity: 0.5; -} -.swagger-section .hljs { - display: block; - overflow-x: auto; - padding: 0.5em; - background: #F0F0F0; -} -.swagger-section .hljs, -.swagger-section .hljs-subst { - color: #444; -} -.swagger-section .hljs-keyword, -.swagger-section .hljs-attribute, -.swagger-section .hljs-selector-tag, -.swagger-section .hljs-meta-keyword, -.swagger-section .hljs-doctag, -.swagger-section .hljs-name { - font-weight: bold; -} -.swagger-section .hljs-built_in, -.swagger-section .hljs-literal, -.swagger-section .hljs-bullet, -.swagger-section .hljs-code, -.swagger-section .hljs-addition { - color: #1F811F; -} -.swagger-section .hljs-regexp, -.swagger-section .hljs-symbol, -.swagger-section .hljs-variable, -.swagger-section .hljs-template-variable, -.swagger-section .hljs-link, -.swagger-section .hljs-selector-attr, -.swagger-section .hljs-selector-pseudo { - color: #BC6060; -} -.swagger-section .hljs-type, -.swagger-section .hljs-string, -.swagger-section .hljs-number, -.swagger-section .hljs-selector-id, -.swagger-section .hljs-selector-class, -.swagger-section .hljs-quote, -.swagger-section .hljs-template-tag, -.swagger-section .hljs-deletion { - color: #880000; -} -.swagger-section .hljs-title, -.swagger-section .hljs-section { - color: #880000; - font-weight: bold; -} -.swagger-section .hljs-comment { - color: #888888; -} -.swagger-section .hljs-meta { - color: #2B6EA1; -} -.swagger-section .hljs-emphasis { - font-style: italic; -} -.swagger-section .hljs-strong { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap { - line-height: 1; - font-family: "Droid Sans", sans-serif; - min-width: 760px; - max-width: 960px; - margin-left: auto; - margin-right: auto; - /* JSONEditor specific styling */ -} -.swagger-section .swagger-ui-wrap b, -.swagger-section .swagger-ui-wrap strong { - font-family: "Droid Sans", sans-serif; - font-weight: bold; -} -.swagger-section .swagger-ui-wrap q, -.swagger-section .swagger-ui-wrap blockquote { - quotes: none; -} -.swagger-section .swagger-ui-wrap p { - line-height: 1.4em; - padding: 0 0 10px; - color: #333333; -} -.swagger-section .swagger-ui-wrap q:before, -.swagger-section .swagger-ui-wrap q:after, -.swagger-section .swagger-ui-wrap blockquote:before, -.swagger-section .swagger-ui-wrap blockquote:after { - content: none; -} -.swagger-section .swagger-ui-wrap .heading_with_menu h1, -.swagger-section .swagger-ui-wrap .heading_with_menu h2, -.swagger-section .swagger-ui-wrap .heading_with_menu h3, -.swagger-section .swagger-ui-wrap .heading_with_menu h4, -.swagger-section .swagger-ui-wrap .heading_with_menu h5, -.swagger-section .swagger-ui-wrap .heading_with_menu h6 { - display: block; - clear: none; - float: left; - -moz-box-sizing: border-box; - -webkit-box-sizing: border-box; - -ms-box-sizing: border-box; - box-sizing: border-box; - width: 60%; -} -.swagger-section .swagger-ui-wrap table { - border-collapse: collapse; - border-spacing: 0; -} -.swagger-section .swagger-ui-wrap table thead tr th { - padding: 5px; - font-size: 0.9em; - color: #666666; - border-bottom: 1px solid #999999; -} -.swagger-section .swagger-ui-wrap table tbody tr:last-child td { - border-bottom: none; -} -.swagger-section .swagger-ui-wrap table tbody tr.offset { - background-color: #f0f0f0; -} -.swagger-section .swagger-ui-wrap table tbody tr td { - padding: 6px; - font-size: 0.9em; - border-bottom: 1px solid #cccccc; - vertical-align: top; - line-height: 1.3em; -} -.swagger-section .swagger-ui-wrap ol { - margin: 0px 0 10px; - padding: 0 0 0 18px; - list-style-type: decimal; -} -.swagger-section .swagger-ui-wrap ol li { - padding: 5px 0px; - font-size: 0.9em; - color: #333333; -} -.swagger-section .swagger-ui-wrap ol, -.swagger-section .swagger-ui-wrap ul { - list-style: none; -} -.swagger-section .swagger-ui-wrap h1 a, -.swagger-section .swagger-ui-wrap h2 a, -.swagger-section .swagger-ui-wrap h3 a, -.swagger-section .swagger-ui-wrap h4 a, -.swagger-section .swagger-ui-wrap h5 a, -.swagger-section .swagger-ui-wrap h6 a { - text-decoration: none; -} -.swagger-section .swagger-ui-wrap h1 a:hover, -.swagger-section .swagger-ui-wrap h2 a:hover, -.swagger-section .swagger-ui-wrap h3 a:hover, -.swagger-section .swagger-ui-wrap h4 a:hover, -.swagger-section .swagger-ui-wrap h5 a:hover, -.swagger-section .swagger-ui-wrap h6 a:hover { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap h1 span.divider, -.swagger-section .swagger-ui-wrap h2 span.divider, -.swagger-section .swagger-ui-wrap h3 span.divider, -.swagger-section .swagger-ui-wrap h4 span.divider, -.swagger-section .swagger-ui-wrap h5 span.divider, -.swagger-section .swagger-ui-wrap h6 span.divider { - color: #aaaaaa; -} -.swagger-section .swagger-ui-wrap a { - color: #547f00; -} -.swagger-section .swagger-ui-wrap a img { - border: none; -} -.swagger-section .swagger-ui-wrap article, -.swagger-section .swagger-ui-wrap aside, -.swagger-section .swagger-ui-wrap details, -.swagger-section .swagger-ui-wrap figcaption, -.swagger-section .swagger-ui-wrap figure, -.swagger-section .swagger-ui-wrap footer, -.swagger-section .swagger-ui-wrap header, -.swagger-section .swagger-ui-wrap hgroup, -.swagger-section .swagger-ui-wrap menu, -.swagger-section .swagger-ui-wrap nav, -.swagger-section .swagger-ui-wrap section, -.swagger-section .swagger-ui-wrap summary { - display: block; -} -.swagger-section .swagger-ui-wrap pre { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - background-color: #fcf6db; - border: 1px solid #e5e0c6; - padding: 10px; -} -.swagger-section .swagger-ui-wrap pre code { - line-height: 1.6em; - background: none; -} -.swagger-section .swagger-ui-wrap .content > .content-type > div > label { - clear: both; - display: block; - color: #0F6AB4; - font-size: 1.1em; - margin: 0; - padding: 15px 0 5px; -} -.swagger-section .swagger-ui-wrap .content pre { - font-size: 12px; - margin-top: 5px; - padding: 5px; -} -.swagger-section .swagger-ui-wrap .icon-btn { - cursor: pointer; -} -.swagger-section .swagger-ui-wrap .info_title { - padding-bottom: 10px; - font-weight: bold; - font-size: 25px; -} -.swagger-section .swagger-ui-wrap .footer { - margin-top: 20px; -} -.swagger-section .swagger-ui-wrap p.big, -.swagger-section .swagger-ui-wrap div.big p { - font-size: 1em; - margin-bottom: 10px; -} -.swagger-section .swagger-ui-wrap form.fullwidth ol li.string input, -.swagger-section .swagger-ui-wrap form.fullwidth ol li.url input, -.swagger-section .swagger-ui-wrap form.fullwidth ol li.text textarea, -.swagger-section .swagger-ui-wrap form.fullwidth ol li.numeric input { - width: 500px !important; -} -.swagger-section .swagger-ui-wrap .info_license { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_tos { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .message-fail { - color: #cc0000; -} -.swagger-section .swagger-ui-wrap .info_url { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_email { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_name { - padding-bottom: 5px; -} -.swagger-section .swagger-ui-wrap .info_description { - padding-bottom: 10px; - font-size: 15px; -} -.swagger-section .swagger-ui-wrap .markdown ol li, -.swagger-section .swagger-ui-wrap .markdown ul li { - padding: 3px 0px; - line-height: 1.4em; - color: #333333; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.string input, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.url input, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.numeric input { - display: block; - padding: 4px; - width: auto; - clear: both; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.string input.title, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.url input.title, -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.numeric input.title { - font-size: 1.3em; -} -.swagger-section .swagger-ui-wrap table.fullwidth { - width: 100%; -} -.swagger-section .swagger-ui-wrap .model-signature { - font-family: "Droid Sans", sans-serif; - font-size: 1em; - line-height: 1.5em; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-nav a { - text-decoration: none; - color: #AAA; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-nav a:hover { - text-decoration: underline; - color: black; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-nav .selected { - color: black; - text-decoration: none; -} -.swagger-section .swagger-ui-wrap .model-signature .propType { - color: #5555aa; -} -.swagger-section .swagger-ui-wrap .model-signature pre:hover { - background-color: #ffffdd; -} -.swagger-section .swagger-ui-wrap .model-signature pre { - font-size: .85em; - line-height: 1.2em; - overflow: auto; - max-height: 200px; - cursor: pointer; -} -.swagger-section .swagger-ui-wrap .model-signature ul.signature-nav { - display: block; - min-width: 230px; - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap .model-signature ul.signature-nav li:last-child { - padding-right: 0; - border-right: none; -} -.swagger-section .swagger-ui-wrap .model-signature ul.signature-nav li { - float: left; - margin: 0 5px 5px 0; - padding: 2px 5px 2px 0; - border-right: 1px solid #ddd; -} -.swagger-section .swagger-ui-wrap .model-signature .propOpt { - color: #555; -} -.swagger-section .swagger-ui-wrap .model-signature .snippet small { - font-size: 0.75em; -} -.swagger-section .swagger-ui-wrap .model-signature .propOptKey { - font-style: italic; -} -.swagger-section .swagger-ui-wrap .model-signature .description .strong { - font-weight: bold; - color: #000; - font-size: .9em; -} -.swagger-section .swagger-ui-wrap .model-signature .description div { - font-size: 0.9em; - line-height: 1.5em; - margin-left: 1em; -} -.swagger-section .swagger-ui-wrap .model-signature .description .stronger { - font-weight: bold; - color: #000; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propWrap .optionsWrapper { - border-spacing: 0; - position: absolute; - background-color: #ffffff; - border: 1px solid #bbbbbb; - display: none; - font-size: 11px; - max-width: 400px; - line-height: 30px; - color: black; - padding: 5px; - margin-left: 10px; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propWrap .optionsWrapper th { - text-align: center; - background-color: #eeeeee; - border: 1px solid #bbbbbb; - font-size: 11px; - color: #666666; - font-weight: bold; - padding: 5px; - line-height: 15px; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propWrap .optionsWrapper .optionName { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propDesc.markdown > p:first-child, -.swagger-section .swagger-ui-wrap .model-signature .description .propDesc.markdown > p:last-child { - display: inline; -} -.swagger-section .swagger-ui-wrap .model-signature .description .propDesc.markdown > p:not(:first-child):before { - display: block; - content: ''; -} -.swagger-section .swagger-ui-wrap .model-signature .description span:last-of-type.propDesc.markdown > p:only-child { - margin-right: -3px; -} -.swagger-section .swagger-ui-wrap .model-signature .propName { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .model-signature .signature-container { - clear: both; -} -.swagger-section .swagger-ui-wrap .body-textarea { - width: 300px; - height: 100px; - border: 1px solid #aaa; -} -.swagger-section .swagger-ui-wrap .markdown p code, -.swagger-section .swagger-ui-wrap .markdown li code { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - background-color: #f0f0f0; - color: black; - padding: 1px 3px; -} -.swagger-section .swagger-ui-wrap .required { - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .editor_holder { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap .editor_holder label { - font-weight: normal!important; - /* JSONEditor uses bold by default for all labels, we revert that back to normal to not give the impression that by default fields are required */ -} -.swagger-section .swagger-ui-wrap .editor_holder label.required { - font-weight: bold!important; -} -.swagger-section .swagger-ui-wrap input.parameter { - width: 300px; - border: 1px solid #aaa; -} -.swagger-section .swagger-ui-wrap h1 { - color: black; - font-size: 1.5em; - line-height: 1.3em; - padding: 10px 0 10px 0; - font-family: "Droid Sans", sans-serif; - font-weight: bold; -} -.swagger-section .swagger-ui-wrap .heading_with_menu { - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap .heading_with_menu ul { - display: block; - clear: none; - float: right; - -moz-box-sizing: border-box; - -webkit-box-sizing: border-box; - -ms-box-sizing: border-box; - box-sizing: border-box; - margin-top: 10px; -} -.swagger-section .swagger-ui-wrap h2 { - color: black; - font-size: 1.3em; - padding: 10px 0 10px 0; -} -.swagger-section .swagger-ui-wrap h2 a { - color: black; -} -.swagger-section .swagger-ui-wrap h2 span.sub { - font-size: 0.7em; - color: #999999; - font-style: italic; -} -.swagger-section .swagger-ui-wrap h2 span.sub a { - color: #777777; -} -.swagger-section .swagger-ui-wrap span.weak { - color: #666666; -} -.swagger-section .swagger-ui-wrap .message-success { - color: #89BF04; -} -.swagger-section .swagger-ui-wrap caption, -.swagger-section .swagger-ui-wrap th, -.swagger-section .swagger-ui-wrap td { - text-align: left; - font-weight: normal; - vertical-align: middle; -} -.swagger-section .swagger-ui-wrap .code { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.text textarea { - font-family: "Droid Sans", sans-serif; - height: 250px; - padding: 4px; - display: block; - clear: both; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.select select { - display: block; - clear: both; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.boolean { - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.boolean label { - display: block; - float: left; - clear: none; - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.boolean input { - display: block; - float: left; - clear: none; - margin: 0 5px 0 0; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li.required label { - color: black; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li label { - display: block; - clear: both; - width: auto; - padding: 0 0 3px; - color: #666666; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li label abbr { - padding-left: 3px; - color: #888888; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.inputs ol li p.inline-hints { - margin-left: 0; - font-style: italic; - font-size: 0.9em; - margin: 0; -} -.swagger-section .swagger-ui-wrap form.formtastic fieldset.buttons { - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap span.blank, -.swagger-section .swagger-ui-wrap span.empty { - color: #888888; - font-style: italic; -} -.swagger-section .swagger-ui-wrap .markdown h3 { - color: #547f00; -} -.swagger-section .swagger-ui-wrap .markdown h4 { - color: #666666; -} -.swagger-section .swagger-ui-wrap .markdown pre { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - background-color: #fcf6db; - border: 1px solid #e5e0c6; - padding: 10px; - margin: 0 0 10px 0; -} -.swagger-section .swagger-ui-wrap .markdown pre code { - line-height: 1.6em; - overflow: auto; -} -.swagger-section .swagger-ui-wrap div.gist { - margin: 20px 0 25px 0 !important; -} -.swagger-section .swagger-ui-wrap ul#resources { - font-family: "Droid Sans", sans-serif; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource { - border-bottom: 1px solid #dddddd; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource:hover div.heading h2 a, -.swagger-section .swagger-ui-wrap ul#resources li.resource.active div.heading h2 a { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource:hover div.heading ul.options li a, -.swagger-section .swagger-ui-wrap ul#resources li.resource.active div.heading ul.options li a { - color: #555555; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource:last-child { - border-bottom: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading { - border: 1px solid transparent; - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options { - overflow: hidden; - padding: 0; - display: block; - clear: none; - float: right; - margin: 14px 10px 0 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li { - float: left; - clear: none; - margin: 0; - padding: 2px 10px; - border-right: 1px solid #dddddd; - color: #666666; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a { - color: #aaaaaa; - text-decoration: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a:hover { - text-decoration: underline; - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a:hover, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a:active, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li a.active { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options li.last { - padding-right: 0; - border-right: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading ul.options.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 { - color: #999999; - padding-left: 0; - display: block; - clear: none; - float: left; - font-family: "Droid Sans", sans-serif; - font-weight: bold; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 a { - color: #999999; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 a:hover { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation { - float: none; - clear: both; - overflow: hidden; - display: block; - margin: 0 0 10px; - padding: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading { - float: none; - clear: both; - overflow: hidden; - display: block; - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 { - display: block; - clear: none; - float: left; - width: auto; - margin: 0; - padding: 0; - line-height: 1.1em; - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path { - padding-left: 10px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path a { - color: black; - text-decoration: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path a.toggleOperation.deprecated { - text-decoration: line-through; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.path a:hover { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span.http_method a { - text-transform: uppercase; - text-decoration: none; - color: white; - display: inline-block; - width: 50px; - font-size: 0.7em; - text-align: center; - padding: 7px 0 4px; - -moz-border-radius: 2px; - -webkit-border-radius: 2px; - -o-border-radius: 2px; - -ms-border-radius: 2px; - -khtml-border-radius: 2px; - border-radius: 2px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading h3 span { - margin: 0; - padding: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options { - overflow: hidden; - padding: 0; - display: block; - clear: none; - float: right; - margin: 6px 10px 0 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li { - float: left; - clear: none; - margin: 0; - padding: 2px 10px; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li a { - text-decoration: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li a .markdown p { - color: inherit; - padding: 0; - line-height: inherit; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.heading ul.options li.access { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content { - border-top: none; - padding: 10px; - -moz-border-radius-bottomleft: 6px; - -webkit-border-bottom-left-radius: 6px; - -o-border-bottom-left-radius: 6px; - -ms-border-bottom-left-radius: 6px; - -khtml-border-bottom-left-radius: 6px; - border-bottom-left-radius: 6px; - -moz-border-radius-bottomright: 6px; - -webkit-border-bottom-right-radius: 6px; - -o-border-bottom-right-radius: 6px; - -ms-border-bottom-right-radius: 6px; - -khtml-border-bottom-right-radius: 6px; - border-bottom-right-radius: 6px; - margin: 0 0 20px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content h4 { - font-size: 1.1em; - margin: 0; - padding: 15px 0 5px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header { - float: none; - clear: both; - overflow: hidden; - display: block; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header a { - padding: 4px 0 0 10px; - display: inline-block; - font-size: 0.9em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header input.submit { - display: block; - clear: none; - float: left; - padding: 6px 8px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.sandbox_header span.response_throbber { - background-image: url('../images/throbber.gif'); - width: 128px; - height: 16px; - display: block; - clear: none; - float: right; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content form input[type='text'].error { - outline: 2px solid black; - outline-color: #cc0000; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content form select[name='parameterContentType'] { - max-width: 300px; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation div.content div.response div.block pre { - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - padding: 10px; - font-size: 0.9em; - max-height: 400px; - overflow-y: auto; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading { - background-color: #f9f2e9; - border: 1px solid #f0e0ca; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading h3 span.http_method a { - background-color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #f0e0ca; - color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li a { - color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content { - background-color: #faf5ee; - border: 1px solid #f0e0ca; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content h4 { - color: #c5862b; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content div.sandbox_header a { - color: #dcb67f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading { - background-color: #fcffcd; - border: 1px solid black; - border-color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading h3 span.http_method a { - text-transform: uppercase; - background-color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #ffd20f; - color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li a { - color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content { - background-color: #fcffcd; - border: 1px solid black; - border-color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content h4 { - color: #ffd20f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content div.sandbox_header a { - color: #6fc992; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading { - background-color: #f5e8e8; - border: 1px solid #e8c6c7; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading h3 span.http_method a { - text-transform: uppercase; - background-color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #e8c6c7; - color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li a { - color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content { - background-color: #f7eded; - border: 1px solid #e8c6c7; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content h4 { - color: #a41e22; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content div.sandbox_header a { - color: #c8787a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading { - background-color: #e7f6ec; - border: 1px solid #c3e8d1; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading h3 span.http_method a { - background-color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #c3e8d1; - color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li a { - color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content { - background-color: #ebf7f0; - border: 1px solid #c3e8d1; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content h4 { - color: #10a54a; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content div.sandbox_header a { - color: #6fc992; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading { - background-color: #FCE9E3; - border: 1px solid #F5D5C3; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading h3 span.http_method a { - background-color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #f0cecb; - color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li a { - color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content { - background-color: #faf0ef; - border: 1px solid #f0cecb; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content h4 { - color: #D38042; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content div.sandbox_header a { - color: #dcb67f; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading { - background-color: #e7f0f7; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading h3 span.http_method a { - background-color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #c3d9ec; - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li a { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content { - background-color: #ebf3f9; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content h4 { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content div.sandbox_header a { - color: #6fa5d2; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading { - background-color: #e7f0f7; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading h3 span.http_method a { - background-color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading ul.options li { - border-right: 1px solid #dddddd; - border-right-color: #c3d9ec; - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.heading ul.options li a { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.content { - background-color: #ebf3f9; - border: 1px solid #c3d9ec; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.content h4 { - color: #0f6ab4; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.options div.content div.sandbox_header a { - color: #6fa5d2; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.content, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.content { - border-top: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li:last-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.get div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.post div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.head div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.put div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.patch div.heading ul.options li.last, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations li.operation.delete div.heading ul.options li.last { - padding-right: 0; - border-right: none; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li a:hover, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li a:active, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li a.active { - text-decoration: underline; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations ul.options li.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations:first-child, -.swagger-section .swagger-ui-wrap ul#resources li.resource ul.endpoints li.endpoint ul.operations.first { - padding-left: 0; -} -.swagger-section .swagger-ui-wrap p#colophon { - margin: 0 15px 40px 15px; - padding: 10px 0; - font-size: 0.8em; - border-top: 1px solid #dddddd; - font-family: "Droid Sans", sans-serif; - color: #999999; - font-style: italic; -} -.swagger-section .swagger-ui-wrap p#colophon a { - text-decoration: none; - color: #547f00; -} -.swagger-section .swagger-ui-wrap h3 { - color: black; - font-size: 1.1em; - padding: 10px 0 10px 0; -} -.swagger-section .swagger-ui-wrap .markdown ol, -.swagger-section .swagger-ui-wrap .markdown ul { - font-family: "Droid Sans", sans-serif; - margin: 5px 0 10px; - padding: 0 0 0 18px; - list-style-type: disc; -} -.swagger-section .swagger-ui-wrap form.form_box { - background-color: #ebf3f9; - border: 1px solid #c3d9ec; - padding: 10px; -} -.swagger-section .swagger-ui-wrap form.form_box label { - color: #0f6ab4 !important; -} -.swagger-section .swagger-ui-wrap form.form_box input[type=submit] { - display: block; - padding: 10px; -} -.swagger-section .swagger-ui-wrap form.form_box p.weak { - font-size: 0.8em; -} -.swagger-section .swagger-ui-wrap form.form_box p { - font-size: 0.9em; - padding: 0 0 15px; - color: #7e7b6d; -} -.swagger-section .swagger-ui-wrap form.form_box p a { - color: #646257; -} -.swagger-section .swagger-ui-wrap form.form_box p strong { - color: black; -} -.swagger-section .swagger-ui-wrap .operation-status td.markdown > p:last-child { - padding-bottom: 0; -} -.swagger-section .title { - font-style: bold; -} -.swagger-section .secondary_form { - display: none; -} -.swagger-section .main_image { - display: block; - margin-left: auto; - margin-right: auto; -} -.swagger-section .oauth_body { - margin-left: 100px; - margin-right: 100px; -} -.swagger-section .oauth_submit { - text-align: center; - display: inline-block; -} -.swagger-section .authorize-wrapper { - margin: 15px 0 10px; -} -.swagger-section .authorize-wrapper_operation { - float: right; -} -.swagger-section .authorize__btn:hover { - text-decoration: underline; - cursor: pointer; -} -.swagger-section .authorize__btn_operation:hover .authorize-scopes { - display: block; -} -.swagger-section .authorize-scopes { - position: absolute; - margin-top: 20px; - background: #FFF; - border: 1px solid #ccc; - border-radius: 5px; - display: none; - font-size: 13px; - max-width: 300px; - line-height: 30px; - color: black; - padding: 5px; -} -.swagger-section .authorize-scopes .authorize__scope { - text-decoration: none; -} -.swagger-section .authorize__btn_operation { - height: 18px; - vertical-align: middle; - display: inline-block; - background: url(../images/explorer_icons.png) no-repeat; -} -.swagger-section .authorize__btn_operation_login { - background-position: 0 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section .authorize__btn_operation_logout { - background-position: -30px 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section #auth_container { - color: #fff; - display: inline-block; - border: none; - padding: 5px; - width: 87px; - height: 13px; -} -.swagger-section #auth_container .authorize__btn { - color: #fff; -} -.swagger-section .auth_container { - padding: 0 0 10px; - margin-bottom: 5px; - border-bottom: solid 1px #CCC; - font-size: 0.9em; -} -.swagger-section .auth_container .auth__title { - color: #547f00; - font-size: 1.2em; -} -.swagger-section .auth_container .basic_auth__label { - display: inline-block; - width: 60px; -} -.swagger-section .auth_container .auth__description { - color: #999999; - margin-bottom: 5px; -} -.swagger-section .auth_container .auth__button { - margin-top: 10px; - height: 30px; -} -.swagger-section .auth_container .key_auth__field { - margin: 5px 0; -} -.swagger-section .auth_container .key_auth__label { - display: inline-block; - width: 60px; -} -.swagger-section .api-popup-dialog { - position: absolute; - display: none; -} -.swagger-section .api-popup-dialog-wrapper { - z-index: 1000; - width: 500px; - background: #FFF; - padding: 20px; - border: 1px solid #ccc; - border-radius: 5px; - font-size: 13px; - color: #777; - position: fixed; - top: 50%; - left: 50%; - transform: translate(-50%, -50%); -} -.swagger-section .api-popup-dialog-shadow { - position: fixed; - top: 0; - left: 0; - width: 100%; - height: 100%; - opacity: 0.2; - background-color: gray; - z-index: 900; -} -.swagger-section .api-popup-dialog .api-popup-title { - font-size: 24px; - padding: 10px 0; -} -.swagger-section .api-popup-dialog .api-popup-title { - font-size: 24px; - padding: 10px 0; -} -.swagger-section .api-popup-dialog .error-msg { - padding-left: 5px; - padding-bottom: 5px; -} -.swagger-section .api-popup-dialog .api-popup-content { - max-height: 500px; - overflow-y: auto; -} -.swagger-section .api-popup-dialog .api-popup-authbtn { - height: 30px; -} -.swagger-section .api-popup-dialog .api-popup-cancel { - height: 30px; -} -.swagger-section .api-popup-scopes { - padding: 10px 20px; -} -.swagger-section .api-popup-scopes li { - padding: 5px 0; - line-height: 20px; -} -.swagger-section .api-popup-scopes li input { - position: relative; - top: 2px; -} -.swagger-section .api-popup-scopes .api-scope-desc { - padding-left: 20px; - font-style: italic; -} -.swagger-section .api-popup-actions { - padding-top: 10px; -} -.swagger-section .access { - float: right; -} -.swagger-section .auth { - float: right; -} -.swagger-section .api-ic { - height: 18px; - vertical-align: middle; - display: inline-block; - background: url(../images/explorer_icons.png) no-repeat; -} -.swagger-section .api-ic .api_information_panel { - position: relative; - margin-top: 20px; - margin-left: -5px; - background: #FFF; - border: 1px solid #ccc; - border-radius: 5px; - display: none; - font-size: 13px; - max-width: 300px; - line-height: 30px; - color: black; - padding: 5px; -} -.swagger-section .api-ic .api_information_panel p .api-msg-enabled { - color: green; -} -.swagger-section .api-ic .api_information_panel p .api-msg-disabled { - color: red; -} -.swagger-section .api-ic:hover .api_information_panel { - position: absolute; - display: block; -} -.swagger-section .ic-info { - background-position: 0 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section .ic-warning { - background-position: -60px 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section .ic-error { - background-position: -30px 0; - width: 18px; - margin-top: -6px; - margin-left: 4px; -} -.swagger-section .ic-off { - background-position: -90px 0; - width: 58px; - margin-top: -4px; - cursor: pointer; -} -.swagger-section .ic-on { - background-position: -160px 0; - width: 58px; - margin-top: -4px; - cursor: pointer; -} -.swagger-section #header { - background-color: #89bf04; - padding: 9px 14px 19px 14px; - height: 23px; - min-width: 775px; -} -.swagger-section #input_baseUrl { - width: 400px; -} -.swagger-section #api_selector { - display: block; - clear: none; - float: right; -} -.swagger-section #api_selector .input { - display: inline-block; - clear: none; - margin: 0 10px 0 0; -} -.swagger-section #api_selector input { - font-size: 0.9em; - padding: 3px; - margin: 0; -} -.swagger-section #input_apiKey { - width: 200px; -} -.swagger-section #explore, -.swagger-section #auth_container .authorize__btn { - display: block; - text-decoration: none; - font-weight: bold; - padding: 6px 8px; - font-size: 0.9em; - color: white; - background-color: #547f00; - -moz-border-radius: 4px; - -webkit-border-radius: 4px; - -o-border-radius: 4px; - -ms-border-radius: 4px; - -khtml-border-radius: 4px; - border-radius: 4px; -} -.swagger-section #explore:hover, -.swagger-section #auth_container .authorize__btn:hover { - background-color: #547f00; -} -.swagger-section #header #logo { - font-size: 1.5em; - font-weight: bold; - text-decoration: none; - color: white; -} -.swagger-section #header #logo .logo__img { - display: block; - float: left; - margin-top: 2px; -} -.swagger-section #header #logo .logo__title { - display: inline-block; - padding: 5px 0 0 10px; -} -.swagger-section #content_message { - margin: 10px 15px; - font-style: italic; - color: #999999; -} -.swagger-section #message-bar { - min-height: 30px; - text-align: center; - padding-top: 10px; -} -.swagger-section .swagger-collapse:before { - content: "-"; -} -.swagger-section .swagger-expand:before { - content: "+"; -} -.swagger-section .error { - outline-color: #cc0000; - background-color: #f2dede; -} diff --git a/connexion/vendor/swagger-ui/css/style.css b/connexion/vendor/swagger-ui/css/style.css deleted file mode 100644 index fc21a31db..000000000 --- a/connexion/vendor/swagger-ui/css/style.css +++ /dev/null @@ -1,250 +0,0 @@ -.swagger-section #header a#logo { - font-size: 1.5em; - font-weight: bold; - text-decoration: none; - background: transparent url(../images/logo.png) no-repeat left center; - padding: 20px 0 20px 40px; -} -#text-head { - font-size: 80px; - font-family: 'Roboto', sans-serif; - color: #ffffff; - float: right; - margin-right: 20%; -} -.navbar-fixed-top .navbar-nav { - height: auto; -} -.navbar-fixed-top .navbar-brand { - height: auto; -} -.navbar-header { - height: auto; -} -.navbar-inverse { - background-color: #000; - border-color: #000; -} -#navbar-brand { - margin-left: 20%; -} -.navtext { - font-size: 10px; -} -.h1, -h1 { - font-size: 60px; -} -.navbar-default .navbar-header .navbar-brand { - color: #a2dfee; -} -/* tag titles */ -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 a { - color: #393939; - font-family: 'Arvo', serif; - font-size: 1.5em; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 a:hover { - color: black; -} -.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 { - color: #525252; - padding-left: 0px; - display: block; - clear: none; - float: left; - font-family: 'Arvo', serif; - font-weight: bold; -} -.navbar-default .navbar-collapse, -.navbar-default .navbar-form { - border-color: #0A0A0A; -} -.container1 { - width: 1500px; - margin: auto; - margin-top: 0; - background-image: url('../images/shield.png'); - background-repeat: no-repeat; - background-position: -40px -20px; - margin-bottom: 210px; -} -.container-inner { - width: 1200px; - margin: auto; - background-color: rgba(223, 227, 228, 0.75); - padding-bottom: 40px; - padding-top: 40px; - border-radius: 15px; -} -.header-content { - padding: 0; - width: 1000px; -} -.title1 { - font-size: 80px; - font-family: 'Vollkorn', serif; - color: #404040; - text-align: center; - padding-top: 40px; - padding-bottom: 100px; -} -#icon { - margin-top: -18px; -} -.subtext { - font-size: 25px; - font-style: italic; - color: #08b; - text-align: right; - padding-right: 250px; -} -.bg-primary { - background-color: #00468b; -} -.navbar-default .nav > li > a, -.navbar-default .nav > li > a:focus { - color: #08b; -} -.navbar-default .nav > li > a, -.navbar-default .nav > li > a:hover { - color: #08b; -} -.navbar-default .nav > li > a, -.navbar-default .nav > li > a:focus:hover { - color: #08b; -} -.text-faded { - font-size: 25px; - font-family: 'Vollkorn', serif; -} -.section-heading { - font-family: 'Vollkorn', serif; - font-size: 45px; - padding-bottom: 10px; -} -hr { - border-color: #00468b; - padding-bottom: 10px; -} -.description { - margin-top: 20px; - padding-bottom: 200px; -} -.description li { - font-family: 'Vollkorn', serif; - font-size: 25px; - color: #525252; - margin-left: 28%; - padding-top: 5px; -} -.gap { - margin-top: 200px; -} -.troubleshootingtext { - color: rgba(255, 255, 255, 0.7); - padding-left: 30%; -} -.troubleshootingtext li { - list-style-type: circle; - font-size: 25px; - padding-bottom: 5px; -} -.overlay { - position: absolute; - top: 0; - left: 0; - width: 100%; - height: 100%; - z-index: 1000; -} -.block.response_body.json:hover { - cursor: pointer; -} -.backdrop { - color: blue; -} -#myModal { - height: 100%; -} -.modal-backdrop { - bottom: 0; - position: fixed; -} -.curl { - padding: 10px; - font-family: "Anonymous Pro", "Menlo", "Consolas", "Bitstream Vera Sans Mono", "Courier New", monospace; - font-size: 0.9em; - max-height: 400px; - margin-top: 5px; - overflow-y: auto; - background-color: #fcf6db; - border: 1px solid #e5e0c6; - border-radius: 4px; -} -.curl_title { - font-size: 1.1em; - margin: 0; - padding: 15px 0 5px; - font-family: 'Open Sans', 'Helvetica Neue', Arial, sans-serif; - font-weight: 500; - line-height: 1.1; -} -.footer { - display: none; -} -.swagger-section .swagger-ui-wrap h2 { - padding: 0; -} -h2 { - margin: 0; - margin-bottom: 5px; -} -.markdown p { - font-size: 15px; - font-family: 'Arvo', serif; -} -.swagger-section .swagger-ui-wrap .code { - font-size: 15px; - font-family: 'Arvo', serif; -} -.swagger-section .swagger-ui-wrap b { - font-family: 'Arvo', serif; -} -#signin:hover { - cursor: pointer; -} -.dropdown-menu { - padding: 15px; -} -.navbar-right .dropdown-menu { - left: 0; - right: auto; -} -#signinbutton { - width: 100%; - height: 32px; - font-size: 13px; - font-weight: bold; - color: #08b; -} -.navbar-default .nav > li .details { - color: #000000; - text-transform: none; - font-size: 15px; - font-weight: normal; - font-family: 'Open Sans', sans-serif; - font-style: italic; - line-height: 20px; - top: -2px; -} -.navbar-default .nav > li .details:hover { - color: black; -} -#signout { - width: 100%; - height: 32px; - font-size: 13px; - font-weight: bold; - color: #08b; -} diff --git a/connexion/vendor/swagger-ui/css/typography.css b/connexion/vendor/swagger-ui/css/typography.css deleted file mode 100644 index efb785fab..000000000 --- a/connexion/vendor/swagger-ui/css/typography.css +++ /dev/null @@ -1,14 +0,0 @@ -/* Google Font's Droid Sans */ -@font-face { - font-family: 'Droid Sans'; - font-style: normal; - font-weight: 400; - src: local('Droid Sans'), local('DroidSans'), url('../fonts/DroidSans.ttf'), format('truetype'); -} -/* Google Font's Droid Sans Bold */ -@font-face { - font-family: 'Droid Sans'; - font-style: normal; - font-weight: 700; - src: local('Droid Sans Bold'), local('DroidSans-Bold'), url('../fonts/DroidSans-Bold.ttf'), format('truetype'); -} diff --git a/connexion/vendor/swagger-ui/fonts/DroidSans-Bold.ttf b/connexion/vendor/swagger-ui/fonts/DroidSans-Bold.ttf deleted file mode 100644 index 036c4d135..000000000 Binary files a/connexion/vendor/swagger-ui/fonts/DroidSans-Bold.ttf and /dev/null differ diff --git a/connexion/vendor/swagger-ui/fonts/DroidSans.ttf b/connexion/vendor/swagger-ui/fonts/DroidSans.ttf deleted file mode 100644 index e517a0c5b..000000000 Binary files a/connexion/vendor/swagger-ui/fonts/DroidSans.ttf and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/collapse.gif b/connexion/vendor/swagger-ui/images/collapse.gif deleted file mode 100644 index 8843e8ce5..000000000 Binary files a/connexion/vendor/swagger-ui/images/collapse.gif and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/expand.gif b/connexion/vendor/swagger-ui/images/expand.gif deleted file mode 100644 index 477bf1371..000000000 Binary files a/connexion/vendor/swagger-ui/images/expand.gif and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/explorer_icons.png b/connexion/vendor/swagger-ui/images/explorer_icons.png deleted file mode 100644 index be43b2739..000000000 Binary files a/connexion/vendor/swagger-ui/images/explorer_icons.png and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/favicon-16x16.png b/connexion/vendor/swagger-ui/images/favicon-16x16.png deleted file mode 100755 index 0f7e13b0d..000000000 Binary files a/connexion/vendor/swagger-ui/images/favicon-16x16.png and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/favicon-32x32.png b/connexion/vendor/swagger-ui/images/favicon-32x32.png deleted file mode 100755 index b0a3352ff..000000000 Binary files a/connexion/vendor/swagger-ui/images/favicon-32x32.png and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/favicon.ico b/connexion/vendor/swagger-ui/images/favicon.ico deleted file mode 100755 index 8b60bcf06..000000000 Binary files a/connexion/vendor/swagger-ui/images/favicon.ico and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/logo_small.png b/connexion/vendor/swagger-ui/images/logo_small.png deleted file mode 100644 index ce3908e3f..000000000 Binary files a/connexion/vendor/swagger-ui/images/logo_small.png and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/pet_store_api.png b/connexion/vendor/swagger-ui/images/pet_store_api.png deleted file mode 100644 index 1192ad8cd..000000000 Binary files a/connexion/vendor/swagger-ui/images/pet_store_api.png and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/throbber.gif b/connexion/vendor/swagger-ui/images/throbber.gif deleted file mode 100644 index 063938892..000000000 Binary files a/connexion/vendor/swagger-ui/images/throbber.gif and /dev/null differ diff --git a/connexion/vendor/swagger-ui/images/wordnik_api.png b/connexion/vendor/swagger-ui/images/wordnik_api.png deleted file mode 100644 index dc0ddab13..000000000 Binary files a/connexion/vendor/swagger-ui/images/wordnik_api.png and /dev/null differ diff --git a/connexion/vendor/swagger-ui/index.html b/connexion/vendor/swagger-ui/index.html deleted file mode 100644 index 0a75cfd5b..000000000 --- a/connexion/vendor/swagger-ui/index.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - Swagger UI - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
-
- - diff --git a/connexion/vendor/swagger-ui/index.html.patch b/connexion/vendor/swagger-ui/index.html.patch deleted file mode 100644 index 62e732fce..000000000 --- a/connexion/vendor/swagger-ui/index.html.patch +++ /dev/null @@ -1,20 +0,0 @@ ---- index.html 2016-09-26 21:25:42.000000000 +0200 -+++ index.html.patched 2016-10-04 14:18:52.110478183 +0200 -@@ -37,7 +37,7 @@ - if (url && url.length > 1) { - url = decodeURIComponent(url[1]); - } else { -- url = "http://petstore.swagger.io/v2/swagger.json"; -+ url = "{{ api_url }}/swagger.json"; - } - - hljs.configure({ -@@ -50,6 +50,8 @@ - } - window.swaggerUi = new SwaggerUi({ - url: url, -+ // https://github.com/zalando/connexion/issues/110 -+ validatorUrl: null, - dom_id: "swagger-ui-container", - supportedSubmitMethods: ['get', 'post', 'put', 'delete', 'patch'], - onComplete: function(swaggerApi, swaggerUi){ diff --git a/connexion/vendor/swagger-ui/lang/ca.js b/connexion/vendor/swagger-ui/lang/ca.js deleted file mode 100644 index f8c815aa9..000000000 --- a/connexion/vendor/swagger-ui/lang/ca.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Advertència: Obsolet", - "Implementation Notes":"Notes d'implementació", - "Response Class":"Classe de la Resposta", - "Status":"Estatus", - "Parameters":"Paràmetres", - "Parameter":"Paràmetre", - "Value":"Valor", - "Description":"Descripció", - "Parameter Type":"Tipus del Paràmetre", - "Data Type":"Tipus de la Dada", - "Response Messages":"Missatges de la Resposta", - "HTTP Status Code":"Codi d'Estatus HTTP", - "Reason":"Raó", - "Response Model":"Model de la Resposta", - "Request URL":"URL de la Sol·licitud", - "Response Body":"Cos de la Resposta", - "Response Code":"Codi de la Resposta", - "Response Headers":"Capçaleres de la Resposta", - "Hide Response":"Amagar Resposta", - "Try it out!":"Prova-ho!", - "Show/Hide":"Mostrar/Amagar", - "List Operations":"Llista Operacions", - "Expand Operations":"Expandir Operacions", - "Raw":"Cru", - "can't parse JSON. Raw result":"no puc analitzar el JSON. Resultat cru", - "Example Value":"Valor d'Exemple", - "Model Schema":"Esquema del Model", - "Model":"Model", - "apply":"aplicar", - "Username":"Nom d'usuari", - "Password":"Contrasenya", - "Terms of service":"Termes del servei", - "Created by":"Creat per", - "See more at":"Veure més en", - "Contact the developer":"Contactar amb el desenvolupador", - "api version":"versió de la api", - "Response Content Type":"Tipus de Contingut de la Resposta", - "fetching resource":"recollint recurs", - "fetching resource list":"recollins llista de recursos", - "Explore":"Explorant", - "Show Swagger Petstore Example Apis":"Mostrar API d'Exemple Swagger Petstore", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"No es pot llegir del servidor. Potser no teniu la configuració de control d'accés apropiada.", - "Please specify the protocol for":"Si us plau, especifiqueu el protocol per a", - "Can't read swagger JSON from":"No es pot llegir el JSON de swagger des de", - "Finished Loading Resource Information. Rendering Swagger UI":"Finalitzada la càrrega del recurs informatiu. Renderitzant Swagger UI", - "Unable to read api":"No es pot llegir l'api", - "from path":"des de la ruta", - "server returned":"el servidor ha retornat" -}); diff --git a/connexion/vendor/swagger-ui/lang/en.js b/connexion/vendor/swagger-ui/lang/en.js deleted file mode 100644 index 918313665..000000000 --- a/connexion/vendor/swagger-ui/lang/en.js +++ /dev/null @@ -1,56 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Warning: Deprecated", - "Implementation Notes":"Implementation Notes", - "Response Class":"Response Class", - "Status":"Status", - "Parameters":"Parameters", - "Parameter":"Parameter", - "Value":"Value", - "Description":"Description", - "Parameter Type":"Parameter Type", - "Data Type":"Data Type", - "Response Messages":"Response Messages", - "HTTP Status Code":"HTTP Status Code", - "Reason":"Reason", - "Response Model":"Response Model", - "Request URL":"Request URL", - "Response Body":"Response Body", - "Response Code":"Response Code", - "Response Headers":"Response Headers", - "Hide Response":"Hide Response", - "Headers":"Headers", - "Try it out!":"Try it out!", - "Show/Hide":"Show/Hide", - "List Operations":"List Operations", - "Expand Operations":"Expand Operations", - "Raw":"Raw", - "can't parse JSON. Raw result":"can't parse JSON. Raw result", - "Example Value":"Example Value", - "Model Schema":"Model Schema", - "Model":"Model", - "Click to set as parameter value":"Click to set as parameter value", - "apply":"apply", - "Username":"Username", - "Password":"Password", - "Terms of service":"Terms of service", - "Created by":"Created by", - "See more at":"See more at", - "Contact the developer":"Contact the developer", - "api version":"api version", - "Response Content Type":"Response Content Type", - "Parameter content type:":"Parameter content type:", - "fetching resource":"fetching resource", - "fetching resource list":"fetching resource list", - "Explore":"Explore", - "Show Swagger Petstore Example Apis":"Show Swagger Petstore Example Apis", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Can't read from server. It may not have the appropriate access-control-origin settings.", - "Please specify the protocol for":"Please specify the protocol for", - "Can't read swagger JSON from":"Can't read swagger JSON from", - "Finished Loading Resource Information. Rendering Swagger UI":"Finished Loading Resource Information. Rendering Swagger UI", - "Unable to read api":"Unable to read api", - "from path":"from path", - "server returned":"server returned" -}); diff --git a/connexion/vendor/swagger-ui/lang/es.js b/connexion/vendor/swagger-ui/lang/es.js deleted file mode 100644 index 13fa015e6..000000000 --- a/connexion/vendor/swagger-ui/lang/es.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Advertencia: Obsoleto", - "Implementation Notes":"Notas de implementación", - "Response Class":"Clase de la Respuesta", - "Status":"Status", - "Parameters":"Parámetros", - "Parameter":"Parámetro", - "Value":"Valor", - "Description":"Descripción", - "Parameter Type":"Tipo del Parámetro", - "Data Type":"Tipo del Dato", - "Response Messages":"Mensajes de la Respuesta", - "HTTP Status Code":"Código de Status HTTP", - "Reason":"Razón", - "Response Model":"Modelo de la Respuesta", - "Request URL":"URL de la Solicitud", - "Response Body":"Cuerpo de la Respuesta", - "Response Code":"Código de la Respuesta", - "Response Headers":"Encabezados de la Respuesta", - "Hide Response":"Ocultar Respuesta", - "Try it out!":"Pruébalo!", - "Show/Hide":"Mostrar/Ocultar", - "List Operations":"Listar Operaciones", - "Expand Operations":"Expandir Operaciones", - "Raw":"Crudo", - "can't parse JSON. Raw result":"no puede parsear el JSON. Resultado crudo", - "Example Value":"Valor de Ejemplo", - "Model Schema":"Esquema del Modelo", - "Model":"Modelo", - "apply":"aplicar", - "Username":"Nombre de usuario", - "Password":"Contraseña", - "Terms of service":"Términos de Servicio", - "Created by":"Creado por", - "See more at":"Ver más en", - "Contact the developer":"Contactar al desarrollador", - "api version":"versión de la api", - "Response Content Type":"Tipo de Contenido (Content Type) de la Respuesta", - "fetching resource":"buscando recurso", - "fetching resource list":"buscando lista del recurso", - "Explore":"Explorar", - "Show Swagger Petstore Example Apis":"Mostrar Api Ejemplo de Swagger Petstore", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"No se puede leer del servidor. Tal vez no tiene la configuración de control de acceso de origen (access-control-origin) apropiado.", - "Please specify the protocol for":"Por favor, especificar el protocola para", - "Can't read swagger JSON from":"No se puede leer el JSON de swagger desde", - "Finished Loading Resource Information. Rendering Swagger UI":"Finalizada la carga del recurso de Información. Mostrando Swagger UI", - "Unable to read api":"No se puede leer la api", - "from path":"desde ruta", - "server returned":"el servidor retornó" -}); diff --git a/connexion/vendor/swagger-ui/lang/fr.js b/connexion/vendor/swagger-ui/lang/fr.js deleted file mode 100644 index 388dff14b..000000000 --- a/connexion/vendor/swagger-ui/lang/fr.js +++ /dev/null @@ -1,54 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Avertissement : Obsolète", - "Implementation Notes":"Notes d'implémentation", - "Response Class":"Classe de la réponse", - "Status":"Statut", - "Parameters":"Paramètres", - "Parameter":"Paramètre", - "Value":"Valeur", - "Description":"Description", - "Parameter Type":"Type du paramètre", - "Data Type":"Type de données", - "Response Messages":"Messages de la réponse", - "HTTP Status Code":"Code de statut HTTP", - "Reason":"Raison", - "Response Model":"Modèle de réponse", - "Request URL":"URL appelée", - "Response Body":"Corps de la réponse", - "Response Code":"Code de la réponse", - "Response Headers":"En-têtes de la réponse", - "Hide Response":"Cacher la réponse", - "Headers":"En-têtes", - "Try it out!":"Testez !", - "Show/Hide":"Afficher/Masquer", - "List Operations":"Liste des opérations", - "Expand Operations":"Développer les opérations", - "Raw":"Brut", - "can't parse JSON. Raw result":"impossible de décoder le JSON. Résultat brut", - "Example Value":"Exemple la valeur", - "Model Schema":"Définition du modèle", - "Model":"Modèle", - "apply":"appliquer", - "Username":"Nom d'utilisateur", - "Password":"Mot de passe", - "Terms of service":"Conditions de service", - "Created by":"Créé par", - "See more at":"Voir plus sur", - "Contact the developer":"Contacter le développeur", - "api version":"version de l'api", - "Response Content Type":"Content Type de la réponse", - "fetching resource":"récupération de la ressource", - "fetching resource list":"récupération de la liste de ressources", - "Explore":"Explorer", - "Show Swagger Petstore Example Apis":"Montrer les Apis de l'exemple Petstore de Swagger", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Impossible de lire à partir du serveur. Il se peut que les réglages access-control-origin ne soient pas appropriés.", - "Please specify the protocol for":"Veuillez spécifier un protocole pour", - "Can't read swagger JSON from":"Impossible de lire le JSON swagger à partir de", - "Finished Loading Resource Information. Rendering Swagger UI":"Chargement des informations terminé. Affichage de Swagger UI", - "Unable to read api":"Impossible de lire l'api", - "from path":"à partir du chemin", - "server returned":"réponse du serveur" -}); diff --git a/connexion/vendor/swagger-ui/lang/geo.js b/connexion/vendor/swagger-ui/lang/geo.js deleted file mode 100644 index 609c20d9c..000000000 --- a/connexion/vendor/swagger-ui/lang/geo.js +++ /dev/null @@ -1,56 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"ყურადღება: აღარ გამოიყენება", - "Implementation Notes":"იმპლემენტაციის აღწერა", - "Response Class":"რესპონს კლასი", - "Status":"სტატუსი", - "Parameters":"პარამეტრები", - "Parameter":"პარამეტრი", - "Value":"მნიშვნელობა", - "Description":"აღწერა", - "Parameter Type":"პარამეტრის ტიპი", - "Data Type":"მონაცემის ტიპი", - "Response Messages":"პასუხი", - "HTTP Status Code":"HTTP სტატუსი", - "Reason":"მიზეზი", - "Response Model":"რესპონს მოდელი", - "Request URL":"მოთხოვნის URL", - "Response Body":"პასუხის სხეული", - "Response Code":"პასუხის კოდი", - "Response Headers":"პასუხის ჰედერები", - "Hide Response":"დამალე პასუხი", - "Headers":"ჰედერები", - "Try it out!":"ცადე !", - "Show/Hide":"გამოჩენა/დამალვა", - "List Operations":"ოპერაციების სია", - "Expand Operations":"ოპერაციები ვრცლად", - "Raw":"ნედლი", - "can't parse JSON. Raw result":"JSON-ის დამუშავება ვერ მოხერხდა. ნედლი პასუხი", - "Example Value":"მაგალითი", - "Model Schema":"მოდელის სტრუქტურა", - "Model":"მოდელი", - "Click to set as parameter value":"პარამეტრისთვის მნიშვნელობის მისანიჭებლად, დააკლიკე", - "apply":"გამოყენება", - "Username":"მოხმარებელი", - "Password":"პაროლი", - "Terms of service":"მომსახურების პირობები", - "Created by":"შექმნა", - "See more at":"ნახე ვრცლად", - "Contact the developer":"დაუკავშირდი დეველოპერს", - "api version":"api ვერსია", - "Response Content Type":"პასუხის კონტენტის ტიპი", - "Parameter content type:":"პარამეტრის კონტენტის ტიპი:", - "fetching resource":"რესურსების მიღება", - "fetching resource list":"რესურსების სიის მიღება", - "Explore":"ნახვა", - "Show Swagger Petstore Example Apis":"ნახე Swagger Petstore სამაგალითო Api", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"სერვერთან დაკავშირება ვერ ხერხდება. შეამოწმეთ access-control-origin.", - "Please specify the protocol for":"მიუთითეთ პროტოკოლი", - "Can't read swagger JSON from":"swagger JSON წაკითხვა ვერ მოხერხდა", - "Finished Loading Resource Information. Rendering Swagger UI":"რესურსების ჩატვირთვა სრულდება. Swagger UI რენდერდება", - "Unable to read api":"api წაკითხვა ვერ მოხერხდა", - "from path":"მისამართიდან", - "server returned":"სერვერმა დააბრუნა" -}); diff --git a/connexion/vendor/swagger-ui/lang/it.js b/connexion/vendor/swagger-ui/lang/it.js deleted file mode 100644 index 8529c2a90..000000000 --- a/connexion/vendor/swagger-ui/lang/it.js +++ /dev/null @@ -1,52 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Attenzione: Deprecato", - "Implementation Notes":"Note di implementazione", - "Response Class":"Classe della risposta", - "Status":"Stato", - "Parameters":"Parametri", - "Parameter":"Parametro", - "Value":"Valore", - "Description":"Descrizione", - "Parameter Type":"Tipo di parametro", - "Data Type":"Tipo di dato", - "Response Messages":"Messaggi della risposta", - "HTTP Status Code":"Codice stato HTTP", - "Reason":"Motivo", - "Response Model":"Modello di risposta", - "Request URL":"URL della richiesta", - "Response Body":"Corpo della risposta", - "Response Code":"Oggetto della risposta", - "Response Headers":"Intestazioni della risposta", - "Hide Response":"Nascondi risposta", - "Try it out!":"Provalo!", - "Show/Hide":"Mostra/Nascondi", - "List Operations":"Mostra operazioni", - "Expand Operations":"Espandi operazioni", - "Raw":"Grezzo (raw)", - "can't parse JSON. Raw result":"non è possibile parsare il JSON. Risultato grezzo (raw).", - "Model Schema":"Schema del modello", - "Model":"Modello", - "apply":"applica", - "Username":"Nome utente", - "Password":"Password", - "Terms of service":"Condizioni del servizio", - "Created by":"Creato da", - "See more at":"Informazioni aggiuntive:", - "Contact the developer":"Contatta lo sviluppatore", - "api version":"versione api", - "Response Content Type":"Tipo di contenuto (content type) della risposta", - "fetching resource":"recuperando la risorsa", - "fetching resource list":"recuperando lista risorse", - "Explore":"Esplora", - "Show Swagger Petstore Example Apis":"Mostra le api di esempio di Swagger Petstore", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Non è possibile leggere dal server. Potrebbe non avere le impostazioni di controllo accesso origine (access-control-origin) appropriate.", - "Please specify the protocol for":"Si prega di specificare il protocollo per", - "Can't read swagger JSON from":"Impossibile leggere JSON swagger da:", - "Finished Loading Resource Information. Rendering Swagger UI":"Lettura informazioni risorse termianta. Swagger UI viene mostrata", - "Unable to read api":"Impossibile leggere la api", - "from path":"da cartella", - "server returned":"il server ha restituito" -}); diff --git a/connexion/vendor/swagger-ui/lang/ja.js b/connexion/vendor/swagger-ui/lang/ja.js deleted file mode 100755 index 3207bfc0b..000000000 --- a/connexion/vendor/swagger-ui/lang/ja.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"警告: 廃止予定", - "Implementation Notes":"実装メモ", - "Response Class":"レスポンスクラス", - "Status":"ステータス", - "Parameters":"パラメータ群", - "Parameter":"パラメータ", - "Value":"値", - "Description":"説明", - "Parameter Type":"パラメータタイプ", - "Data Type":"データタイプ", - "Response Messages":"レスポンスメッセージ", - "HTTP Status Code":"HTTPステータスコード", - "Reason":"理由", - "Response Model":"レスポンスモデル", - "Request URL":"リクエストURL", - "Response Body":"レスポンスボディ", - "Response Code":"レスポンスコード", - "Response Headers":"レスポンスヘッダ", - "Hide Response":"レスポンスを隠す", - "Headers":"ヘッダ", - "Try it out!":"実際に実行!", - "Show/Hide":"表示/非表示", - "List Operations":"操作一覧", - "Expand Operations":"操作の展開", - "Raw":"Raw", - "can't parse JSON. Raw result":"JSONへ解釈できません. 未加工の結果", - "Model Schema":"モデルスキーマ", - "Model":"モデル", - "apply":"実行", - "Username":"ユーザ名", - "Password":"パスワード", - "Terms of service":"サービス利用規約", - "Created by":"Created by", - "See more at":"See more at", - "Contact the developer":"開発者に連絡", - "api version":"APIバージョン", - "Response Content Type":"レスポンス コンテンツタイプ", - "fetching resource":"リソースの取得", - "fetching resource list":"リソース一覧の取得", - "Explore":"Explore", - "Show Swagger Petstore Example Apis":"SwaggerペットストアAPIの表示", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"サーバから読み込めません. 適切なaccess-control-origin設定を持っていない可能性があります.", - "Please specify the protocol for":"プロトコルを指定してください", - "Can't read swagger JSON from":"次からswagger JSONを読み込めません", - "Finished Loading Resource Information. Rendering Swagger UI":"リソース情報の読み込みが完了しました. Swagger UIを描画しています", - "Unable to read api":"APIを読み込めません", - "from path":"次のパスから", - "server returned":"サーバからの返答" -}); diff --git a/connexion/vendor/swagger-ui/lang/ko-kr.js b/connexion/vendor/swagger-ui/lang/ko-kr.js deleted file mode 100644 index 03c7626d7..000000000 --- a/connexion/vendor/swagger-ui/lang/ko-kr.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"경고:폐기예정됨", - "Implementation Notes":"구현 노트", - "Response Class":"응답 클래스", - "Status":"상태", - "Parameters":"매개변수들", - "Parameter":"매개변수", - "Value":"값", - "Description":"설명", - "Parameter Type":"매개변수 타입", - "Data Type":"데이터 타입", - "Response Messages":"응답 메세지", - "HTTP Status Code":"HTTP 상태 코드", - "Reason":"원인", - "Response Model":"응답 모델", - "Request URL":"요청 URL", - "Response Body":"응답 본문", - "Response Code":"응답 코드", - "Response Headers":"응답 헤더", - "Hide Response":"응답 숨기기", - "Headers":"헤더", - "Try it out!":"써보기!", - "Show/Hide":"보이기/숨기기", - "List Operations":"목록 작업", - "Expand Operations":"전개 작업", - "Raw":"원본", - "can't parse JSON. Raw result":"JSON을 파싱할수 없음. 원본결과:", - "Model Schema":"모델 스키마", - "Model":"모델", - "apply":"적용", - "Username":"사용자 이름", - "Password":"암호", - "Terms of service":"이용약관", - "Created by":"작성자", - "See more at":"추가정보:", - "Contact the developer":"개발자에게 문의", - "api version":"api버전", - "Response Content Type":"응답Content Type", - "fetching resource":"리소스 가져오기", - "fetching resource list":"리소스 목록 가져오기", - "Explore":"탐색", - "Show Swagger Petstore Example Apis":"Swagger Petstore 예제 보기", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"서버로부터 읽어들일수 없습니다. access-control-origin 설정이 올바르지 않을수 있습니다.", - "Please specify the protocol for":"다음을 위한 프로토콜을 정하세요", - "Can't read swagger JSON from":"swagger JSON 을 다음으로 부터 읽을수 없습니다", - "Finished Loading Resource Information. Rendering Swagger UI":"리소스 정보 불러오기 완료. Swagger UI 랜더링", - "Unable to read api":"api를 읽을 수 없습니다.", - "from path":"다음 경로로 부터", - "server returned":"서버 응답함." -}); diff --git a/connexion/vendor/swagger-ui/lang/pl.js b/connexion/vendor/swagger-ui/lang/pl.js deleted file mode 100644 index ce41e9179..000000000 --- a/connexion/vendor/swagger-ui/lang/pl.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Uwaga: Wycofane", - "Implementation Notes":"Uwagi Implementacji", - "Response Class":"Klasa Odpowiedzi", - "Status":"Status", - "Parameters":"Parametry", - "Parameter":"Parametr", - "Value":"Wartość", - "Description":"Opis", - "Parameter Type":"Typ Parametru", - "Data Type":"Typ Danych", - "Response Messages":"Wiadomości Odpowiedzi", - "HTTP Status Code":"Kod Statusu HTTP", - "Reason":"Przyczyna", - "Response Model":"Model Odpowiedzi", - "Request URL":"URL Wywołania", - "Response Body":"Treść Odpowiedzi", - "Response Code":"Kod Odpowiedzi", - "Response Headers":"Nagłówki Odpowiedzi", - "Hide Response":"Ukryj Odpowiedź", - "Headers":"Nagłówki", - "Try it out!":"Wypróbuj!", - "Show/Hide":"Pokaż/Ukryj", - "List Operations":"Lista Operacji", - "Expand Operations":"Rozwiń Operacje", - "Raw":"Nieprzetworzone", - "can't parse JSON. Raw result":"nie można przetworzyć pliku JSON. Nieprzetworzone dane", - "Model Schema":"Schemat Modelu", - "Model":"Model", - "apply":"użyj", - "Username":"Nazwa użytkownika", - "Password":"Hasło", - "Terms of service":"Warunki używania", - "Created by":"Utworzone przez", - "See more at":"Zobacz więcej na", - "Contact the developer":"Kontakt z deweloperem", - "api version":"wersja api", - "Response Content Type":"Typ Zasobu Odpowiedzi", - "fetching resource":"ładowanie zasobu", - "fetching resource list":"ładowanie listy zasobów", - "Explore":"Eksploruj", - "Show Swagger Petstore Example Apis":"Pokaż Przykładowe Api Swagger Petstore", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Brak połączenia z serwerem. Może on nie mieć odpowiednich ustawień access-control-origin.", - "Please specify the protocol for":"Proszę podać protokół dla", - "Can't read swagger JSON from":"Nie można odczytać swagger JSON z", - "Finished Loading Resource Information. Rendering Swagger UI":"Ukończono Ładowanie Informacji o Zasobie. Renderowanie Swagger UI", - "Unable to read api":"Nie można odczytać api", - "from path":"ze ścieżki", - "server returned":"serwer zwrócił" -}); diff --git a/connexion/vendor/swagger-ui/lang/pt.js b/connexion/vendor/swagger-ui/lang/pt.js deleted file mode 100644 index f2e7c13d4..000000000 --- a/connexion/vendor/swagger-ui/lang/pt.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Aviso: Depreciado", - "Implementation Notes":"Notas de Implementação", - "Response Class":"Classe de resposta", - "Status":"Status", - "Parameters":"Parâmetros", - "Parameter":"Parâmetro", - "Value":"Valor", - "Description":"Descrição", - "Parameter Type":"Tipo de parâmetro", - "Data Type":"Tipo de dados", - "Response Messages":"Mensagens de resposta", - "HTTP Status Code":"Código de status HTTP", - "Reason":"Razão", - "Response Model":"Modelo resposta", - "Request URL":"URL requisição", - "Response Body":"Corpo da resposta", - "Response Code":"Código da resposta", - "Response Headers":"Cabeçalho da resposta", - "Headers":"Cabeçalhos", - "Hide Response":"Esconder resposta", - "Try it out!":"Tente agora!", - "Show/Hide":"Mostrar/Esconder", - "List Operations":"Listar operações", - "Expand Operations":"Expandir operações", - "Raw":"Cru", - "can't parse JSON. Raw result":"Falha ao analisar JSON. Resulto cru", - "Model Schema":"Modelo esquema", - "Model":"Modelo", - "apply":"Aplicar", - "Username":"Usuário", - "Password":"Senha", - "Terms of service":"Termos do serviço", - "Created by":"Criado por", - "See more at":"Veja mais em", - "Contact the developer":"Contate o desenvolvedor", - "api version":"Versão api", - "Response Content Type":"Tipo de conteúdo da resposta", - "fetching resource":"busca recurso", - "fetching resource list":"buscando lista de recursos", - "Explore":"Explorar", - "Show Swagger Petstore Example Apis":"Show Swagger Petstore Example Apis", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Não é possível ler do servidor. Pode não ter as apropriadas configurações access-control-origin", - "Please specify the protocol for":"Por favor especifique o protocolo", - "Can't read swagger JSON from":"Não é possível ler o JSON Swagger de", - "Finished Loading Resource Information. Rendering Swagger UI":"Carregar informação de recurso finalizada. Renderizando Swagger UI", - "Unable to read api":"Não foi possível ler api", - "from path":"do caminho", - "server returned":"servidor retornou" -}); diff --git a/connexion/vendor/swagger-ui/lang/ru.js b/connexion/vendor/swagger-ui/lang/ru.js deleted file mode 100644 index 592744e95..000000000 --- a/connexion/vendor/swagger-ui/lang/ru.js +++ /dev/null @@ -1,56 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Предупреждение: Устарело", - "Implementation Notes":"Заметки", - "Response Class":"Пример ответа", - "Status":"Статус", - "Parameters":"Параметры", - "Parameter":"Параметр", - "Value":"Значение", - "Description":"Описание", - "Parameter Type":"Тип параметра", - "Data Type":"Тип данных", - "HTTP Status Code":"HTTP код", - "Reason":"Причина", - "Response Model":"Структура ответа", - "Request URL":"URL запроса", - "Response Body":"Тело ответа", - "Response Code":"HTTP код ответа", - "Response Headers":"Заголовки ответа", - "Hide Response":"Спрятать ответ", - "Headers":"Заголовки", - "Response Messages":"Что может прийти в ответ", - "Try it out!":"Попробовать!", - "Show/Hide":"Показать/Скрыть", - "List Operations":"Операции кратко", - "Expand Operations":"Операции подробно", - "Raw":"В сыром виде", - "can't parse JSON. Raw result":"Не удается распарсить ответ:", - "Example Value":"Пример", - "Model Schema":"Структура", - "Model":"Описание", - "Click to set as parameter value":"Нажмите, чтобы испльзовать в качестве значения параметра", - "apply":"применить", - "Username":"Имя пользователя", - "Password":"Пароль", - "Terms of service":"Условия использования", - "Created by":"Разработано", - "See more at":"Еще тут", - "Contact the developer":"Связаться с разработчиком", - "api version":"Версия API", - "Response Content Type":"Content Type ответа", - "Parameter content type:":"Content Type параметра:", - "fetching resource":"Получение ресурса", - "fetching resource list":"Получение ресурсов", - "Explore":"Показать", - "Show Swagger Petstore Example Apis":"Показать примеры АПИ", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Не удается получить ответ от сервера. Возможно, проблема с настройками доступа", - "Please specify the protocol for":"Пожалуйста, укажите протокол для", - "Can't read swagger JSON from":"Не получается прочитать swagger json из", - "Finished Loading Resource Information. Rendering Swagger UI":"Загрузка информации о ресурсах завершена. Рендерим", - "Unable to read api":"Не удалось прочитать api", - "from path":"по адресу", - "server returned":"сервер сказал" -}); diff --git a/connexion/vendor/swagger-ui/lang/tr.js b/connexion/vendor/swagger-ui/lang/tr.js deleted file mode 100644 index 16426a9c3..000000000 --- a/connexion/vendor/swagger-ui/lang/tr.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"Uyarı: Deprecated", - "Implementation Notes":"Gerçekleştirim Notları", - "Response Class":"Dönen Sınıf", - "Status":"Statü", - "Parameters":"Parametreler", - "Parameter":"Parametre", - "Value":"Değer", - "Description":"Açıklama", - "Parameter Type":"Parametre Tipi", - "Data Type":"Veri Tipi", - "Response Messages":"Dönüş Mesajı", - "HTTP Status Code":"HTTP Statü Kodu", - "Reason":"Gerekçe", - "Response Model":"Dönüş Modeli", - "Request URL":"İstek URL", - "Response Body":"Dönüş İçeriği", - "Response Code":"Dönüş Kodu", - "Response Headers":"Dönüş Üst Bilgileri", - "Hide Response":"Dönüşü Gizle", - "Headers":"Üst Bilgiler", - "Try it out!":"Dene!", - "Show/Hide":"Göster/Gizle", - "List Operations":"Operasyonları Listele", - "Expand Operations":"Operasyonları Aç", - "Raw":"Ham", - "can't parse JSON. Raw result":"JSON çözümlenemiyor. Ham sonuç", - "Model Schema":"Model Şema", - "Model":"Model", - "apply":"uygula", - "Username":"Kullanıcı Adı", - "Password":"Parola", - "Terms of service":"Servis şartları", - "Created by":"Oluşturan", - "See more at":"Daha fazlası için", - "Contact the developer":"Geliştirici ile İletişime Geçin", - "api version":"api versiyon", - "Response Content Type":"Dönüş İçerik Tipi", - "fetching resource":"kaynak getiriliyor", - "fetching resource list":"kaynak listesi getiriliyor", - "Explore":"Keşfet", - "Show Swagger Petstore Example Apis":"Swagger Petstore Örnek Api'yi Gör", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"Sunucudan okuma yapılamıyor. Sunucu access-control-origin ayarlarınızı kontrol edin.", - "Please specify the protocol for":"Lütfen istenen adres için protokol belirtiniz", - "Can't read swagger JSON from":"Swagger JSON bu kaynaktan okunamıyor", - "Finished Loading Resource Information. Rendering Swagger UI":"Kaynak baglantısı tamamlandı. Swagger UI gösterime hazırlanıyor", - "Unable to read api":"api okunamadı", - "from path":"yoldan", - "server returned":"sunucuya dönüldü" -}); diff --git a/connexion/vendor/swagger-ui/lang/translator.js b/connexion/vendor/swagger-ui/lang/translator.js deleted file mode 100644 index ffb879f9a..000000000 --- a/connexion/vendor/swagger-ui/lang/translator.js +++ /dev/null @@ -1,39 +0,0 @@ -'use strict'; - -/** - * Translator for documentation pages. - * - * To enable translation you should include one of language-files in your index.html - * after . - * For example - - * - * If you wish to translate some new texts you should do two things: - * 1. Add a new phrase pair ("New Phrase": "New Translation") into your language file (for example lang/ru.js). It will be great if you add it in other language files too. - * 2. Mark that text it templates this way New Phrase or . - * The main thing here is attribute data-sw-translate. Only inner html, title-attribute and value-attribute are going to translate. - * - */ -window.SwaggerTranslator = { - - _words:[], - - translate: function(sel) { - var $this = this; - sel = sel || '[data-sw-translate]'; - - $(sel).each(function() { - $(this).html($this._tryTranslate($(this).html())); - - $(this).val($this._tryTranslate($(this).val())); - $(this).attr('title', $this._tryTranslate($(this).attr('title'))); - }); - }, - - _tryTranslate: function(word) { - return this._words[$.trim(word)] !== undefined ? this._words[$.trim(word)] : word; - }, - - learn: function(wordsMap) { - this._words = wordsMap; - } -}; diff --git a/connexion/vendor/swagger-ui/lang/zh-cn.js b/connexion/vendor/swagger-ui/lang/zh-cn.js deleted file mode 100644 index 570319ba1..000000000 --- a/connexion/vendor/swagger-ui/lang/zh-cn.js +++ /dev/null @@ -1,53 +0,0 @@ -'use strict'; - -/* jshint quotmark: double */ -window.SwaggerTranslator.learn({ - "Warning: Deprecated":"警告:已过时", - "Implementation Notes":"实现备注", - "Response Class":"响应类", - "Status":"状态", - "Parameters":"参数", - "Parameter":"参数", - "Value":"值", - "Description":"描述", - "Parameter Type":"参数类型", - "Data Type":"数据类型", - "Response Messages":"响应消息", - "HTTP Status Code":"HTTP状态码", - "Reason":"原因", - "Response Model":"响应模型", - "Request URL":"请求URL", - "Response Body":"响应体", - "Response Code":"响应码", - "Response Headers":"响应头", - "Hide Response":"隐藏响应", - "Headers":"头", - "Try it out!":"试一下!", - "Show/Hide":"显示/隐藏", - "List Operations":"显示操作", - "Expand Operations":"展开操作", - "Raw":"原始", - "can't parse JSON. Raw result":"无法解析JSON. 原始结果", - "Model Schema":"模型架构", - "Model":"模型", - "apply":"应用", - "Username":"用户名", - "Password":"密码", - "Terms of service":"服务条款", - "Created by":"创建者", - "See more at":"查看更多:", - "Contact the developer":"联系开发者", - "api version":"api版本", - "Response Content Type":"响应Content Type", - "fetching resource":"正在获取资源", - "fetching resource list":"正在获取资源列表", - "Explore":"浏览", - "Show Swagger Petstore Example Apis":"显示 Swagger Petstore 示例 Apis", - "Can't read from server. It may not have the appropriate access-control-origin settings.":"无法从服务器读取。可能没有正确设置access-control-origin。", - "Please specify the protocol for":"请指定协议:", - "Can't read swagger JSON from":"无法读取swagger JSON于", - "Finished Loading Resource Information. Rendering Swagger UI":"已加载资源信息。正在渲染Swagger UI", - "Unable to read api":"无法读取api", - "from path":"从路径", - "server returned":"服务器返回" -}); diff --git a/connexion/vendor/swagger-ui/lib/backbone-min.js b/connexion/vendor/swagger-ui/lib/backbone-min.js deleted file mode 100644 index a3f544be6..000000000 --- a/connexion/vendor/swagger-ui/lib/backbone-min.js +++ /dev/null @@ -1,15 +0,0 @@ -// Backbone.js 1.1.2 - -(function(t,e){if(typeof define==="function"&&define.amd){define(["underscore","jquery","exports"],function(i,r,s){t.Backbone=e(t,s,i,r)})}else if(typeof exports!=="undefined"){var i=require("underscore");e(t,exports,i)}else{t.Backbone=e(t,{},t._,t.jQuery||t.Zepto||t.ender||t.$)}})(this,function(t,e,i,r){var s=t.Backbone;var n=[];var a=n.push;var o=n.slice;var h=n.splice;e.VERSION="1.1.2";e.$=r;e.noConflict=function(){t.Backbone=s;return this};e.emulateHTTP=false;e.emulateJSON=false;var u=e.Events={on:function(t,e,i){if(!c(this,"on",t,[e,i])||!e)return this;this._events||(this._events={});var r=this._events[t]||(this._events[t]=[]);r.push({callback:e,context:i,ctx:i||this});return this},once:function(t,e,r){if(!c(this,"once",t,[e,r])||!e)return this;var s=this;var n=i.once(function(){s.off(t,n);e.apply(this,arguments)});n._callback=e;return this.on(t,n,r)},off:function(t,e,r){var s,n,a,o,h,u,l,f;if(!this._events||!c(this,"off",t,[e,r]))return this;if(!t&&!e&&!r){this._events=void 0;return this}o=t?[t]:i.keys(this._events);for(h=0,u=o.length;h").attr(t);this.setElement(r,false)}else{this.setElement(i.result(this,"el"),false)}}});e.sync=function(t,r,s){var n=T[t];i.defaults(s||(s={}),{emulateHTTP:e.emulateHTTP,emulateJSON:e.emulateJSON});var a={type:n,dataType:"json"};if(!s.url){a.url=i.result(r,"url")||M()}if(s.data==null&&r&&(t==="create"||t==="update"||t==="patch")){a.contentType="application/json";a.data=JSON.stringify(s.attrs||r.toJSON(s))}if(s.emulateJSON){a.contentType="application/x-www-form-urlencoded";a.data=a.data?{model:a.data}:{}}if(s.emulateHTTP&&(n==="PUT"||n==="DELETE"||n==="PATCH")){a.type="POST";if(s.emulateJSON)a.data._method=n;var o=s.beforeSend;s.beforeSend=function(t){t.setRequestHeader("X-HTTP-Method-Override",n);if(o)return o.apply(this,arguments)}}if(a.type!=="GET"&&!s.emulateJSON){a.processData=false}if(a.type==="PATCH"&&k){a.xhr=function(){return new ActiveXObject("Microsoft.XMLHTTP")}}var h=s.xhr=e.ajax(i.extend(a,s));r.trigger("request",r,h,s);return h};var k=typeof window!=="undefined"&&!!window.ActiveXObject&&!(window.XMLHttpRequest&&(new XMLHttpRequest).dispatchEvent);var T={create:"POST",update:"PUT",patch:"PATCH","delete":"DELETE",read:"GET"};e.ajax=function(){return e.$.ajax.apply(e.$,arguments)};var $=e.Router=function(t){t||(t={});if(t.routes)this.routes=t.routes;this._bindRoutes();this.initialize.apply(this,arguments)};var S=/\((.*?)\)/g;var H=/(\(\?)?:\w+/g;var A=/\*\w+/g;var I=/[\-{}\[\]+?.,\\\^$|#\s]/g;i.extend($.prototype,u,{initialize:function(){},route:function(t,r,s){if(!i.isRegExp(t))t=this._routeToRegExp(t);if(i.isFunction(r)){s=r;r=""}if(!s)s=this[r];var n=this;e.history.route(t,function(i){var a=n._extractParameters(t,i);n.execute(s,a);n.trigger.apply(n,["route:"+r].concat(a));n.trigger("route",r,a);e.history.trigger("route",n,r,a)});return this},execute:function(t,e){if(t)t.apply(this,e)},navigate:function(t,i){e.history.navigate(t,i);return this},_bindRoutes:function(){if(!this.routes)return;this.routes=i.result(this,"routes");var t,e=i.keys(this.routes);while((t=e.pop())!=null){this.route(t,this.routes[t])}},_routeToRegExp:function(t){t=t.replace(I,"\\$&").replace(S,"(?:$1)?").replace(H,function(t,e){return e?t:"([^/?]+)"}).replace(A,"([^?]*?)");return new RegExp("^"+t+"(?:\\?([\\s\\S]*))?$")},_extractParameters:function(t,e){var r=t.exec(e).slice(1);return i.map(r,function(t,e){if(e===r.length-1)return t||null;return t?decodeURIComponent(t):null})}});var N=e.History=function(){this.handlers=[];i.bindAll(this,"checkUrl");if(typeof window!=="undefined"){this.location=window.location;this.history=window.history}};var R=/^[#\/]|\s+$/g;var O=/^\/+|\/+$/g;var P=/msie [\w.]+/;var C=/\/$/;var j=/#.*$/;N.started=false;i.extend(N.prototype,u,{interval:50,atRoot:function(){return this.location.pathname.replace(/[^\/]$/,"$&/")===this.root},getHash:function(t){var e=(t||this).location.href.match(/#(.*)$/);return e?e[1]:""},getFragment:function(t,e){if(t==null){if(this._hasPushState||!this._wantsHashChange||e){t=decodeURI(this.location.pathname+this.location.search);var i=this.root.replace(C,"");if(!t.indexOf(i))t=t.slice(i.length)}else{t=this.getHash()}}return t.replace(R,"")},start:function(t){if(N.started)throw new Error("Backbone.history has already been started");N.started=true;this.options=i.extend({root:"/"},this.options,t);this.root=this.options.root;this._wantsHashChange=this.options.hashChange!==false;this._wantsPushState=!!this.options.pushState;this._hasPushState=!!(this.options.pushState&&this.history&&this.history.pushState);var r=this.getFragment();var s=document.documentMode;var n=P.exec(navigator.userAgent.toLowerCase())&&(!s||s<=7);this.root=("/"+this.root+"/").replace(O,"/");if(n&&this._wantsHashChange){var a=e.$('