Golang的database/sql提供了统一的标准数据库接口,不同的数据库有不同的数据库驱动,例如mysql的,有个github.com/go-sql-driver/mysql 包可以用,编写代码之前,请先 go get github.com/go-sql-driver/mysql
下面是demo:
package main
import (
"database/sql"
"fmt"
_ "github.com/go-sql-driver/mysql"
"time"
)
var Db *sql.DB
func init(){
var err error
Db, err = sql.Open("mysql", "root:123456@tcp(127.0.0.1:3306)/test?charset=utf8mb4")
if err != nil {
panic(err)
}
}
func Select(){
var Username string
var Money float64
var Birthday sql.NullString
//参数绑定,可以避免sql注入
rows := Db.QueryRow("SELECT username,money,birthday FROM member WHERE id=?",1)
err := rows.Scan(&Username,&Money,&Birthday)
if err != nil{
fmt.Println("scan err:",err)
return
}
fmt.Println(Username,Money,Birthday.String)
}
func Insert(){
result,err:=Db.Exec("INSERT INTO member(username,money,birthday,created_at)VALUES (?,?,?,?)","test","10",nil,time.Now().Unix())
if err!=nil {
fmt.Println(err);return
}
//获取修改的行数
id,err:=result.LastInsertId()
if err != nil {
fmt.Println(err); return
}
fmt.Println(id)
}
func Update(){
result,err:=Db.Exec("UPDATE member set money=money+10 WHERE id=?",1)
if err!=nil {
fmt.Println(err);return
}
//获取修改的行数
rows,err:=result.RowsAffected()
if err != nil {
fmt.Println(err); return
}
fmt.Println(rows)
}
func Delete(){
result,err:=Db.Exec("DELETE FROM member WHERE id=?",3)
if err!=nil {
fmt.Println(err);return
}
//获取删除的行数
rows,err:=result.RowsAffected()
if err != nil {
fmt.Println(err); return
}
fmt.Println(rows)
}
func Transaction(){
tx,err:=Db.Begin()
if err!=nil { panic(err) }
defer clearTransaction(tx) //如果执行过程中都没有 commit和roolback那就由这个来收尾
//1、修改
result,err:=tx.Exec("UPDATE member set money=money+10 WHERE id=?",1)
if err!=nil {
tx.Rollback(); return
}
//获取修改的行数
rows,err:=result.RowsAffected()
if err != nil {
tx.Rollback(); return
}
fmt.Println(rows) //这里需要的话,可以改成判断函数,等于小于0,rollback
//2、修改
result,err=tx.Exec("UPDATE member set money=money-10 WHERE id=?",2)
if err!=nil {
tx.Rollback(); return
}
//获取修改的行数
rows,err=result.RowsAffected()
if err != nil {
tx.Rollback(); return
}
fmt.Println(rows) //这里需要的话,可以改成判断函数,等于小于0,rollback
tx.Commit()
}
//事务回滚
func clearTransaction(tx *sql.Tx){
err := tx.Rollback()
fmt.Println("执行了rollback")
if err != sql.ErrTxDone && err != nil{
fmt.Println(err)
}
}
func main() {
//Select()
//Insert()
//Update()
//Delete()
//事务处理
//Transaction()
}
表结构和数据:
CREATE TABLE `member` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`username` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL,
`money` decimal(10,2) unsigned NOT NULL,
`birthday` date DEFAULT NULL,
`created_at` int(11) unsigned NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='用户表';
INSERT INTO `test`.`member` (`id`, `username`, `money`, `birthday`, `created_at`) VALUES ('1', 'mrtwenty', '130.00', '2019-06-19', '1223');
INSERT INTO `test`.`member` (`id`, `username`, `money`, `birthday`, `created_at`) VALUES ('2', 'zhao', '80.00', NULL, '2323');
空值处理请看这行代码:
var Birthday sql.NullString
类似的还有: sql.NullFloat64,sql.NullString,sql.NullBool,sql.NullInt64
可以根据自己的需求,如果字段设计是允许为空的,就需要使用这些了。