exception

package
v0.0.0-...-8e0b234 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 28, 2024 License: OSL-3.0 Imports: 3 Imported by: 0

README

业务异常

为什么需要业务异常

判断 令牌过期

业务异常的使用方式:

err := Biz_Call()
if err == TokenExpired {

}

字符串比对, 可能造成误杀

access token expired %f minutes

hasPrefix("access token expired")

设计一套业务专用的业务异常, 通常设计为异常码(Error Code):

// err.ErrorCode == xxxx
if exception.IsTokenExpired(err) {

}

怎么设计业务异常

本书需要兼容Error的场景:

func XXX() error

go 里面的Error是个接口

// The error built-in interface type is the conventional interface for
// representing an error condition, with the nil value representing no error.
type error interface {
	Error() string
}

fmt包里面提供的Error实现

type wrapError struct {
	msg string
	err error
}

func (e *wrapError) Error() string {
	return e.msg
}

func (e *wrapError) Unwrap() error {
	return e.err
}

type wrapErrors struct {
	msg  string
	errs []error
}

func (e *wrapErrors) Error() string {
	return e.msg
}

func (e *wrapErrors) Unwrap() []error {
	return e.errs
}

如何定义自定义异常: APIException

func NewAPIException(code int, msg string) *APIException {
	return &APIException{
		code: code,
		msg:  msg,
	}
}

// error的自定义实现
type APIException struct {
	code int
	msg  string
}

func (e *APIException) Error() string {
	return e.msg
}

func (e *APIException) Code() int {
	return e.code
}

定义业务异常

  1. 定义 TokenExired 5000
// 这个模块定义的业务异常
// token expired %f minitues
// 约定俗成:  ErrXXXXX 来进行自定义异常定义, 方便快速在包里搜索
var (
	ErrAccessTokenExpired  = exception.NewAPIException(5000, "access token expired")
	ErrRefreshTokenExpired = exception.NewAPIException(5001, "refresh token expired")
)
  1. 使用自定义异常
if aDelta > 0 {
    return ErrAccessTokenExpired.WithMessagef("access token expired %f minutes", aDelta)
}

如果判断异常是否相等喃

  1. 基于断言后根据Code来进行业务异常判断
if e, ok := err.(*exception.APIException); ok {
    t.Log(e.String())
    // 判断该异常是不是 TokenExpired异常
    if e.Code == token.ErrAccessTokenExpired.Code {
        t.Log(e.String())
    }
}
// 	 exception.IsException(err, token.ErrAccessTokenExpired)
// 给一个异常判断的方法
func IsException(err error, e *APIException) bool {
	if targe, ok := err.(*APIException); ok {
		return targe.Code == e.Code
	}

	return false
}

Documentation

Index

Constants

This section is empty.

Variables

View Source
var (
	// 请求不合法
	ErrBadRequest = NewAPIException(http.StatusBadRequest, http.StatusText(http.StatusBadRequest)).
					WithHttpCode(http.StatusBadRequest).
					WithMessage("请求不合法")

	// 未认证, 没有登录, Token没传递
	ErrUnauthorized = NewAPIException(http.StatusUnauthorized, http.StatusText(http.StatusUnauthorized)).
					WithHttpCode(http.StatusUnauthorized).
					WithMessage("请先登录")
	// 鉴权失败, 认证通过,但是没有权限操作 该接口
	ErrPermissionDeny = NewAPIException(http.StatusForbidden, http.StatusText(http.StatusForbidden)).
						WithHttpCode(http.StatusForbidden).
						WithMessage("无权限访问")
)

Functions

func IsException

func IsException(err error, e *APIException) bool

给一个异常判断的方法

Types

type APIException

type APIException struct {
	HttpCode int    `json:"-"`
	Code     int    `json:"code"`
	Reason   string `json:"reason"`
	Message  string `json:"message"`
}

error的自定义实现 通过 API 直接序列号化{}

func NewAPIException

func NewAPIException(code int, Reason string) *APIException

func (*APIException) Error

func (e *APIException) Error() string

func (*APIException) String

func (e *APIException) String() string

控制用fmt.Print等函数的输出

func (*APIException) WithHttpCode

func (e *APIException) WithHttpCode(code int) *APIException

设计为链式调用 New().WithHttpCode()

func (*APIException) WithMessage

func (e *APIException) WithMessage(msg string) *APIException

设计为链式调用 New().WithMessage()

func (*APIException) WithMessagef

func (e *APIException) WithMessagef(format string, a ...any) *APIException

设计为链式调用 New().WithMessagef()

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL