github.com/akamai/AkamaiOPEN-edgegrid-golang/v2@v2.17.0/pkg/appsec/errors.go (about) 1 package appsec 2 3 import ( 4 "encoding/json" 5 "errors" 6 "fmt" 7 "io/ioutil" 8 "net/http" 9 ) 10 11 var ( 12 // ErrBadRequest is returned when a required parameter is missing. 13 ErrBadRequest = errors.New("missing argument") 14 ) 15 16 type ( 17 // Error is an appsec error interface. 18 Error struct { 19 Type string `json:"type"` 20 Title string `json:"title"` 21 Detail string `json:"detail"` 22 Instance string `json:"instance,omitempty"` 23 BehaviorName string `json:"behaviorName,omitempty"` 24 ErrorLocation string `json:"errorLocation,omitempty"` 25 StatusCode int `json:"-"` 26 } 27 ) 28 29 func (p *appsec) Error(r *http.Response) error { 30 var e Error 31 32 var body []byte 33 34 body, err := ioutil.ReadAll(r.Body) 35 if err != nil { 36 p.Log(r.Request.Context()).Errorf("reading error response body: %s", err) 37 e.StatusCode = r.StatusCode 38 e.Title = "Failed to read error body" 39 e.Detail = err.Error() 40 return &e 41 } 42 43 if err := json.Unmarshal(body, &e); err != nil { 44 p.Log(r.Request.Context()).Errorf("could not unmarshal API error: %s", err) 45 e.Title = "Failed to unmarshal error body" 46 e.Detail = err.Error() 47 } 48 49 e.StatusCode = r.StatusCode 50 51 return &e 52 } 53 54 // Error returns a string formatted using a given title, type, and detail information. 55 func (e *Error) Error() string { 56 return fmt.Sprintf("Title: %s; Type: %s; Detail: %s", e.Title, e.Type, e.Detail) 57 } 58 59 // Is handles error comparisons. 60 func (e *Error) Is(target error) bool { 61 var t *Error 62 if !errors.As(target, &t) { 63 return false 64 } 65 66 if e == t { 67 return true 68 } 69 70 if e.StatusCode != t.StatusCode { 71 return false 72 } 73 74 return e.Error() == t.Error() 75 }