/
errors.go
159 lines (141 loc) · 3.84 KB
/
errors.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
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
package jsonapi
import (
"fmt"
"net/http"
"strconv"
)
// SourceError contains references to the source of the error
type SourceError struct {
Pointer string `json:"pointer,omitempty"`
Parameter string `json:"parameter,omitempty"`
}
// Error objects provide additional information about problems encountered
// while performing an operation.
// See http://jsonapi.org/format/#error-objects
type Error struct {
Status int `json:"status,string"`
Title string `json:"title"`
Code string `json:"code,omitempty"`
Detail string `json:"detail,omitempty"`
Source SourceError `json:"source,omitempty"`
Links *LinksList `json:"links,omitempty"`
}
// ErrorList is just an array of error objects
type ErrorList []*Error
func (e *Error) Error() string {
return e.Title + "(" + strconv.Itoa(e.Status) + ")" + ": " + e.Detail
}
// NewError creates a new generic Error
func NewError(status int, detail string) *Error {
return &Error{
Status: status,
Title: http.StatusText(status),
Detail: detail,
}
}
// Errorf creates a new generic Error with detail build as Sprintf
func Errorf(status int, format string, args ...interface{}) *Error {
detail := fmt.Sprintf(format, args...)
return NewError(status, detail)
}
// NotFound returns a 404 formatted error
func NotFound(err error) *Error {
return &Error{
Status: http.StatusNotFound,
Title: "Not Found",
Detail: err.Error(),
}
}
// BadRequest returns a 400 formatted error
func BadRequest(err error) *Error {
return &Error{
Status: http.StatusBadRequest,
Title: "Bad request",
Detail: err.Error(),
}
}
// BadJSON returns a 400 formatted error meaning the json input is
// malformed.
func BadJSON() *Error {
return &Error{
Status: http.StatusBadRequest,
Title: "Bad request",
Detail: "JSON input is malformed or is missing mandatory fields",
}
}
// MethodNotAllowed returns a 405 formatted error
func MethodNotAllowed(method string) *Error {
return &Error{
Status: http.StatusMethodNotAllowed,
Title: "Method Not Allowed",
Detail: method + " is not allowed on this endpoint",
}
}
// Conflict returns a 409 formatted error representing a conflict
func Conflict(err error) *Error {
return &Error{
Status: http.StatusConflict,
Title: "Conflict",
Detail: err.Error(),
}
}
// InternalServerError returns a 500 formatted error
func InternalServerError(err error) *Error {
return &Error{
Status: http.StatusInternalServerError,
Title: "Internal Server Error",
Detail: err.Error(),
}
}
// PreconditionFailed returns a 412 formatted error when an expectation from an
// HTTP header is not matched
func PreconditionFailed(parameter string, err error) *Error {
return &Error{
Status: http.StatusPreconditionFailed,
Title: "Precondition Failed",
Detail: err.Error(),
Source: SourceError{
Parameter: parameter,
},
}
}
// InvalidParameter returns a 422 formatted error when an HTTP or Query-String
// parameter is invalid
func InvalidParameter(parameter string, err error) *Error {
return &Error{
Status: http.StatusUnprocessableEntity,
Title: "Invalid Parameter",
Detail: err.Error(),
Source: SourceError{
Parameter: parameter,
},
}
}
// InvalidAttribute returns a 422 formatted error when an attribute is invalid
func InvalidAttribute(attribute string, err error) *Error {
return &Error{
Status: http.StatusUnprocessableEntity,
Title: "Invalid Attribute",
Detail: err.Error(),
Source: SourceError{
Pointer: "/data/attributes/" + attribute,
},
}
}
// Forbidden returns a 403 Forbidden error formatted when an action is
// fobidden.
func Forbidden(err error) *Error {
return &Error{
Status: http.StatusForbidden,
Title: "Forbidden",
Detail: err.Error(),
}
}
// BadGateway returns a 502 formatted error
func BadGateway(err error) *Error {
return &Error{
Status: http.StatusBadGateway,
Title: "Bad Gateway",
Detail: err.Error(),
}
}