Bootstrap

gin框架学习之旅(基于七米老师)

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档


前言☀️☀️☀️

在这里插入图片描述

Gin 是一个 Go (Golang) 编写的轻量级 http web 框架,运行速度非常快,如果你是性能和高效的追求者
Gin 最擅长的就是 Api 接口的高并发,如果项目的规模不大,业务相对简单,这个时候我们也推荐您使用 Gin
Gin 的官网:https://gin-gonic.com/zh-cn/
Github 地址:https://github.com/gin-gonic/gin

一、搭建简单的web平台(没有基于gin)

Handd在这里插入图片描述
HandleFunc(路径,函数)

在这里插入图片描述
在这里插入图片描述
在大多数情况下,每个套接字地址(包括协议、网络地址和端口号)只能被一个程序或服务同时使用。
当我没有关闭端口时,重复使用同一个端口就会报错

二、gin框架初识

在这里插入图片描述

 func sayHello(c *gin.Context) { //gin.Context是一定要的
	c.JSON(200, gin.H{
		"message": "Hello golang!",
	})
}

func main() {
	r := gin.Default() // 返回默认的路由引擎

	r.GET("/book", func(c *gin.Context) {
		c.JSON(http.StatusOK, gin.H{
			"method": "GET",
		})
	})

	r.POST("/book", func(c *gin.Context) {
		c.JSON(http.StatusOK, gin.H{
			"method": "POST",
		})
	})

	r.PUT("/book", func(c *gin.Context) {
		c.JSON(http.StatusOK, gin.H{
			"method": "PUT",
		})
	})

	r.DELETE("/book", func(c *gin.Context) {
		c.JSON(http.StatusOK, gin.H{
			"method": "DELETE",
		})
	})

三、template初识

在这里插入图片描述

在这里插入图片描述

<!DOCTYPE html>
<html lang = "Zh-CN">
<head>
<title>Hello</title>
</head>
<body>
<p>Hello{{ . }}</p> //这个.表示后端渲染的时候传来的变量
</body>
</html>
package main

import (
	"fmt"
	"html/template"
	"net/http"
)

func sayHello(w http.ResponseWriter, r *http.Request) {
	//2解析模板
	t, err := template.ParseFiles("./hello.tmpl")
	if err != nil {
		fmt.Println("Parse template failed,err:%v", err)
		return
	}

	//3.渲染模板
	name := "小王子"
	err = t.Execute(w, name)
	if err != nil {
		fmt.Println("render template failed,err:%v", err)
		return
	}
}

func main() {
	http.HandleFunc("/", sayHello)
	err := http.ListenAndServe(":9090", nil)
	if err != nil {
		fmt.Println("Http server start falied, err:%v", err)
		return
	}
}

四、go模板语法详解

type User struct {
	Name   string
	Gender string
	Age    int
}

func sayHello(w http.ResponseWriter, r *http.Request) {
	//2解析模板
	t, err := template.ParseFiles("./hello.tmpl")
	if err != nil {
		fmt.Println("Parse template failed,err:%v", err)
		return
	}

	//3.渲染模板
	u1 := User{
		Name:   "小王子",
		Gender: "男",
		Age:    18,
	}
	t.Execute(w, u1)
}
<!DOCTYPE html>
<html lang = "Zh-CN">
<head>
<title>Hello</title>
</head>
<body>
<p>Hello{{ .Name }}</p>
<p>年龄:{{ .Age }}</p>
<p>性别:{{.Gender }}</p>
</body>
</html>

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述== 第二行 :如果pipeline为真,则执行T1;否则执行T0。==

五、模板嵌套

package main

import (
	"fmt"
	"html/template"
	"net/http"
)

func f1(w http.ResponseWriter, r *http.Request) {
	//定义一个函数Kua
	//要么只有一个返回值,要么有两个,第二个必须是error类型

	k := func(name string) (string, error) {
		return name + "我喜欢你哟!", nil
	}

	//定义模板
	t := template.New("f.tmpl") //创建一个名字是f的模板对象,名字一定要与模板能对应上
	//告诉模板引擎,我现在多了一个自定义的函数kua
	t.Funcs(template.FuncMap{
		"kua": k,
	})

	//解析模板
	_, err := t.ParseFiles("./f.tmpl")
	if err != nil {
		fmt.Printf("parse template failed,err: %v", err)
		return
	}
	name := "小王子"

	//3.渲染模板
	t.Execute(w, name)
}

func main() {
	http.HandleFunc("/", f1)
	err := http.ListenAndServe(":9090", nil)
	if err != nil {
		fmt.Println("Http server start failed, err:%v", err)
		return
	}
}
 <!DOCTYPE html>
<html lang = "Zh-CN">
<head>
<title>自定义函数</title>
</head>
<body>
{{ kua . }} //kua后面有空格
</body>
</html>

t.tmpl

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>

<h1>测试嵌套tmplate语法</h1>
<hr>
{{/*嵌套了另外一个单独的模板文件*/}}
{{template "ul.tmpl"}}
<hr>
{{/*嵌套另外一个define定义的模板*/}}
{{template "ol.tmpl"}}

<div>你好,{{.}}</div>
</body>
</html>
{{/*通过define定义一个模板*/}}
{{ define "ol.tmpl"}}
    <ol>
        <li>吃饭</li>
        <li>睡觉</li>
        <li>打豆豆</li>
    </ol>
{{end}}

ul.tmpl

<ul>
    <li>注释</li>
    <li>日志</li>
    <li>测试</li>
</ui>
func demo(w http.ResponseWriter, r *http.Request) {
	//定义模板
	//解析模板
	t, err := template.ParseFiles("./t.tmpl", "./ul.tmpl")  被包含的模板要写在后面
	if err != nil {
		fmt.Printf("parse temple failed, err : %v", err)
		return
	}
	name := "郑艺"
	//渲染模板
	t.Execute(w, name)
}

func main() {
	http.HandleFunc("/", f1)
	http.HandleFunc("/tmplDemo", demo)
	err := http.ListenAndServe(":9090", nil)
	if err != nil {
		fmt.Println("Http server start failed, err:%v", err)
		return
	}

六、模板继承

package main

import (
	"fmt"
	"html/template"
	"net/http"
)

func index(w http.ResponseWriter, r *http.Request) {
	//定义模板
	//解析模板
	t, err := template.ParseFiles("./index.tmpl")
	if err != nil {
		fmt.Printf("parse template failed, err: %v", err)
		return
	}
	msg := "郑艺"
	//渲染模板
	t.Execute(w, msg)
}
func home(w http.ResponseWriter, r *http.Request) {
	//定义模板
	//解析模板
	t, err := template.ParseFiles("./home.tmpl")
	if err != nil {
		fmt.Printf("parse template failed, err: %v", err)
		return
	}
	msg := "郑艺"
	//渲染模板
	t.Execute(w, msg)
}

func main() {
	http.HandleFunc("/index", index)
	http.HandleFunc("/home", home)
	err := http.ListenAndServe(":9090", nil)
	if err != nil {
		fmt.Println("Http server start failed, err:%v", err)
		return
	}
}
<!DOCTYPE html>
<html lang="Zh-CN">

<head>
    <title>模板继承</title>
    <style>
        * {
            margin: 0
        }

        .nav {   //导航栏内容
            height: 50px;
            width:100%;
            position: fixed;
            top: 0;
            background-color: burlywood;
        }

        .main {  //主内容区域
            margin-top: 50px;
        }

        .menu { //侧边栏
            width: 20%;
            height: 100%;
            position: fixed;
            left: 0;
            background-color: cornflowerblue;
        }
        .center {
        text-align: center;
        }
    </style>
</head>

<body>

    <div class="nav"></div>
    <div class="main"></div>
    <div class="menu"></div>
    <div class="content center">
    <h1>这是一个index页面</h1>
    <p>hello{{.}}</p>
    </div>
</body>

</html>

== block ==
在这里插入图片描述

== base.tmpl ==

<body>

    <div class="nav"></div>
    <div class="main"></div>
    <div class="menu"></div>
    <div class="content center">  
    {{block "content" .}} {{end}}
    </div>
</body>

== index2 ==

{{/*】继承根模板*/}}
{{template "base.tmpl" .}}
{{/*重新定义块模板*/}}
{{define "content"}}
    <h1>这是一个index页面!<h1>
    <p>Hello {{ . }}</p>
{{end}}

在这里插入图片描述
为什么没有hello 后面没有打印郑艺?
因为在根模板中 . 已经导入到子模板了,但是子模板没有接收到

<div class="content center">  
    {{block "content" .}} {{end}}
    </div>
func index2(w http.ResponseWriter, r *http.Request) {
	//定义模板
	//解析模板
	t, err := template.ParseFiles("./base.tmpl", "./index2.tmpl")
	if err != nil {
		fmt.Printf("parse template failed, err: %v", err)
		return
	}
	name := "郑艺"
	//渲染模板
	t.ExecuteTemplate(w, "index2.tmpl", name) //为什么要用ExecuteTemplate,因为现在解析两个模板
}

func home2(w http.ResponseWriter, r *http.Request) {
	//定义模板
	//解析模板
	t, err := template.ParseFiles("./base.tmpl", "./home2.tmpl")
	if err != nil {
		fmt.Printf("parse template failed, err: %v", err)
		return
	}
	name := "郑艺"
	//渲染模板
	t.ExecuteTemplate(w, "home2.tmpl", name)
}

七、模板补充

在这里插入图片描述
在这里插入图片描述

八、gin框架返回json

package main

import (
	"net/http"

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

func main() {

	r := gin.Default()

	r.GET("/json", func(c *gin.Context) {

		// 方法一: 使用map
		// data := map[string]interface{}{
		// 	"name":    "郑艺",
		// 	"message": "你真是个人才",
		// 	"age":     18,
		// }
		data := gin.H{"name": "郑艺", "age": 18, "message": "你好帅"}
		c.JSON(http.StatusOK, data)
	})

	r.Run(":9090")
}

在这里插入图片描述

//方法二:结构体
	type msg struct {
		Name    string
		Message string
		Age     int
	}
	r.GET("another_json", func(c *gin.Context) {
		data := msg{
			Name:    "郑艺",
			Message: "Hello golang!",
			Age:     18,
		}
		c.JSON(http.StatusOK, data)
	})
	r.Run(":9090")
}

在这里插入图片描述

九、总结🍓🍓🍓

在这里插入图片描述

悦读

道可道,非常道;名可名,非常名。 无名,天地之始,有名,万物之母。 故常无欲,以观其妙,常有欲,以观其徼。 此两者,同出而异名,同谓之玄,玄之又玄,众妙之门。

;