diff --git a/README.md b/README.md
index b792c13..689bcaf 100644
--- a/README.md
+++ b/README.md
@@ -1,4 +1,6 @@
-# echoswagger
+English | [简体中文](./README_zh-CN.md)
+
+# Echoswagger
Swagger UI generator for Echo framework
[![Go Report Card](https://goreportcard.com/badge/github.com/elvinchan/echoswagger)](https://goreportcard.com/report/github.com/elvinchan/echoswagger)
@@ -6,11 +8,16 @@ Swagger UI generator for Echo framework
[![codecov](https://codecov.io/gh/elvinchan/echoswagger/branch/master/graph/badge.svg)](https://codecov.io/gh/elvinchan/echoswagger)
## Feature
-- No SwaggerUI html/css dependency
-- Highly integrated with echo, low intrusive design
-- Take advantage of the strong typing language to make it easy to use
+- No SwaggerUI HTML/CSS dependency
+- Highly integrated with Echo, low intrusive design
+- Take advantage of the strong typing language and chain programming to make it easy to use
- Recycle garbage in time, low memory usage
+## Installation
+```
+go get github.com/elvinchan/echoswagger
+```
+
## Example
```go
package main
@@ -24,15 +31,15 @@ import (
func main() {
// ApiRoot with Echo instance
- e := echoswagger.New(echo.New(), "/v2", "doc/", nil)
+ r := echoswagger.New(echo.New(), "/v1", "doc/", nil)
// Routes with parameters & responses
- e.POST("/", createUser).
+ r.POST("/", createUser).
AddParamBody(User{}, "body", "User input struct", true).
AddResponse(http.StatusCreated, "successful", nil, nil)
// Start server
- e.Echo().Logger.Fatal(e.Echo().Start(":1323"))
+ r.Echo().Logger.Fatal(r.Echo().Start(":1323"))
}
type User struct {
@@ -45,3 +52,178 @@ func createUser(c echo.Context) error {
}
```
+
+## Usage
+#### Create a `ApiRoot` with `New()`, which is a wrapper of `echo.New()`
+```
+r := echoswagger.New(echo.New(), "/v1", "doc/", nil)
+```
+You can use the result `ApiRoot` instance to:
+- Setup Security definitions, request/response Content-Types, UI options, etc.
+```
+r.AddSecurityAPIKey("JWT", "JWT Token", echoswagger.SecurityInHeader).
+ SetRequestContentType("application/x-www-form-urlencoded", "multipart/form-data").
+ SetUI(UISetting{HideTop: true})
+```
+- Get `echo.Echo` instance.
+```
+r.Echo()
+```
+- Registers a new GET, POST, PUT, DELETE, OPTIONS, HEAD or PATCH route in default group, these are wrappers of Echo's create route methods.
+It returns a new `Api` instance.
+```
+r.GET("/:id", handler)
+```
+- And: ↓
+
+#### Create a `ApiGroup` with `Group()`, which is a wrapper of `echo.Group()`
+```
+g := r.Group("Users", "/users")
+```
+You can use the result `ApiGroup` instance to:
+- Set description, etc.
+```
+g.SetDescription("The desc of group")
+```
+- Set security for all routes in this group.
+```
+g.SetSecurity("JWT")
+```
+- Get `echo.Group` instance.
+```
+g.EchoGroup()
+```
+- And: ↓
+
+#### Registers a new route in `ApiGroup`
+GET, POST, PUT, DELETE, OPTIONS, HEAD or PATCH methods are supported by Echoswagger, these are wrappers of Echo's create route methods.
+```
+a := g.GET("/:id", handler)
+```
+You can use the result `Api` instance to:
+- Add parameter with these methods:
+```
+AddParamPath(p interface{}, name, desc string)
+
+AddParamPathNested(p interface{})
+
+AddParamQuery(p interface{}, name, desc string, required bool)
+
+AddParamQueryNested(p interface{})
+
+AddParamForm(p interface{}, name, desc string, required bool)
+
+AddParamFormNested(p interface{})
+
+AddParamHeader(p interface{}, name, desc string, required bool)
+
+AddParamHeaderNested(p interface{})
+
+AddParamBody(p interface{}, name, desc string, required bool)
+
+AddParamFile(name, desc string, required bool)
+```
+
+The methods which name's suffix are `Nested` means these methods treat parameter `p` 's fields as paramters, so it must be a struct type.
+
+e.g.
+```
+type SearchInput struct {
+ Q string `query:"q" swagger:"desc("Keywords"),required"`
+ SkipCount int `query:"skipCount"`
+}
+a.AddParamQueryNested(SearchInput{})
+```
+Is equivalent to:
+```
+a.AddParamQuery("", "q", "", true).
+ AddParamQuery(0, "skipCount", "", false)
+```
+- Add responses.
+```
+a.AddResponse(http.StatusOK, "response desc", body{}, nil)
+```
+- Set Security, request/response Content-Types, summary, description, etc.
+```
+a.SetSecurity("JWT").
+ SetResponseContentType("application/xml").
+ SetSummary("The summary of API").
+ SetDescription("The desc of API")
+```
+- Get `echo.Route` instance.
+```
+a.Route()
+```
+
+#### With swagger tag, you can set more info with `AddParam...` methods.
+e.g.
+```
+type User struct {
+ Age int `swagger:"min(0),max(99)"`
+ Gender string `swagger:"enum(male|female|other),required"`
+ Money []float64 `swagger:"default(0),readOnly"`
+}
+a.AddParamBody(&User{}, "Body", "", true)
+```
+The definition is equivalent to:
+```
+{
+ "definitions": {
+ "User": {
+ "type": "object",
+ "properties": {
+ "Age": {
+ "type": "integer",
+ "format": "int32",
+ "minimum": 0,
+ "maximum": 99
+ },
+ "Gender": {
+ "type": "string",
+ "enum": [
+ "male",
+ "female",
+ "other"
+ ],
+ "format": "string"
+ },
+ "Money": {
+ "type": "array",
+ "items": {
+ "type": "number",
+ "default": 0,
+ "format": "double"
+ },
+ "readOnly": true
+ }
+ },
+ "required": [
+ "Gender"
+ ]
+ }
+ }
+}
+```
+
+**Supported swagger tags:**
+
+Tag | Type | Description
+---|:---:|---
+collect | `string` | Determines the format of the array if type array is used. Possible values are:
- `csv` - comma separated values `foo,bar`.
- `ssv` - space separated values `foo bar`.
- `tsv` - tab separated values `foo\tbar`.
- `pipes` - pipe separated values `foo\|bar`.
Default value is `csv`.
+desc | `string` | Description.
+maximum | `number` | -
+minimum | `number` | -
+maxLength | `integer` | -
+minLength | `integer` | -
+allowEmpty | `boolean` | Sets the ability to pass empty-valued parameters. This is valid only for either `query` or `formData` parameters and allows you to send a parameter with a name only or an empty value. Default value is `false`.
+required | `boolean` | Determines whether this parameter is mandatory. If the parameter is `in` "path", this property is `true` without setting. Otherwise, the property MAY be included and its default value is `false`.
+readOnly | `boolean` | Relevant only for Schema `"properties"` definitions. Declares the property as "read only". This means that it MAY be sent as part of a response but MUST NOT be sent as part of the request. Properties marked as `readOnly` being `true` SHOULD NOT be in the `required` list of the defined schema. Default value is `false`.
+enum | [*] | Enumerate value, multiple values should be separated by "\|"
+default | * | Default value, which type is same as the field's type.
+
+## Reference
+[OpenAPI Specification 2.0](https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md)
+
+## License
+
+[MIT](https://github.com/elvinchan/echoswagger/blob/master/LICENSE)
diff --git a/README_zh-CN.md b/README_zh-CN.md
new file mode 100644
index 0000000..a2cef53
--- /dev/null
+++ b/README_zh-CN.md
@@ -0,0 +1,229 @@
+[English](./README.md) | 简体中文
+
+# Echoswagger
+[Echo](https://github.com/labstack/echo) 框架的 [Swagger UI](https://github.com/swagger-api/swagger-ui) 生成器
+
+[![Go Report Card](https://goreportcard.com/badge/github.com/elvinchan/echoswagger)](https://goreportcard.com/report/github.com/elvinchan/echoswagger)
+[![Build Status](https://travis-ci.org/elvinchan/echoswagger.svg?branch=master)](https://travis-ci.org/elvinchan/echoswagger)
+[![codecov](https://codecov.io/gh/elvinchan/echoswagger/branch/master/graph/badge.svg)](https://codecov.io/gh/elvinchan/echoswagger)
+
+## 特性
+- 不依赖任何SwaggerUI的HTML/CSS文件
+- 与Echo高度整合,低侵入式设计
+- 利用强类型语言和链式编程的优势,简单易用
+- 及时的垃圾回收,低内存占用
+
+## 安装
+```
+go get github.com/elvinchan/echoswagger
+```
+
+## 示例
+```go
+package main
+
+import (
+ "net/http"
+
+ "github.com/elvinchan/echoswagger"
+ "github.com/labstack/echo"
+)
+
+func main() {
+ // ApiRoot with Echo instance
+ r := echoswagger.New(echo.New(), "/v1", "doc/", nil)
+
+ // Routes with parameters & responses
+ r.POST("/", createUser).
+ AddParamBody(User{}, "body", "User input struct", true).
+ AddResponse(http.StatusCreated, "successful", nil, nil)
+
+ // Start server
+ r.Echo().Logger.Fatal(r.Echo().Start(":1323"))
+}
+
+type User struct {
+ Name string
+}
+
+// Handler
+func createUser(c echo.Context) error {
+ return c.JSON(http.StatusCreated, nil)
+}
+
+```
+
+## 用法
+#### 用`New()`创建`ApiRoot`,此方法是对`echo.New()`方法的封装
+```
+r := echoswagger.New(echo.New(), "/v1", "doc/", nil)
+```
+你可以用这个`ApiRoot`来:
+- 设置Security定义, 请求/响应Content-Type,UI选项,等。
+```
+r.AddSecurityAPIKey("JWT", "JWT Token", echoswagger.SecurityInHeader).
+ SetRequestContentType("application/x-www-form-urlencoded", "multipart/form-data").
+ SetUI(UISetting{HideTop: true})
+```
+- 获取`echo.Echo`实例。
+```
+r.Echo()
+```
+- 在默认组中注册一个GET、POST、PUT、DELETE、OPTIONS、HEAD或PATCH路由,这些是对Echo的注册路由方法的封装。
+此方法返回一个`Api`实例。
+```
+r.GET("/:id", handler)
+```
+- 以及: ↓
+
+#### 用`Group()`创建`ApiGroup`,此方法是对`echo.Group()`方法的封装
+```
+g := r.Group("Users", "/users")
+```
+你可以用这个`ApiGroup`来:
+- 设置描述,等。
+```
+g.SetDescription("The desc of group")
+```
+- 为此组中的所有路由设置Security。
+```
+g.SetSecurity("JWT")
+```
+- 获取`echo.Group`实例。
+```
+g.EchoGroup()
+```
+- 以及: ↓
+
+#### 在`ApiGroup`中注册一个新的路由
+Echoswagger支持GET、POST、PUT、DELETE、OPTIONS、HEAD或PATCH方法,这些是对Echo的注册路由方法的封装。
+```
+a := g.GET("/:id", handler)
+```
+你可以使用此`Api`实例来:
+- 使用以下方法添加参数:
+```
+AddParamPath(p interface{}, name, desc string)
+
+AddParamPathNested(p interface{})
+
+AddParamQuery(p interface{}, name, desc string, required bool)
+
+AddParamQueryNested(p interface{})
+
+AddParamForm(p interface{}, name, desc string, required bool)
+
+AddParamFormNested(p interface{})
+
+AddParamHeader(p interface{}, name, desc string, required bool)
+
+AddParamHeaderNested(p interface{})
+
+AddParamBody(p interface{}, name, desc string, required bool)
+
+AddParamFile(name, desc string, required bool)
+```
+
+后缀带有`Nested`的方法把参数`p`的字段看做多个参数,所以它必须是结构体类型的。
+
+例:
+```
+type SearchInput struct {
+ Q string `query:"q" swagger:"desc("Keywords"),required"`
+ SkipCount int `query:"skipCount"`
+}
+a.AddParamQueryNested(SearchInput{})
+```
+等价于:
+```
+a.AddParamQuery("", "q", "", true).
+ AddParamQuery(0, "skipCount", "", false)
+```
+- 添加响应。
+```
+a.AddResponse(http.StatusOK, "response desc", body{}, nil)
+```
+- 设置Security,请求/响应的Content-Type,概要,描述,等。
+```
+a.SetSecurity("JWT").
+ SetResponseContentType("application/xml").
+ SetSummary("The summary of API").
+ SetDescription("The desc of API")
+```
+- 获取`echo.Route`实例。
+```
+a.Route()
+```
+
+#### 使用swagger标签,你可以在`AddParam...`方法中设置更多信息
+例:
+```
+type User struct {
+ Age int `swagger:"min(0),max(99)"`
+ Gender string `swagger:"enum(male|female|other),required"`
+ Money []float64 `swagger:"default(0),readOnly"`
+}
+a.AddParamBody(&User{}, "Body", "", true)
+```
+此定义等价于:
+```
+{
+ "definitions": {
+ "User": {
+ "type": "object",
+ "properties": {
+ "Age": {
+ "type": "integer",
+ "format": "int32",
+ "minimum": 0,
+ "maximum": 99
+ },
+ "Gender": {
+ "type": "string",
+ "enum": [
+ "male",
+ "female",
+ "other"
+ ],
+ "format": "string"
+ },
+ "Money": {
+ "type": "array",
+ "items": {
+ "type": "number",
+ "default": 0,
+ "format": "double"
+ },
+ "readOnly": true
+ }
+ },
+ "required": [
+ "Gender"
+ ]
+ }
+ }
+}
+```
+
+**支持的`swagger`标签:**
+
+Tag | Type | Description
+---|:---:|---
+collect | `string` | 如果类型是数组,确定其格式。可能的值有:- `csv` - 逗号分隔的值 `foo,bar`。
- `ssv` - 空格分隔的值 `foo bar`。
- `tsv` - tab分隔的值 `foo\tbar`。
- `pipes` - pipe分隔的值 `foo\|bar`。
默认值是 `csv`。
+desc | `string` | 描述。
+maximum | `number` | -
+minimum | `number` | -
+maxLength | `integer` | -
+minLength | `integer` | -
+allowEmpty | `boolean` | 设置传递空值参数的功能。 这仅对`query`或`formData`参数有效,并允许你发送仅具有名称或空值的参数。默认值为“false”。
+required | `boolean` | 确定此参数是否必需。如果参数是`in`“path”,则此属性默认为“true”。否则,可以设置此属性,其默认值为“false”。
+readOnly | `boolean` | 仅与Schema`"properties"`定义相关。将属性声明为“只读”。这意味着它可以作为响应的一部分发送,但绝不能作为请求的一部分发送。标记为“readOnly”的属性为“true”,不应位于已定义模式的“required”列表中。默认值为“false”。
+enum | [*] | 枚举值,多个值应以“\|”分隔。
+default | * | 默认值,该类型与字段的类型相同。
+
+## 参考
+[OpenAPI Specification 2.0](https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md)
+
+## License
+
+[MIT](https://github.com/elvinchan/echoswagger/blob/master/LICENSE)