使用gin的理由
- Gin是一个golang的微框架,封装比较优雅,API友好,源码注释比较明确,具有快速灵活,容错方便等特点
- 对于golang而言,web框架的依赖要远比Python,Java之类的要小。自身的
net/http
足够简单,性能也非常不错 - 借助框架开发,不仅可以省去很多常用的封装带来的时间,也有助于团队的编码风格和形成规范
简单使用
安装
go get -u github.com/gin-gonic/gin
导入
import “github.com/gin-gonic/gin”
hello word示例
package main import ( "github.com/gin-gonic/gin" "net/http" ) func main(){ // 1.创建路由 r := gin.Default() // 2.绑定路由规则,执行的函数 // gin.Context,封装了request和response r.GET("/", func(c *gin.Context) { c.String(http.StatusOK, "hello World!") }) // 3.监听端口,默认在8080 // Run("里面不指定端口号默认为8080") // 指定端口避免:8080这个常用端口被占用 r.Run(":8000") }
结果:
gin路由
基本路由
- gin 框架中采用的路由库是基于httprouter做的
- 因为虽然
net/http
这个包里有着默认路由,但是仍存在着不足,所以使用httprouter - httprouter 是一个高性能、可扩展的HTTP路由,上面我们列举的net/http默认路由的不足,都被httprouter 实现
- 要想了解更多的有关httprouter的知识,请访问:Git仓库地址
API
- 使用Restful风格的API(URL定位资源,用HTTP描述操作)
1.获取文章 /blog/getXxx Get blog/Xxx
2.添加 /blog/addXxx POST blog/Xxx
3.修改 /blog/updateXxx PUT blog/Xxx
4.删除 /blog/delXxxx DELETE blog/Xxx
参数获取
API参数
- 通过Context的Param方法来获取API参数
示例:
package main import ( "github.com/gin-gonic/gin" "net/http" "strings" ) func main() { r := gin.Default() r.GET("/user/:name/*action", func(c *gin.Context) { name := c.Param("name") action := c.Param("action") //c.String(http.StatusOK,"name = "+name+"action = "+action) //截取/ action = strings.Trim(action, "/") c.String(http.StatusOK, name+" is "+action) }) //默认为监听8080端口 r.Run(":8000") }
结果:
url参数
- URL参数可以通过DefaultQuery()或Query()方法获取
- DefaultQuery()若参数不村则,返回默认值,Query()若不存在,返回空串
示例:
package main import ( "fmt" "github.com/gin-gonic/gin" "net/http" ) func main() { r := gin.Default() r.GET("/user", func(c *gin.Context) { //不指定默认值,若是不传参则接受的是空串 //name := c.Query("name") //指定默认值 //http://localhost:8080/user 才会打印出来默认的值 name := c.DefaultQuery("name", "Re") c.String(http.StatusOK, fmt.Sprintf("hello %s", name)) }) r.Run(":8000") }
不传参
传参
表单参数
- 表单传输为post请求,http常见的传输格式为四种:
- application/json
- application/x-www-form-urlencoded
- application/xml
- multipart/form-data
- 表单参数可以通过PostForm()方法获取,该方法默认解析的是x-www-form-urlencoded或from-data格式的参数
示例:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>提交页面</title> </head> <body> <form action="http://localhost:8000/form" method="post" action="application/x-www-form-urlencoded"> 用户名:<input type="text" name="username" placeholder="请输入你的用户名"> <br> 密 码:<input type="password" name="password" placeholder="请输入你的用户名"> <input type="submit" value="提交"> </form> </body> </html>
package main import ( "fmt" "github.com/gin-gonic/gin" "net/http" ) func main() { r := gin.Default() r.POST("/form", func(c *gin.Context) { // 获取/form的请求类型,及各参数 types := c.DefaultPostForm("type", "post") username := c.PostForm("username") password := c.PostForm("password") c.String(http.StatusOK, fmt.Sprintf("username:%s,password:%s,type:%s", username, password, types)) }) r.Run(":8000") }
结果:
上传文件
- multipart/form-data格式用于文件上传
- gin文件上传与原生的net/http方法类似,不同在于gin把原生的request封装到c.Request中
单个文件
- 使用 Request.FormFile 方法获取文件
示例:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>上传单个文件</title> </head> <body> <form action="http://localhost:8000/upload" method="post" enctype="multipart/form-data"> 上传文件:<input type="file" name="file" > <input type="submit" value="提交"> </form> </body> </html>
package main import ( "github.com/gin-gonic/gin" "log" "net/http" ) // 上传文件 func main() { r := gin.Default() //限制上传最大尺寸 r.MaxMultipartMemory = 8 << 20 r.POST("/upload", func(c *gin.Context) { _, headers, err := c.Request.FormFile("file") if err != nil { log.Printf("Error when try to get file: %v", err) } //上传特定的文件 //headers.Size 获取文件大小 //if headers.Size > 1024*1024*2 { // fmt.Println("文件太大了") // return //} //headers.Header.Get("Content-Type")获取上传文件的类型 //if headers.Header.Get("Content-Type") != "image/png" { // fmt.Println("只允许上传png图片") // return //} c.SaveUploadedFile(headers, "./video/"+headers.Filename) c.String(http.StatusOK, "上传成功" + headers.Filename) }) r.Run(":8000")
结果:
多个文件
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>上传多个文件</title> </head> <body> <form action="http://localhost:8000/upload" method="post" enctype="multipart/form-data"> 上传文件:<input type="file" name="files" multiple> <input type="submit" value="提交"> </form> </body> </html>
func main() { // 1.创建路由 // 默认使用了2个中间件Logger(), Recovery() r := gin.Default() // 限制表单上传大小 8MB,默认为32MB r.MaxMultipartMemory = 8 << 20 r.POST("/upload", func(c *gin.Context) { form, err := c.MultipartForm() if err != nil { c.String(http.StatusBadRequest, fmt.Sprintf("get err %s", err.Error())) } // 获取所有图片 files := form.File["files"] // 遍历所有图片 for _, file := range files { // 逐个存 if err := c.SaveUploadedFile(file, file.Filename); err != nil { c.String(http.StatusBadRequest, fmt.Sprintf("upload err %s", err.Error())) return } } c.String(200, fmt.Sprintf("upload ok %d files", len(files))) }) //默认端口号是8080 r.Run(":8000") }
结果: