gin 是一个使用 Go 语言编写的 Web 后端框架,具有简洁、轻量、支持高并发、封装优雅、API 友好、快速灵活、容错方便等特点。
简单搭建网站
先不使用框架,搭建一个网站
package main
import (
"fmt"
"log"
"net/http"
)
func sayHello(writer http.ResponseWriter, request *http.Request) {
_, _ = fmt.Fprintln(writer, "Hello Golang")
}
func main() {
http.HandleFunc("/hello", sayHello)
err := http.ListenAndServe(":9091", nil)
if err != nil {
log.Println(err)
}
}
上述这段程序就可以简单搭建一个网站,访问localhost:9091/hello,就可以看到页面显示"Hello Golang"
http.HandleFunc中第一个参数是路径,第二个参数则是访问该路径时对应的处理函数
http.ListenAndServe监听指定的端口,并且处理传入的请求
如果要显示HTML页面,只要将HTML文档中的内容作为返回给客户端的数据,而HTTP 处理程序使用 ResponseWriter 接口来构造 HTTP 响应。
如下是html文件
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Golang</title>
</head>
<body>
<h1>Hello Golang</h1>
</body>
</html>
示例:
package main
import (
"fmt"
"io/ioutil"
"log"
"net/http"
)
func sayHello(writer http.ResponseWriter, request *http.Request) {
file, err := ioutil.ReadFile("./hello.html")
if err != nil {
fmt.Println(err)
return
}
fmt.Fprintln(writer, string(file))
}
func main() {
http.HandleFunc("/hello", sayHello)
err := http.ListenAndServe(":9091", nil)
if err != nil {
log.Println(err)
}
}
先用ReadFile读取文件内容,该函数返回的是字节类型的切片,将其转化为字符串,再使用Fprintln函数写入writer,作为响应内容返回给浏览器。
Gin框架
改用Gin来搭建该网站
路由是 web 框架的核心功能,就是根据 HTTP 请求的 url 路径,设置由哪个函数来处理请求。Gin 的路由支持 HTTP 的 GET , POST , PUT , DELETE , PATCH , HEAD , OPTIONS 方法的请求,同时还有一个 Any 函数,可以同时支持以上的所有请求。
package main
import (
"github.com/gin-gonic/gin"
"log"
)
// gin.Context 封装了request和response
func sayHello(context *gin.Context) {
// 将JSON数据返回前端
context.JSON(200, gin.H{
"message": "Hello golang!",
})
}
func main() {
router := gin.Default() // 默认路由路径
// 指定信任代理
router.SetTrustedProxies([]string{"127.0.0.1"})
// 路由/hello 绑定函数
router.GET("/hello", sayHello)
err := router.Run(":9090") // 监听在9090端口
if err != nil {
log.Fatalln(err)
}
}
RESTful API 风格
REST的含义是客户端与WEB服务器之间进行交互,在 RESTful API 设计理论中,对于资源的操作,由 HTTP 动词表示。
常用的 HTTP 动词有下面五个(括号里是对应的数据库 SQL 命令)。
- GET(SELECT):从服务器取出资源(一项或多项)
- POST(CREATE):在服务器新建一个资源
- PUT(UPDATE):在服务器更新资源(客户端提供改变后的完整资源)
- PATCH(UPDATE):在服务器更新资源(客户端提供改变的属性)
- DELETE(DELETE):从服务器删除资源
还有两个不常用的HTTP动词。
- HEAD:获取资源的元数据。
- OPTIONS:获取信息,关于资源的哪些属性是客户端可以改变的。
只要API程序遵循了API风格,就可以称之为RESTful API。
相关链接: https://restfulapi.cn/
模拟对图书的增删改查,大概是如下这个情形
package main
import (
"github.com/gin-gonic/gin"
"log"
"net/http"
)
func main() {
router := gin.Default() // 默认路由路径
// 指定信任代理
router.SetTrustedProxies([]string{"127.0.0.1"})
// 指定用户使用GET访问/hello 绑定函数
router.GET("/book", func(context *gin.Context) {
context.JSON(http.StatusOK, gin.H{
"method": "GET",
})
})
router.POST("/book", func(context *gin.Context) {
context.JSON(http.StatusOK, gin.H{
"method": "POST",
})
})
router.PUT("/book", func(context *gin.Context) {
context.JSON(http.StatusOK, gin.H{
"method": "PUT",
})
})
router.DELETE("/book", func(context *gin.Context) {
context.JSON(http.StatusOK, gin.H{
"method": "DELETE",
})
})
err := router.Run(":9090") // 监听在9090端口
if err != nil {
log.Fatalln(err)
}
}
Gin渲染
HTML渲染,首先定义一个存放模板文件的templates文件夹,然后在其内部按照业务分别定义一个posts文件夹和一个user文件夹。
Go语言内置了文本模板引擎和用于HTML文档的html/template,作用是可简单归纳如下:
-
模板文件通常定义为.tmpl和.tpl为后缀(也可以使用其他的后缀),必须使用UTF8编码
-
模板文件中使用{{和}}包裹和标识要传入的数据
-
传给模板的数据可以通过(.)来访问,如果数据是复杂的数据类型,可以通过{{.FieldName}}来访问其字段
-
除{{和}}包裹的内容外,其他内容均不做修改,原样输出
模板与渲染,这里的模板可以理解为事先定义好的HTML文档文件,模板渲染的作用机制可以简单理解为文本替换操作-使用相应的数据去替换HTML文档中事先准备好的标记。
下面先仅使用http库来渲染模板
如下是一个tmpl文件
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<title>Hello</title>
</head>
<body>
<p>Hello {{ . }}</p>
</body>
</html>
代码示例
package main
import (
"fmt"
"html/template"
"log"
"net/http"
)
func sayHello(writer http.ResponseWriter, request *http.Request) {
// 解析模板
temp, err := template.ParseFiles("./hello.tmpl") // 解析文件
if err != nil {
fmt.Printf("Parse template failed,err: %v\n", err)
}
// 渲染模板
err = temp.Execute(writer, "Golang")
if err != nil {
log.Fatalln(err)
}
}
func main() {
http.HandleFunc("/hello", sayHello)
err := http.ListenAndServe(":9090", nil)
if err != nil {
log.Fatalln(err)
}
}
运行后访问localhost:9090/hello,可以看到页面显示hello Golang
"Golang"这个常量字符串变量被传入模板,放在了{{.}}所在的位置