Skip to content

Commit ffcba91

Browse files
authoredMar 21, 2025··
fix(googleapi): add JSON array support to CheckResponseWithBody (#3075)
fixes: googleapis/gax-go#389
1 parent b041969 commit ffcba91

File tree

2 files changed

+42
-2
lines changed

2 files changed

+42
-2
lines changed
 

‎googleapi/googleapi.go

+16-2
Original file line numberDiff line numberDiff line change
@@ -163,8 +163,7 @@ func CheckResponseWithBody(res *http.Response, body []byte) error {
163163
return nil
164164
}
165165

166-
jerr := new(errorReply)
167-
err := json.Unmarshal(body, jerr)
166+
jerr, err := errorReplyFromBody(body)
168167
if err == nil && jerr.Error != nil {
169168
if jerr.Error.Code == 0 {
170169
jerr.Error.Code = res.StatusCode
@@ -181,6 +180,21 @@ func CheckResponseWithBody(res *http.Response, body []byte) error {
181180
}
182181
}
183182

183+
// errorReplyFromBody attempts to get the error from body. The body
184+
// may be a JSON object or JSON array, or may be something else.
185+
func errorReplyFromBody(body []byte) (*errorReply, error) {
186+
jerr := new(errorReply)
187+
if len(body) > 0 && body[0] == '[' {
188+
// Attempt JSON array
189+
jsonArr := []*errorReply{jerr}
190+
err := json.Unmarshal(body, &jsonArr)
191+
return jerr, err
192+
}
193+
// Attempt JSON object
194+
err := json.Unmarshal(body, jerr)
195+
return jerr, err
196+
}
197+
184198
// IsNotModified reports whether err is the result of the
185199
// server replying with http.StatusNotModified.
186200
// Such error values are sometimes returned by "Do" methods

‎googleapi/googleapi_test.go

+26
Original file line numberDiff line numberDiff line change
@@ -312,6 +312,32 @@ Details:
312312
},
313313
`googleapi: got HTTP response code 500 with body: {"error":{}}`,
314314
},
315+
{
316+
// Case: Error in JSON object in body.
317+
&http.Response{
318+
StatusCode: http.StatusTooManyRequests,
319+
},
320+
`{"error":{"code": 429,"message": "Resource has been exhausted (e.g. check quota).","status": "RESOURCE_EXHAUSTED"}}`,
321+
&Error{
322+
Code: http.StatusTooManyRequests,
323+
Message: "Resource has been exhausted (e.g. check quota).",
324+
Body: `{"error":{"code": 429,"message": "Resource has been exhausted (e.g. check quota).","status": "RESOURCE_EXHAUSTED"}}`,
325+
},
326+
`googleapi: Error 429: Resource has been exhausted (e.g. check quota).`,
327+
},
328+
{
329+
// Case: Streaming error in JSON array in body.
330+
&http.Response{
331+
StatusCode: http.StatusTooManyRequests,
332+
},
333+
`[{"error":{"code": 429,"message": "Resource has been exhausted (e.g. check quota).","status": "RESOURCE_EXHAUSTED"}}]`,
334+
&Error{
335+
Code: http.StatusTooManyRequests,
336+
Message: "Resource has been exhausted (e.g. check quota).",
337+
Body: `[{"error":{"code": 429,"message": "Resource has been exhausted (e.g. check quota).","status": "RESOURCE_EXHAUSTED"}}]`,
338+
},
339+
`googleapi: Error 429: Resource has been exhausted (e.g. check quota).`,
340+
},
315341
}
316342

317343
func TestCheckResponse(t *testing.T) {

0 commit comments

Comments
 (0)
Please sign in to comment.