使用原生的Golang进行数据库CRUD感觉到诸多不变,于是参照之前使用数据库类的习惯用法,

封装了一个数据库操作方法集:

package lib

import (

"database/sql"

_ "github.com/go-sql-driver/mysql"

"strings"

"fmt"

)

type dbRow map[string]interface{}

type Dblib struct {

db *sql.DB

}

func NewDblib(driver, dsn string) (*Dblib, error) {

db, err := sql.Open(driver, dsn)

if err != nil {

return nil, err

}

err = db.Ping()

if err != nil {

return nil, err

}

p := new(Dblib)

p.db = db

return p, nil

}

func scanRow(rows *sql.Rows) (dbRow, error) {

columns, _ := rows.Columns()

vals := make([]interface{}, len(columns))

valsPtr := make([]interface{}, len(columns))

for i := range vals {

valsPtr[i] = &vals[i]

}

err := rows.Scan(valsPtr...)

if err != nil {

return nil ,err

}

r := make(dbRow)

for i, v := range columns {

if va, ok := vals[i].([]byte); ok {

r[v] = string(va)

} else {

r[v] = vals[i]

}

}

return r, nil

}

// 获取一行记录

func (d *Dblib) GetOne(sql string, args ...interface{}) (dbRow, error) {

rows, err := d.db.Query(sql, args...)

if err != nil {

return nil, err

}

defer rows.Close()

rows.Next()

result, err := scanRow(rows)

return result, err

}

// 获取多行记录

func (d *Dblib) GetAll(sql string, args ...interface{}) ([]dbRow, error) {

rows, err := d.db.Query(sql, args...)

if err != nil {

return nil, err

}

defer rows.Close()

result := make([]dbRow, 0)

for rows.Next() {

r, err := scanRow(rows)

if err != nil {

continue

}

result = append(result, r)

}

return result, nil

}

// 写入记录

func (d *Dblib) Insert(table string, data dbRow) (int64, error) {

fields := make([]string, 0)

vals := make([]interface{}, 0)

placeHolder := make([]string, 0)

for f, v := range data {

fields = append(fields, f)

vals = append(vals, v)

placeHolder = append(placeHolder, "?")

}

sql := fmt.Sprintf("INSERT INTO %s(%s) VALUES(%s) ", table, strings.Join(fields, ","), strings.Join(placeHolder, ","))

result, err := d.db.Exec(sql, vals...)

if err != nil {

return 0, err

}

lID, err := result.LastInsertId()

if err != nil {

return 0, err

}

return lID, nil

}

// 更新记录

func (d *Dblib) Update(table, condition string, data dbRow, args ...interface{}) (int64, error) {

params := make([]string, 0)

vals := make([]interface{}, 0)

for f, v := range data {

params = append(params, f + "=?")

vals = append(vals, v)

}

sql := "UPDATE %s SET %s"

if condition != "" {

sql += " WHERE %s"

sql = fmt.Sprintf(sql, table, strings.Join(params, ","), condition)

vals = append(vals, args...)

} else {

sql = fmt.Sprintf(sql, table, strings.Join(params, ","))

}

result, err := d.db.Exec(sql, vals...)

if err != nil {

return 0, err

}

aID, err := result.RowsAffected()

if err != nil {

return 0, err

}

return aID, nil

}

// 删除记录

func (d *Dblib) Delete(table, condition string, args ...interface{}) (int64, error) {

sql := "DELETE FROM %s "

if condition != "" {

sql += "WHERE %s"

sql = fmt.Sprintf(sql, table, condition)

} else {

sql = fmt.Sprintf(sql, table)

}

result, err := d.db.Exec(sql, args...)

if err != nil {

return 0, err

}

aID, err := result.RowsAffected()

if err != nil {

return 0, err

}

return aID, nil

}