golang微框架Gin

这篇具有很好参考价值的文章主要介绍了golang微框架Gin。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

Gin简介

Gin是一个golang的微框架,基于httprouter,封装比较优雅,API友好,源码注释比较明确,具有快速灵活,容错方便等特点

Gin特征

速度快:基于基数树的路由,内存占用小,没有反射,可预测的APi性能

中间件支持

传入的http请求可以有中间件链和最终操作处理,例如:Logger,Authorization,GZip最后在Db中发布以条消息

Crash-free

Gin可以捕获Http请求期间发生的panic并恢复它,这样你的服务器始终都可用

JSON验证

Gin可以解析和验证请求的JSON——例如,检查所需的值是否存在

路由分组

更好的组织您的路线,需要授权与不需要授权,不同的API版本,此外,组可以无限嵌套,而不会降低性能

错误管理

Gin提供了一种方便的方法用来收集HTTP请求期间发生的所有错误,最终 ,中间件可以将它们写入日志,数据并通过网络发送他们

内置渲染

GIn为JSon,XML,HTML渲染提供了简单易用·的API

可扩展

创建一个新的中间件非常简单,只需要查看实例代码就可以

第一个Gin

安装Gin

 go get -u github.com/gin-gonic/gin

导入项目

import "github.com/gin-gonic/gin"

实现代码

package main

import "github.com/gin-gonic/gin"

func main() {
	r := gin.Default()
	r.GET("/ping", func(c *gin.Context) {
		c.JSON(200, gin.H{
			"message": "pong",
		})
	})
	r.Run() // listen and serve on 0.0.0.0:8080
}

Gin实现用户登录

实现步骤

创建一个文件templates

在项目根目录下边创建文件夹templtes,用来保存静态文件

创建一个登录的html文件

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Login</title>
</head>
<body>

    <form action="/login" method="post">
        Username: <input type="text" name="username"><br>
        Password: <input type="password" name="password"><br>
        <input type="submit" value="Login">
    </form>
    
</body>
</html>

创建一个欢迎html页面

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Welcome</title>
</head>
<body>

    Welcome, {{.username}}
    
</body>
</html>

使用Gin处理逻辑

package main

import "github.com/gin-gonic/gin"

func MyHandler(c *gin.Context) {
	c.JSON(200, gin.H{
		"hello": "hello world",
	})
}

func Login(c *gin.Context) {
	c.HTML(200, "login.html", nil)
}

func DoLogin(c *gin.Context) {
	username := c.PostForm("username")
	password := c.PostForm("password")

	c.HTML(200, "welcome.html", gin.H{
		"username": username,
		"password": password,
	})

}

func main() {
	e := gin.Default()
	e.LoadHTMLGlob("templates/*")

	e.GET("/login", Login)
	e.POST("/login", DoLogin)
	e.Run()
}

使用Gin请求参数

Get请求参数
使用c.Query(“key”),或者c.DefaultQuery(”key”)方法

package main

import "github.com/gin-gonic/gin"

func TestQueryString(c *gin.Context) {
	username := c.Query("username")
	site := c.DefaultQuery("site", "www.duoke360.com")

	c.String(200, "username:%s, site:%s", username, site)
}

func main() {

	e := gin.Default()
	// url : http://localhost:8080/testQueryString?username=郭宏志&site=多课网
	e.GET("/testQueryString", TestQueryString)

	e.Run()

}

Gin数据绑定

绑定Form表单

package main

import (
	"github.com/gin-gonic/gin"
)

type User struct {
	Username string   `form:"username"`
	Password string   `form:"password"`
	Hobby    []string `form:"hobby"`
	Gender   string   `form:"gender"`
	City     string   `form:"city"`
}

func Regsiter(c *gin.Context) {
	var user User
	c.ShouldBind(&user)
	c.String(200, "User:%s", user)
}

func GoRegister(c *gin.Context) {
	c.HTML(200, "register.html", nil)
}

func main() {
	e := gin.Default()
	e.LoadHTMLGlob("templates/*")
	e.POST("/register", Regsiter)
	e.GET("/register", GoRegister)
	e.Run()
}

绑定查询参数

package main

import (
	"log"

	"github.com/gin-gonic/gin"
)

type User struct {
	Username string `form:"username"`
	Password string `form:"password"`
}

func TestGetBind(c *gin.Context) {
	var user User
	err := c.ShouldBind(&user)
	if err != nil {
		log.Fatal(err)
	}
	c.String(200, "User:%s", user)
}

