Skip to content
This repository was archived by the owner on Aug 1, 2023. It is now read-only.

Commit e52d480

Browse files
committed
Merge pull request #437 from smashwilson/clb-creation-err
Rackspace CLB ExtractNodes call does not propagate errors correctly
2 parents 7af4dbf + 2c749a0 commit e52d480

File tree

5 files changed

+80
-8
lines changed

5 files changed

+80
-8
lines changed

pagination/http.go

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,13 +36,19 @@ func PageResultFrom(resp *http.Response) (PageResult, error) {
3636
parsedBody = rawBody
3737
}
3838

39+
return PageResultFromParsed(resp, parsedBody), err
40+
}
41+
42+
// PageResultFromParsed constructs a PageResult from an HTTP response that has already had its
43+
// body parsed as JSON (and closed).
44+
func PageResultFromParsed(resp *http.Response, body interface{}) PageResult {
3945
return PageResult{
4046
Result: gophercloud.Result{
41-
Body: parsedBody,
47+
Body: body,
4248
Header: resp.Header,
4349
},
4450
URL: *resp.Request.URL,
45-
}, err
51+
}
4652
}
4753

4854
// Request performs an HTTP request and extracts the http.Response from the result.

rackspace/lb/v1/nodes/fixtures.go

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,42 @@ func mockCreateResponse(t *testing.T, lbID int) {
107107
})
108108
}
109109

110+
func mockCreateErrResponse(t *testing.T, lbID int) {
111+
th.Mux.HandleFunc(_rootURL(lbID), func(w http.ResponseWriter, r *http.Request) {
112+
th.TestMethod(t, r, "POST")
113+
th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
114+
115+
th.TestJSONRequest(t, r, `
116+
{
117+
"nodes": [
118+
{
119+
"address": "10.2.2.3",
120+
"port": 80,
121+
"condition": "ENABLED",
122+
"type": "PRIMARY"
123+
},
124+
{
125+
"address": "10.2.2.4",
126+
"port": 81,
127+
"condition": "ENABLED",
128+
"type": "SECONDARY"
129+
}
130+
]
131+
}
132+
`)
133+
134+
w.Header().Add("Content-Type", "application/json")
135+
w.WriteHeader(422) // Unprocessable Entity
136+
137+
fmt.Fprintf(w, `
138+
{
139+
"code": 422,
140+
"message": "Load Balancer '%d' has a status of 'PENDING_UPDATE' and is considered immutable."
141+
}
142+
`, lbID)
143+
})
144+
}
145+
110146
func mockBatchDeleteResponse(t *testing.T, lbID int, ids []int) {
111147
th.Mux.HandleFunc(_rootURL(lbID), func(w http.ResponseWriter, r *http.Request) {
112148
th.TestMethod(t, r, "DELETE")

rackspace/lb/v1/nodes/requests.go

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -119,12 +119,7 @@ func Create(client *gophercloud.ServiceClient, loadBalancerID int, opts CreateOp
119119
return res
120120
}
121121

122-
pr, err := pagination.PageResultFrom(resp)
123-
if err != nil {
124-
res.Err = err
125-
return res
126-
}
127-
122+
pr := pagination.PageResultFromParsed(resp, res.Body)
128123
return CreateResult{pagination.SinglePageBase(pr)}
129124
}
130125

rackspace/lb/v1/nodes/requests_test.go

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,38 @@ func TestCreate(t *testing.T) {
108108
th.CheckDeepEquals(t, expected, actual)
109109
}
110110

111+
func TestCreateErr(t *testing.T) {
112+
th.SetupHTTP()
113+
defer th.TeardownHTTP()
114+
115+
mockCreateErrResponse(t, lbID)
116+
117+
opts := CreateOpts{
118+
CreateOpt{
119+
Address: "10.2.2.3",
120+
Port: 80,
121+
Condition: ENABLED,
122+
Type: PRIMARY,
123+
},
124+
CreateOpt{
125+
Address: "10.2.2.4",
126+
Port: 81,
127+
Condition: ENABLED,
128+
Type: SECONDARY,
129+
},
130+
}
131+
132+
page := Create(client.ServiceClient(), lbID, opts)
133+
134+
actual, err := page.ExtractNodes()
135+
if err == nil {
136+
t.Fatal("Did not receive expected error from ExtractNodes")
137+
}
138+
if actual != nil {
139+
t.Fatalf("Received non-nil result from failed ExtractNodes: %#v", actual)
140+
}
141+
}
142+
111143
func TestBulkDelete(t *testing.T) {
112144
th.SetupHTTP()
113145
defer th.TeardownHTTP()

rackspace/lb/v1/nodes/results.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -126,6 +126,9 @@ type CreateResult struct {
126126

127127
// ExtractNodes extracts a slice of Node structs from a CreateResult.
128128
func (res CreateResult) ExtractNodes() ([]Node, error) {
129+
if res.Err != nil {
130+
return nil, res.Err
131+
}
129132
return commonExtractNodes(res.Body)
130133
}
131134

0 commit comments

Comments
 (0)