panic: runtime error: invalid memory address or nil pointer dereference
来源:3-7 编码实战:从文件表中获取元数据

慕函数5852696
2020-03-31
panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x0 pc=0x10d8296]
goroutine 1 [running]:
database/sql.(*DB).SetMaxOpenConns(0x0, 0xa)
/usr/local/go/src/database/sql/sql.go:847 +0x26
github.com/xiaobaiadm/filestore-server/db/mysql.init.0()
/Users/baijunhua/newgo/src/github.com/xiaobaiadm/filestore-server/db/mysql/conn.go:14 +0x7a
附代码,14行报上面的错误,这块实在不知道那错了,遇到这种问题怎么排查呢,烦请老师给个思路。
func init() {
db,_ = sql.Open(“mysql”,“dog:1233456@localhost/fileserver”)
db.SetMaxOpenConns(10)
if err := db.Ping(); err != nil {
fmt.Println(“db connet,err:”,err)
os.Exit(1)
}
}
//返回数据库连接
func DbConn() *sql.DB {
return db
}
4回答
-
xiaomo
2020-04-02
可以看到sql.Open这个方法是有返回err信息的,源码:
func Open(driverName, dataSourceName string) (*DB, error) { driversMu.RLock() driveri, ok := drivers[driverName] driversMu.RUnlock() if !ok { return nil, fmt.Errorf("sql: unknown driver %q (forgotten import?)", driverName) } if driverCtx, ok := driveri.(driver.DriverContext); ok { connector, err := driverCtx.OpenConnector(dataSourceName) if err != nil { return nil, err } return OpenDB(connector), nil } return OpenDB(dsnConnector{dsn: dataSourceName, driver: driveri}), nil }
里面返回来的error是由底层的sql driver来提供的,不同的driver可能会返回不同信息。 为了可以处理这种异常,我们这里的代码需要优化一下:
db, err := sql.Open("mysql", "test:test@tcp(127.0.0.1:3306)/fileserver?charset=utf8") if err != nil { panic(err) // 这里是否直接panic, 根据具体场景决定(也可以增加重试,或者只报warning后续再做处理) } db.SetMaxOpenConns(1000) err := db.Ping() if err != nil { fmt.Println("Failed to connect to mysql, err:" + err.Error()) os.Exit(1) }
00 -
xiaomo
2020-04-02
处理panic的一般做法是捕获异常,和其他语言的try-catch是类似的原理,比如:
func doSomething(index int) { defer func() { if r := recover(); r != nil { fmt.Printf("异常捕获:%s\n", r) } }() if index < 0 { panic("index必须大于0") } fmt.Println("方根运算:", math.Sqrt(float64(index))) }
上述的init方法中,在创建Mysql连接时可以优化一下,加上类似逻辑.
00 -
慕函数5852696
提问者
2020-04-01
已经修复了 ,确实我之前某块地方写错了 ,今天早上尝试的时候好了,但是如果这块没有明显的错误,例如连接数据库出现账号密码错误等这样的明确的信息提示,直接来了一个panic ,出现这种情况我该怎么具体的排查呢,因为在这块开发中可能会遇到各种各样的panic ,有工具或者是什么可以排查代码么,让输出更明确一些,麻烦老师能给个思路,谢谢。
之前还遇到了 编译过程中的panic00 -
xiaomo
2020-04-01
同学你好,这个应该是与数据库建立连接没有成功。上面的14行的代码应该是这行?
db.SetMaxOpenConns(10)
这说明以下这行代码出了问题:
db,_ = sql.Open(“mysql”,“dog:1233456@localhost/fileserver”)
可以参考下git上的代码:https://git.imooc.com/coding-323/filestore-server/src/charter3/db/mysql/conn.go
var db *sql.DB func init() { db, _ = sql.Open("mysql", "root:root@tcp(127.0.0.1:3306)/fileserver?charset=utf8") db.SetMaxOpenConns(1000) err := db.Ping() if err != nil { fmt.Println("Failed to connect to mysql, err:" + err.Error()) os.Exit(1) } }
把你的代码换成:
db,_ = sql.Open(“mysql”,“dog:1233456@tcp(127.0.0.1:3306)/fileserver?charset=utf8”)
这样试试看。还有就是检查用户名(dog)密码(1233456)是否正确?
00
相似问题