def test_build_fluent(): base_dir = _get_base_dir() full = yaml.load(open(path.join(base_dir, "full.yml")).read()) spec = SpecBuilder().add_spec(path.join(base_dir, "security.yml"))\ .add_spec(path.join(base_dir, "base.yml"))\ .add_spec(path.join(base_dir, "definitions.yml"))\ .add_spec(path.join(base_dir, "paths.yml")) _check_dicts(full, spec) _check_dicts(spec, full)
def test_dump(): base_dir = _get_base_dir() parts = ["base.yml", "definitions.yml", "paths.yml", "security.yml"] full = yaml.load(open(path.join(base_dir, "full.yml")).read()) spec = SpecBuilder() for p in parts: spec.add_spec(path.join(base_dir, p)) # Dumping and reloading the yaml is slow, but we can't compare dumped # strings because of potential key ordering differences. assert full == yaml.load(spec.dump())
def add_openapi(app): """Add OpenAPI specification to connexion app instance""" try: specs = SpecBuilder()\ .add_spec(config["openapi"]["drs"])\ .add_spec(config["openapi"]["db_update"]) app.add_api( specs, validate_responses=True, strict_validation=True, ) except KeyError: sys.exit("Config file corrupt. Execution aborted.") return app
def pytest_generate_tests(metafunc): if 'path' in metafunc.fixturenames: from swagger_parser import SwaggerParser from specsynthase.specbuilder import SpecBuilder import glob from os import path spec = SpecBuilder() for spec_file in glob.glob(path.join(path.dirname(__file__), '../swagger/*')): spec.add_spec(spec_file) requests = [] for path_name, path_spec in spec['paths'].iteritems(): url = _url_from_swagger_spec(path_name, path_spec) service = _identify_service_from_tag(path_spec['get']['tags']) requests.append((service, url)) metafunc.parametrize("service,path", requests)
try: from urllib import unquote except ImportError: # pragma: no cover from urllib.parse import unquote log = logging.getLogger(__name__) current_dir = path.dirname(__file__) web_dir = path.dirname(auslib.web.__file__) spec = ( SpecBuilder() .add_spec(path.join(current_dir, "swagger/api.yml")) .add_spec(path.join(web_dir, "common/swagger/definitions.yml")) .add_spec(path.join(web_dir, "common/swagger/parameters.yml")) .add_spec(path.join(web_dir, "common/swagger/responses.yml")) ) validator_map = {"body": BalrogRequestBodyValidator} connexion_app = connexion.App(__name__, debug=False, options={"swagger_ui": False}) connexion_app.add_api(spec, validator_map=validator_map, strict_validation=True) connexion_app.add_api(path.join(current_dir, "swagger", "api_v2.yml"), base_path="/v2", strict_validation=True, validate_responses=True) app = connexion_app.app create_dockerflow_endpoints(app) # When running under uwsgi, paths will not get decoded before hitting the app.
from flask_cors import CORS CORS(app.app) from services.cache import cache cache.init_app(app.app) import services.limiter limiter = services.limiter.init(app.app) import config from specsynthase.specbuilder import SpecBuilder import glob from os import path spec = SpecBuilder() if not 'EXPOSED_APIS' in dir(config) or len(config.EXPOSED_APIS) == 0: for spec_file in glob.glob(path.join(path.dirname(__file__), 'swagger/*')): spec.add_spec(spec_file) else: spec.add_spec(path.join(path.dirname(__file__), 'swagger/api.yaml')) for api in config.EXPOSED_APIS: spec.add_spec( path.join(path.dirname(__file__), 'swagger/paths_{}.yaml'.format(api))) app.add_api(spec) import services.profiler services.profiler.init_app(app.app) application = app.app
from os import path from flask import request from connexion import problem from flask_compress import Compress from auslib.web.admin.views.validators import BalrogRequestBodyValidator from raven.contrib.flask import Sentry from specsynthase.specbuilder import SpecBuilder log = logging.getLogger(__name__) current_dir = path.dirname(__file__) web_dir = path.dirname(auslib.web.__file__) spec = SpecBuilder().add_spec(path.join(current_dir, 'swagger/api.yaml'))\ .add_spec(path.join(web_dir, 'common/swagger/definitions.yml'))\ .add_spec(path.join(web_dir, 'common/swagger/parameters.yml'))\ .add_spec(path.join(web_dir, 'common/swagger/responses.yml')) validator_map = {'body': BalrogRequestBodyValidator} connexion_app = connexion.App(__name__, validator_map=validator_map, debug=False) connexion_app.add_api(spec, validate_responses=True, strict_validation=True) app = connexion_app.app sentry = Sentry() from auslib.dockerflow import create_dockerflow_endpoints create_dockerflow_endpoints(app)
from flask_cors import CORS from pathlib import Path from os import path from specsynthase.specbuilder import SpecBuilder from swagger_ui_bundle import swagger_ui_3_path from connexion.resolver import Resolver from connexion.utils import get_function_from_name from db.mongo import MongoDb spec_dir = "./specs" current_dir = path.dirname(__file__) spec_path = Path(f"{current_dir}/{spec_dir}").resolve() spec = SpecBuilder()\ .add_spec(spec_path.joinpath("cm4.yaml")) \ .add_spec(spec_path.joinpath("vm.yaml")) \ .add_spec(spec_path.joinpath("flavor.yaml"))\ .add_spec(spec_path.joinpath("image.yaml")) options = {'swagger_path': swagger_ui_3_path} app = connexion.FlaskApp(__name__, specification_dir=spec_dir, options=options) # Inject the `controllers` namespace into `operationId`s specified in the spec # files. This allows for the (potentially many) controllers to be organized # into thier own folder and to potentially have multiple versions of the # controller classes in different folders. custom_resolver = Resolver(function_resolver=lambda fname: get_function_from_name(f"controllers.{fname}")) app.add_api(spec, resolver=custom_resolver) CORS(app.app)
def test_validation_fail(): base_dir = _get_base_dir() with pytest.raises(SwaggerValidationError): SpecBuilder().add_spec(path.join(base_dir, "base.yml")).validate()
def test_build_existing_key(): base_dir = _get_base_dir() with pytest.raises(ValueError): SpecBuilder().add_spec(path.join(base_dir, "base.yml"))\ .add_spec(path.join(base_dir, "definitions.yml"))\ .add_spec(path.join(base_dir, "definitions.yml"))
def create_app(config_object='config.DevelopmentConfig'): app = connexion.FlaskApp(__name__, specification_dir='api/specification/') # This is required for Flask CLI and FLASK_APP env to work flask_app = app.app flask_app.secret_key = os.environ.get('APP_SECRET_KEY') flask_app.config.from_object(config_object) # Specsynthase's SpecBuilder combines multiple Swagger yaml files into a one. # This is purely used for modularity. # https://github.com/zalando/connexion/issues/254 api_spec = _build_swagger_spec(SpecBuilder()) # In case you don't want to show the swagger_ui for private endpoints # You might want to split this into two apis enable_swagger = flask_app.config['ENABLE_SWAGGER_UI'] app.add_api(api_spec, options={"swagger_ui": enable_swagger}) db.init_app(flask_app) JWT.init_app(flask_app) migrate = Migrate(flask_app, db, compare_type=True) # CORS settings for allowing suggestions from a Skosmos client CORS(flask_app, resources={ r"/api/suggestions": { "origins": os.environ.get('SKOSMOS_URI'), "allow_headers": ['Content-Type', 'Access-Control-Allow-Origin'], "methods": ['POST', 'OPTIONS'] } }) @flask_app.shell_context_processor def shell_context(): #pylint: disable=unused-variable #pylint: disable=import-outside-toplevel from pprint import pprint from api import models #pylint: enable=import-outside-toplevel return { 'app': app, 'db': models.db, 'pprint': pprint, 'models': models } # models.db. @flask_app.cli.command(db.JSON) def prune(): #pylint: disable=unused-variable """ Prunes the JWT token blacklist. Run this from command line (or periodically from crontab, for example) >> flask prune """ no_pruned = prune_expired_tokens() click.echo( '{} expired tokens pruned from the database.'.format(no_pruned)) @flask_app.cli.command() @click.argument('name') @click.argument('email') @click.argument('password') def create_admin(name, email, password): #pylint: disable=unused-variable """ Creates an admin user Run this from command line >> flask create_admin """ user = User(name=name, email=email, password=password, role=UserRoles.ADMIN) db.session.add(user) db.session.commit() click.echo('Created admin user {}.'.format(email)) return app