func main() {
	e := gin.Default()
	// http://localhost:8080/testGetBind?username=ghz&password=123
	e.GET("/testGetBind", TestGetBind)
	e.Run()
}

绑定路径请求参数

package main

import (
	"log"

	"github.com/gin-gonic/gin"
)

type User struct {
	Username string `uri:"username"`
	Password string `uri:"password"`
}

func TestGetBind(c *gin.Context) {
	var user User
	err := c.ShouldBindUri(&user)
	if err != nil {
		log.Fatal(err)
	}
	c.String(200, "User:%s", user)
}

func main() {
	e := gin.Default()
	// http://localhost:8080/testGetBind/ghz/123
	e.GET("/testGetBind/:username/:password", TestGetBind)
	e.Run()
}

GIN 访问静态文件集成BootStrap框架

下载bootstrap
下载地址:
https://getbootstrap.com/

添加bootstrap css 和js 文件

创建一个assets文件夹 将 css和js文件添加到该文件夹中
创建html文件

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <link rel="stylesheet" href="/assets/css/bootstrap.min.css">
    
    <title>Login</title>
</head>
<body>

   <div class="container">
    
    <form>
        <div class="mb-3">
          <label for="exampleInputEmail1" class="form-label">Email address</label>
          <input type="email" class="form-control" id="exampleInputEmail1" aria-describedby="emailHelp">
          <div id="emailHelp" class="form-text">We'll never share your email with anyone else.</div>
        </div>
        <div class="mb-3">
          <label for="exampleInputPassword1" class="form-label">Password</label>
          <input type="password" class="form-control" id="exampleInputPassword1">
        </div>
        <div class="mb-3 form-check">
          <input type="checkbox" class="form-check-input" id="exampleCheck1">
          <label class="form-check-label" for="exampleCheck1">Check me out</label>
        </div>
        <button type="submit" class="btn btn-primary">Submit</button>
      </form>
   </div>
    
</body>
</html>

go code
package main

import (
	"net/http"

	"github.com/gin-gonic/gin"
)

func Login(c *gin.Context) {
	c.HTML(200, "login.html", nil)
}

func main() {
	e := gin.Default()
	e.LoadHTMLGlob("templates/*")

	e.Static("/assets", "./assets")
	e.StaticFS("/croot", http.Dir("c:/"))
	e.StaticFile("/favicon.ico", "./assets/favicon.ico")

	e.GET("/login", Login)
	e.POST("/login", DoLogin)
	e.Run()
}

Gin使用中间件

中间件听起来非常高大上的名字,实际上非常简单,就是在请求中间其拦截作用的处理函数

Gin默认中间件

如果你使用Gin.Default实例化gin引擎,默认有俩个中间件,LOgger和Recover,分别用来处理日志和处理错误,如果使用Gin.New需要重新添加

// 新建一个没有任何默认中间件的路由
r := gin.New()

// 全局中间件
// Logger 中间件将日志写入 gin.DefaultWriter,即使你将 GIN_MODE 设置为 release。
// By default gin.DefaultWriter = os.Stdout
r.Use(gin.Logger())

// Recovery 中间件会 recover 任何 panic。如果有 panic 的话,会写入 500。
r.Use(gin.Recovery())

自定义中间件

1.自定义中间件非常简单,定义一个符合下边格式的处理函数
type HandlerFunc func(*Context)
2.使用Use方法调用

package main

import (
	"fmt"

	"github.com/gin-gonic/gin"
)

func TestMW(c *gin.Context) {
	c.String(200, "hello,%s", "ghz")
}

func MyMiddleware1(c *gin.Context) {
	fmt.Println("我的第一个中间件")
}

func MyMiddleware2(c *gin.Context) {
	fmt.Println("我的第二个中间件")
}

func main() {

	/* 	func Default() *Engine {
		debugPrintWARNINGDefault()
		engine := New()
		engine.Use(Logger(), Recovery())
		return engine
	} */
	// e := gin.Default()
	// e := gin.New()

	e := gin.Default()

	e.Use(MyMiddleware1, MyMiddleware2)

	e.GET("testmw", TestMW)

	e.Run()

}

使用Gin BasicAuth中间件

Gin提供了BasicAuth的中间件,用来对网络资源的访问保护
实例:

package main

import (
	"fmt"
	"net/http"

	"github.com/gin-gonic/gin"
)

