创建项目
创建项目 z-wiki
新建main.go
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
| package main
import ( "github.com/gin-gonic/gin" )
func helloHandler(c *gin.Context) { c.JSON(200, gin.H{ "message": "hello world!", }) }
func main() { g := gin.Default()
g.GET("/hello", helloHandler)
g.Run() }
|
目录下执行
1 2
| go mod init z-wiki go mod tidy
|
运行
访问:http://localhost:8080/hello
设置启动端口
1 2
| port := "9999" g.Run(":" + port)
|
允许跨域
下载
1
| go get github.com/gin-contrib/cors
|
引用
1
| import "github.com/gin-contrib/cors"
|
设置允许的域
1 2 3 4 5 6 7 8 9
| func main() { g := gin.Default()
corsConfig := cors.DefaultConfig() corsConfig.AllowOrigins = []string{"http://www.psvmc.cn", "http://psvmc.cn"} g.Use(cors.New(corsConfig))
g.Run() }
|
允许所有
等效于
1 2 3
| corsConfig := cors.DefaultConfig() corsConfig.AllowOrigins = []string{"*"} g.Use(cors.New(corsConfig))
|
1 2 3 4
| corsConfig := cors.DefaultConfig() corsConfig.AllowOrigins = []string{"*"} corsConfig.AllowHeaders = []string{"Content-Type", "Z-UserId"} g.Use(cors.New(corsConfig))
|
路由拆分
main.go
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| package main
import ( "z-wiki/routers"
"github.com/gin-contrib/cors" "github.com/gin-gonic/gin" )
func main() { g := gin.Default() g.Use(cors.Default()) routers.LoadUser(g) g.Run() }
|
routers/user_router.go
1 2 3 4 5 6 7 8 9 10 11 12 13
| package routers
import "github.com/gin-gonic/gin"
func LoadUser(e *gin.Engine) { e.GET("/user/info", helloHandler) }
func helloHandler(c *gin.Context) { c.JSON(200, gin.H{ "name": "小明", }) }
|
访问:http://localhost:8080/user/info
注意:
对其他包暴露的方法首字母要大写。
静态化与重定向
我们想项目的根路由重定向到项目的static/index.html中
手相添加静态目录
1 2
| g.Static("/static", "./static")
|
添加路由重定向
routers/index_router.go
1 2 3 4 5 6 7 8 9 10 11 12
| package routers
import ( "github.com/gin-gonic/gin" )
func LoadIndex(e *gin.Engine) { e.GET("/", func(c *gin.Context) { c.Redirect(301, "/static") }) }
|
加载路由
请求参数
URL中的参数
JSON参数
在 Gin 框架中,你可以使用 ShouldBindJSON() 方法来获取 POST 请求中的 JSON 参数。
以下是一个示例代码,演示如何在 Go 中使用 Gin 框架获取请求的 JSON 参数:
假设有一个 POST 请求发送了一个 JSON 参数,如 {"name": "Alice", "age": 30}。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
| package main
import ( "github.com/gin-gonic/gin" "net/http" )
type Person struct { Name string `json:"name"` Age int `json:"age"` }
func main() { r := gin.Default()
r.POST("/person", func(c *gin.Context) { var person Person
if err := c.ShouldBindJSON(&person); err != nil { c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) return }
c.JSON(http.StatusOK, gin.H{ "name": person.Name, "age": person.Age, }) })
r.Run(":9999") }
|
在上面的示例中,我们定义了一个 Person 结构体来表示 JSON 中的参数。在路由 /person 中,我们使用 ShouldBindJSON() 方法将请求的 JSON 参数绑定到 person 变量中。如果绑定成功,则返回 JSON 格式的姓名和年龄信息;如果绑定失败,则返回错误信息。
当发送 POST 请求到 http://localhost:9999/person 并携带 JSON 参数时,Gin 框架将解析请求中的 JSON 参数,并将其存储在 person 变量中。然后我们可以通过 person.Name 和 person.Age 访问参数的值。
文件参数
1 2
| file, err := c.FormFile("file") userid := c.PostForm("userid")
|
1
| userId := c.Request.Header.Get("Z-UserId")
|
文件上传
file_router.go
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45
| package routers
import ( "fmt" "github.com/gin-gonic/gin" "github.com/google/uuid" "os" "path" "path/filepath" "strings" "time" "z-wiki/model" )
func LoadFile(e *gin.Engine) { e.POST("/file/upload", uploadHandler) }
func uploadHandler(c *gin.Context) { file, err := c.FormFile("file") userid := c.PostForm("userid") fmt.Println("userid:", userid) if err != nil { c.JSON(200, model.ResultVo[string]{Code: 1, Msg: "未找到文件", Obj: ""}) return } dateStr := time.Now().Format("200601") pathStr := path.Join("static", "upload", dateStr) err = os.MkdirAll(pathStr, os.ModePerm) if err != nil { c.JSON(200, model.ResultVo[string]{Code: 1, Msg: "上传失败", Obj: ""}) return }
uuidStr := uuid.New().String() fileExt := filepath.Ext(file.Filename) filePathAll := path.Join(pathStr, uuidStr+strings.ToLower(fileExt)) fmt.Println("filePathAll", filePathAll) err = c.SaveUploadedFile(file, filePathAll) if err != nil { c.JSON(200, model.ResultVo[string]{Code: 1, Msg: "上传失败", Obj: ""}) return } c.JSON(200, model.ResultVo[string]{Code: 0, Msg: "上传成功", Obj: filePathAll}) }
|
resultvo.go
1 2 3 4 5 6 7
| package model
type ResultVo[T any] struct { Code int `json:"code"` Msg string `json:"msg"` Obj T `json:"obj"` }
|
配置读取
配置文件
config/config.json
1 2 3 4 5 6
| { "port":"8888", "db_host": "dbtest.psvmc.cn", "db_user": "zhangjian", "db_pwd": "Test_123456" }
|
工具类
utils/config_reader.go
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33
| package utils
import ( "encoding/json" "fmt" "os" )
type Config struct { PORT string `json:"port"` DBHost string `json:"db_host"` DBUser string `json:"db_user"` DBPwd string `json:"db_pwd"` }
func ReadConfig() *Config { file, err := os.Open("config/config.json") if err != nil { fmt.Println("Failed to open config file:", err) return nil } defer file.Close()
decoder := json.NewDecoder(file) config := Config{} err = decoder.Decode(&config) if err != nil { fmt.Println("Failed to decode config file:", err) return nil }
return &config }
|
调用
1 2 3 4 5 6 7 8 9 10
| config := utils.ReadConfig() if config == nil { return } fmt.Println("-----------------------------") fmt.Println("PORT:", config.PORT) fmt.Println("DBHost:", config.DBHost) fmt.Println("DBUser:", config.DBUser) fmt.Println("DBPwd:", config.DBPwd) fmt.Println("-----------------------------")
|
JSON序列化与反序列化
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33
| package main
import ( "encoding/json" "fmt" )
type Person struct { Name string Age int }
func Json2Str() { person := Person{Name: "Alice", Age: 30} jsonData, err := json.Marshal(person) if err != nil { fmt.Println("转换失败:", err) return } jsonString := string(jsonData) fmt.Println("Json2Str:", jsonString) }
func Str2Json() { str := `{"Name": "Alice", "Age": 30}` var person Person err := json.Unmarshal([]byte(str), &person) if err != nil { fmt.Println("转换失败:", err) return } fmt.Printf("Str2Json:%+v\n", person) }
|