Error异常

Error的定义

  • Golang Error VS 其它语言的Error

在其它开发语言中,异常对于程序是致命的。而对于golang异常则是在程序出现不期望的状态时的特殊返回值。
_

  • error是golang内置的类型,它的零值是 nil
  • error实际是一种接口类型,任何实现该接口的结构体都是error的子类型
  1. type error interface {
  2. Error() string
  3. }

Error的使用

  • 通过实现golang内置error接口的结构体实现Error
  1. package main
  2. import "fmt"
  3. type MyError struct {}
  4. func (myError *MyError)Error() string{
  5. return "Somethings happen"
  6. }
  7. func main() {
  8. myError := &MyError{}
  9. fmt.Println(myError)
  10. }
  • 通过使用内置模块 errors 中的 New 函数使用Error
  1. package main
  2. import (
  3. "fmt"
  4. "errors"
  5. )
  6. func main() {
  7. myError := errors.New("Somethings happen")
  8. fmt.Println(myError)
  9. }
  • 通过使用内置模块 fmt 中的 Errorf 函数使用Error
  1. package main
  2. import "fmt"
  3. type MyError struct{}
  4. func (myError *MyError) Error() string {
  5. return "Some error happens"
  6. }
  7. func main() {
  8. myError := &MyError{}
  9. fmt.Println(myError)
  10. }

error 接口内嵌在结构体

  1. package main
  2. import "fmt"
  3. type UnauthorizedError struct {
  4. UserId int
  5. error // error 内嵌在结构体中
  6. }
  7. func validateUser(userID int) error {
  8. err := fmt.Errorf("Session invalid for user %d", userID)
  9. return &UnauthorizedError{userID, err}
  10. }
  11. func main() {
  12. err := validateUser(1)
  13. if err != nil {
  14. fmt.Println(err)
  15. } else {
  16. fmt.Println("Succesfully")
  17. }
  18. }

error 内嵌到接口

  1. package main
  2. import "fmt"
  3. // UserSessionState ...
  4. type UserSessionState interface {
  5. error // error 内嵌到接口中
  6. isLoggedIn() bool
  7. getSessionId() int
  8. }
  9. // UnauthorizedError ...
  10. type UnauthorizedError struct{
  11. UserID int
  12. SessionID int
  13. }
  14. func (err *UnauthorizedError)isLoggedIn() bool {
  15. return err.SessionID != 0
  16. }
  17. func (err *UnauthorizedError)getSessionId() int{
  18. return err.SessionID
  19. }
  20. func (err *UnauthorizedError)Error() string{
  21. return fmt.Sprintf("User with id %v cannot perform current ation", err.SessionID)
  22. }
  23. func validateUser(userID int) error {
  24. return &UnauthorizedError{userID, 12312}
  25. }
  26. func main() {
  27. err := validateUser(123)
  28. if err != nil {
  29. fmt.Println(err)
  30. if errVal, ok := err.(UserSessionState); ok {
  31. ...
  32. }
  33. } else {
  34. fmt.Println("User is allowed to perform this action")
  35. }
  36. }

为error添加track信息

  1. package main
  2. import (
  3. "fmt"
  4. "github.com/pkg/errors"
  5. )
  6. func main() {
  7. originError := errors.New("123")
  8. fmt.Println(originError)
  9. // Wrap error message
  10. err := errors.Wrap(originError, "Context info use wrap func")
  11. fmt.Printf("normal => %v\n\n", err)
  12. // print with stack trace
  13. fmt.Printf("normal with stack trace %+v\n\n", err)
  14. // remove wrap
  15. originErrorUnWrap := errors.Cause(err)
  16. fmt.Println(originErrorUnWrap)
  17. }