// 模拟一些私人数据
var secrets = gin.H{
	"foo":    gin.H{"email": "foo@bar.com", "phone": "123433"},
	"austin": gin.H{"email": "austin@example.com", "phone": "666"},
	"lena":   gin.H{"email": "lena@guapa.com", "phone": "523443"},
}

func main() {
	r := gin.Default()

	// 路由组使用 gin.BasicAuth() 中间件
	// gin.Accounts 是 map[string]string 的一种快捷方式
	authorized := r.Group("/admin", gin.BasicAuth(gin.Accounts{
		"foo":    "bar",
		"austin": "1234",
		"lena":   "hello2",
		"manu":   "4321",
	}))

	// /admin/secrets 端点
	// 触发 "localhost:8080/admin/secrets
	authorized.GET("/secrets", func(c *gin.Context) {
		// 获取用户,它是由 BasicAuth 中间件设置的
		user := c.MustGet(gin.AuthUserKey).(string)
		fmt.Println(user)
		if secret, ok := secrets[user]; ok {
			c.JSON(http.StatusOK, gin.H{"user": user, "secret": secret})
		} else {
			c.JSON(http.StatusOK, gin.H{"user": user, "secret": "NO SECRET :("})
		}
	})

	// 监听并在 0.0.0.0:8080 上启动服务
	r.Run(":8080")
}

测试

在浏览器中输入localhost:8080/admin/secrets时,会弹出一个对话框,要求输入正确的用户名和密码,才能访问资源。

Gin cookie的使用

cookie是服务器向客户端写的一些数据,可以实现像自动登陆等功能
Gin cookie的使用

package main

import "github.com/gin-gonic/gin"

func Handler(c *gin.Context) {
	// 获得cookie
	s, err := c.Cookie("username")
	if err != nil {
		s = "ghz"
		// 设置cookie
		c.SetCookie("username", s, 60*60, "/", "localhost", false, true)
	}

	c.String(200, "测试cookie")
}

func main() {
	e := gin.Default()
	e.GET("/test", Handler)
	e.Run()
}

Gin使用session

因为http是无状态短连接 ,如何保存客户端和服务器直接的会话状态呢?可以使用session

使用gin session中间件

gin本身没有对session的支持,可以使用第三方中间件

go get github.com/gin-contrib/sessions
import "github.com/gin-contrib/sessions"

该中间件提更了很多后端支持:
cookie-based
redis
memcached
MongoDB
memstore
PostgreSQL
实例:

package main

import (
  "github.com/gin-contrib/sessions"
  "github.com/gin-contrib/sessions/cookie"
  "github.com/gin-gonic/gin"
)

func main() {
  r := gin.Default()
  store := cookie.NewStore([]byte("secret"))
  r.Use(sessions.Sessions("mysession", store))

  r.GET("/hello", func(c *gin.Context) {
    session := sessions.Default(c)

    if session.Get("hello") != "world" {
      session.Set("hello", "world")
      session.Save()
    }

    c.JSON(200, gin.H{"hello": session.Get("hello")})
  })
  r.Run(":8000")
}

Gin实现restful风格的CURD

package main

import (
	"fmt"
	"strconv"
	"github.com/gin-gonic/gin"
)

type User struct {
	UId  int    `json:"uid"`
	Name string `json:"name"`
	Age  int    `json:"age"`
}

var users = make([]User, 3)

func init() {
	u1 := User{1, "tom", 20}
	u2 := User{2, "kite", 30}
	u3 := User{3, "rose", 40}
	users = append(users, u1)
	users = append(users, u2)
	users = append(users, u3)
	fmt.Println(users)
}

func find(uid int) (*User, int) {
	for i, u := range users {
		if u.UId == uid {
			return &u, i
		}
	}
	return nil, -1
}

func AddUser(c *gin.Context) {
	u4 := User{4, "Joe", 50}
	users = append(users, u4)
	c.JSON(200, users)
}
func DelUser(c *gin.Context) {
	uid := c.Param("uid")
	id, _ := strconv.Atoi(uid)
	_, i := find(id)
	users = append(users[:i], users[i+1:]...)
	c.JSON(200, users)
}

func UpdateUser(c *gin.Context) {
	uid := c.Param("uid")
	id, _ := strconv.Atoi(uid)
	u, _ := find(id)
	u.Name = "修改的Name"
	c.JSON(200, u)
}

