refactor for better error reporting on sql error (#1016)
* refactor for better error reporting on sql error * fix errors * add docs
This commit is contained in:
@@ -4,11 +4,9 @@ import (
|
|||||||
"database/sql"
|
"database/sql"
|
||||||
|
|
||||||
"github.com/tal-tech/go-zero/core/breaker"
|
"github.com/tal-tech/go-zero/core/breaker"
|
||||||
|
"github.com/tal-tech/go-zero/core/logx"
|
||||||
)
|
)
|
||||||
|
|
||||||
// datasource placeholder for logging error.
|
|
||||||
const rawDB = "sql.DB"
|
|
||||||
|
|
||||||
// ErrNotFound is an alias of sql.ErrNoRows
|
// ErrNotFound is an alias of sql.ErrNoRows
|
||||||
var ErrNotFound = sql.ErrNoRows
|
var ErrNotFound = sql.ErrNoRows
|
||||||
|
|
||||||
@@ -26,6 +24,7 @@ type (
|
|||||||
// SqlConn only stands for raw connections, so Transact method can be called.
|
// SqlConn only stands for raw connections, so Transact method can be called.
|
||||||
SqlConn interface {
|
SqlConn interface {
|
||||||
Session
|
Session
|
||||||
|
// RawDB is for other ORM to operate with, use it with caution.
|
||||||
RawDB() (*sql.DB, error)
|
RawDB() (*sql.DB, error)
|
||||||
Transact(func(session Session) error) error
|
Transact(func(session Session) error) error
|
||||||
}
|
}
|
||||||
@@ -47,11 +46,11 @@ type (
|
|||||||
// Because CORBA doesn't support PREPARE, so we need to combine the
|
// Because CORBA doesn't support PREPARE, so we need to combine the
|
||||||
// query arguments into one string and do underlying query without arguments
|
// query arguments into one string and do underlying query without arguments
|
||||||
commonSqlConn struct {
|
commonSqlConn struct {
|
||||||
datasource string
|
connProv connProvider
|
||||||
connProv connProvider
|
onError func(error)
|
||||||
beginTx beginnable
|
beginTx beginnable
|
||||||
brk breaker.Breaker
|
brk breaker.Breaker
|
||||||
accept func(error) bool
|
accept func(error) bool
|
||||||
}
|
}
|
||||||
|
|
||||||
connProvider func() (*sql.DB, error)
|
connProvider func() (*sql.DB, error)
|
||||||
@@ -75,10 +74,12 @@ type (
|
|||||||
// NewSqlConn returns a SqlConn with given driver name and datasource.
|
// NewSqlConn returns a SqlConn with given driver name and datasource.
|
||||||
func NewSqlConn(driverName, datasource string, opts ...SqlOption) SqlConn {
|
func NewSqlConn(driverName, datasource string, opts ...SqlOption) SqlConn {
|
||||||
conn := &commonSqlConn{
|
conn := &commonSqlConn{
|
||||||
datasource: datasource,
|
|
||||||
connProv: func() (*sql.DB, error) {
|
connProv: func() (*sql.DB, error) {
|
||||||
return getSqlConn(driverName, datasource)
|
return getSqlConn(driverName, datasource)
|
||||||
},
|
},
|
||||||
|
onError: func(err error) {
|
||||||
|
logInstanceError(datasource, err)
|
||||||
|
},
|
||||||
beginTx: begin,
|
beginTx: begin,
|
||||||
brk: breaker.NewBreaker(),
|
brk: breaker.NewBreaker(),
|
||||||
}
|
}
|
||||||
@@ -93,10 +94,12 @@ func NewSqlConn(driverName, datasource string, opts ...SqlOption) SqlConn {
|
|||||||
// Use it with caution, it's provided for other ORM to interact with.
|
// Use it with caution, it's provided for other ORM to interact with.
|
||||||
func NewSqlConnFromDB(db *sql.DB, opts ...SqlOption) SqlConn {
|
func NewSqlConnFromDB(db *sql.DB, opts ...SqlOption) SqlConn {
|
||||||
conn := &commonSqlConn{
|
conn := &commonSqlConn{
|
||||||
datasource: rawDB,
|
|
||||||
connProv: func() (*sql.DB, error) {
|
connProv: func() (*sql.DB, error) {
|
||||||
return db, nil
|
return db, nil
|
||||||
},
|
},
|
||||||
|
onError: func(err error) {
|
||||||
|
logx.Errorf("Error on getting sql instance: %v", err)
|
||||||
|
},
|
||||||
beginTx: begin,
|
beginTx: begin,
|
||||||
brk: breaker.NewBreaker(),
|
brk: breaker.NewBreaker(),
|
||||||
}
|
}
|
||||||
@@ -112,7 +115,7 @@ func (db *commonSqlConn) Exec(q string, args ...interface{}) (result sql.Result,
|
|||||||
var conn *sql.DB
|
var conn *sql.DB
|
||||||
conn, err = db.connProv()
|
conn, err = db.connProv()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logInstanceError(db.datasource, err)
|
db.onError(err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -128,7 +131,7 @@ func (db *commonSqlConn) Prepare(query string) (stmt StmtSession, err error) {
|
|||||||
var conn *sql.DB
|
var conn *sql.DB
|
||||||
conn, err = db.connProv()
|
conn, err = db.connProv()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logInstanceError(db.datasource, err)
|
db.onError(err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -195,7 +198,7 @@ func (db *commonSqlConn) queryRows(scanner func(*sql.Rows) error, q string, args
|
|||||||
return db.brk.DoWithAcceptable(func() error {
|
return db.brk.DoWithAcceptable(func() error {
|
||||||
conn, err := db.connProv()
|
conn, err := db.connProv()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logInstanceError(db.datasource, err)
|
db.onError(err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -73,7 +73,7 @@ func begin(db *sql.DB) (trans, error) {
|
|||||||
func transact(db *commonSqlConn, b beginnable, fn func(Session) error) (err error) {
|
func transact(db *commonSqlConn, b beginnable, fn func(Session) error) (err error) {
|
||||||
conn, err := db.connProv()
|
conn, err := db.connProv()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logInstanceError(db.datasource, err)
|
db.onError(err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
9
zrpc/internal/resolver/kube/deploy/clusterrole.yaml
Normal file
9
zrpc/internal/resolver/kube/deploy/clusterrole.yaml
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
apiVersion: rbac.authorization.k8s.io/v1
|
||||||
|
kind: ClusterRole
|
||||||
|
metadata:
|
||||||
|
name: endpoints-reader
|
||||||
|
rules:
|
||||||
|
- apiGroups: [""]
|
||||||
|
resources: ["endpoints"]
|
||||||
|
verbs: ["get", "watch", "list"]
|
||||||
|
|
||||||
12
zrpc/internal/resolver/kube/deploy/clusterrolebinding.yaml
Normal file
12
zrpc/internal/resolver/kube/deploy/clusterrolebinding.yaml
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
apiVersion: rbac.authorization.k8s.io/v1
|
||||||
|
kind: ClusterRoleBinding
|
||||||
|
metadata:
|
||||||
|
name: endpoints-reader
|
||||||
|
subjects:
|
||||||
|
- kind: ServiceAccount
|
||||||
|
name: endpoints-reader
|
||||||
|
namespace: kevin # the namespace that the ServiceAccount resides in
|
||||||
|
roleRef:
|
||||||
|
kind: ClusterRole
|
||||||
|
name: endpoints-reader
|
||||||
|
apiGroup: rbac.authorization.k8s.io
|
||||||
5
zrpc/internal/resolver/kube/deploy/serviceaccount.yaml
Normal file
5
zrpc/internal/resolver/kube/deploy/serviceaccount.yaml
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
apiVersion: v1
|
||||||
|
kind: ServiceAccount
|
||||||
|
metadata:
|
||||||
|
name: endpoints-reader
|
||||||
|
namespace: kevin # the namespace to create the ServiceAccount
|
||||||
Reference in New Issue
Block a user