Gin框架: 从0开始搭建 Gin Web 服务

最近在学习 Go Web 开发,记录一下 Go 小白 如何从0开始,搭建出 Gin Web 服务,快速了解Gin Web开发的关键步骤。

题外话:博主做过多年的 Java Web、Python Web 开发,习惯在用不同框架开发前,先了解框架的目录结构、开发规范,按照标准规范进行开发,这样可以避免踩很多不必要的坑。Gin 算是 Go Web 中发展比较成熟的框架了,插件的支持也都很完善,但官网上并没有目录结构、开发规范的相关介绍,所以,本文的代码结构是参考 Github 众多开源项目的目录结构及开发规范后创建的。

先决条件

搭建本地的 Go 开发环境,具体搭建过程可以参考大量文章,自行百度即可。

创建 Gin Web 服务的目录结构

1、创建目录 ast-framework-service

1
$ mkdir ast-framework-service

2、初始化为 Go 项目

1
2
$ cd ast-framework-service
$ go mod init io.ast.service

3、安装 gin 模块

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

4、创建基本的目录结构及文件

1
2
3
4
5
6
7
8
9
10
$ mkdir router model service config
# 创建 router 目录,用于创建 Go Web 的 API 路由
# 创建 model 目录,保存应用与数据库交互式使用到的对象模型
# 创建 service 目录,保存 API 的具体处理逻辑
# 创建 config 目录,创建配置文件,保存运行所需的各种配置

$ touch app.go config/config.ini model/mysql_driver.go router/router_init.go
# 创建 app.go 文件,作为应用的入口,注册路由、启动服务、监听端口等
# 创建配置文件
# 创建数据库连接文件、API 路由入口文件

配置文件 config/config.ini 内容如下:

1
2
3
4
5
6
7
8
9
10
11
[server]
; :8080 表示监听 0.0.0.0:8080
addr = 127.0.0.1:8080

[mysql]
db_host = db_host
db_port = 3306
db_name = db_name
db_user = db_user
db_pwd = db_pwd
db_charset = db_charset

数据库连接文件 model/mysql_driver.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
package model

import (
"fmt"

"gopkg.in/ini.v1"
"gorm.io/driver/mysql"
"gorm.io/gorm"
)

var DB *gorm.DB

func InitDB(conf *ini.File) *gorm.DB {
mysqlName := conf.Section("mysql").Key("db_name").String()
mysqlUser := conf.Section("mysql").Key("db_user").String()
mysqlPwd := conf.Section("mysql").Key("db_pwd").Value()
mysqlHost := conf.Section("mysql").Key("db_host").String()
mysqlPort := conf.Section("mysql").Key("db_port").String()
mysqlCharset := conf.Section("mysql").Key("db_charset").String()
mysqlPwd = mysqlPwd + "#"
fmt.Println(mysqlPwd)
dsn := mysqlUser + ":" + mysqlPwd + "@tcp(" + mysqlHost + ":" + mysqlPort + ")/" + mysqlName + "?charset=" + mysqlCharset
fmt.Println(dsn)
DB, _ = gorm.Open(mysql.Open(dsn), &gorm.Config{})
return DB
}

API 路由入口文件 router/router_init.go 如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
package router

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

var (
anonymousRouterRole = make([]func(*gin.RouterGroup), 0)
)

func Init(r *gin.Engine) {
registerRoute(r)
}

func registerRoute(r *gin.Engine) {
v1 := r.Group("/api/v1")
for _, f := range anonymousRouterRole {
f(v1)
}
}

Gin-Web 应用入口文件 app.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
package main

import (
"log"

"github.com/gin-gonic/gin"
"golang.org/x/sync/errgroup"
"gopkg.in/ini.v1"
"io.gin.sample/model"
router "io.gin.sample/router"
)

var (
g errgroup.Group
)

func main() {
conf, err := ini.Load("config/app.ini")
if err != nil {
return
}
model.InitDB(conf)
r := gin.Default()
router.Init(r)
// 监听并在 0.0.0.0:8080 上启动服务
g.Go(func() error {
return r.Run(conf.Section("server").Key("addr").String())
})
if err := g.Wait(); err != nil {
log.Fatal(err)
}
}

创建 sayHi API 实现打招呼的功能

创建 service 文件 service/say_hi.go,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
package service

import (
"fmt"
"net/http"

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

func Sayhi(c *gin.Context) {
name := c.Query("name")
c.JSON(http.StatusOK, gin.H{
"code": 200,
"msg": "success",
"data": fmt.Sprintf("hello, world. my name is %s", name),
})
}

创建 route 文件 router/say_hi.go,注册路由并绑定处理方法,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
package router

import (
"github.com/gin-gonic/gin"
"io.gin.sample/service"
)

func init() {
anonymousRouterRole = append(anonymousRouterRole, registerAgentRoute)
}

func registerAgentRoute(rg *gin.RouterGroup) {
rg.GET("/sayhi", service.Sayhi)
}

运行 Gin-Web 服务

1
$ go run app.go

访问 sayhi 打招呼:

参考链接

owefsad wechat
进击的DevSecOps,持续分享SAST/IAST/RASP的技术原理及甲方落地实践。如果你对 SAST、IAST、RASP方向感兴趣,可以扫描下方二维码关注公众号,获得更及时的内容推送。
0%