func (c *Client) merchantUploadImageFromStringsReader(filename string, reader *strings.Reader) (imageURL string, err error) { originalOffset, err := reader.Seek(0, 1) if err != nil { return } FormDataFileName := escapeQuotes(filename) ContentLength := int64(multipart_constPartLen + len(FormDataFileName) + reader.Len()) hasRetry := false RETRY: token, err := c.Token() if err != nil { return } url_ := merchantUploadImageURL(token, filename) if hasRetry { if _, err = reader.Seek(originalOffset, 0); err != nil { return } } mr := io.MultiReader( strings.NewReader(multipart_formDataFront), strings.NewReader(FormDataFileName), strings.NewReader(multipart_formDataMiddle), reader, strings.NewReader(multipart_formDataEnd), ) httpReq, err := http.NewRequest("POST", url_, mr) if err != nil { return } httpReq.Header.Set("Content-Type", multipart_ContentType) httpReq.ContentLength = ContentLength httpResp, err := c.httpClient.Do(httpReq) if err != nil { return } defer httpResp.Body.Close() if httpResp.StatusCode != http.StatusOK { err = fmt.Errorf("http.Status: %s", httpResp.Status) return } var result struct { Error ImageURL string `json:"image_url"` } if err = json.NewDecoder(httpResp.Body).Decode(&result); err != nil { return } switch result.ErrCode { case errCodeOK: imageURL = result.ImageURL return case errCodeTimeout: if !hasRetry { hasRetry = true timeoutRetryWait() goto RETRY } fallthrough default: err = &result.Error return } }