From 38b71c3469ffc88e9241a9dd7c95fddc0f4961dd Mon Sep 17 00:00:00 2001 From: Timo Reimann Date: Wed, 11 Dec 2019 20:52:04 +0100 Subject: [PATCH] Deserialize meta field for remaining APIs --- CHANGELOG.md | 2 +- action.go | 4 ++ action_test.go | 28 ++++++-- cdn.go | 4 ++ cdn_test.go | 20 ++++-- certificates.go | 4 ++ certificates_test.go | 13 ++-- domains.go | 4 ++ domains_test.go | 30 ++++++-- droplets.go | 19 +++++ droplets_test.go | 156 ++++++++++++++++++++++++++++++++-------- firewalls.go | 4 ++ firewalls_test.go | 16 +++-- floating_ips.go | 4 ++ floating_ips_test.go | 17 +++-- images.go | 4 ++ images_test.go | 135 +++++++++++++++++++++++++++------- keys.go | 4 ++ keys_test.go | 27 +++++-- kubernetes.go | 9 +++ kubernetes_test.go | 33 +++++++-- load_balancers.go | 4 ++ load_balancers_test.go | 9 ++- projects.go | 8 +++ projects_test.go | 34 +++++---- regions.go | 4 ++ regions_test.go | 27 +++++-- sizes.go | 4 ++ sizes_test.go | 27 +++++-- storage_actions.go | 3 + storage_actions_test.go | 24 +++++-- tags.go | 4 ++ tags_test.go | 13 ++-- vpcs.go | 4 ++ vpcs_test.go | 9 ++- 35 files changed, 582 insertions(+), 129 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9974165d..612abca0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,7 +3,7 @@ ## unreleased - #288 Add Balance Get method - @rbutler -- #286 Deserialize meta - @timoreimann +- #286,#289 Deserialize meta field - @timoreimann ## [v1.28.0] - 2019-12-04 diff --git a/action.go b/action.go index 67ef3ab8..e3176005 100644 --- a/action.go +++ b/action.go @@ -34,6 +34,7 @@ var _ ActionsService = &ActionsServiceOp{} type actionsRoot struct { Actions []Action `json:"actions"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type actionRoot struct { @@ -74,6 +75,9 @@ func (s *ActionsServiceOp) List(ctx context.Context, opt *ListOptions) ([]Action if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Actions, resp, err } diff --git a/action_test.go b/action_test.go index fb7a6e94..31c50680 100644 --- a/action_test.go +++ b/action_test.go @@ -13,18 +13,36 @@ func TestAction_List(t *testing.T) { defer teardown() mux.HandleFunc("/v2/actions", func(w http.ResponseWriter, r *http.Request) { - fmt.Fprint(w, `{"actions": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "actions": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }, + `) testMethod(t, r, http.MethodGet) }) - actions, _, err := client.Actions.List(ctx, nil) + actions, resp, err := client.Actions.List(ctx, nil) if err != nil { t.Fatalf("unexpected error: %s", err) } - expected := []Action{{ID: 1}, {ID: 2}} - if len(actions) != len(expected) || actions[0].ID != expected[0].ID || actions[1].ID != expected[1].ID { - t.Fatalf("unexpected response") + expectedActions := []Action{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(actions, expectedActions) { + t.Errorf("Actions.List returned actions %+v, expected %+v", actions, expectedActions) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Actions.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/cdn.go b/cdn.go index 2e8f475a..4c97d117 100644 --- a/cdn.go +++ b/cdn.go @@ -47,6 +47,7 @@ type cdnRoot struct { type cdnsRoot struct { Endpoints []CDN `json:"endpoints"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } // CDNCreateRequest represents a request to create a CDN. @@ -93,6 +94,9 @@ func (c CDNServiceOp) List(ctx context.Context, opt *ListOptions) ([]CDN, *Respo if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Endpoints, resp, err } diff --git a/cdn_test.go b/cdn_test.go index 74812aac..de4c7be3 100644 --- a/cdn_test.go +++ b/cdn_test.go @@ -32,17 +32,20 @@ func TestCDN_ListCDN(t *testing.T) { "ttl": 3600, "created_at": "2012-10-03T15:00:01.05Z" } - ] + ], + "meta": { + "total": 2 + } }`, ) }) - cdns, _, err := client.CDNs.List(ctx, nil) + cdns, resp, err := client.CDNs.List(ctx, nil) if err != nil { t.Errorf("CDNs.List returned error: %v", err) } - expected := []CDN{ + expectedCDNs := []CDN{ { ID: "892071a0-bb95-49bc-8021-3afd67a210bf", Origin: "my-space.nyc3.digitaloceanspaces.com", @@ -59,8 +62,15 @@ func TestCDN_ListCDN(t *testing.T) { }, } - if !reflect.DeepEqual(cdns, expected) { - t.Errorf("CDNs.List returned %+v, expected %+v", cdns, expected) + if !reflect.DeepEqual(cdns, expectedCDNs) { + t.Errorf("CDNs.List returned CDNs %+v, expected %+v", cdns, expectedCDNs) + } + + expectedMeta := &Meta{ + Total: 2, + } + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("CDNs.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/certificates.go b/certificates.go index cbc3e16a..9a6bdb2d 100644 --- a/certificates.go +++ b/certificates.go @@ -46,6 +46,7 @@ type certificateRoot struct { type certificatesRoot struct { Certificates []Certificate `json:"certificates"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } // CertificatesServiceOp handles communication with certificates methods of the DigitalOcean API. @@ -93,6 +94,9 @@ func (c *CertificatesServiceOp) List(ctx context.Context, opt *ListOptions) ([]C if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Certificates, resp, nil } diff --git a/certificates_test.go b/certificates_test.go index e522da5b..d52188a1 100644 --- a/certificates_test.go +++ b/certificates_test.go @@ -57,7 +57,7 @@ var certsJSONResponse = ` ], "links": {}, "meta": { - "total": 1 + "total": 2 } } ` @@ -103,13 +103,13 @@ func TestCertificates_List(t *testing.T) { fmt.Fprint(w, certsJSONResponse) }) - certificates, _, err := client.Certificates.List(ctx, nil) + certificates, resp, err := client.Certificates.List(ctx, nil) if err != nil { t.Errorf("Certificates.List returned error: %v", err) } - expected := []Certificate{ + expectedCertificates := []Certificate{ { ID: "892071a0-bb95-49bc-8021-3afd67a210bf", Name: "web-cert-01", @@ -132,7 +132,12 @@ func TestCertificates_List(t *testing.T) { }, } - assert.Equal(t, expected, certificates) + assert.Equal(t, expectedCertificates, certificates) + + expectedMeta := &Meta{ + Total: 2, + } + assert.Equal(t, expectedMeta, resp.Meta) } func TestCertificates_Create(t *testing.T) { diff --git a/domains.go b/domains.go index 1014e9b9..43c04244 100644 --- a/domains.go +++ b/domains.go @@ -47,6 +47,7 @@ type domainRoot struct { type domainsRoot struct { Domains []Domain `json:"domains"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } // DomainCreateRequest respresents a request to create a domain. @@ -122,6 +123,9 @@ func (s DomainsServiceOp) List(ctx context.Context, opt *ListOptions) ([]Domain, if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Domains, resp, err } diff --git a/domains_test.go b/domains_test.go index cc5a35b0..f79e24e3 100644 --- a/domains_test.go +++ b/domains_test.go @@ -14,17 +14,34 @@ func TestDomains_ListDomains(t *testing.T) { mux.HandleFunc("/v2/domains", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"domains": [{"name":"foo.com"},{"name":"bar.com"}]}`) + fmt.Fprint(w, `{ + "domains": [ + { + "name":"foo.com" + }, + { + "name":"bar.com" + } + ], + "meta": { + "total": 2 + } + }`) }) - domains, _, err := client.Domains.List(ctx, nil) + domains, resp, err := client.Domains.List(ctx, nil) if err != nil { t.Errorf("Domains.List returned error: %v", err) } - expected := []Domain{{Name: "foo.com"}, {Name: "bar.com"}} - if !reflect.DeepEqual(domains, expected) { - t.Errorf("Domains.List returned %+v, expected %+v", domains, expected) + expectedDomains := []Domain{{Name: "foo.com"}, {Name: "bar.com"}} + if !reflect.DeepEqual(domains, expectedDomains) { + t.Errorf("Domains.List returned domains %+v, expected %+v", domains, expectedDomains) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Domains.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -59,6 +76,9 @@ func TestDomains_RetrievePageByNumber(t *testing.T) { "last":"http://example.com/v2/domains/?page=3", "first":"http://example.com/v2/domains/?page=1" } + }, + "meta":{ + "total":2 } }` diff --git a/droplets.go b/droplets.go index 06d4debf..72edf2b4 100644 --- a/droplets.go +++ b/droplets.go @@ -139,21 +139,25 @@ type dropletRoot struct { type dropletsRoot struct { Droplets []Droplet `json:"droplets"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type kernelsRoot struct { Kernels []Kernel `json:"kernels,omitempty"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type dropletSnapshotsRoot struct { Snapshots []Image `json:"snapshots,omitempty"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type backupsRoot struct { Backups []Image `json:"backups,omitempty"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } // DropletCreateImage identifies an image for the create request. It prefers slug over ID. @@ -295,6 +299,9 @@ func (s *DropletsServiceOp) list(ctx context.Context, path string) ([]Droplet, * if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Droplets, resp, err } @@ -449,6 +456,9 @@ func (s *DropletsServiceOp) Kernels(ctx context.Context, dropletID int, opt *Lis if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Kernels, resp, err } @@ -478,6 +488,9 @@ func (s *DropletsServiceOp) Actions(ctx context.Context, dropletID int, opt *Lis if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Actions, resp, err } @@ -507,6 +520,9 @@ func (s *DropletsServiceOp) Backups(ctx context.Context, dropletID int, opt *Lis if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Backups, resp, err } @@ -536,6 +552,9 @@ func (s *DropletsServiceOp) Snapshots(ctx context.Context, dropletID int, opt *L if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Snapshots, resp, err } diff --git a/droplets_test.go b/droplets_test.go index c7c1d06d..875412e2 100644 --- a/droplets_test.go +++ b/droplets_test.go @@ -14,17 +14,33 @@ func TestDroplets_ListDroplets(t *testing.T) { mux.HandleFunc("/v2/droplets", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"droplets": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "droplets": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - droplets, _, err := client.Droplets.List(ctx, nil) + droplets, resp, err := client.Droplets.List(ctx, nil) if err != nil { t.Errorf("Droplets.List returned error: %v", err) } - expected := []Droplet{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(droplets, expected) { - t.Errorf("Droplets.List\n got=%#v\nwant=%#v", droplets, expected) + expectedDroplets := []Droplet{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(droplets, expectedDroplets) { + t.Errorf("Droplets.List\nDroplets: got=%#v\nwant=%#v", droplets, expectedDroplets) + } + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Droplets.List\nMeta: got=%#v\nwant=%#v", resp.Meta, expectedMeta) } } @@ -38,17 +54,33 @@ func TestDroplets_ListDropletsByTag(t *testing.T) { } testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"droplets": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "droplets": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - droplets, _, err := client.Droplets.ListByTag(ctx, "testing-1", nil) + droplets, resp, err := client.Droplets.ListByTag(ctx, "testing-1", nil) if err != nil { t.Errorf("Droplets.ListByTag returned error: %v", err) } - expected := []Droplet{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(droplets, expected) { - t.Errorf("Droplets.ListByTag returned %+v, expected %+v", droplets, expected) + expectedDroplets := []Droplet{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(droplets, expectedDroplets) { + t.Errorf("Droplets.ListByTag returned droplets %+v, expected %+v", droplets, expectedDroplets) + } + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Droplets.ListByTag returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -354,18 +386,34 @@ func TestDroplets_Kernels(t *testing.T) { mux.HandleFunc("/v2/droplets/12345/kernels", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"kernels": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "kernels": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) opt := &ListOptions{Page: 2} - kernels, _, err := client.Droplets.Kernels(ctx, 12345, opt) + kernels, resp, err := client.Droplets.Kernels(ctx, 12345, opt) if err != nil { t.Errorf("Droplets.Kernels returned error: %v", err) } - expected := []Kernel{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(kernels, expected) { - t.Errorf("Droplets.Kernels\n got=%#v\nwant=%#v", kernels, expected) + expectedKernels := []Kernel{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(kernels, expectedKernels) { + t.Errorf("Droplets.Kernels\nKernels got=%#v\nwant=%#v", kernels, expectedKernels) + } + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Droplets.Kernels\nMeta: got=%#v\nwant=%#v", resp.Meta, expectedMeta) } } @@ -375,18 +423,34 @@ func TestDroplets_Snapshots(t *testing.T) { mux.HandleFunc("/v2/droplets/12345/snapshots", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"snapshots": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "snapshots": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) opt := &ListOptions{Page: 2} - snapshots, _, err := client.Droplets.Snapshots(ctx, 12345, opt) + snapshots, resp, err := client.Droplets.Snapshots(ctx, 12345, opt) if err != nil { t.Errorf("Droplets.Snapshots returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(snapshots, expected) { - t.Errorf("Droplets.Snapshots\n got=%#v\nwant=%#v", snapshots, expected) + expectedSnapshots := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(snapshots, expectedSnapshots) { + t.Errorf("Droplets.Snapshots\nSnapshots got=%#v\nwant=%#v", snapshots, expectedSnapshots) + } + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Droplets.Snapshots\nMeta: got=%#v\nwant=%#v", resp.Meta, expectedMeta) } } @@ -396,18 +460,34 @@ func TestDroplets_Backups(t *testing.T) { mux.HandleFunc("/v2/droplets/12345/backups", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"backups": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "backups": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) opt := &ListOptions{Page: 2} - backups, _, err := client.Droplets.Backups(ctx, 12345, opt) + backups, resp, err := client.Droplets.Backups(ctx, 12345, opt) if err != nil { t.Errorf("Droplets.Backups returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(backups, expected) { - t.Errorf("Droplets.Backups\n got=%#v\nwant=%#v", backups, expected) + expectedBackups := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(backups, expectedBackups) { + t.Errorf("Droplets.Backups\nBackups got=%#v\nwant=%#v", backups, expectedBackups) + } + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Droplets.Backups\nMeta: got=%#v\nwant=%#v", resp.Meta, expectedMeta) } } @@ -417,18 +497,34 @@ func TestDroplets_Actions(t *testing.T) { mux.HandleFunc("/v2/droplets/12345/actions", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"actions": [{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "actions": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) opt := &ListOptions{Page: 2} - actions, _, err := client.Droplets.Actions(ctx, 12345, opt) + actions, resp, err := client.Droplets.Actions(ctx, 12345, opt) if err != nil { t.Errorf("Droplets.Actions returned error: %v", err) } - expected := []Action{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(actions, expected) { - t.Errorf("Droplets.Actions\n got=%#v\nwant=%#v", actions, expected) + expectedActions := []Action{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(actions, expectedActions) { + t.Errorf("Droplets.Actions\nActions got=%#v\nwant=%#v", actions, expectedActions) + } + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Droplets.Actions\nMeta: got=%#v\nwant=%#v", resp.Meta, expectedMeta) } } diff --git a/firewalls.go b/firewalls.go index 316b394a..8453e664 100644 --- a/firewalls.go +++ b/firewalls.go @@ -237,6 +237,7 @@ type firewallRoot struct { type firewallsRoot struct { Firewalls []Firewall `json:"firewalls"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } func (fw *FirewallsServiceOp) createAndDoReq(ctx context.Context, method, path string, v interface{}) (*Response, error) { @@ -262,6 +263,9 @@ func (fw *FirewallsServiceOp) listHelper(ctx context.Context, path string) ([]Fi if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Firewalls, resp, err } diff --git a/firewalls_test.go b/firewalls_test.go index 9a555030..7e50b9ba 100644 --- a/firewalls_test.go +++ b/firewalls_test.go @@ -500,7 +500,7 @@ func TestFirewalls_List(t *testing.T) { fmt.Fprint(w, firewallListJSONResponse) }) - actualFirewalls, _, err := client.Firewalls.List(ctx, nil) + actualFirewalls, resp, err := client.Firewalls.List(ctx, nil) if err != nil { t.Errorf("Firewalls.List returned error: %v", err) @@ -508,7 +508,11 @@ func TestFirewalls_List(t *testing.T) { expectedFirewalls := makeExpectedFirewalls() if !reflect.DeepEqual(actualFirewalls, expectedFirewalls) { - t.Errorf("Firewalls.List returned %+v, expected %+v", actualFirewalls, expectedFirewalls) + t.Errorf("Firewalls.List returned firewalls %+v, expected %+v", actualFirewalls, expectedFirewalls) + } + expectedMeta := &Meta{Total: 1} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Firewalls.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -521,7 +525,7 @@ func TestFirewalls_ListByDroplet(t *testing.T) { fmt.Fprint(w, firewallListJSONResponse) }) - actualFirewalls, _, err := client.Firewalls.ListByDroplet(ctx, 123, nil) + actualFirewalls, resp, err := client.Firewalls.ListByDroplet(ctx, 123, nil) if err != nil { t.Errorf("Firewalls.List returned error: %v", err) @@ -529,7 +533,11 @@ func TestFirewalls_ListByDroplet(t *testing.T) { expectedFirewalls := makeExpectedFirewalls() if !reflect.DeepEqual(actualFirewalls, expectedFirewalls) { - t.Errorf("Firewalls.List returned %+v, expected %+v", actualFirewalls, expectedFirewalls) + t.Errorf("Firewalls.List returned firewalls %+v, expected %+v", actualFirewalls, expectedFirewalls) + } + expectedMeta := &Meta{Total: 1} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Firewalls.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/floating_ips.go b/floating_ips.go index 4545e903..1720d767 100644 --- a/floating_ips.go +++ b/floating_ips.go @@ -44,6 +44,7 @@ func (f FloatingIP) URN() string { type floatingIPsRoot struct { FloatingIPs []FloatingIP `json:"floating_ips"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type floatingIPRoot struct { @@ -80,6 +81,9 @@ func (f *FloatingIPsServiceOp) List(ctx context.Context, opt *ListOptions) ([]Fl if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.FloatingIPs, resp, err } diff --git a/floating_ips_test.go b/floating_ips_test.go index ccb3c67b..02312f83 100644 --- a/floating_ips_test.go +++ b/floating_ips_test.go @@ -14,20 +14,27 @@ func TestFloatingIPs_ListFloatingIPs(t *testing.T) { mux.HandleFunc("/v2/floating_ips", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"floating_ips": [{"region":{"slug":"nyc3"},"droplet":{"id":1},"ip":"192.168.0.1"},{"region":{"slug":"nyc3"},"droplet":{"id":2},"ip":"192.168.0.2"}]}`) + fmt.Fprint(w, `{"floating_ips": [{"region":{"slug":"nyc3"},"droplet":{"id":1},"ip":"192.168.0.1"},{"region":{"slug":"nyc3"},"droplet":{"id":2},"ip":"192.168.0.2"}],"meta":{"total":2}}`) }) - floatingIPs, _, err := client.FloatingIPs.List(ctx, nil) + floatingIPs, resp, err := client.FloatingIPs.List(ctx, nil) if err != nil { t.Errorf("FloatingIPs.List returned error: %v", err) } - expected := []FloatingIP{ + expectedFloatingIPs := []FloatingIP{ {Region: &Region{Slug: "nyc3"}, Droplet: &Droplet{ID: 1}, IP: "192.168.0.1"}, {Region: &Region{Slug: "nyc3"}, Droplet: &Droplet{ID: 2}, IP: "192.168.0.2"}, } - if !reflect.DeepEqual(floatingIPs, expected) { - t.Errorf("FloatingIPs.List returned %+v, expected %+v", floatingIPs, expected) + if !reflect.DeepEqual(floatingIPs, expectedFloatingIPs) { + t.Errorf("FloatingIPs.List returned floating IPs %+v, expected %+v", floatingIPs, expectedFloatingIPs) + } + + expectedMeta := &Meta{ + Total: 2, + } + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("FloatingIPs.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/images.go b/images.go index 69de4c07..64e72e75 100644 --- a/images.go +++ b/images.go @@ -72,6 +72,7 @@ type imageRoot struct { type imagesRoot struct { Images []Image Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type listImageOptions struct { @@ -236,6 +237,9 @@ func (s *ImagesServiceOp) list(ctx context.Context, opt *ListOptions, listOpt *l if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Images, resp, err } diff --git a/images_test.go b/images_test.go index 9dab7f70..49f49b43 100644 --- a/images_test.go +++ b/images_test.go @@ -14,17 +14,34 @@ func TestImages_List(t *testing.T) { mux.HandleFunc("/v2/images", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"images":[{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "images": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - images, _, err := client.Images.List(ctx, nil) + images, resp, err := client.Images.List(ctx, nil) if err != nil { t.Errorf("Images.List returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(images, expected) { - t.Errorf("Images.List returned %+v, expected %+v", images, expected) + expectedImages := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(images, expectedImages) { + t.Errorf("Images.List returned images %+v, expected %+v", images, expectedImages) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Images.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -39,17 +56,34 @@ func TestImages_ListDistribution(t *testing.T) { if actual != expected { t.Errorf("'type' query = %v, expected %v", actual, expected) } - fmt.Fprint(w, `{"images":[{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "images": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - images, _, err := client.Images.ListDistribution(ctx, nil) + images, resp, err := client.Images.ListDistribution(ctx, nil) if err != nil { t.Errorf("Images.ListDistribution returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(images, expected) { - t.Errorf("Images.ListDistribution returned %+v, expected %+v", images, expected) + expectedImages := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(images, expectedImages) { + t.Errorf("Images.ListDistribution returned images %+v, expected %+v", images, expectedImages) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Images.ListDistribution returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -64,17 +98,34 @@ func TestImages_ListApplication(t *testing.T) { if actual != expected { t.Errorf("'type' query = %v, expected %v", actual, expected) } - fmt.Fprint(w, `{"images":[{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "images": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - images, _, err := client.Images.ListApplication(ctx, nil) + images, resp, err := client.Images.ListApplication(ctx, nil) if err != nil { t.Errorf("Images.ListApplication returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(images, expected) { - t.Errorf("Images.ListApplication returned %+v, expected %+v", images, expected) + expectedImages := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(images, expectedImages) { + t.Errorf("Images.ListApplication returned images %+v, expected %+v", images, expectedImages) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Images.ListApplication returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -90,17 +141,34 @@ func TestImages_ListUser(t *testing.T) { t.Errorf("'private' query = %v, expected %v", actual, expected) } - fmt.Fprint(w, `{"images":[{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "images": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - images, _, err := client.Images.ListUser(ctx, nil) + images, resp, err := client.Images.ListUser(ctx, nil) if err != nil { t.Errorf("Images.ListUser returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(images, expected) { - t.Errorf("Images.ListUser returned %+v, expected %+v", images, expected) + expectedImages := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(images, expectedImages) { + t.Errorf("Images.ListUser returned images %+v, expected %+v", images, expectedImages) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Images.ListUser returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -116,17 +184,34 @@ func TestImages_ListByTag(t *testing.T) { t.Errorf("'tag_name' query = %v, expected %v", actual, expected) } - fmt.Fprint(w, `{"images":[{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "images": [ + { + "id": 1 + }, + { + "id":2 + } + ], + "meta": { + "total": 2 + } + }`) }) - images, _, err := client.Images.ListByTag(ctx, "foo", nil) + images, resp, err := client.Images.ListByTag(ctx, "foo", nil) if err != nil { t.Errorf("Images.ListByTag returned error: %v", err) } - expected := []Image{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(images, expected) { - t.Errorf("Images.ListByTag returned %+v, expected %+v", images, expected) + expectedImages := []Image{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(images, expectedImages) { + t.Errorf("Images.ListByTag returned images %+v, expected %+v", images, expectedImages) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Images.ListByTag returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/keys.go b/keys.go index 9695c21f..b97554d1 100644 --- a/keys.go +++ b/keys.go @@ -46,6 +46,7 @@ type KeyUpdateRequest struct { type keysRoot struct { SSHKeys []Key `json:"ssh_keys"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type keyRoot struct { @@ -83,6 +84,9 @@ func (s *KeysServiceOp) List(ctx context.Context, opt *ListOptions) ([]Key, *Res if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.SSHKeys, resp, err } diff --git a/keys_test.go b/keys_test.go index e1c56ae8..c8163409 100644 --- a/keys_test.go +++ b/keys_test.go @@ -14,17 +14,34 @@ func TestKeys_List(t *testing.T) { mux.HandleFunc("/v2/account/keys", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"ssh_keys":[{"id":1},{"id":2}]}`) + fmt.Fprint(w, `{ + "ssh_keys": [ + { + "id": 1 + }, + { + "id": 2 + } + ], + "meta": { + "total": 2 + } + }`) }) - keys, _, err := client.Keys.List(ctx, nil) + keys, resp, err := client.Keys.List(ctx, nil) if err != nil { t.Errorf("Keys.List returned error: %v", err) } - expected := []Key{{ID: 1}, {ID: 2}} - if !reflect.DeepEqual(keys, expected) { - t.Errorf("Keys.List returned %+v, expected %+v", keys, expected) + expectedKeys := []Key{{ID: 1}, {ID: 2}} + if !reflect.DeepEqual(keys, expectedKeys) { + t.Errorf("Keys.List returned keys %+v, expected %+v", keys, expectedKeys) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Keys.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/kubernetes.go b/kubernetes.go index 35fcd19a..a43a8dd0 100644 --- a/kubernetes.go +++ b/kubernetes.go @@ -354,6 +354,7 @@ type KubernetesRegion struct { type kubernetesClustersRoot struct { Clusters []*KubernetesCluster `json:"kubernetes_clusters,omitempty"` Links *Links `json:"links,omitempty"` + Meta *Meta `json:"meta"` } type kubernetesClusterRoot struct { @@ -469,6 +470,14 @@ func (svc *KubernetesServiceOp) List(ctx context.Context, opts *ListOptions) ([] if err != nil { return nil, resp, err } + + if l := root.Links; l != nil { + resp.Links = l + } + if m := root.Meta; m != nil { + resp.Meta = m + } + return root.Clusters, resp, nil } diff --git a/kubernetes_test.go b/kubernetes_test.go index 1d9471c5..1a22e17e 100644 --- a/kubernetes_test.go +++ b/kubernetes_test.go @@ -4,6 +4,7 @@ import ( "bytes" "encoding/json" "fmt" + "github.com/stretchr/testify/assert" "net/http" "testing" "time" @@ -17,7 +18,7 @@ func TestKubernetesClusters_ListClusters(t *testing.T) { kubeSvc := client.Kubernetes - want := []*KubernetesCluster{ + wantClusters := []*KubernetesCluster{ &KubernetesCluster{ ID: "8d91899c-0739-4a1a-acc5-deadbeefbb8f", Name: "blablabla", @@ -201,7 +202,16 @@ func TestKubernetesClusters_ListClusters(t *testing.T) { "created_at": "2018-06-15T07:10:23Z", "updated_at": "2018-06-15T07:11:26Z" } - ] + ], + "links": { + "pages": { + "next": "https://api.digitalocean.com/v2/kubernetes/clusters?page=2", + "last": "https://api.digitalocean.com/v2/kubernetes/clusters?page=2" + } + }, + "meta": { + "total": 2 + } }` mux.HandleFunc("/v2/kubernetes/clusters", func(w http.ResponseWriter, r *http.Request) { @@ -209,9 +219,24 @@ func TestKubernetesClusters_ListClusters(t *testing.T) { fmt.Fprint(w, jBlob) }) - got, _, err := kubeSvc.List(ctx, nil) + gotClusters, resp, err := kubeSvc.List(ctx, nil) require.NoError(t, err) - require.Equal(t, want, got) + assert.Equal(t, wantClusters, gotClusters) + + gotRespLinks := resp.Links + wantRespLinks := &Links{ + Pages: &Pages{ + Next: "https://api.digitalocean.com/v2/kubernetes/clusters?page=2", + Last: "https://api.digitalocean.com/v2/kubernetes/clusters?page=2", + }, + } + assert.Equal(t, wantRespLinks, gotRespLinks) + + gotRespMeta := resp.Meta + wantRespMeta := &Meta{ + Total: 2, + } + assert.Equal(t, wantRespMeta, gotRespMeta) } func TestKubernetesClusters_Get(t *testing.T) { diff --git a/load_balancers.go b/load_balancers.go index c565e229..b5c1731b 100644 --- a/load_balancers.go +++ b/load_balancers.go @@ -167,6 +167,7 @@ func (l dropletIDsRequest) String() string { type loadBalancersRoot struct { LoadBalancers []LoadBalancer `json:"load_balancers"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type loadBalancerRoot struct { @@ -218,6 +219,9 @@ func (l *LoadBalancersServiceOp) List(ctx context.Context, opt *ListOptions) ([] if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.LoadBalancers, resp, err } diff --git a/load_balancers_test.go b/load_balancers_test.go index 96c77a7e..16d9a43a 100644 --- a/load_balancers_test.go +++ b/load_balancers_test.go @@ -563,13 +563,13 @@ func TestLoadBalancers_List(t *testing.T) { fmt.Fprint(w, lbListJSONResponse) }) - loadBalancers, _, err := client.LoadBalancers.List(ctx, nil) + loadBalancers, resp, err := client.LoadBalancers.List(ctx, nil) if err != nil { t.Errorf("LoadBalancers.List returned error: %v", err) } - expected := []LoadBalancer{ + expectedLBs := []LoadBalancer{ { ID: "37e6be88-01ec-4ec7-9bc6-a514d4719057", Name: "example-lb-01", @@ -611,7 +611,10 @@ func TestLoadBalancers_List(t *testing.T) { }, } - assert.Equal(t, expected, loadBalancers) + assert.Equal(t, expectedLBs, loadBalancers) + + expectedMeta := &Meta{Total: 3} + assert.Equal(t, expectedMeta, resp.Meta) } func TestLoadBalancers_List_Pagination(t *testing.T) { diff --git a/projects.go b/projects.go index 02ca0211..172c2c9e 100644 --- a/projects.go +++ b/projects.go @@ -125,6 +125,7 @@ type ProjectResourceLinks struct { type projectsRoot struct { Projects []Project `json:"projects"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type projectRoot struct { @@ -134,6 +135,7 @@ type projectRoot struct { type projectResourcesRoot struct { Resources []ProjectResource `json:"resources"` Links *Links `json:"links,omitempty"` + Meta *Meta `json:"meta"` } var _ ProjectsService = &ProjectsServiceOp{} @@ -158,6 +160,9 @@ func (p *ProjectsServiceOp) List(ctx context.Context, opts *ListOptions) ([]Proj if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Projects, resp, err } @@ -238,6 +243,9 @@ func (p *ProjectsServiceOp) ListResources(ctx context.Context, projectID string, if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Resources, resp, err } diff --git a/projects_test.go b/projects_test.go index aeefd9c9..62c08183 100644 --- a/projects_test.go +++ b/projects_test.go @@ -14,7 +14,7 @@ func TestProjects_List(t *testing.T) { setup() defer teardown() - projects := []Project{ + expectedProjects := []Project{ { ID: "project-1", Name: "project-1", @@ -27,17 +27,22 @@ func TestProjects_List(t *testing.T) { mux.HandleFunc("/v2/projects", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - resp, _ := json.Marshal(projects) - fmt.Fprint(w, fmt.Sprintf(`{"projects":%s}`, string(resp))) + resp, _ := json.Marshal(expectedProjects) + fmt.Fprint(w, fmt.Sprintf(`{"projects":%s, "meta": {"total": 2}}`, string(resp))) }) - resp, _, err := client.Projects.List(ctx, nil) + projects, resp, err := client.Projects.List(ctx, nil) if err != nil { t.Errorf("Projects.List returned error: %v", err) } - if !reflect.DeepEqual(resp, projects) { - t.Errorf("Projects.List returned %+v, expected %+v", resp, projects) + if !reflect.DeepEqual(projects, expectedProjects) { + t.Errorf("Projects.List returned projects %+v, expected %+v", projects, expectedProjects) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Projects.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } @@ -315,7 +320,7 @@ func TestProjects_ListResources(t *testing.T) { setup() defer teardown() - resources := []ProjectResource{ + expectedResources := []ProjectResource{ { URN: "do:droplet:1", AssignedAt: "2018-09-27 00:00:00", @@ -334,17 +339,22 @@ func TestProjects_ListResources(t *testing.T) { mux.HandleFunc("/v2/projects/project-1/resources", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - resp, _ := json.Marshal(resources) - fmt.Fprint(w, fmt.Sprintf(`{"resources":%s}`, string(resp))) + resp, _ := json.Marshal(expectedResources) + fmt.Fprint(w, fmt.Sprintf(`{"resources":%s, "meta": {"total": 2}}`, string(resp))) }) - resp, _, err := client.Projects.ListResources(ctx, "project-1", nil) + resources, resp, err := client.Projects.ListResources(ctx, "project-1", nil) if err != nil { t.Errorf("Projects.List returned error: %v", err) } - if !reflect.DeepEqual(resp, resources) { - t.Errorf("Projects.ListResources returned %+v, expected %+v", resp, resources) + if !reflect.DeepEqual(resources, expectedResources) { + t.Errorf("Projects.ListResources returned resources %+v, expected %+v", resources, expectedResources) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Projects.ListResources returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/regions.go b/regions.go index 409959d9..b07175e8 100644 --- a/regions.go +++ b/regions.go @@ -32,6 +32,7 @@ type Region struct { type regionsRoot struct { Regions []Region Links *Links `json:"links"` + Meta *Meta `json:"meta"` } func (r Region) String() string { @@ -59,6 +60,9 @@ func (s *RegionsServiceOp) List(ctx context.Context, opt *ListOptions) ([]Region if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Regions, resp, err } diff --git a/regions_test.go b/regions_test.go index 9f008a44..2a97390f 100644 --- a/regions_test.go +++ b/regions_test.go @@ -13,17 +13,34 @@ func TestRegions_List(t *testing.T) { mux.HandleFunc("/v2/regions", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"regions":[{"slug":"1"},{"slug":"2"}]}`) + fmt.Fprint(w, `{ + "regions": [ + { + "slug": "1" + }, + { + "slug": "2" + } + ], + "meta": { + "total": 2 + } + }`) }) - regions, _, err := client.Regions.List(ctx, nil) + regions, resp, err := client.Regions.List(ctx, nil) if err != nil { t.Errorf("Regions.List returned error: %v", err) } - expected := []Region{{Slug: "1"}, {Slug: "2"}} - if !reflect.DeepEqual(regions, expected) { - t.Errorf("Regions.List returned %+v, expected %+v", regions, expected) + expectedRegions := []Region{{Slug: "1"}, {Slug: "2"}} + if !reflect.DeepEqual(regions, expectedRegions) { + t.Errorf("Regions.List returned regions %+v, expected %+v", regions, expectedRegions) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Regions.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/sizes.go b/sizes.go index da8207c0..d2b93ea7 100644 --- a/sizes.go +++ b/sizes.go @@ -40,6 +40,7 @@ func (s Size) String() string { type sizesRoot struct { Sizes []Size Links *Links `json:"links"` + Meta *Meta `json:"meta"` } // List all images @@ -63,6 +64,9 @@ func (s *SizesServiceOp) List(ctx context.Context, opt *ListOptions) ([]Size, *R if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Sizes, resp, err } diff --git a/sizes_test.go b/sizes_test.go index 053db7b1..5c6bdd3e 100644 --- a/sizes_test.go +++ b/sizes_test.go @@ -13,17 +13,34 @@ func TestSizes_List(t *testing.T) { mux.HandleFunc("/v2/sizes", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprint(w, `{"sizes":[{"slug":"1"},{"slug":"2"}]}`) + fmt.Fprint(w, `{ + "sizes": [ + { + "slug": "1" + }, + { + "slug": "2" + } + ], + "meta": { + "total": 2 + } + }`) }) - sizes, _, err := client.Sizes.List(ctx, nil) + sizes, resp, err := client.Sizes.List(ctx, nil) if err != nil { t.Errorf("Sizes.List returned error: %v", err) } - expected := []Size{{Slug: "1"}, {Slug: "2"}} - if !reflect.DeepEqual(sizes, expected) { - t.Errorf("Sizes.List returned %+v, expected %+v", sizes, expected) + expectedSizes := []Size{{Slug: "1"}, {Slug: "2"}} + if !reflect.DeepEqual(sizes, expectedSizes) { + t.Errorf("Sizes.List returned sizes %+v, expected %+v", sizes, expectedSizes) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Sizes.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/storage_actions.go b/storage_actions.go index 94889756..234aba90 100644 --- a/storage_actions.go +++ b/storage_actions.go @@ -120,6 +120,9 @@ func (s *StorageActionsServiceOp) list(ctx context.Context, path string) ([]Acti if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Actions, resp, err } diff --git a/storage_actions_test.go b/storage_actions_test.go index c22f7add..c04c19c0 100644 --- a/storage_actions_test.go +++ b/storage_actions_test.go @@ -102,17 +102,31 @@ func TestStorageActions_List(t *testing.T) { mux.HandleFunc("/v2/volumes/"+volumeID+"/actions", func(w http.ResponseWriter, r *http.Request) { testMethod(t, r, http.MethodGet) - fmt.Fprintf(w, `{"actions":[{"status":"in-progress"}]}`) + fmt.Fprintf(w, `{ + "actions": [ + { + "status": "in-progress" + } + ], + "meta": { + "total": 1 + } + }`) }) - actions, _, err := client.StorageActions.List(ctx, volumeID, nil) + actions, resp, err := client.StorageActions.List(ctx, volumeID, nil) if err != nil { t.Errorf("StorageActions.List returned error: %v", err) } - expected := []Action{{Status: "in-progress"}} - if !reflect.DeepEqual(actions, expected) { - t.Errorf("StorageActions.List returned %+v, expected %+v", actions, expected) + expectedActions := []Action{{Status: "in-progress"}} + if !reflect.DeepEqual(actions, expectedActions) { + t.Errorf("StorageActions.List returned actions %+v, expected %+v", actions, expectedActions) + } + + expectedMeta := &Meta{Total: 1} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("StorageActions.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/tags.go b/tags.go index e2caecf8..6301e15f 100644 --- a/tags.go +++ b/tags.go @@ -113,6 +113,7 @@ type UntagResourcesRequest struct { type tagsRoot struct { Tags []Tag `json:"tags"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } type tagRoot struct { @@ -141,6 +142,9 @@ func (s *TagsServiceOp) List(ctx context.Context, opt *ListOptions) ([]Tag, *Res if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.Tags, resp, err } diff --git a/tags_test.go b/tags_test.go index 5fce8ad8..1a75799b 100644 --- a/tags_test.go +++ b/tags_test.go @@ -231,17 +231,22 @@ func TestTags_List(t *testing.T) { fmt.Fprint(w, listJSON) }) - tags, _, err := client.Tags.List(ctx, nil) + tags, resp, err := client.Tags.List(ctx, nil) if err != nil { t.Errorf("Tags.List returned error: %v", err) } - expected := []Tag{ + expectedTags := []Tag{ {Name: "testing-1", Resources: &TaggedResources{Count: 0, Droplets: &TaggedDropletsResources{Count: 0, LastTagged: nil}, Images: &TaggedImagesResources{Count: 0}, Volumes: &TaggedVolumesResources{Count: 0}, VolumeSnapshots: &TaggedVolumeSnapshotsResources{Count: 0}, Databases: &TaggedDatabasesResources{Count: 0}}}, {Name: "testing-2", Resources: &TaggedResources{Count: 0, Droplets: &TaggedDropletsResources{Count: 0, LastTagged: nil}, Images: &TaggedImagesResources{Count: 0}, Volumes: &TaggedVolumesResources{Count: 0}, VolumeSnapshots: &TaggedVolumeSnapshotsResources{Count: 0}, Databases: &TaggedDatabasesResources{Count: 0}}}, } - if !reflect.DeepEqual(tags, expected) { - t.Errorf("Tags.List returned %+v, expected %+v", tags, expected) + if !reflect.DeepEqual(tags, expectedTags) { + t.Errorf("Tags.List returned tags %+v, expected %+v", tags, expectedTags) + } + + expectedMeta := &Meta{Total: 2} + if !reflect.DeepEqual(resp.Meta, expectedMeta) { + t.Errorf("Tags.List returned meta %+v, expected %+v", resp.Meta, expectedMeta) } } diff --git a/vpcs.go b/vpcs.go index 24752d37..f2aba8e6 100644 --- a/vpcs.go +++ b/vpcs.go @@ -63,6 +63,7 @@ type vpcRoot struct { type vpcsRoot struct { VPCs []*VPC `json:"vpcs"` Links *Links `json:"links"` + Meta *Meta `json:"meta"` } // Get returns the details of a Virtual Private Cloud. @@ -118,6 +119,9 @@ func (v *VPCsServiceOp) List(ctx context.Context, opt *ListOptions) ([]*VPC, *Re if l := root.Links; l != nil { resp.Links = l } + if m := root.Meta; m != nil { + resp.Meta = m + } return root.VPCs, resp, nil } diff --git a/vpcs_test.go b/vpcs_test.go index 2d325a63..791dcf3e 100644 --- a/vpcs_test.go +++ b/vpcs_test.go @@ -3,6 +3,7 @@ package godo import ( "encoding/json" "fmt" + "github.com/stretchr/testify/assert" "net/http" "testing" "time" @@ -68,6 +69,9 @@ func TestVPCs_List(t *testing.T) { Next: "http://localhost/v2/vpcs?page=2&per_page=1", }, } + meta := &Meta{ + Total: 3, + } jsonBlob := ` { "vpcs": [ @@ -89,8 +93,9 @@ func TestVPCs_List(t *testing.T) { got, resp, err := svc.List(ctx, nil) require.NoError(t, err) - require.Equal(t, want, got) - require.Equal(t, resp.Links, links) + assert.Equal(t, want, got) + assert.Equal(t, resp.Links, links) + assert.Equal(t, resp.Meta, meta) } func TestVPCs_Create(t *testing.T) {