github.com/akamai/AkamaiOPEN-edgegrid-golang/v8@v8.1.0/pkg/edgeworkers/errors.go (about) 1 package edgeworkers 2 3 import ( 4 "encoding/json" 5 "errors" 6 "fmt" 7 "io/ioutil" 8 "net/http" 9 10 "github.com/akamai/AkamaiOPEN-edgegrid-golang/v8/pkg/errs" 11 ) 12 13 type ( 14 // Error is an edgeworkers error implementation 15 // For details on possible error types, refer to: https://techdocs.akamai.com/edgeworkers/reference/api-errors 16 Error struct { 17 Type string `json:"type,omitempty"` 18 Title string `json:"title,omitempty"` 19 Detail string `json:"detail,omitempty"` 20 Instance string `json:"instance,omitempty"` 21 Status int `json:"status,omitempty"` 22 ErrorCode string `json:"errorCode,omitempty"` 23 Method string `json:"method,omitempty"` 24 ServerIP string `json:"serverIp,omitempty"` 25 ClientIP string `json:"clientIp,omitempty"` 26 RequestID string `json:"requestId,omitempty"` 27 RequestTime string `json:"requestTime,omitempty"` 28 AuthzRealm string `json:"authzRealm,omitempty"` 29 AdditionalDetail Additional `json:"additionalDetail,omitempty"` 30 } 31 32 // Additional holds request_id for edgekv errors 33 Additional struct { 34 RequestID string `json:"requestId,omitempty"` 35 } 36 ) 37 38 const ( 39 errorCodeNotFound = "EKV_9000" 40 errorCodeVersionIsBeingDeactivated = "EW1031" 41 errorCodeVersionAlreadyDeactivated = "EW1032" 42 ) 43 44 var ( 45 // ErrNotFound is returned when edgeKV resource does not exist 46 ErrNotFound = errors.New("specified edgeKV resource does not exist") 47 // ErrVersionBeingDeactivated is returned when edgeworkers version is currently being deactivated 48 ErrVersionBeingDeactivated = errors.New("version is being deactivated") 49 // ErrVersionAlreadyDeactivated is returned when edgeworkers version is already deactivated 50 ErrVersionAlreadyDeactivated = errors.New("version is already deactivated") 51 ) 52 53 // Error parses an error from the response 54 func (e *edgeworkers) Error(r *http.Response) error { 55 var result Error 56 var body []byte 57 body, err := ioutil.ReadAll(r.Body) 58 if err != nil { 59 e.Log(r.Request.Context()).Errorf("reading error response body: %s", err) 60 result.Status = r.StatusCode 61 result.Title = "Failed to read error body" 62 result.Detail = err.Error() 63 return &result 64 } 65 66 if err := json.Unmarshal(body, &result); err != nil { 67 e.Log(r.Request.Context()).Errorf("could not unmarshal API error: %s", err) 68 result.Title = fmt.Sprintf("Failed to unmarshal error body. Edgeworkers API failed. Check details for more information.") 69 result.Detail = errs.UnescapeContent(string(body)) 70 result.Status = r.StatusCode 71 } 72 return &result 73 } 74 75 func (e *Error) Error() string { 76 msg, err := json.MarshalIndent(e, "", "\t") 77 if err != nil { 78 return fmt.Sprintf("error marshaling API error: %s", err) 79 } 80 return fmt.Sprintf("API error: \n%s", msg) 81 } 82 83 // Is handles error comparisons 84 func (e *Error) Is(target error) bool { 85 if errors.Is(target, ErrNotFound) { 86 return e.Status == http.StatusNotFound && e.ErrorCode == errorCodeNotFound 87 } 88 if errors.Is(target, ErrVersionBeingDeactivated) { 89 return e.ErrorCode == errorCodeVersionIsBeingDeactivated 90 } 91 if errors.Is(target, ErrVersionAlreadyDeactivated) { 92 return e.ErrorCode == errorCodeVersionAlreadyDeactivated 93 } 94 95 var t *Error 96 if !errors.As(target, &t) { 97 return false 98 } 99 100 if e == t { 101 return true 102 } 103 104 if e.Status != t.Status { 105 return false 106 } 107 108 return e.Error() == t.Error() 109 }