【go】go 使用 Mysql 包报错: database is closed?

题目描述

使用的go-sql-driver/mysql 驱动,在另一个 package 中初始化连接池对象, 并且将 *sq;.DB 设为全局变量在 另一个包中引用,使用Query 获取 MySQL 连接 ,查询一直报错 ?

相关代码

package database

import (

"database/sql"

"fmt"

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

"log"

)

var Db *sql.DB

func init() {

var err error

Db, err = sql.Open("mysql", "root:[email protected](127.0.0.1:3306)/blog?charset=utf8")

if err != nil {

fmt.Println("conn failed!")

log.Fatal(err.Error())

}

defer Db.Close()

fmt.Println(&Db)

Db.SetMaxOpenConns(2000)

Db.SetMaxIdleConns(1000)

err = Db.Ping()

if err != nil {

log.Fatal(err.Error())

}

fmt.Println("db inti")

}

package controllers

import (

. "build-web-application/004-blog/database"

//"database/sql"

"fmt"

"github.com/gin-gonic/gin"

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

"log"

)

func GetPosts(c *gin.Context) {

rows, err := Db.Query(`SELECT * FROM t_post`)

if err != nil {

log.Fatal(err)

}

// defer rows.Close()

for rows.Next() {

var id int

var post string

err = rows.Scan(&id, &post)

fmt.Println(id)

fmt.Println(post)

}

}

@勤奋的小小尘 说的对,你在init()中使用defer Db.Close()的结果是,init函数返回的时候,关闭了数据库连接,而后又在GetPosts()中调用,就会报数据库已关闭的错误。

正确的做法是,在你完全使用完Db后,再进行关闭。我之前写过一篇关于defer的文章,可以看一下:https://segmentfault.com/a/11...

【go】go 使用 Mysql  包报错: database is closed?

看划红线的地方,你已经close了,外面这么可能还能用。。
建议先理解defer的含义。
一定要先看基础,循序渐进,不要急躁

defer Db.Close()
会在init函数结束的时候执行。
所以这种类型的资源是不需要defer关闭的

回答

以上是 【go】go 使用 Mysql 包报错: database is closed? 的全部内容, 来源链接: utcz.com/a/109641.html

回到顶部