-
Notifications
You must be signed in to change notification settings - Fork 1
/
RpcError.go
92 lines (73 loc) · 2.1 KB
/
RpcError.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
package jrm1
import "errors"
const (
ErrUserGeneratedErrorsUseAnotherConstructor = "user-generated errors use another constructor"
ErrUserGeneratedErrorsHaveSpecialCodes = "user-generated errors have special codes"
)
// RpcError is an RPC error.
type RpcError struct {
// Error code.
Code RpcErrorCode `json:"code"`
// Error message.
Message RpcErrorMessage `json:"message"`
// Some additional details about an error.
Data any `json:"data"`
}
// NewRpcError is a common constructor of an RPC error.
// It returns an error in a Go-language style.
// This constructor is not for user-generated errors.
func NewRpcError(code int, data any) (re *RpcError, err error) {
re = &RpcError{
Code: RpcErrorCode(code),
}
err = re.Code.Check()
if err != nil {
if re.Code.IsGeneratedByUser() {
return nil, errors.New(ErrUserGeneratedErrorsUseAnotherConstructor)
}
return nil, err
}
re.Message, err = findMessageForErrorCode(re.Code)
if err != nil {
return nil, err
}
err = re.Message.Check()
if err != nil {
return nil, err
}
re.Data = data
return re, nil
}
// NewRpcErrorFast is a fast constructor which throws an exception on error.
// This constructor should only be used if you know what it is.
func NewRpcErrorFast(code int) (re *RpcError) {
var err error
re, err = NewRpcError(code, nil)
if err != nil {
panic(err)
return nil // This line is normally unreachable, but we expect anything.
}
return re
}
// NewRpcErrorByUser is a constructor of an RPC error created by user.
// This function throws an exception on error.
func NewRpcErrorByUser(code int, message string, data any) (re *RpcError) {
re = &RpcError{
Code: RpcErrorCode(code),
Message: RpcErrorMessage(message),
Data: data,
}
if !re.Code.IsGeneratedByUser() {
err := errors.New(ErrUserGeneratedErrorsHaveSpecialCodes)
panic(err)
return nil // This line is normally unreachable, but we expect anything.
}
return re
}
// AsError returns an RPC error as a standard error.
func (re *RpcError) AsError() *RpcErrorStd {
if re == nil {
return nil
}
return NewRpcErrorStd(re.Code, re.Message, re.Data)
}