Search code examples
pythonswaggerswagger-uiflask-restplus

How to generate a machine readable yaml specification of an existing API written in flask-restplus?


I have a simple API written with the help of flask-restplus:

from flask import Flask
from flask_restplus import Resource, Api

app = Flask(__name__)                  #  Create a Flask WSGI application
api = Api(app)                         #  Create a Flask-RESTPlus API

@api.route('/hello')                   #  Create a URL route to this resource
class HelloWorld(Resource):            #  Create a RESTful resource
    def get(self):                     #  Create GET endpoint
        return {'hello': 'world'}

if __name__ == '__main__':
    app.run(debug=True) 

When I navigate to loacalhost:5000/ in the browser I get a basic Swagger documentation, but I can't find where do I get a machine readable plain yaml representation of the API, should't it be also generated automatically?


Solution

  • I could not find any information around "Swagger Yaml documentation generation" in the official flask-restplus docs. So, I decided to examine the source code and found that the Swagger class implements the Swagger documentation generation for the API instance.

    The Swagger class in the flask-restplus source-code is the Swagger documentation wrapper for an API instance. All methods in this class suggest that the API data is serialized as a JSON dictionary. For instance, consider the as_dict() function of this class which serializes the full Swagger specification as a serializable dict. Take a look at the docstring for this function:

    from flask import Flask
    from flask_restplus import Resource, Api
    from flask_restplus.api import Swagger
    
    app = Flask(__name__)                  
    api = Api(app)
    
    swag = Swagger(api)
    print(swag.as_dict.__doc__) 
    
    #Output:
    Output the specification as a serializable ``dict``.
    
        :returns: the full Swagger specification in a serializable format
        :rtype: dict
    

    I maybe wrong but the source code suggests that the API documentation is only returned as JSON which is available at http://localhost:5000/swagger.json by default. I could not find anything for YAML.

    But there is a workaround to generate YAML documentation for your API. I used the json and yaml libraries to dump the json response from /swagger.json into YAML and save it to yamldoc.yml. You can invoke this by going to http://localhost:5000/swagger.yml. The full code:

    from flask import Flask
    from flask_restplus import Resource, Api
    from flask_restplus.api import Swagger
    import requests
    import json, yaml
    
    app = Flask(__name__)                  #  Create a Flask WSGI application
    api = Api(app)                         #  Create a Flask-RESTPlus API
    
    @api.route('/hello')                   #  Create a URL route to this resource
    class HelloWorld(Resource):            #  Create a RESTful resource
        def get(self):                  
            return {'hello': 'world'}
    
    @api.route('/swagger.yml')
    class HelloWorld(Resource):    
        def get(self):
           url = 'http://localhost:5000/swagger.json'       
           resp = requests.get(url)
           data = json.loads(resp.content)    
           with open('yamldoc.yml', 'w') as yamlf:
               yaml.dump(data, yamlf, allow_unicode=True)
           return {"message":"Yaml document generated!"}
    
    
    if __name__ == '__main__':
        app.run(debug=True) 
    

    I hope this helps.