Gin实战:Gin+Mysql简单的Restful风格的API(二)
上一篇介绍了Gin+Mysql简单的Restful风格的API,但代码放在一个文件中,还不属于restful风格,接下来将进行进一步的封装。
目录结构
☁ gin_restful2 tree
.
├── api
│ └── users.go
├── db
│ └── mysql.go
├── main.go
├── models
│ └── users.go
└── router.go
api文件夹存放我们的handler函数,用于逻辑处理,models文件夹用来存放我们的数据模型。
myql.go的包代码如下:
package db import (
"database/sql"
_ "github.com/go-sql-driver/mysql"
"log"
) var SqlDB *sql.DB
func init() {
var err error
SqlDB, err = sql.Open("mysql", "root:password@tcp(127.0.0.1:3306)/test?charset=utf8mb4")
if err != nil {
log.Fatal(err.Error())
}
err = SqlDB.Ping()
if err != nil {
log.Fatal(err.Error())
}
}
因为我们需要在别的地方使用SqlDB这个变量,因此依照golang的习惯,变量名必须大写开头。
数据model封装
修改models文件夹下的users.go,把对应的Person结构及其方法移到这里:
package models
import (
"gin_restful2/db"
"log"
) type Person struct {
Id int `json:"id" form:"id"`
Name string `json:"name" form:"name"`
Telephone string `json:"telephone" form:"telephone"`
} //插入
func (person *Person) Create() int64 {
rs, err := db.SqlDB.Exec("INSERT into users (name, telephone) value (?,?)", person.Name, person.Telephone)
if err != nil{
log.Fatal(err)
}
id, err := rs.LastInsertId()
if err != nil{
log.Fatal(err)
}
return id
} //查询一条记录
func (p *Person) GetRow() (person Person, err error) {
person = Person{}
err = db.SqlDB.QueryRow("select id,name,telephone from users where id = ?", p.Id).Scan(&person.Id, &person.Name, &person.Telephone)
return
} //查询所有记录
func (person *Person) GetRows() (persons []Person, err error) {
rows, err := db.SqlDB.Query("select id,name,telephone from users")
for rows.Next(){
person := Person{}
err := rows.Scan(&person.Id, &person.Name, &person.Telephone)
if err != nil {
log.Fatal(err)
}
persons = append(persons, person)
}
rows.Close()
return
} //修改
func (person *Person) Update() int64{
rs, err := db.SqlDB.Exec("update users set telephone = ? where id = ?", person.Telephone, person.Id)
if err != nil {
log.Fatal(err)
}
rows, err := rs.RowsAffected()
if err != nil {
log.Fatal(err)
}
return rows
} //删除一条记录
func Delete(id int) int64 {
rs, err := db.SqlDB.Exec("delete from users where id = ?", id)
if err != nil {
log.Fatal()
}
rows, err := rs.RowsAffected()
if err != nil {
log.Fatal()
}
return rows
}
handler
然后把具体的handler函数封装到api包中,因为handler函数要操作数据库,所以会引用model包,api/users.go代码如下:
package api import (
"github.com/gin-gonic/gin"
"net/http"
"fmt"
."gin_restful2/models"
"strconv"
) //index
func IndexUsers(c *gin.Context) {
c.String(http.StatusOK, "It works")
} //增加一条记录
func AddUsers(c *gin.Context) {
name := c.Request.FormValue("name")
telephone := c.Request.FormValue("telephone")
person := Person{
Name:name,
Telephone:telephone,
}
id := person.Create()
msg := fmt.Sprintf("insert successful %d", id)
c.JSON(http.StatusOK, gin.H{
"msg": msg,
})
} //获得一条记录
func GetOne(c *gin.Context) {
ids := c.Param("id")
id, _ := strconv.Atoi(ids)
p := Person{
Id:id,
}
rs, _ := p.GetRow()
c.JSON(http.StatusOK, gin.H{
"result": rs,
})
} //获得所有记录
func GetAll(c *gin.Context) {
p := Person{}
rs, _ := p.GetRows()
c.JSON(http.StatusOK, gin.H{
"list": rs,
})
} func UpdateUser(c *gin.Context) {
ids := c.Request.FormValue("id")
id, _ := strconv.Atoi(ids)
telephone := c.Request.FormValue("telephone")
person := Person{
Id:id,
Telephone:telephone,
}
row := person.Update()
msg := fmt.Sprintf("updated successful %d", row)
c.JSON(http.StatusOK, gin.H{
"msg": msg,
})
} //删除一条记录
func DelUser(c *gin.Context) {
ids := c.Request.FormValue("id")
id, _ := strconv.Atoi(ids)
row := Delete(id)
msg := fmt.Sprintf("delete successful %d", row)
c.JSON(http.StatusOK, gin.H{
"msg": msg,
})
}
路由
最后就是把路由抽离出来,修改router.go,我们在路由文件中封装路由函数
package main import (
"github.com/gin-gonic/gin"
. "gin_restful2/api"
) func initRouter() *gin.Engine {
router := gin.Default()
router.GET("/", IndexUsers) //http://localhost:8806 //路由群组
users := router.Group("api/v1/users")
{
users.GET("", GetAll) //http://localhost:8806/api/v1/users
users.POST("/add", AddUsers) //http://localhost:8806/api/v1/users/add
users.GET("/get/:id", GetOne) //http://localhost:8806/api/v1/users/get/5
users.POST("/update", UpdateUser)
users.POST("/del", DelUser)
} return router
}
app入口
最后就是main函数的app入口,将路由导入,同时我们要在main函数结束的时候,关闭全局的数据库连接池:
main.go
package main import (
"gin_restful2/db"
) func main() {
defer db.SqlDB.Close()
router := initRouter()
router.Run(":8806")
}
至此,我们就把简单程序进行了更好的组织。当然,golang的程序组织依包为基础,不拘泥,根据具体的应用场景可以组织。
此时运行项目,不能像之前简单的使用go run main.go
,因为包main包含main.go和router.go的文件,因此需要运行go run *.go
命令编译运行。如果是最终编译二进制项目,则运行go build -o app
Gin实战:Gin+Mysql简单的Restful风格的API(二)的更多相关文章
- Gin实战:Gin+Mysql简单的Restful风格的API
我们已经了解了Golang的Gin框架.对于Webservice服务,restful风格几乎一统天下.Gin也天然的支持restful.下面就使用gin写一个简单的服务,麻雀虽小,五脏俱全.我们先以一 ...
- 使用webpy创建一个简单的restful风格的webservice应用
下载:wget http://webpy.org/static/web.py-0.38.tar.gz解压并进入web.py-0.38文件夹安装:easy_install web.py 这是一个如何使用 ...
- PHP实现Restful风格的API
Restful是一种设计风格而不是标准,比如一个接口原本是这样的: http://www1.qixoo.com/user/view/id/1表示获取id为1的用户信息,如果使用Restful风格,可以 ...
- [01] 浅谈RESTful风格的API
1.什么是RESTful风格的API REST,即Representational State Transfer,可以理解为"(资源的)表现层状态转化". 在网络上,我们通过浏览器 ...
- Dubbo 03 Restful风格的API
目录 Dubbo03 restful风格的API 根路径 协议 版本 用HTTP协议里的动词来实现资源的增删改查 用例 swagger(丝袜哥) OpenAPI 资源 编写API文档 整合Spring ...
- 测开大佬告诉你:如何5分钟快速创建restful风格的API接口-使用django restframework框架
一.思考❓❔ 1.创建API接口难吗? 软件测试工程师: 只测过API接口, 从没创建过 应该需要掌握一门后端开发语言和后端开发框架吧!? 脑容量有限,想想就可怕 2.如何创建API接口呢? 使用Dj ...
- PHP实现Restful风格的API(转)
Restful是一种设计风格而不是标准,比如一个接口原本是这样的: http://www1.qixoo.com/user/view/id/1表示获取id为1的用户信息,如果使用Restful风格,可以 ...
- PHP实现RESTful风格的API实例(三)
接前一篇PHP实现RESTful风格的API实例(二) .htaccess :重写URL,使URL以 /restful/class/1 形式访问文件 Options +FollowSymlinks R ...
- PHP实现RESTful风格的API实例(二)
接前一篇PHP实现RESTful风格的API实例(一) Response.php :包含一个Request类,即输出类.根据接收到的Content-Type,将Request类返回的数组拼接成对应的格 ...
随机推荐
- Katalon Studio简单使用(一)
官网地址:https://www.katalon.com/ katalon 目前有两种产品 一个是studio 另外一个是katalon analytics,此处先来学习studio部分. 文章学习内 ...
- ASP.NET基于Aspose.Words插入Word水印以及多个水印
using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Da ...
- iOS 应用隐藏状态栏
有时候在 Storyboard 和 target 里的设定并不足以使得应用能够完全隐藏状态栏. 这时候需要到 Info.plist,添加一项:View controller-based status ...
- linux中使用unzip命令中文乱码解决办法
今天在使用unzip进行解压缩文件时,发现解压出的文件中文乱码,最后使用如下命令解决: unzip -O CP936 xxx.zip 特此记录一下.
- HTTP请求报文支持的各种方法
常见的HTTP方法如下: 1.GET GET是最常用的方法.通常用于请求服务器发送某个资源. 2.HEAD HEAD与GET的行为类似,但服务器在响应中只返回首部,不会返回实体的部分.这就允许客户端在 ...
- [Objective-C语言教程]错误处理(22)
在Objective-C编程中,错误处理由Foundation框架中提供的NSError类提供处理. 与仅使用错误代码或错误字符串相比,NSError对象封装了更丰富且更具可扩展性的错误信息. NSE ...
- 浅谈javascript和python语言的深拷贝
深拷贝: 之前在开发中我遇到一个很大的bug,经过我多次调试之后我发现原本应该有保存数据的地方数据全部被清空,仔细一看发现原来是被人为删除,明明操作的是一个副本,为什么原本也会跟着一起被删除呢?经过了 ...
- C#-WebForm-ajax状态保持
cookies: ashx端赋值: context.Response.Cookies["Username"].Value = ""; 后台端加载: Respon ...
- 使用sqlyog将sql server 迁移到mysql
使用软件工具sqlyog(64位) sqlyog 迁移步骤 1.使用sqlyog连接目标数据库 连接目标数据库 2.选择目标数据库(需要先把表结构建好,从SQL Server同步表结构也可以使用工具, ...
- hdu 1233 还是畅通工程 并查集or最小生成树
某省调查乡村交通状况,得到的统计表中列出了任意两村庄间的距离.省政府“畅通工程”的目标是使全省任何两个村庄间都可以实现公路交通(但不一定有直接的公路相连,只要能间接通过公路可达即可),并要求铺设的公路 ...