blob: f5906fac409859e77a9379dd3606f7a6315c0098 [file] [log] [blame]
Jamie Hannaford89f9af22014-09-17 12:21:48 +02001package subnets
Jamie Hannaford0708c002014-09-17 16:08:49 +02002
3import (
Krzysztof Szukiełojć3f41d082017-05-07 14:43:06 +02004 "gerrit.mcp.mirantis.net/debian/gophercloud.git"
Krzysztof Szukiełojć24a29ce2017-05-07 14:24:02 +02005 "gerrit.mcp.mirantis.net/debian/gophercloud.git/pagination"
Jamie Hannaford0708c002014-09-17 16:08:49 +02006)
7
Jon Perritt04851d32014-10-14 02:07:13 -05008// ListOptsBuilder allows extensions to add additional parameters to the
9// List request.
10type ListOptsBuilder interface {
Jon Perritt26780d52014-10-14 11:35:58 -050011 ToSubnetListQuery() (string, error)
Jon Perritt04851d32014-10-14 02:07:13 -050012}
13
Jamie Hannaford686c4962014-09-23 10:46:20 +020014// ListOpts allows the filtering and sorting of paginated collections through
15// the API. Filtering is achieved by passing in struct field values that map to
16// the subnet attributes you want to see returned. SortKey allows you to sort
17// by a particular subnet attribute. SortDir sets the direction, and is either
18// `asc' or `desc'. Marker and Limit are used for pagination.
Jamie Hannaford0708c002014-09-17 16:08:49 +020019type ListOpts struct {
Krzysztof Szukiełojć718e5c42017-05-09 11:34:47 +020020 Name string `q:"name"`
21 EnableDHCP *bool `q:"enable_dhcp"`
22 NetworkID string `q:"network_id"`
23 TenantID string `q:"tenant_id"`
24 IPVersion int `q:"ip_version"`
25 GatewayIP string `q:"gateway_ip"`
26 CIDR string `q:"cidr"`
27 ID string `q:"id"`
28 Limit int `q:"limit"`
29 Marker string `q:"marker"`
30 SortKey string `q:"sort_key"`
31 SortDir string `q:"sort_dir"`
32 Fields []string `q:"fields"`
Jamie Hannaford0708c002014-09-17 16:08:49 +020033}
34
Jon Perritt26780d52014-10-14 11:35:58 -050035// ToSubnetListQuery formats a ListOpts into a query string.
36func (opts ListOpts) ToSubnetListQuery() (string, error) {
Jon Perritt04851d32014-10-14 02:07:13 -050037 q, err := gophercloud.BuildQueryString(opts)
Jon Perritte1c6ceb2016-03-14 12:09:36 -050038 return q.String(), err
Jon Perritt04851d32014-10-14 02:07:13 -050039}
40
Jamie Hannaford686c4962014-09-23 10:46:20 +020041// List returns a Pager which allows you to iterate over a collection of
42// subnets. It accepts a ListOpts struct, which allows you to filter and sort
43// the returned collection for greater efficiency.
44//
45// Default policy settings return only those subnets that are owned by the tenant
Alex Gaynora6d5f9f2014-10-27 10:52:32 -070046// who submits the request, unless the request is submitted by a user with
Jamie Hannaford686c4962014-09-23 10:46:20 +020047// administrative rights.
Jon Perritt04851d32014-10-14 02:07:13 -050048func List(c *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
49 url := listURL(c)
50 if opts != nil {
Jon Perritt26780d52014-10-14 11:35:58 -050051 query, err := opts.ToSubnetListQuery()
Jon Perritt04851d32014-10-14 02:07:13 -050052 if err != nil {
53 return pagination.Pager{Err: err}
54 }
55 url += query
Jamie Hannaford92523e32014-10-02 11:08:36 +020056 }
Ash Wilsonb8b16f82014-10-20 10:19:49 -040057 return pagination.NewPager(c, url, func(r pagination.PageResult) pagination.Page {
58 return SubnetPage{pagination.LinkedPageBase{PageResult: r}}
Jamie Hannaford0708c002014-09-17 16:08:49 +020059 })
60}
61
Jamie Hannaford686c4962014-09-23 10:46:20 +020062// Get retrieves a specific subnet based on its unique ID.
Jon Perritt3860b512016-03-29 12:01:48 -050063func Get(c *gophercloud.ServiceClient, id string) (r GetResult) {
Jon Perritte1c6ceb2016-03-14 12:09:36 -050064 _, r.Err = c.Get(getURL(c, id), &r.Body, nil)
jrperritt29ae6b32016-04-13 12:59:37 -050065 return
Jamie Hannaford0708c002014-09-17 16:08:49 +020066}
Jamie Hannaford63631432014-09-18 11:40:09 +020067
Jon Perritt04851d32014-10-14 02:07:13 -050068// CreateOptsBuilder is the interface options structs have to satisfy in order
69// to be used in the main Create operation in this package. Since many
70// extensions decorate or modify the common logic, it is useful for them to
71// satisfy a basic interface in order for them to be used.
72type CreateOptsBuilder interface {
73 ToSubnetCreateMap() (map[string]interface{}, error)
74}
75
Jamie Hannaford686c4962014-09-23 10:46:20 +020076// CreateOpts represents the attributes used when creating a new subnet.
Jamie Hannaford965ae702014-09-22 14:58:19 +020077type CreateOpts struct {
jrperrittbc548612016-04-13 17:03:59 -050078 NetworkID string `json:"network_id" required:"true"`
79 CIDR string `json:"cidr" required:"true"`
80 Name string `json:"name,omitempty"`
81 TenantID string `json:"tenant_id,omitempty"`
82 AllocationPools []AllocationPool `json:"allocation_pools,omitempty"`
Joe Topjian19e713b2016-10-06 10:10:24 -060083 GatewayIP *string `json:"gateway_ip,omitempty"`
jrperrittbc548612016-04-13 17:03:59 -050084 IPVersion gophercloud.IPVersion `json:"ip_version,omitempty"`
85 EnableDHCP *bool `json:"enable_dhcp,omitempty"`
86 DNSNameservers []string `json:"dns_nameservers,omitempty"`
87 HostRoutes []HostRoute `json:"host_routes,omitempty"`
Jamie Hannaford63631432014-09-18 11:40:09 +020088}
89
Jon Perritt04851d32014-10-14 02:07:13 -050090// ToSubnetCreateMap casts a CreateOpts struct to a map.
91func (opts CreateOpts) ToSubnetCreateMap() (map[string]interface{}, error) {
Joe Topjian19e713b2016-10-06 10:10:24 -060092 b, err := gophercloud.BuildRequestBody(opts, "subnet")
93 if err != nil {
94 return nil, err
95 }
96
97 if m := b["subnet"].(map[string]interface{}); m["gateway_ip"] == "" {
98 m["gateway_ip"] = nil
99 }
100
101 return b, nil
Jon Perritt04851d32014-10-14 02:07:13 -0500102}
103
104// Create accepts a CreateOpts struct and creates a new subnet using the values
105// provided. You must remember to provide a valid NetworkID, CIDR and IP version.
Jon Perritt3860b512016-03-29 12:01:48 -0500106func Create(c *gophercloud.ServiceClient, opts CreateOptsBuilder) (r CreateResult) {
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500107 b, err := opts.ToSubnetCreateMap()
Jon Perritt04851d32014-10-14 02:07:13 -0500108 if err != nil {
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500109 r.Err = err
Jon Perritt3860b512016-03-29 12:01:48 -0500110 return
Jamie Hannaford965ae702014-09-22 14:58:19 +0200111 }
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500112 _, r.Err = c.Post(createURL(c), b, &r.Body, nil)
jrperritt29ae6b32016-04-13 12:59:37 -0500113 return
Jamie Hannaford63631432014-09-18 11:40:09 +0200114}
Jamie Hannafordd11e20c2014-09-18 12:03:01 +0200115
Jon Perritt04851d32014-10-14 02:07:13 -0500116// UpdateOptsBuilder allows extensions to add additional parameters to the
117// Update request.
118type UpdateOptsBuilder interface {
119 ToSubnetUpdateMap() (map[string]interface{}, error)
120}
121
Jamie Hannaford686c4962014-09-23 10:46:20 +0200122// UpdateOpts represents the attributes used when updating an existing subnet.
Jamie Hannaford965ae702014-09-22 14:58:19 +0200123type UpdateOpts struct {
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500124 Name string `json:"name,omitempty"`
Joe Topjian19e713b2016-10-06 10:10:24 -0600125 GatewayIP *string `json:"gateway_ip,omitempty"`
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500126 DNSNameservers []string `json:"dns_nameservers,omitempty"`
127 HostRoutes []HostRoute `json:"host_routes,omitempty"`
128 EnableDHCP *bool `json:"enable_dhcp,omitempty"`
Jamie Hannaford965ae702014-09-22 14:58:19 +0200129}
Jamie Hannafordd11e20c2014-09-18 12:03:01 +0200130
Jon Perritt04851d32014-10-14 02:07:13 -0500131// ToSubnetUpdateMap casts an UpdateOpts struct to a map.
132func (opts UpdateOpts) ToSubnetUpdateMap() (map[string]interface{}, error) {
Joe Topjian19e713b2016-10-06 10:10:24 -0600133 b, err := gophercloud.BuildRequestBody(opts, "subnet")
134 if err != nil {
135 return nil, err
136 }
137
138 if m := b["subnet"].(map[string]interface{}); m["gateway_ip"] == "" {
139 m["gateway_ip"] = nil
140 }
141
142 return b, nil
Jon Perritt04851d32014-10-14 02:07:13 -0500143}
144
Jamie Hannaford686c4962014-09-23 10:46:20 +0200145// Update accepts a UpdateOpts struct and updates an existing subnet using the
146// values provided.
Jon Perritt3860b512016-03-29 12:01:48 -0500147func Update(c *gophercloud.ServiceClient, id string, opts UpdateOptsBuilder) (r UpdateResult) {
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500148 b, err := opts.ToSubnetUpdateMap()
Jon Perritt04851d32014-10-14 02:07:13 -0500149 if err != nil {
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500150 r.Err = err
Jon Perritt3860b512016-03-29 12:01:48 -0500151 return
Jon Perritt04851d32014-10-14 02:07:13 -0500152 }
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500153 _, r.Err = c.Put(updateURL(c, id), b, &r.Body, &gophercloud.RequestOpts{
Jamie Hannaford059e1502015-03-24 16:20:32 +0100154 OkCodes: []int{200, 201},
Jamie Hannafordd11e20c2014-09-18 12:03:01 +0200155 })
jrperritt29ae6b32016-04-13 12:59:37 -0500156 return
Jamie Hannafordd11e20c2014-09-18 12:03:01 +0200157}
158
Jamie Hannaford686c4962014-09-23 10:46:20 +0200159// Delete accepts a unique ID and deletes the subnet associated with it.
Jon Perritt3860b512016-03-29 12:01:48 -0500160func Delete(c *gophercloud.ServiceClient, id string) (r DeleteResult) {
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500161 _, r.Err = c.Delete(deleteURL(c, id), nil)
jrperritt29ae6b32016-04-13 12:59:37 -0500162 return
Jamie Hannafordd11e20c2014-09-18 12:03:01 +0200163}
Jon Perritt7ab13282015-06-28 18:47:19 -0600164
jrperritt5d1d8352015-06-28 19:08:09 -0600165// IDFromName is a convenience function that returns a subnet's ID given its name.
Jon Perritt7ab13282015-06-28 18:47:19 -0600166func IDFromName(client *gophercloud.ServiceClient, name string) (string, error) {
Jon Perritte3cb7e42016-03-07 06:24:11 -0600167 count := 0
168 id := ""
Jon Perritte3cb7e42016-03-07 06:24:11 -0600169 pages, err := List(client, nil).AllPages()
170 if err != nil {
171 return "", err
172 }
Jon Perritt7ab13282015-06-28 18:47:19 -0600173
Jon Perritte3cb7e42016-03-07 06:24:11 -0600174 all, err := ExtractSubnets(pages)
175 if err != nil {
176 return "", err
177 }
178
179 for _, s := range all {
180 if s.Name == name {
181 count++
182 id = s.ID
183 }
184 }
185
186 switch count {
Jon Perritt7ab13282015-06-28 18:47:19 -0600187 case 0:
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500188 return "", gophercloud.ErrResourceNotFound{Name: name, ResourceType: "subnet"}
Jon Perritt7ab13282015-06-28 18:47:19 -0600189 case 1:
Jon Perritte3cb7e42016-03-07 06:24:11 -0600190 return id, nil
Jon Perritt7ab13282015-06-28 18:47:19 -0600191 default:
Jon Perritte1c6ceb2016-03-14 12:09:36 -0500192 return "", gophercloud.ErrMultipleResourcesFound{Name: name, Count: count, ResourceType: "subnet"}
Jon Perritt7ab13282015-06-28 18:47:19 -0600193 }
194}