add README.md to introduce the usage of tornado_swagger 67/15067/3
authorSerenaFeng <feng.xiaowei@zte.com.cn>
Thu, 2 Jun 2016 07:49:03 +0000 (15:49 +0800)
committerSerenaFeng <feng.xiaowei@zte.com.cn>
Thu, 2 Jun 2016 14:44:30 +0000 (22:44 +0800)
add README.md file in tornado_swagger package

JIRA: FUNCTEST-290

Change-Id: I0ba306f0e5dfb576b34959f054e1c9cc61079039
Signed-off-by: SerenaFeng <feng.xiaowei@zte.com.cn>
utils/test/result_collection_api/opnfv_testapi/tornado_swagger/README.md [new file with mode: 0644]

diff --git a/utils/test/result_collection_api/opnfv_testapi/tornado_swagger/README.md b/utils/test/result_collection_api/opnfv_testapi/tornado_swagger/README.md
new file mode 100644 (file)
index 0000000..d815f21
--- /dev/null
@@ -0,0 +1,273 @@
+# tornado-swagger
+
+## What is tornado-swagger?
+tornado is a wrapper for tornado which enables swagger-ui support.
+
+In essense, you just need to wrap the Api instance and add a few python decorators to
+get full swagger support.http://swagger.io/
+
+
+## How to use:
+
+
+```python
+from tornado.web import RequestHandler, HTTPError
+from tornado_swagger import swagger
+
+swagger.docs()
+
+# You may decorate your operation with @swagger.operation and use docs to inform information
+class ItemNoParamHandler(GenericApiHandler):
+    @swagger.operation(nickname='create')
+    def post(self):
+        """
+            @param body: create test results for a item.
+            @type body: L{Item}
+            @return 200: item is created.
+            @raise 400: invalid input
+        """
+
+# Operations not decorated with @swagger.operation do not get added to the swagger docs
+
+class ItemNoParamHandler(GenericApiHandler):
+    def options(self):
+        """
+        I'm not visible in the swagger docs
+        """
+        pass
+
+
+# Then you use swagger.Application instead of tornado.web.Application
+# and do other operations as usual
+
+def make_app():
+    return swagger.Application([
+        (r"/items", ItemNoParamHandler),
+        (r"/items/([^/]+)", ItemHandler),
+        (r"/items/([^/]+)/cases/([^/]+)", ItemOptionParamHandler),
+    ])
+
+# You define models like this:
+@swagger.model
+class Item:
+    """
+        @descriptin:
+            This is an example of a model class that has parameters in its constructor
+            and the fields in the swagger spec are derived from the parameters to __init__.
+        @notes:
+            In this case we would have property1, property2 as required parameters
+            and property3 as optional parameter.
+        @property property3: Item decription
+        @ptype property3: L{PropertySubclass}
+    """
+    def __init__(self, property1, property2=None):
+        self.property1 = property1
+        self.property2 = property2
+
+# Swagger json:
+    "models": {
+        "Item": {
+            "description": "A description...",
+            "id": "Item",
+            "required": [
+                "property1",
+            ],
+            "properties": [
+                "property1": {
+                    "type": "string"
+                },
+                "property2": {
+                    "type": "string"
+                    "default": null
+                }
+            ]
+        }
+    }
+
+# If you declare an __init__ method with meaningful arguments
+# then those args could be used to deduce the swagger model fields.
+# just as shown above
+
+# if you declare an @property in docs, this property property2 will also be used
+# to deduce the swagger model fields
+class Item:
+    """
+        @property property3: Item description
+    """
+    def __init__(self, property1, property2):
+        self.property1 = property1
+        self.property2 = property2
+
+# Swagger json:
+    "models": {
+        "Item": {
+            "description": "A description...",
+            "id": "Item",
+            "required": [
+                "property1",
+            ],
+            "properties": [
+                "property1": {
+                    "type": "string"
+                },
+                "property2": {
+                    "type": "string"
+                }
+                "property3": {
+                    "type": "string"
+                }
+            ]
+        }
+    }
+
+# if you declare an argument with @ptype, the type of this argument will be specified
+# rather than the default 'string'
+class Item:
+    """
+        @ptype property3: L{PropertySubclass}
+    """
+    def __init__(self, property1, property2, property3=None):
+        self.property1 = property1
+        self.property2 = property2
+        self.property3 = property3
+
+# Swagger json:
+    "models": {
+        "Item": {
+            "description": "A description...",
+            "id": "Item",
+            "required": [
+                "property1",
+            ],
+            "properties": [
+                "property1": {
+                    "type": "string"
+                },
+                "property2": {
+                    "type": "string"
+                },
+                "property3": {
+                    "type": "PropertySubclass"
+                    "default": null
+                }
+            ]
+        }
+    }
+
+# if you want to declare an list property, you can do it like this:
+class Item:
+    """
+        @ptype property3: L{PropertySubclass}
+        @ptype property4: C{list} of L{PropertySubclass}
+    """
+    def __init__(self, property1, property2, property3, property4=None):
+        self.property1 = property1
+        self.property2 = property2
+        self.property3 = property3
+        self.property4 = property4
+
+# Swagger json:
+    "models": {
+        "Item": {
+            "description": "A description...",
+            "id": "Item",
+            "required": [
+                "property1",
+            ],
+            "properties": [
+                "property1": {
+                    "type": "string"
+                },
+                "property2": {
+                    "type": "string"
+                },
+                "property3": {
+                    "type": "PropertySubclass"
+                    "default": null
+                },
+                "property4": {
+                    "default": null,
+                    "items": {
+                        "type": "PropertySubclass"},
+                        "type": "array"
+                    }
+                }
+            ]
+        }
+    }
+
+# if it is a query:
+class ItemQueryHandler(GenericApiHandler):
+    @swagger.operation(nickname='query')
+    def get(self):
+        """
+           @param property1:
+           @type property1: L{string}
+           @in property1: query
+           @required property1: False
+
+           @param property2:
+           @type property2: L{string}
+           @in property2: query
+           @required property2: True
+           @rtype: L{Item}
+
+           @notes: GET /item?property1=1&property2=1
+        """
+
+# Swagger json:
+    "apis": [
+        {
+            "operations": [
+                {
+                    "parameters": [
+                        {
+                            "name": "property1",
+                            "dataType": "string",
+                            "paramType": "query",
+                            "description": ""
+                        },
+                        {
+                            "name": "property2",
+                            "dataType": "string",
+                            "paramType": "query",
+                            "required": true,
+                            "description": ""
+                        }
+                    ],
+                    "responseClass": "Item",
+                    "notes": null,
+                    "responseMessages": [],
+                    "summary": null,
+                    "httpMethod": "GET",
+                    "nickname": "query"
+                }
+            ],
+            "path": "/item",
+            "description": null
+        },
+        ....
+    ]
+```
+
+# Running and testing
+
+Now run your tornado app
+
+```
+python main.py
+```
+
+And visit:
+
+```
+curl http://ip:port/swagger/spec
+```
+
+access to web
+```
+http://ip:port/swagger/spec.html
+```
+
+# Passing more metadata to swagger
+customized arguments used in creating the 'swagger.docs' object will be supported later