func FindUser(c *gin.Context) {
	uid := c.Param("uid")
	id, _ := strconv.Atoi(uid)
	u, _ := find(id)
	c.JSON(200, u)
}
func main() {

	e := gin.Default()
	e.GET("/user/:uid", FindUser)
	e.PUT("/user/:uid", UpdateUser)
	e.DELETE("/user/:uid", DelUser)
	e.POST("/user/", AddUser)
	e.Run()

}

Gin实现路由分组

假如你的网站上有很多个模块:博客,教程,视频,回答,每个模块又有很多个路由,这样就可以进行路由分组,使用的方法是router.Group(“分组名称”)

package main

import "github.com/gin-gonic/gin"

func F1(c *gin.Context) {}
func F2(c *gin.Context) {}
func F3(c *gin.Context) {}
func F4(c *gin.Context) {}
func F5(c *gin.Context) {}
func F6(c *gin.Context) {}

func main() {
	router := gin.Default()

	// 博客
	// 访问:http://localhost:8080/blog/list
	v1 := router.Group("/blog")
	{
		v1.POST("/list", F1)
		v1.POST("/post", F2)
		v1.POST("/add", F3)
	}

	// 视频
	// 访问:http://localhost:8080/video/list
	v2 := router.Group("/video")
	{
		v2.POST("/list", F4)
		v2.POST("/post", F5)
		v2.POST("/add", F6)
	}

	router.Run(":8080")
}

Gin输出渲染

Gin支持很多种输出渲染,可以是简单的字符串,Json,xml,html,protoBuf。使用的方法如下:

c.JSON(200, nil)
c.XML(200, nil)
c.HTML(200, "", nil)
c.String(200, "")
c.ProtoBuf(200, nil)

这里像字符串,json,html我们都用过,这里我们再总结一下:

package main

import "github.com/gin-gonic/gin"

func TestJson(c *gin.Context) {
	c.JSON(200, gin.H{
		"name": "多课网",
		"site": "www.duoke360.com",
	})
}

func TestXML(c *gin.Context) {
	c.XML(200, gin.H{
		"name": "多课网",
		"site": "www.duoke360.com",
	})
}

func TestHtml(c *gin.Context) {
	c.HTML(200, "login.html", nil)
}

func TestString(c *gin.Context) {
	c.String(200, "多课网,老郭讲golang")
}

func main() {
	e := gin.Default()

	e.GET("/test_json", TestJson)
	e.GET("/test_xml", TestXML)
	e.LoadHTMLGlob("templates/*")
	e.GET("/test_html", TestHtml)
	e.GET("/test_string", TestString)

> 这里是引用

	e.Run()
}

Gin实现文件上传

创建xml文件文章来源地址https://www.toymoban.com/news/detail-708870.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    
    <form action="/upload" method="post" enctype="multipart/form-data">
    请选择上传文件:<input type="file" name="file" id=""><br>
    <input type="submit" value="上传">
    </form>
    
</body>
</html>

Go code

package main

import (
	"fmt"
	"log"
	"net/http"

	"github.com/gin-gonic/gin"
)

func Upload(c *gin.Context) {
	// 单文件
	file, _ := c.FormFile("file")
	log.Println(file.Filename)

	// 上传文件到项目根目录,使用原文件名
	c.SaveUploadedFile(file, file.Filename)

	c.String(http.StatusOK, fmt.Sprintf("'%s' uploaded!", file.Filename))
}

func GoUpload(c *gin.Context) {
	c.HTML(200, "upload.html", nil)
}

func main() {
	router := gin.Default()
	// 为 multipart forms 设置较低的内存限制 (默认是 32 MiB)
	router.MaxMultipartMemory = 8 << 20 // 8 MiB
	router.LoadHTMLGlob("templates/*")
	router.GET("/upload", GoUpload)
	router.POST("/upload", Upload)
	router.Run(":8080")
}

