Go处理数据库错误需区分错误类型:连接类、锁超时等可重试,主键冲突、事务异常等不可重试;应使用驱动提供的错误谓词函数精准判断,并实施最多3次指数退避重试。
Go 语言中处理数据库错误,关键不是“捕获所有 error”,而是识别错误类型、区分可恢复与不可恢复错误,并对网络抖动、锁冲突等常见临时性问题实施有节制的重试。直接 if err != nil { log.Fatal(err) } 在生产环境极易导致服务雪崩。
Go 的 database/sql 本身不定义具体错误码,实际错误来自底层驱动(如 github.com/lib/pq、github.com/go-sql-driver/mysql)。需按驱动文档解析错误细节:
dial tcp: i/o timeout、connection refused、server closed —— 属于临时性故障,适合重试23505,MySQL 的 1062)、外键约束失败(23503)、空值违例(23502)—— 逻辑错误,重试无意义,应修正输入或业务逻辑55P03(lock_not_available),MySQL 的 1205(deadlock)或 1206(lock_wait_timeout)—— 可重试,但需退避pq: current transaction is aborted, commands ignored until end of transaction block —— 必须回滚后新建事务,不能继续执行避免字符串匹配,优先使用驱动提供的错误检查函数:
import "github.com/lib/pq"func isUniqueViolation(err error) bool { if pqErr, ok := err.(*pq.Error); ok { return pqErr.Code == "23505" } return false }
func isLockTimeout(err error) bool { if pqErr, ok := err.(*pq.Error); ok { return pqErr.Code == "55P03" } return false }
func isNetworkError(err error) bool { return strings.Contains(err.Error(), "i/o timeout") || strings.Contains(err.Error(), "connection refused") || strings.Contains(err.Error(), "broken pipe") || errors.Is(err, io.EOF) }
MySQL 驱动也提供类似能力:mysql.MySQLError 结构体含 Number 字段,可直接比对错误码(如 err.Number == 1062)。
重试不是越多越好。推荐最多 3 次,配合指数退避(如 100ms → 300ms → 900ms),并排除不可重试错误:
func withRetry(fn func() error, maxRetries int) error {
var err error
for i := 0; i <= maxRetries; i++ {
err = fn()
if err == nil {
return nil
}
if !shouldRetry(err) {
return err // 不该重试,立即返回
}
if i < maxRetries {
d := time.Duration(math.Pow(3, float64(i))) * time.Millisecond * 100
time.Sleep(d)
}
}
return err
}
func shouldRetry(err error) bool {
return isNetworkError(err) || isLockTimeout(err)
}
注意:不要在事务内部盲目重试整个事务块 —— 若已执行部分语句,重试可能造成重复写入。应在事务外重试“事务函数”本身。
数据库错误不应透传给前端。建议统一转换为业务错误码和提示:
可用简单错误包装器实现
:
type AppError struct {
Code int
Message string
Err error
}
func (e AppError) Error() string { return e.Message }
func (e AppError) Unwrap() error { return e.Err }
基本上就这些。核心是分清错误性质:临时的就等一等再试,逻辑错的就别硬刚,网络断的就重连,约束炸的就改数据。不复杂但容易忽略。
# mysql
# git
# go
# github
# golang
# ai
# red
# sql
# if
# Error
# 字符串
# 结构体
# nil
# number
# database
# postgresql
# 数据库
# 重试
# 最多
# 主键
# 错误码
# 再试
# 已被
# 不存在
# 越多
# 不应
# 并对
相关文章:
常州企业网站制作公司,全国继续教育网怎么登录?
名字制作网站免费,所有小说网站的名字?
如何用景安虚拟主机手机版绑定域名建站?
如何高效配置香港服务器实现快速建站?
广州营销型建站服务商推荐:技术优势与SEO优化解析
音乐网站服务器如何优化API响应速度?
哪家制作企业网站好,开办像阿里巴巴那样的网络公司和网站要怎么做?
如何在建站之星绑定自定义域名?
c# F# 的 MailboxProcessor 和 C# 的 Actor 模型
如何在阿里云ECS服务器部署织梦CMS网站?
外贸公司网站制作,外贸网站建设一般有哪些步骤?
建站之星在线版空间:自助建站+智能模板一键生成方案
小米网站链接制作教程,请问miui新增网页链接调用服务有什么用啊?
官网网站制作腾讯审核要多久,联想路由器newifi官网
广东企业建站网站优化与SEO营销核心策略指南
较简单的网站制作软件有哪些,手机版网页制作用什么软件?
上海网站制作网页,上海本地的生活网站有哪些?最好包括生活的各个方面的?
小程序网站制作需要准备什么资料,如何制作小程序?
建站之星安装步骤有哪些常见问题?
如何通过虚拟机搭建网站?详细步骤解析
建站主机如何选?高性价比方案全解析
企业宣传片制作网站有哪些,传媒公司怎么找企业宣传片项目?
,网页ppt怎么弄成自己的ppt?
建站之星官网登录失败?如何快速解决?
创业网站制作流程,创业网站可靠吗?
矢量图网站制作软件,用千图网的一张矢量图做公司app首页,该网站并未说明版权等问题,这样做算不算侵权?应该如何解决?
如何解决ASP生成WAP建站中文乱码问题?
购物网站制作公司有哪些,哪个购物网站比较好?
胶州企业网站制作公司,青岛石头网络科技有限公司怎么样?
模具网站制作流程,如何找模具客户?
如何在云服务器上快速搭建个人网站?
关于BootStrap modal 在IOS9中不能弹出的解决方法(IOS 9 bootstrap modal ios 9 noticework)
广平建站公司哪家专业可靠?如何选择?
如何自定义建站之星网站的导航菜单样式?
临沂网站制作公司有哪些,临沂第四中学官网?
建站之星Pro快速搭建教程:模板选择与功能配置指南
盘锦网站制作公司,盘锦大洼有多少5G网站?
如何快速搭建安全的FTP站点?
深圳网站制作设计招聘,关于服装设计的流行趋势,哪里的资料比较全面?
如何使用Golang table-driven基准测试_多组数据测量函数效率
北京制作网站的公司排名,北京三快科技有限公司是做什么?北京三快科技?
C#如何序列化对象为XML XmlSerializer用法
香港服务器选型指南:免备案配置与高效建站方案解析
最好的网站制作公司,网购哪个网站口碑最好,推荐几个?谢谢?
高防服务器租用指南:配置选择与快速部署攻略
网站设计制作公司地址,网站建设比较好的公司都有哪些?
如何做网站制作流程,*游戏网站怎么搭建?
已有域名和空间,如何快速搭建网站?
php json中文编码为null的解决办法
电视网站制作tvbox接口,云海电视怎样自定义添加电视源?
*请认真填写需求信息,我们会在24小时内与您取得联系。