您好,登錄后才能下訂單哦!
默認的錯誤處理是 errors.New("錯誤信息"),這個信息通過 error 類型的返回值進行返回。
舉個簡單的例子:
func hello(name string) (str string, err error) { if name == "" { err = errors.New("name 不能為空") return } str = fmt.Sprintf("hello: %s", name) return }
當調用這個方法時:
var name = "" str, err := hello(name) if err != nil { fmt.Println(err.Error()) return }
這個默認的錯誤處理,只是得到了一個錯誤信息的字符串。
自定義錯誤處理
咱們定義一個 alarm.go,用于處理告警。
廢話不多說,直接看代碼。
package alarm import ( "encoding/json" "fmt" "ginDemo/common/function" "path/filepath" "runtime" "strings" ) type errorString struct { s string } type errorInfo struct { Time string `json:"time"` Alarm string `json:"alarm"` Message string `json:"message"` Filename string `json:"filename"` Line int `json:"line"` Funcname string `json:"funcname"` } func (e *errorString) Error() string { return e.s } func New (text string) error { alarm("INFO", text) return &errorString{text} } // 發郵件 func Email (text string) error { alarm("EMAIL", text) return &errorString{text} } // 發短信 func Sms (text string) error { alarm("SMS", text) return &errorString{text} } // 發微信 func WeChat (text string) error { alarm("WX", text) return &errorString{text} } // 告警方法 func alarm(level string, str string) { // 當前時間 currentTime := function.GetTimeStr() // 定義 文件名、行號、方法名 fileName, line, functionName := "?", 0 , "?" pc, fileName, line, ok := runtime.Caller(2) if ok { functionName = runtime.FuncForPC(pc).Name() functionName = filepath.Ext(functionName) functionName = strings.TrimPrefix(functionName, ".") } var msg = errorInfo { Time : currentTime, Alarm : level, Message : str, Filename : fileName, Line : line, Funcname : functionName, } jsons, errs := json.Marshal(msg) if errs != nil { fmt.Println("json marshal error:", errs) } errorJsonInfo := string(jsons) fmt.Println(errorJsonInfo) if level == "EMAIL" { // 執行發郵件 } else if level == "SMS" { // 執行發短信 } else if level == "WX" { // 執行發微信 } else if level == "INFO" { // 執行記日志 } }
看下如何調用:
package v1 import ( "fmt" "ginDemo/common/alarm" "ginDemo/entity" "github.com/gin-gonic/gin" "net/http" ) func AddProduct(c *gin.Context) { // 獲取 Get 參數 name := c.Query("name") var res = entity.Result{} str, err := hello(name) if err != nil { res.SetCode(entity.CODE_ERROR) res.SetMessage(err.Error()) c.JSON(http.StatusOK, res) c.Abort() return } res.SetCode(entity.CODE_SUCCESS) res.SetMessage(str) c.JSON(http.StatusOK, res) } func hello(name string) (str string, err error) { if name == "" { err = alarm.WeChat("name 不能為空") return } str = fmt.Sprintf("hello: %s", name) return }
訪問:http://localhost:8080/v1/product/add?name=a
{ "code": 1, "msg": "hello: a", "data": null }
未拋出錯誤,不會輸出信息。
訪問:http://localhost:8080/v1/product/add
{ "code": -1, "msg": "name 不能為空", "data": null }
拋出了錯誤,輸出信息如下:
{"time":"2019-07-23 22:19:17","alarm":"WX","message":"name 不能為空","filename":"絕對路徑/ginDemo/router/v1/product.go","line":33,"funcname":"hello"}
panic 和 recover
當程序不能繼續運行的時候,才應該使用 panic 拋出錯誤。
當程序發生 panic 后,在 defer(延遲函數) 內部可以調用 recover 進行控制,不過有個前提條件,只有在相同的 Go 協程中才可以。
有意拋出的 panic:
package main import ( "fmt" ) func main() { fmt.Println("-- 1 --") defer func() { if r := recover(); r != nil { fmt.Printf("panic: %s\n", r) } fmt.Println("-- 2 --") }() panic("i am panic") }
輸出:
-- 1 -- panic: i am panic -- 2 --
無意拋出的 panic:
package main import ( "fmt" ) func main() { fmt.Println("-- 1 --") defer func() { if r := recover(); r != nil { fmt.Printf("panic: %s\n", r) } fmt.Println("-- 2 --") }() var slice = [] int {1, 2, 3, 4, 5} slice[6] = 6 }
輸出:
-- 1 -- panic: runtime error: index out of range -- 2 --
以上就是golang gin框架錯誤處理的詳細內容,更多請關注億速云其它相關文章!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。