From cafd9098d76891c6a9028f5140dcfc284e1bd85d Mon Sep 17 00:00:00 2001 From: John Guo Date: Wed, 22 Dec 2021 22:22:42 +0800 Subject: [PATCH] change errors wrapped by gerror.Wrap with error stack info for all packages --- database/gredis/gredis_adapter.go | 2 +- database/gredis/gredis_adapter_goredis.go | 8 +- .../gredis/gredis_adapter_goredis_conn.go | 66 +++++++++------ database/gredis/gredis_config.go | 2 +- database/gredis/gredis_redis.go | 2 +- database/gredis/gredis_redis_conn.go | 2 +- net/gipv4/gipv4_ip.go | 2 +- net/gtcp/gtcp_conn.go | 82 +++++++++++-------- net/gtcp/gtcp_conn_pkg.go | 10 ++- net/gtcp/gtcp_func.go | 22 +++-- net/gtcp/gtcp_pool.go | 10 +-- net/gtcp/gtcp_pool_pkg.go | 4 +- net/gtcp/gtcp_server.go | 28 +++---- net/gudp/gudp_conn.go | 41 ++++++---- net/gudp/gudp_func.go | 12 ++- net/gudp/gudp_server.go | 18 ++-- os/gcfg/gcfg_adapter_file.go | 12 +-- os/gcfg/gcfg_adapter_file_path.go | 14 ++-- os/gcron/gcron_z_unit_schedule.go | 10 +-- os/genv/genv.go | 20 +++-- os/gfile/gfile.go | 6 +- os/gfile/gfile_home.go | 2 +- os/gfile/gfile_scan.go | 2 +- os/gfile/gfile_search.go | 2 +- os/gproc/gproc_comm.go | 2 +- 25 files changed, 223 insertions(+), 158 deletions(-) diff --git a/database/gredis/gredis_adapter.go b/database/gredis/gredis_adapter.go index 99531e4be..b4598bd72 100644 --- a/database/gredis/gredis_adapter.go +++ b/database/gredis/gredis_adapter.go @@ -24,7 +24,7 @@ type Adapter interface { // Conn is an interface of a connection from universal redis client. type Conn interface { - // Do sends a command to the server and returns the received reply. + // Do send a command to the server and returns the received reply. // It uses json.Marshal for struct/slice/map type values before committing them to redis. Do(ctx context.Context, command string, args ...interface{}) (result *gvar.Var, err error) diff --git a/database/gredis/gredis_adapter_goredis.go b/database/gredis/gredis_adapter_goredis.go index ed5c3feae..027d806f3 100644 --- a/database/gredis/gredis_adapter_goredis.go +++ b/database/gredis/gredis_adapter_goredis.go @@ -11,6 +11,7 @@ import ( "time" "github.com/go-redis/redis/v8" + "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/text/gstr" ) @@ -54,8 +55,11 @@ func NewAdapterGoRedis(config *Config) *AdapterGoRedis { // Close closes the redis connection pool, which will release all connections reserved by this pool. // It is commonly not necessary to call Close manually. -func (r *AdapterGoRedis) Close(ctx context.Context) error { - return r.client.Close() +func (r *AdapterGoRedis) Close(ctx context.Context) (err error) { + if err = r.client.Close(); err != nil { + err = gerror.Wrap(err, `Redis Client Close failed`) + } + return } // Conn retrieves and returns a connection object for continuous operations. diff --git a/database/gredis/gredis_adapter_goredis_conn.go b/database/gredis/gredis_adapter_goredis_conn.go index a4a1bd243..fe0df51b2 100644 --- a/database/gredis/gredis_adapter_goredis_conn.go +++ b/database/gredis/gredis_adapter_goredis_conn.go @@ -10,6 +10,7 @@ import ( "context" "github.com/go-redis/redis/v8" + "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/container/gvar" "github.com/gogf/gf/v2/text/gstr" @@ -21,54 +22,45 @@ type localAdapterGoRedisConn struct { redis *AdapterGoRedis } -// Do sends a command to the server and returns the received reply. +// Do send a command to the server and returns the received reply. // It uses json.Marshal for struct/slice/map type values before committing them to redis. func (c *localAdapterGoRedisConn) Do(ctx context.Context, command string, args ...interface{}) (reply *gvar.Var, err error) { + argStrSlice := gconv.Strings(args) switch gstr.ToLower(command) { case `subscribe`: - c.ps = c.redis.client.Subscribe(ctx, gconv.Strings(args)...) + c.ps = c.redis.client.Subscribe(ctx, argStrSlice...) case `psubscribe`: - c.ps = c.redis.client.PSubscribe(ctx, gconv.Strings(args)...) + c.ps = c.redis.client.PSubscribe(ctx, argStrSlice...) case `unsubscribe`: if c.ps != nil { - err = c.ps.Unsubscribe(ctx, gconv.Strings(args)...) + err = c.ps.Unsubscribe(ctx, argStrSlice...) + if err != nil { + err = gerror.Wrapf(err, `Redis PubSub Unsubscribe failed with arguments "%v"`, argStrSlice) + } } case `punsubscribe`: if c.ps != nil { - err = c.ps.PUnsubscribe(ctx, gconv.Strings(args)...) + err = c.ps.PUnsubscribe(ctx, argStrSlice...) + if err != nil { + err = gerror.Wrapf(err, `Redis PubSub PUnsubscribe failed with arguments "%v"`, argStrSlice) + } } default: arguments := make([]interface{}, len(args)+1) copy(arguments, []interface{}{command}) copy(arguments[1:], args) - reply, err = c.resultToVar( - c.redis.client.Do(ctx, arguments...).Result(), - ) + reply, err = c.resultToVar(c.redis.client.Do(ctx, arguments...).Result()) + if err != nil { + err = gerror.Wrapf(err, `Redis Client Do failed with arguments "%v"`, arguments) + } } - return } -// Receive receives a single reply as gvar.Var from the Redis server. -func (c *localAdapterGoRedisConn) Receive(ctx context.Context) (*gvar.Var, error) { - if c.ps != nil { - return c.resultToVar(c.ps.Receive(ctx)) - } - return nil, nil -} - -// Close closes current PubSub or puts the connection back to connection pool. -func (c *localAdapterGoRedisConn) Close(ctx context.Context) error { - if c.ps != nil { - return c.ps.Close() - } - return nil -} - // resultToVar converts redis operation result to gvar.Var. func (c *localAdapterGoRedisConn) resultToVar(result interface{}, err error) (*gvar.Var, error) { if err == redis.Nil { @@ -98,5 +90,29 @@ func (c *localAdapterGoRedisConn) resultToVar(result interface{}, err error) (*g } } } + return gvar.New(result), err } + +// Receive receives a single reply as gvar.Var from the Redis server. +func (c *localAdapterGoRedisConn) Receive(ctx context.Context) (*gvar.Var, error) { + if c.ps != nil { + v, err := c.resultToVar(c.ps.Receive(ctx)) + if err != nil { + err = gerror.Wrapf(err, `Redis PubSub Receive failed`) + } + return v, err + } + return nil, nil +} + +// Close closes current PubSub or puts the connection back to connection pool. +func (c *localAdapterGoRedisConn) Close(ctx context.Context) (err error) { + if c.ps != nil { + err = c.ps.Close() + if err != nil { + err = gerror.Wrapf(err, `Redis PubSub Close failed`) + } + } + return +} diff --git a/database/gredis/gredis_config.go b/database/gredis/gredis_config.go index 2d94dda84..dbcde08ee 100644 --- a/database/gredis/gredis_config.go +++ b/database/gredis/gredis_config.go @@ -78,7 +78,7 @@ func SetConfigByMap(m map[string]interface{}, name ...string) error { func ConfigFromMap(m map[string]interface{}) (config *Config, err error) { config = &Config{} if err = gconv.Scan(m, config); err != nil { - err = gerror.NewCodef(gcode.CodeInvalidConfiguration, `invalid redis configuration: "%+v"`, m) + err = gerror.NewCodef(gcode.CodeInvalidConfiguration, `invalid redis configuration: %#v`, m) } if config.DialTimeout < 1000 { config.DialTimeout = config.DialTimeout * time.Second diff --git a/database/gredis/gredis_redis.go b/database/gredis/gredis_redis.go index 9ade61f5a..44c66556f 100644 --- a/database/gredis/gredis_redis.go +++ b/database/gredis/gredis_redis.go @@ -56,7 +56,7 @@ func (r *Redis) Conn(ctx context.Context) (*RedisConn, error) { }, nil } -// Do sends a command to the server and returns the received reply. +// Do send a command to the server and returns the received reply. // It uses json.Marshal for struct/slice/map type values before committing them to redis. func (r *Redis) Do(ctx context.Context, command string, args ...interface{}) (*gvar.Var, error) { if r == nil { diff --git a/database/gredis/gredis_redis_conn.go b/database/gredis/gredis_redis_conn.go index 78396c737..773011464 100644 --- a/database/gredis/gredis_redis_conn.go +++ b/database/gredis/gredis_redis_conn.go @@ -22,7 +22,7 @@ type RedisConn struct { redis *Redis } -// Do sends a command to the server and returns the received reply. +// Do send a command to the server and returns the received reply. // It uses json.Marshal for struct/slice/map type values before committing them to redis. func (c *RedisConn) Do(ctx context.Context, command string, args ...interface{}) (reply *gvar.Var, err error) { for k, v := range args { diff --git a/net/gipv4/gipv4_ip.go b/net/gipv4/gipv4_ip.go index 8e270cf6a..646470637 100644 --- a/net/gipv4/gipv4_ip.go +++ b/net/gipv4/gipv4_ip.go @@ -41,7 +41,7 @@ func GetIntranetIp() (ip string, err error) { return "", err } if len(ips) == 0 { - return "", gerror.NewCode(gcode.CodeOperationFailed, "no intranet ip found") + return "", gerror.New("no intranet ip found") } return ips[0], nil } diff --git a/net/gtcp/gtcp_conn.go b/net/gtcp/gtcp_conn.go index dbea3eb96..92eb5a5ce 100644 --- a/net/gtcp/gtcp_conn.go +++ b/net/gtcp/gtcp_conn.go @@ -13,6 +13,8 @@ import ( "io" "net" "time" + + "github.com/gogf/gf/v2/errors/gerror" ) // Conn is the TCP connection object. @@ -79,6 +81,7 @@ func (c *Conn) Send(data []byte, retry ...Retry) error { } // Still failed even after retrying. if len(retry) == 0 || retry[0].Count == 0 { + err = gerror.Wrap(err, `Write data failed`) return err } if len(retry) > 0 { @@ -104,12 +107,13 @@ func (c *Conn) Send(data []byte, retry ...Retry) error { // 3. If length > 0, which means it blocks reading data from connection until length size was received. // It is the most commonly used length value for data receiving. func (c *Conn) Recv(length int, retry ...Retry) ([]byte, error) { - var err error // Reading error. - var size int // Reading size. - var index int // Received size. - var buffer []byte // Buffer object. - var bufferWait bool // Whether buffer reading timeout set. - + var ( + err error // Reading error. + size int // Reading size. + index int // Received size. + buffer []byte // Buffer object. + bufferWait bool // Whether buffer reading timeout set. + ) if length > 0 { buffer = make([]byte, length) } else { @@ -120,6 +124,7 @@ func (c *Conn) Recv(length int, retry ...Retry) ([]byte, error) { if length < 0 && index > 0 { bufferWait = true if err = c.SetReadDeadline(time.Now().Add(c.receiveBufferWait)); err != nil { + err = gerror.Wrap(err, `SetReadDeadline for connection failed`) return nil, err } } @@ -151,6 +156,7 @@ func (c *Conn) Recv(length int, retry ...Retry) ([]byte, error) { // Re-set the timeout when reading data. if bufferWait && isTimeout(err) { if err = c.SetReadDeadline(c.receiveDeadline); err != nil { + err = gerror.Wrap(err, `SetReadDeadline for connection failed`) return nil, err } err = nil @@ -181,9 +187,11 @@ func (c *Conn) Recv(length int, retry ...Retry) ([]byte, error) { // RecvLine reads data from the connection until reads char '\n'. // Note that the returned result does not contain the last char '\n'. func (c *Conn) RecvLine(retry ...Retry) ([]byte, error) { - var err error - var buffer []byte - data := make([]byte, 0) + var ( + err error + buffer []byte + data = make([]byte, 0) + ) for { buffer, err = c.Recv(1, retry...) if len(buffer) > 0 { @@ -201,13 +209,15 @@ func (c *Conn) RecvLine(retry ...Retry) ([]byte, error) { return data, err } -// RecvTil reads data from the connection until reads bytes `til`. +// RecvTill reads data from the connection until reads bytes `til`. // Note that the returned result contains the last bytes `til`. -func (c *Conn) RecvTil(til []byte, retry ...Retry) ([]byte, error) { - var err error - var buffer []byte - data := make([]byte, 0) - length := len(til) +func (c *Conn) RecvTill(til []byte, retry ...Retry) ([]byte, error) { + var ( + err error + buffer []byte + data = make([]byte, 0) + length = len(til) + ) for { buffer, err = c.Recv(1, retry...) if len(buffer) > 0 { @@ -230,17 +240,17 @@ func (c *Conn) RecvTil(til []byte, retry ...Retry) ([]byte, error) { // RecvWithTimeout reads data from the connection with timeout. func (c *Conn) RecvWithTimeout(length int, timeout time.Duration, retry ...Retry) (data []byte, err error) { - if err := c.SetreceiveDeadline(time.Now().Add(timeout)); err != nil { + if err = c.SetReceiveDeadline(time.Now().Add(timeout)); err != nil { return nil, err } - defer c.SetreceiveDeadline(time.Time{}) + defer c.SetReceiveDeadline(time.Time{}) data, err = c.Recv(length, retry...) return } // SendWithTimeout writes data to the connection with timeout. func (c *Conn) SendWithTimeout(data []byte, timeout time.Duration, retry ...Retry) (err error) { - if err := c.SetSendDeadline(time.Now().Add(timeout)); err != nil { + if err = c.SetSendDeadline(time.Now().Add(timeout)); err != nil { return err } defer c.SetSendDeadline(time.Time{}) @@ -266,33 +276,39 @@ func (c *Conn) SendRecvWithTimeout(data []byte, length int, timeout time.Duratio } } -func (c *Conn) SetDeadline(t time.Time) error { - err := c.Conn.SetDeadline(t) - if err == nil { +func (c *Conn) SetDeadline(t time.Time) (err error) { + if err = c.Conn.SetDeadline(t); err == nil { c.receiveDeadline = t c.sendDeadline = t } + if err != nil { + err = gerror.Wrapf(err, `SetDeadline for connection failed with "%s"`, t) + } return err } -func (c *Conn) SetreceiveDeadline(t time.Time) error { - err := c.SetReadDeadline(t) - if err == nil { +func (c *Conn) SetReceiveDeadline(t time.Time) (err error) { + if err = c.SetReadDeadline(t); err == nil { c.receiveDeadline = t } - return err -} - -func (c *Conn) SetSendDeadline(t time.Time) error { - err := c.SetWriteDeadline(t) - if err == nil { - c.sendDeadline = t + if err != nil { + err = gerror.Wrapf(err, `SetReadDeadline for connection failed with "%s"`, t) } return err } -// SetreceiveBufferWait sets the buffer waiting timeout when reading all data from connection. +func (c *Conn) SetSendDeadline(t time.Time) (err error) { + if err = c.SetWriteDeadline(t); err == nil { + c.sendDeadline = t + } + if err != nil { + err = gerror.Wrapf(err, `SetWriteDeadline for connection failed with "%s"`, t) + } + return err +} + +// SetReceiveBufferWait sets the buffer waiting timeout when reading all data from connection. // The waiting duration cannot be too long which might delay receiving data from remote address. -func (c *Conn) SetreceiveBufferWait(bufferWaitDuration time.Duration) { +func (c *Conn) SetReceiveBufferWait(bufferWaitDuration time.Duration) { c.receiveBufferWait = bufferWaitDuration } diff --git a/net/gtcp/gtcp_conn_pkg.go b/net/gtcp/gtcp_conn_pkg.go index c39b7d636..f54ff88ce 100644 --- a/net/gtcp/gtcp_conn_pkg.go +++ b/net/gtcp/gtcp_conn_pkg.go @@ -94,8 +94,10 @@ func (c *Conn) SendRecvPkgWithTimeout(data []byte, timeout time.Duration, option // RecvPkg receives data from connection using simple package protocol. func (c *Conn) RecvPkg(option ...PkgOption) (result []byte, err error) { - var buffer []byte - var length int + var ( + buffer []byte + length int + ) pkgOption, err := getPkgOption(option...) if err != nil { return nil, err @@ -131,10 +133,10 @@ func (c *Conn) RecvPkg(option ...PkgOption) (result []byte, err error) { // RecvPkgWithTimeout reads data from connection with timeout using simple package protocol. func (c *Conn) RecvPkgWithTimeout(timeout time.Duration, option ...PkgOption) (data []byte, err error) { - if err := c.SetreceiveDeadline(time.Now().Add(timeout)); err != nil { + if err := c.SetReceiveDeadline(time.Now().Add(timeout)); err != nil { return nil, err } - defer c.SetreceiveDeadline(time.Time{}) + defer c.SetReceiveDeadline(time.Time{}) data, err = c.RecvPkg(option...) return } diff --git a/net/gtcp/gtcp_func.go b/net/gtcp/gtcp_func.go index 5520b6aec..69fffbb63 100644 --- a/net/gtcp/gtcp_func.go +++ b/net/gtcp/gtcp_func.go @@ -12,6 +12,7 @@ import ( "net" "time" + "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/os/gfile" ) @@ -28,24 +29,32 @@ type Retry struct { // NewNetConn creates and returns a net.Conn with given address like "127.0.0.1:80". // The optional parameter `timeout` specifies the timeout for dialing connection. -func NewNetConn(addr string, timeout ...time.Duration) (net.Conn, error) { - d := defaultConnTimeout +func NewNetConn(address string, timeout ...time.Duration) (net.Conn, error) { + duration := defaultConnTimeout if len(timeout) > 0 { - d = timeout[0] + duration = timeout[0] } - return net.DialTimeout("tcp", addr, d) + conn, err := net.DialTimeout("tcp", address, duration) + if err != nil { + err = gerror.Wrapf(err, `net.DialTimeout failed with address "%s", timeout "%s"`, address, duration) + } + return conn, err } // NewNetConnTLS creates and returns a TLS net.Conn with given address like "127.0.0.1:80". // The optional parameter `timeout` specifies the timeout for dialing connection. -func NewNetConnTLS(addr string, tlsConfig *tls.Config, timeout ...time.Duration) (net.Conn, error) { +func NewNetConnTLS(address string, tlsConfig *tls.Config, timeout ...time.Duration) (net.Conn, error) { dialer := &net.Dialer{ Timeout: defaultConnTimeout, } if len(timeout) > 0 { dialer.Timeout = timeout[0] } - return tls.DialWithDialer(dialer, "tcp", addr, tlsConfig) + conn, err := tls.DialWithDialer(dialer, "tcp", address, tlsConfig) + if err != nil { + err = gerror.Wrapf(err, `tls.DialWithDialer failed with address "%s"`, address) + } + return conn, err } // NewNetConnKeyCrt creates and returns a TLS net.Conn with given TLS certificate and key files @@ -129,6 +138,7 @@ func LoadKeyCrt(crtFile, keyFile string) (*tls.Config, error) { } crt, err := tls.LoadX509KeyPair(crtPath, keyPath) if err != nil { + err = gerror.Wrapf(err, `tls.LoadX509KeyPair failed for certFile "%s" and keyFile "%s"`, crtPath, keyPath) return nil, err } tlsConfig := &tls.Config{} diff --git a/net/gtcp/gtcp_pool.go b/net/gtcp/gtcp_pool.go index c65027168..f905b852b 100644 --- a/net/gtcp/gtcp_pool.go +++ b/net/gtcp/gtcp_pool.go @@ -111,10 +111,10 @@ func (c *PoolConn) RecvLine(retry ...Retry) ([]byte, error) { return data, err } -// RecvTil reads data from the connection until reads bytes `til`. +// RecvTill reads data from the connection until reads bytes `til`. // Note that the returned result contains the last bytes `til`. -func (c *PoolConn) RecvTil(til []byte, retry ...Retry) ([]byte, error) { - data, err := c.Conn.RecvTil(til, retry...) +func (c *PoolConn) RecvTill(til []byte, retry ...Retry) ([]byte, error) { + data, err := c.Conn.RecvTill(til, retry...) if err != nil { c.status = connStatusError } else { @@ -125,10 +125,10 @@ func (c *PoolConn) RecvTil(til []byte, retry ...Retry) ([]byte, error) { // RecvWithTimeout reads data from the connection with timeout. func (c *PoolConn) RecvWithTimeout(length int, timeout time.Duration, retry ...Retry) (data []byte, err error) { - if err := c.SetreceiveDeadline(time.Now().Add(timeout)); err != nil { + if err := c.SetReceiveDeadline(time.Now().Add(timeout)); err != nil { return nil, err } - defer c.SetreceiveDeadline(time.Time{}) + defer c.SetReceiveDeadline(time.Time{}) data, err = c.Recv(length, retry...) return } diff --git a/net/gtcp/gtcp_pool_pkg.go b/net/gtcp/gtcp_pool_pkg.go index 20b328756..1e1eb2f64 100644 --- a/net/gtcp/gtcp_pool_pkg.go +++ b/net/gtcp/gtcp_pool_pkg.go @@ -43,10 +43,10 @@ func (c *PoolConn) RecvPkg(option ...PkgOption) ([]byte, error) { // RecvPkgWithTimeout reads data from connection with timeout using simple package protocol. func (c *PoolConn) RecvPkgWithTimeout(timeout time.Duration, option ...PkgOption) (data []byte, err error) { - if err := c.SetreceiveDeadline(time.Now().Add(timeout)); err != nil { + if err := c.SetReceiveDeadline(time.Now().Add(timeout)); err != nil { return nil, err } - defer c.SetreceiveDeadline(time.Time{}) + defer c.SetReceiveDeadline(time.Time{}) data, err = c.RecvPkg(option...) return } diff --git a/net/gtcp/gtcp_server.go b/net/gtcp/gtcp_server.go index 33b686dbd..01f1920b3 100644 --- a/net/gtcp/gtcp_server.go +++ b/net/gtcp/gtcp_server.go @@ -7,7 +7,6 @@ package gtcp import ( - "context" "crypto/tls" "net" "sync" @@ -16,7 +15,6 @@ import ( "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/container/gmap" - "github.com/gogf/gf/v2/os/glog" "github.com/gogf/gf/v2/util/gconv" ) @@ -73,12 +71,12 @@ func NewServerTLS(address string, tlsConfig *tls.Config, handler func(*Conn), na // NewServerKeyCrt creates and returns a new TCP server with TLS support. // The parameter `name` is optional, which is used to specify the instance name of the server. -func NewServerKeyCrt(address, crtFile, keyFile string, handler func(*Conn), name ...string) *Server { +func NewServerKeyCrt(address, crtFile, keyFile string, handler func(*Conn), name ...string) (*Server, error) { s := NewServer(address, handler, name...) if err := s.SetTLSKeyCrt(crtFile, keyFile); err != nil { - glog.Error(context.TODO(), err) + return nil, err } - return s + return s, nil } // SetAddress sets the listening address for server. @@ -118,12 +116,8 @@ func (s *Server) Close() error { // Run starts running the TCP Server. func (s *Server) Run() (err error) { - var ( - ctx = context.TODO() - ) if s.handler == nil { err = gerror.NewCode(gcode.CodeMissingConfiguration, "start running failed: socket handler not defined") - glog.Error(ctx, err) return } if s.tlsConfig != nil { @@ -132,27 +126,29 @@ func (s *Server) Run() (err error) { s.listen, err = tls.Listen("tcp", s.address, s.tlsConfig) s.mu.Unlock() if err != nil { - glog.Error(ctx, err) + err = gerror.Wrapf(err, `tls.Listen failed for address "%s"`, s.address) return } } else { // Normal Server - addr, err := net.ResolveTCPAddr("tcp", s.address) - if err != nil { - glog.Error(ctx, err) + var tcpAddr *net.TCPAddr + if tcpAddr, err = net.ResolveTCPAddr("tcp", s.address); err != nil { + err = gerror.Wrapf(err, `net.ResolveTCPAddr failed for address "%s"`, s.address) return err } s.mu.Lock() - s.listen, err = net.ListenTCP("tcp", addr) + s.listen, err = net.ListenTCP("tcp", tcpAddr) s.mu.Unlock() if err != nil { - glog.Error(ctx, err) + err = gerror.Wrapf(err, `net.ListenTCP failed for address "%s"`, s.address) return err } } // Listening loop. for { - if conn, err := s.listen.Accept(); err != nil { + var conn net.Conn + if conn, err = s.listen.Accept(); err != nil { + err = gerror.Wrapf(err, `Listener.Accept failed`) return err } else if conn != nil { go s.handler(NewConnByNetConn(conn)) diff --git a/net/gudp/gudp_conn.go b/net/gudp/gudp_conn.go index a1fc1058e..f9683b8dc 100644 --- a/net/gudp/gudp_conn.go +++ b/net/gudp/gudp_conn.go @@ -10,6 +10,8 @@ import ( "io" "net" "time" + + "github.com/gogf/gf/v2/errors/gerror" ) // Conn handles the UDP connection. @@ -67,6 +69,7 @@ func (c *Conn) Send(data []byte, retry ...Retry) (err error) { } // Still failed even after retrying. if len(retry) == 0 || retry[0].Count == 0 { + err = gerror.Wrap(err, `Write data failed`) return err } if len(retry) > 0 { @@ -90,10 +93,12 @@ func (c *Conn) Send(data []byte, retry ...Retry) (err error) { // buffer size is big enough. VERY NOTE that we should receive the complete package in once // or else the leftover package data would be dropped. func (c *Conn) Recv(buffer int, retry ...Retry) ([]byte, error) { - var err error // Reading error. - var size int // Reading size. - var data []byte // Buffer object. - var remoteAddr *net.UDPAddr // Current remote address for reading. + var ( + err error // Reading error + size int // Reading size + data []byte // Buffer object + remoteAddr *net.UDPAddr // Current remote address for reading + ) if buffer > 0 { data = make([]byte, buffer) } else { @@ -121,6 +126,7 @@ func (c *Conn) Recv(buffer int, retry ...Retry) ([]byte, error) { time.Sleep(retry[0].Interval) continue } + err = gerror.Wrap(err, `ReadFromUDP failed`) break } break @@ -139,7 +145,7 @@ func (c *Conn) SendRecv(data []byte, receive int, retry ...Retry) ([]byte, error // RecvWithTimeout reads data from remote address with timeout. func (c *Conn) RecvWithTimeout(length int, timeout time.Duration, retry ...Retry) (data []byte, err error) { - if err := c.SetRecvDeadline(time.Now().Add(timeout)); err != nil { + if err = c.SetRecvDeadline(time.Now().Add(timeout)); err != nil { return nil, err } defer c.SetRecvDeadline(time.Time{}) @@ -149,7 +155,7 @@ func (c *Conn) RecvWithTimeout(length int, timeout time.Duration, retry ...Retry // SendWithTimeout writes data to connection with timeout. func (c *Conn) SendWithTimeout(data []byte, timeout time.Duration, retry ...Retry) (err error) { - if err := c.SetSendDeadline(time.Now().Add(timeout)); err != nil { + if err = c.SetSendDeadline(time.Now().Add(timeout)); err != nil { return err } defer c.SetSendDeadline(time.Time{}) @@ -166,27 +172,30 @@ func (c *Conn) SendRecvWithTimeout(data []byte, receive int, timeout time.Durati } } -func (c *Conn) SetDeadline(t time.Time) error { - err := c.UDPConn.SetDeadline(t) - if err == nil { +func (c *Conn) SetDeadline(t time.Time) (err error) { + if err = c.UDPConn.SetDeadline(t); err == nil { c.receiveDeadline = t c.sendDeadline = t + } else { + err = gerror.Wrapf(err, `SetDeadline for connection failed with "%s"`, t) } return err } -func (c *Conn) SetRecvDeadline(t time.Time) error { - err := c.SetReadDeadline(t) - if err == nil { +func (c *Conn) SetRecvDeadline(t time.Time) (err error) { + if err = c.SetReadDeadline(t); err == nil { c.receiveDeadline = t + } else { + err = gerror.Wrapf(err, `SetReadDeadline for connection failed with "%s"`, t) } return err } -func (c *Conn) SetSendDeadline(t time.Time) error { - err := c.SetWriteDeadline(t) - if err == nil { +func (c *Conn) SetSendDeadline(t time.Time) (err error) { + if err = c.SetWriteDeadline(t); err == nil { c.sendDeadline = t + } else { + err = gerror.Wrapf(err, `SetWriteDeadline for connection failed with "%s"`, t) } return err } @@ -198,7 +207,7 @@ func (c *Conn) SetRecvBufferWait(d time.Duration) { } // RemoteAddr returns the remote address of current UDP connection. -// Note that it cannot use c.conn.RemoteAddr() as it's nil. +// Note that it cannot use c.conn.RemoteAddr() as it is nil. func (c *Conn) RemoteAddr() net.Addr { //return c.conn.RemoteAddr() return c.remoteAddr diff --git a/net/gudp/gudp_func.go b/net/gudp/gudp_func.go index 74072aefa..2ce42735d 100644 --- a/net/gudp/gudp_func.go +++ b/net/gudp/gudp_func.go @@ -8,24 +8,32 @@ package gudp import ( "net" + + "github.com/gogf/gf/v2/errors/gerror" ) // NewNetConn creates and returns a *net.UDPConn with given addresses. func NewNetConn(remoteAddress string, localAddress ...string) (*net.UDPConn, error) { - var err error - var remoteAddr, localAddr *net.UDPAddr + var ( + err error + remoteAddr *net.UDPAddr + localAddr *net.UDPAddr + ) remoteAddr, err = net.ResolveUDPAddr("udp", remoteAddress) if err != nil { + err = gerror.Wrapf(err, `net.ResolveUDPAddr failed for address "%s"`, remoteAddress) return nil, err } if len(localAddress) > 0 { localAddr, err = net.ResolveUDPAddr("udp", localAddress[0]) if err != nil { + err = gerror.Wrapf(err, `net.ResolveUDPAddr failed for address "%s"`, localAddress[0]) return nil, err } } conn, err := net.DialUDP("udp", localAddr, remoteAddr) if err != nil { + err = gerror.Wrapf(err, `net.DialUDP failed for local "%s", remote "%s"`, localAddr.String(), remoteAddr.String()) return nil, err } return conn, nil diff --git a/net/gudp/gudp_server.go b/net/gudp/gudp_server.go index fa9c0d43f..5bfd5ab5d 100644 --- a/net/gudp/gudp_server.go +++ b/net/gudp/gudp_server.go @@ -7,14 +7,12 @@ package gudp import ( - "context" "net" "github.com/gogf/gf/v2/errors/gcode" "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/container/gmap" - "github.com/gogf/gf/v2/os/glog" "github.com/gogf/gf/v2/util/gconv" ) @@ -74,28 +72,28 @@ func (s *Server) SetHandler(handler func(*Conn)) { // Close closes the connection. // It will make server shutdowns immediately. -func (s *Server) Close() error { - return s.conn.Close() +func (s *Server) Close() (err error) { + err = s.conn.Close() + if err != nil { + err = gerror.Wrap(err, "connection failed") + } + return } // Run starts listening UDP connection. func (s *Server) Run() error { - var ( - ctx = context.TODO() - ) if s.handler == nil { err := gerror.NewCode(gcode.CodeMissingConfiguration, "start running failed: socket handler not defined") - glog.Error(ctx, err) return err } addr, err := net.ResolveUDPAddr("udp", s.address) if err != nil { - glog.Error(ctx, err) + err = gerror.Wrapf(err, `net.ResolveUDPAddr failed for address "%s"`, s.address) return err } conn, err := net.ListenUDP("udp", addr) if err != nil { - glog.Error(ctx, err) + err = gerror.Wrapf(err, `net.ListenUDP failed for address "%s"`, s.address) return err } s.conn = NewConnByNetConn(conn) diff --git a/os/gcfg/gcfg_adapter_file.go b/os/gcfg/gcfg_adapter_file.go index f3a7115d7..b36814cd0 100644 --- a/os/gcfg/gcfg_adapter_file.go +++ b/os/gcfg/gcfg_adapter_file.go @@ -65,7 +65,7 @@ func NewAdapterFile(file ...string) (*AdapterFile, error) { name = customFile } } - c := &AdapterFile{ + config := &AdapterFile{ defaultName: name, searchPaths: garray.NewStrArray(true), jsonMap: gmap.NewStrAnyMap(true), @@ -73,7 +73,7 @@ func NewAdapterFile(file ...string) (*AdapterFile, error) { // Customized dir path from env/cmd. if customPath := command.GetOptWithEnv(commandEnvKeyForPath); customPath != "" { if gfile.Exists(customPath) { - if err = c.SetPath(customPath); err != nil { + if err = config.SetPath(customPath); err != nil { return nil, err } } else { @@ -86,25 +86,25 @@ func NewAdapterFile(file ...string) (*AdapterFile, error) { // ================================================================================ // Dir path of working dir. - if err := c.AddPath(gfile.Pwd()); err != nil { + if err = config.AddPath(gfile.Pwd()); err != nil { intlog.Error(context.TODO(), err) } // Dir path of main package. if mainPath := gfile.MainPkgPath(); mainPath != "" && gfile.Exists(mainPath) { - if err := c.AddPath(mainPath); err != nil { + if err = config.AddPath(mainPath); err != nil { intlog.Error(context.TODO(), err) } } // Dir path of binary. if selfPath := gfile.SelfDir(); selfPath != "" && gfile.Exists(selfPath) { - if err := c.AddPath(selfPath); err != nil { + if err = config.AddPath(selfPath); err != nil { intlog.Error(context.TODO(), err) } } } - return c, nil + return config, nil } // SetViolenceCheck sets whether to perform hierarchical conflict checking. diff --git a/os/gcfg/gcfg_adapter_file_path.go b/os/gcfg/gcfg_adapter_file_path.go index eb27c107b..c94d34644 100644 --- a/os/gcfg/gcfg_adapter_file_path.go +++ b/os/gcfg/gcfg_adapter_file_path.go @@ -38,8 +38,8 @@ func (c *AdapterFile) SetPath(path string) (err error) { // Relative path. c.searchPaths.RLockFunc(func(array []string) { for _, v := range array { - if path, _ := gspath.Search(v, path); path != "" { - realPath = path + if searchedPath, _ := gspath.Search(v, path); searchedPath != "" { + realPath = searchedPath break } } @@ -62,7 +62,7 @@ func (c *AdapterFile) SetPath(path string) (err error) { } else { buffer.WriteString(fmt.Sprintf(`SetPath failed: path "%s" does not exist`, path)) } - return gerror.NewCode(gcode.CodeOperationFailed, buffer.String()) + return gerror.New(buffer.String()) } // Should be a directory. if !isDir { @@ -101,8 +101,8 @@ func (c *AdapterFile) AddPath(path string) (err error) { // Relative path. c.searchPaths.RLockFunc(func(array []string) { for _, v := range array { - if path, _ := gspath.Search(v, path); path != "" { - realPath = path + if searchedPath, _ := gspath.Search(v, path); searchedPath != "" { + realPath = searchedPath break } } @@ -124,7 +124,7 @@ func (c *AdapterFile) AddPath(path string) (err error) { } else { buffer.WriteString(fmt.Sprintf(`AddPath failed: path "%s" does not exist`, path)) } - return gerror.NewCode(gcode.CodeOperationFailed, buffer.String()) + return gerror.New(buffer.String()) } if !isDir { return gerror.NewCodef(gcode.CodeInvalidParameter, `AddPath failed: path "%s" should be directory type`, path) @@ -214,7 +214,7 @@ func (c *AdapterFile) GetFilePath(fileName ...string) (path string, err error) { } else { buffer.WriteString(fmt.Sprintf(`cannot find config file "%s" with no path configured`, usedFileName)) } - err = gerror.NewCode(gcode.CodeOperationFailed, buffer.String()) + err = gerror.New(buffer.String()) } return } diff --git a/os/gcron/gcron_z_unit_schedule.go b/os/gcron/gcron_z_unit_schedule.go index 7aae47b2e..9c5432849 100644 --- a/os/gcron/gcron_z_unit_schedule.go +++ b/os/gcron/gcron_z_unit_schedule.go @@ -157,14 +157,14 @@ func parsePatternItem(item string, min int, max int, allowQuestionMark bool) (ma } } else { // Like: MON,FRI - for _, item := range strings.Split(item, ",") { + for _, itemElem := range strings.Split(item, ",") { var ( interval = 1 - intervalArray = strings.Split(item, "/") + intervalArray = strings.Split(itemElem, "/") ) if len(intervalArray) == 2 { if number, err := strconv.Atoi(intervalArray[1]); err != nil { - return nil, gerror.NewCodef(gcode.CodeInvalidParameter, `invalid pattern item: "%s"`, item) + return nil, gerror.NewCodef(gcode.CodeInvalidParameter, `invalid pattern item: "%s"`, itemElem) } else { interval = number } @@ -186,7 +186,7 @@ func parsePatternItem(item string, min int, max int, allowQuestionMark bool) (ma // Eg: */5 if rangeArray[0] != "*" { if number, err := parsePatternItemValue(rangeArray[0], itemType); err != nil { - return nil, gerror.NewCodef(gcode.CodeInvalidParameter, `invalid pattern item: "%s"`, item) + return nil, gerror.NewCodef(gcode.CodeInvalidParameter, `invalid pattern item: "%s"`, itemElem) } else { rangeMin = number if len(intervalArray) == 1 { @@ -196,7 +196,7 @@ func parsePatternItem(item string, min int, max int, allowQuestionMark bool) (ma } if len(rangeArray) == 2 { if number, err := parsePatternItemValue(rangeArray[1], itemType); err != nil { - return nil, gerror.NewCodef(gcode.CodeInvalidParameter, `invalid pattern item: "%s"`, item) + return nil, gerror.NewCodef(gcode.CodeInvalidParameter, `invalid pattern item: "%s"`, itemElem) } else { rangeMax = number } diff --git a/os/genv/genv.go b/os/genv/genv.go index 573a714c9..f687f3220 100644 --- a/os/genv/genv.go +++ b/os/genv/genv.go @@ -12,6 +12,7 @@ import ( "strings" "github.com/gogf/gf/v2/container/gvar" + "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/internal/command" "github.com/gogf/gf/v2/internal/utils" ) @@ -49,14 +50,18 @@ func Get(key string, def ...interface{}) *gvar.Var { // Set sets the value of the environment variable named by the `key`. // It returns an error, if any. -func Set(key, value string) error { - return os.Setenv(key, value) +func Set(key, value string) (err error) { + err = os.Setenv(key, value) + if err != nil { + err = gerror.Wrapf(err, `set environment key-value failed with key "%s", value "%s"`, key, value) + } + return } // SetMap sets the environment variables using map. -func SetMap(m map[string]string) error { +func SetMap(m map[string]string) (err error) { for k, v := range m { - if err := os.Setenv(k, v); err != nil { + if err = Set(k, v); err != nil { return err } } @@ -70,11 +75,10 @@ func Contains(key string) bool { } // Remove deletes one or more environment variables. -func Remove(key ...string) error { - var err error +func Remove(key ...string) (err error) { for _, v := range key { - err = os.Unsetenv(v) - if err != nil { + if err = os.Unsetenv(v); err != nil { + err = gerror.Wrapf(err, `delete environment key failed with key "%s"`, v) return err } } diff --git a/os/gfile/gfile.go b/os/gfile/gfile.go index d635108c2..e8855b896 100644 --- a/os/gfile/gfile.go +++ b/os/gfile/gfile.go @@ -15,6 +15,7 @@ import ( "time" "github.com/gogf/gf/v2/container/gtype" + "github.com/gogf/gf/v2/errors/gerror" "github.com/gogf/gf/v2/text/gstr" "github.com/gogf/gf/v2/util/gconv" ) @@ -60,8 +61,9 @@ func init() { // Mkdir creates directories recursively with given `path`. // The parameter `path` is suggested to be an absolute path instead of relative one. -func Mkdir(path string) error { - if err := os.MkdirAll(path, os.ModePerm); err != nil { +func Mkdir(path string) (err error) { + if err = os.MkdirAll(path, os.ModePerm); err != nil { + err = gerror.Wrapf(err, `os.MkdirAll failed for path "%s"`, path) return err } return nil diff --git a/os/gfile/gfile_home.go b/os/gfile/gfile_home.go index 817d6aaa9..134c70d9a 100644 --- a/os/gfile/gfile_home.go +++ b/os/gfile/gfile_home.go @@ -75,7 +75,7 @@ func homeWindows() (string, error) { home = os.Getenv("USERPROFILE") } if home == "" { - return "", gerror.NewCode(gcode.CodeOperationFailed, "HOMEDRIVE, HOMEPATH, and USERPROFILE are blank") + return "", gerror.New("HOMEDRIVE, HOMEPATH, and USERPROFILE are blank") } return home, nil diff --git a/os/gfile/gfile_scan.go b/os/gfile/gfile_scan.go index d5b02a370..a525dca4a 100644 --- a/os/gfile/gfile_scan.go +++ b/os/gfile/gfile_scan.go @@ -139,7 +139,7 @@ func ScanDirFileFunc(path string, pattern string, recursive bool, handler func(p // string, or else it appends the sub-file path to result slice. func doScanDir(depth int, path string, pattern string, recursive bool, handler func(path string) string) ([]string, error) { if depth >= maxScanDepth { - return nil, gerror.NewCodef(gcode.CodeOperationFailed, "directory scanning exceeds max recursive depth: %d", maxScanDepth) + return nil, gerror.Newf("directory scanning exceeds max recursive depth: %d", maxScanDepth) } list := ([]string)(nil) file, err := os.Open(path) diff --git a/os/gfile/gfile_search.go b/os/gfile/gfile_search.go index e344aa896..3715f7d4a 100644 --- a/os/gfile/gfile_search.go +++ b/os/gfile/gfile_search.go @@ -53,7 +53,7 @@ func Search(name string, prioritySearchPaths ...string) (realPath string, err er buffer.WriteString(fmt.Sprintf("\n%d. %s", k+1, v)) } }) - err = gerror.NewCode(gcode.CodeOperationFailed, buffer.String()) + err = gerror.New(buffer.String()) } return } diff --git a/os/gproc/gproc_comm.go b/os/gproc/gproc_comm.go index a1ed5db1c..e569c076b 100644 --- a/os/gproc/gproc_comm.go +++ b/os/gproc/gproc_comm.go @@ -89,7 +89,7 @@ func getConnByPid(pid int) (*gtcp.PoolConn, error) { return nil, err } } - return nil, gerror.NewCodef(gcode.CodeOperationFailed, "could not find port for pid: %d", pid) + return nil, gerror.Newf("could not find port for pid: %d", pid) } // getPortByPid returns the listening port for specified pid.