到了这里,关于golang微框架Gin的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • [golang gin框架] 37.ElasticSearch 全文搜索引擎的使用

    ElasticSearch 是一个基于 Lucene 的 搜索服务器 ,它提供了一个 分布式多用户 能力的 全文搜索引擎 ,基于 RESTful web 接口,Elasticsearch 是用 Java 开发的,并作为 Apache 许可条款下的开放源码发布,是当前流行的企业级搜索引擎,设计用于云计算中,能够达到 实时搜索 , 稳定 , 可靠

    2024年02月11日
    浏览(58)
  • [golang gin框架] 38.Gin操作Elasticsearch创建索引、修改映射、数据CURD以及数据分页

    常见的 Golang 操作 ElasticSearch 的插件主要有下面两个: 第三方插件: github.com/olivere/elastic 官网插件 github.com/elastic/go-elasticsearch 其中 elastic 比 go-elasticsearch 文档更全面一些,start 量也更多一些,本节讲解 elastic 使用第三方库 https://github.com/olivere/elastic 来连接 ES 并进行操作 注意

    2024年02月09日
    浏览(63)
  • [golang gin框架] 45.Gin商城项目-微服务实战之后台Rbac微服务之角色权限关联

    角色和权限的关联关系在前面文章中有讲解,见[golang gin框架] 14.Gin 商城项目-RBAC管理之角色和权限关联,角色授权,在这里通过微服务来实现 角色对权限的授权 操作,这里要实现的有两个功能,一个是进入授权,另一个是,授权提交操作,页面如下:  这里需要在proto/rbacRole.proto中增加

    2024年02月14日
    浏览(57)
  • [golang gin框架] 26.Gin 商城项目-前台自定义商品列表模板, 商品详情数据渲染,Markdown语法使用

    当在首页分类点击进入分类商品列表页面时,可以根据后台分类中的分类模板跳转到对应的模板商品列表页面 (1).商品控制器方法Category()完善 修改controllers/frontend/productController.go中的方法Category(), 判断分类模板,如果后台没有设置,则使用默认模板 (2).模板页面案例 先来回顾一

    2024年02月01日
    浏览(55)
  • [golang gin框架] 42.Gin商城项目-微服务实战之后台Rbac微服务角色增删改查微服务

    上一节讲解了后台Rbac微服务用户登录功能以及Gorm数据库配置单独抽离,Consul配置单独抽离,这一节讲解 后台Rbac微服务 角色 增删改查微服务 功能,Rbac微服务角色增删改查微服务和 后 台Rbac用户登录微服务 是属于 同一个Rbac微服务 的 不同子微服务功能 ,为了区分不同子微

    2024年02月15日
    浏览(40)
  • [golang gin框架] 44.Gin商城项目-微服务实战之后台Rbac微服务之权限的增删改查微服务

    上一节讲解了[golang gin框架] 43.Gin商城项目-微服务实战之后台Rbac微服务之管理员的增删改查以及管理员和角色关联,这里讲解权限管理Rbac微服务权限的增删改查微服务 要实现权限的增删改查,就需要创建对应的模型,故在server/rbac/models下创建Access.go模型文件,参考[golang gin框架]

    2024年02月14日
    浏览(43)
  • [golang gin框架] 43.Gin商城项目-微服务实战之后台Rbac微服务之管理员的增删改查以及管理员和角色关联

    上一节讲解了后台Rbac微服务角色增删改查微服务,这里讲解权限管理Rbac微服务管理员的增删改查微服务以及管理员和角色关联微服务功能 要实现管理员的增删改查,就需要创建对应的模型,故在server/rbac/models下创建manager.go模型文件,参考[golang gin框架] 14.Gin 商城项目-RBAC管理代码

    2024年02月14日
    浏览(45)
  • Golang | Web开发之Gin多服务配置及优雅关闭平滑重启

    欢迎关注「 全栈工程师修炼指南 」公众号 点击 👇  下方卡片  即可关注我哟! 设为 「 星标⭐ 」 每天带你  基础入门  到  进阶实践  再到  放弃学习 ! 专注  企业运维实践、网络安全、系统运维、应用开发、物联网实战、全栈文章  等知识分享 “    花开堪折直须折

    2024年02月08日
    浏览(43)
  • Go语言web框架——Gin

    Gin是一个go语言写的Web框架 客户机通过TCP/IP协议建立到服务器的TCP连接 客户端向服务器发送HTTP协议请求 Request GET /url ,请求服务器里的资源文档 服务器向客户机发送HTTP协议应答Response,如果请求的资源包含有动态语言的内容,那么服务器会调用动态语言的解释引擎负责处理

    2023年04月14日
    浏览(81)
  • go语言Gin框架常见面试题(1)

    Gin框架是一种基于Go语言的轻量级Web框架,具有高效、快速、易用等优点。Gin采用了类似于Expres

    2024年02月08日
    浏览(63)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包