// WithOdataErrorUnlessStatusCode returns a RespondDecorator that emits an // azure.RequestError by reading the response body unless the response HTTP status code // is among the set passed. // // If there is a chance service may return responses other than the Azure error // format and the response cannot be parsed into an error, a decoding error will // be returned containing the response body. In any case, the Responder will // return an error if the status code is not satisfied. // // If this Responder returns an error, the response body will be replaced with // an in-memory reader, which needs no further closing. // // NOTE(axw) this function is based on go-autorest/autorest/azure.WithErrorUnlessStatusCode. // The only difference is that we extract "odata.error", instead of "error", // from the response body; and we do not extract the message, which is in a // different format for odata.error, and irrelevant to us. func WithOdataErrorUnlessStatusCode(codes ...int) autorest.RespondDecorator { return func(r autorest.Responder) autorest.Responder { return autorest.ResponderFunc(func(resp *http.Response) error { err := r.Respond(resp) if err == nil && !autorest.ResponseHasStatusCode(resp, codes...) { var oe odataRequestError defer resp.Body.Close() // Copy and replace the Body in case it does not contain an error object. // This will leave the Body available to the caller. b, decodeErr := autorest.CopyAndDecode(autorest.EncodedAsJSON, resp.Body, &oe) resp.Body = ioutil.NopCloser(&b) if decodeErr != nil { return fmt.Errorf("ad: error response cannot be parsed: %q error: %v", b.String(), decodeErr) } else if oe.ServiceError == nil { oe.ServiceError = &odataServiceError{Code: "Unknown"} } e := azure.RequestError{ ServiceError: &azure.ServiceError{Code: oe.ServiceError.Code}, RequestID: azure.ExtractRequestID(resp), } if e.StatusCode == nil { e.StatusCode = resp.StatusCode } err = &e } return err }) } }
func byInspecting() autorest.RespondDecorator { return func(r autorest.Responder) autorest.Responder { return autorest.ResponderFunc(func(resp *http.Response) error { log.Debug("Azure response", logutil.Fields{ "status": resp.Status, "method": resp.Request.Method, "request": resp.Request.URL.String(), "x-ms-request-id": azure.ExtractRequestID(resp), }) return r.Respond(resp) }) } }
func byInspecting(maxlen int64) autorest.RespondDecorator { return func(r autorest.Responder) autorest.Responder { return autorest.ResponderFunc(func(resp *http.Response) error { body, bodyString := handleBody(resp.Body, maxlen) resp.Body = body log.Print("Azure response", logutil.Fields{ "status": resp.Status, "method": resp.Request.Method, "request": resp.Request.URL.String(), "x-ms-request-id": azure.ExtractRequestID(resp), "body": bodyString, }) return r.Respond(resp) }) } }