blob: 48ff6983a604387aba81b1d30d8407843497095c [file] [log] [blame]
Jamie Hannaford924c09d2014-11-19 12:05:38 +01001package secgroups
2
3import (
Jon Perritt27249f42016-02-18 10:35:59 -06004 "github.com/gophercloud/gophercloud"
5 "github.com/gophercloud/gophercloud/pagination"
Jamie Hannaford924c09d2014-11-19 12:05:38 +01006)
7
Jamie Hannaford19151792014-11-19 12:46:47 +01008func commonList(client *gophercloud.ServiceClient, url string) pagination.Pager {
Jon Perrittdb0ae142016-03-13 00:33:41 -06009 return pagination.NewPager(client, url, func(r pagination.PageResult) pagination.Page {
Jamie Hannaford924c09d2014-11-19 12:05:38 +010010 return SecurityGroupPage{pagination.SinglePageBase(r)}
Jon Perrittdb0ae142016-03-13 00:33:41 -060011 })
Jamie Hannaford19151792014-11-19 12:46:47 +010012}
13
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010014// List will return a collection of all the security groups for a particular
15// tenant.
Jamie Hannaford19151792014-11-19 12:46:47 +010016func List(client *gophercloud.ServiceClient) pagination.Pager {
17 return commonList(client, rootURL(client))
18}
19
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010020// ListByServer will return a collection of all the security groups which are
21// associated with a particular server.
Jamie Hannaford19151792014-11-19 12:46:47 +010022func ListByServer(client *gophercloud.ServiceClient, serverID string) pagination.Pager {
23 return commonList(client, listByServerURL(client, serverID))
Jamie Hannaford924c09d2014-11-19 12:05:38 +010024}
Jamie Hannaforda493e642014-11-19 12:40:30 +010025
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010026// GroupOpts is the underlying struct responsible for creating or updating
27// security groups. It therefore represents the mutable attributes of a
28// security group.
Jamie Hannaford30c74662014-11-19 15:37:34 +010029type GroupOpts struct {
Jon Perrittdb0ae142016-03-13 00:33:41 -060030 // the name of your security group.
31 Name string `json:"name" required:"true"`
32 // the description of your security group.
33 Description string `json:"description" required:"true"`
Jamie Hannaforda493e642014-11-19 12:40:30 +010034}
35
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010036// CreateOpts is the struct responsible for creating a security group.
Jamie Hannaford30c74662014-11-19 15:37:34 +010037type CreateOpts GroupOpts
38
Jamie Hannaford04abbc72014-11-21 11:27:57 +010039// CreateOptsBuilder builds the create options into a serializable format.
40type CreateOptsBuilder interface {
41 ToSecGroupCreateMap() (map[string]interface{}, error)
42}
43
44// ToSecGroupCreateMap builds the create options into a serializable format.
45func (opts CreateOpts) ToSecGroupCreateMap() (map[string]interface{}, error) {
Jon Perrittdb0ae142016-03-13 00:33:41 -060046 return gophercloud.BuildRequestBody(opts, "security_group")
Jamie Hannaford04abbc72014-11-21 11:27:57 +010047}
48
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010049// Create will create a new security group.
Jamie Hannaford04abbc72014-11-21 11:27:57 +010050func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
Jon Perrittdb0ae142016-03-13 00:33:41 -060051 var r CreateResult
52 b, err := opts.ToSecGroupCreateMap()
Jamie Hannaford04abbc72014-11-21 11:27:57 +010053 if err != nil {
Jon Perrittdb0ae142016-03-13 00:33:41 -060054 r.Err = err
55 return r
Jamie Hannaford04abbc72014-11-21 11:27:57 +010056 }
Jon Perrittdb0ae142016-03-13 00:33:41 -060057 _, r.Err = client.Post(rootURL(client), b, &r.Body, &gophercloud.RequestOpts{
Jamie Hannaford6a3a78f2015-03-24 14:56:12 +010058 OkCodes: []int{200},
Jamie Hannaforda493e642014-11-19 12:40:30 +010059 })
Jon Perrittdb0ae142016-03-13 00:33:41 -060060 return r
Jamie Hannaforda493e642014-11-19 12:40:30 +010061}
Jamie Hannafordb38dd312014-11-19 13:02:11 +010062
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010063// UpdateOpts is the struct responsible for updating an existing security group.
Jamie Hannaford30c74662014-11-19 15:37:34 +010064type UpdateOpts GroupOpts
65
Jamie Hannaford04abbc72014-11-21 11:27:57 +010066// UpdateOptsBuilder builds the update options into a serializable format.
67type UpdateOptsBuilder interface {
68 ToSecGroupUpdateMap() (map[string]interface{}, error)
69}
70
71// ToSecGroupUpdateMap builds the update options into a serializable format.
72func (opts UpdateOpts) ToSecGroupUpdateMap() (map[string]interface{}, error) {
Jon Perrittdb0ae142016-03-13 00:33:41 -060073 return gophercloud.BuildRequestBody(opts, "security_group")
Jamie Hannaford04abbc72014-11-21 11:27:57 +010074}
75
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010076// Update will modify the mutable properties of a security group, notably its
77// name and description.
Jamie Hannaford2f226172014-11-25 11:52:25 +010078func Update(client *gophercloud.ServiceClient, id string, opts UpdateOptsBuilder) UpdateResult {
Jon Perrittdb0ae142016-03-13 00:33:41 -060079 var r UpdateResult
80 b, err := opts.ToSecGroupUpdateMap()
Jamie Hannaford04abbc72014-11-21 11:27:57 +010081 if err != nil {
Jon Perrittdb0ae142016-03-13 00:33:41 -060082 r.Err = err
83 return r
Jamie Hannaford04abbc72014-11-21 11:27:57 +010084 }
Jon Perrittdb0ae142016-03-13 00:33:41 -060085 _, r.Err = client.Put(resourceURL(client, id), b, &r.Body, &gophercloud.RequestOpts{
Jamie Hannaford6a3a78f2015-03-24 14:56:12 +010086 OkCodes: []int{200},
Jamie Hannaford30c74662014-11-19 15:37:34 +010087 })
Jon Perrittdb0ae142016-03-13 00:33:41 -060088 return r
Jamie Hannaford30c74662014-11-19 15:37:34 +010089}
90
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010091// Get will return details for a particular security group.
Jamie Hannaford2f226172014-11-25 11:52:25 +010092func Get(client *gophercloud.ServiceClient, id string) GetResult {
Jon Perrittdb0ae142016-03-13 00:33:41 -060093 var r GetResult
94 _, r.Err = client.Get(resourceURL(client, id), &r.Body, nil)
95 return r
Jamie Hannafordb38dd312014-11-19 13:02:11 +010096}
Jamie Hannafordd276e612014-11-19 13:56:28 +010097
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +010098// Delete will permanently delete a security group from the project.
Jamie Hannaford2f226172014-11-25 11:52:25 +010099func Delete(client *gophercloud.ServiceClient, id string) gophercloud.ErrResult {
Jon Perrittdb0ae142016-03-13 00:33:41 -0600100 var r gophercloud.ErrResult
101 _, r.Err = client.Delete(resourceURL(client, id), nil)
102 return r
Jamie Hannafordd276e612014-11-19 13:56:28 +0100103}
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100104
Jamie Hannaford04abbc72014-11-21 11:27:57 +0100105// CreateRuleOpts represents the configuration for adding a new rule to an
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +0100106// existing security group.
Jamie Hannaford04abbc72014-11-21 11:27:57 +0100107type CreateRuleOpts struct {
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100108 // Required - the ID of the group that this rule will be added to.
Jon Perrittdb0ae142016-03-13 00:33:41 -0600109 ParentGroupID string `json:"parent_group_id" required:"true"`
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100110 // Required - the lower bound of the port range that will be opened.
Jon Perrittdb0ae142016-03-13 00:33:41 -0600111 FromPort int `json:"from_port" required:"true"`
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100112 // Required - the upper bound of the port range that will be opened.
Jon Perrittdb0ae142016-03-13 00:33:41 -0600113 ToPort int `json:"to_port" required:"true"`
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100114 // Required - the protocol type that will be allowed, e.g. TCP.
Jon Perrittdb0ae142016-03-13 00:33:41 -0600115 IPProtocol string `json:"ip_protocol" required:"true"`
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100116 // ONLY required if FromGroupID is blank. This represents the IP range that
117 // will be the source of network traffic to your security group. Use
118 // 0.0.0.0/0 to allow all IP addresses.
119 CIDR string `json:"cidr,omitempty"`
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100120 // ONLY required if CIDR is blank. This value represents the ID of a group
121 // that forwards traffic to the parent group. So, instead of accepting
122 // network traffic from an entire IP range, you can instead refine the
123 // inbound source by an existing security group.
124 FromGroupID string `json:"group_id,omitempty"`
125}
126
Jamie Hannaford04abbc72014-11-21 11:27:57 +0100127// CreateRuleOptsBuilder builds the create rule options into a serializable format.
128type CreateRuleOptsBuilder interface {
129 ToRuleCreateMap() (map[string]interface{}, error)
130}
131
132// ToRuleCreateMap builds the create rule options into a serializable format.
133func (opts CreateRuleOpts) ToRuleCreateMap() (map[string]interface{}, error) {
Jon Perrittdb0ae142016-03-13 00:33:41 -0600134 return gophercloud.BuildRequestBody(opts, "security_group_rule")
Jamie Hannaford04abbc72014-11-21 11:27:57 +0100135}
136
137// CreateRule will add a new rule to an existing security group (whose ID is
138// specified in CreateRuleOpts). You have the option of controlling inbound
139// traffic from either an IP range (CIDR) or from another security group.
140func CreateRule(client *gophercloud.ServiceClient, opts CreateRuleOptsBuilder) CreateRuleResult {
Jon Perrittdb0ae142016-03-13 00:33:41 -0600141 var r CreateRuleResult
142 b, err := opts.ToRuleCreateMap()
Jamie Hannaford04abbc72014-11-21 11:27:57 +0100143 if err != nil {
Jon Perrittdb0ae142016-03-13 00:33:41 -0600144 r.Err = err
145 return r
Jamie Hannaford04abbc72014-11-21 11:27:57 +0100146 }
Jon Perrittdb0ae142016-03-13 00:33:41 -0600147 _, r.Err = client.Post(rootRuleURL(client), b, &r.Body, &gophercloud.RequestOpts{
Jamie Hannaford6a3a78f2015-03-24 14:56:12 +0100148 OkCodes: []int{200},
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100149 })
Jon Perrittdb0ae142016-03-13 00:33:41 -0600150 return r
Jamie Hannaford8badf1e2014-11-19 14:39:26 +0100151}
Jamie Hannaford61f81ca2014-11-19 14:44:33 +0100152
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +0100153// DeleteRule will permanently delete a rule from a security group.
Jamie Hannaford2f226172014-11-25 11:52:25 +0100154func DeleteRule(client *gophercloud.ServiceClient, id string) gophercloud.ErrResult {
Jon Perrittdb0ae142016-03-13 00:33:41 -0600155 var r gophercloud.ErrResult
156 _, r.Err = client.Delete(resourceRuleURL(client, id), nil)
157 return r
Jamie Hannaford61f81ca2014-11-19 14:44:33 +0100158}
Jamie Hannaford740e4a32014-11-19 16:13:30 +0100159
160func actionMap(prefix, groupName string) map[string]map[string]string {
161 return map[string]map[string]string{
162 prefix + "SecurityGroup": map[string]string{"name": groupName},
163 }
164}
165
Jon Perrittdb0ae142016-03-13 00:33:41 -0600166// AddServer will associate a server and a security group, enforcing the
Jamie Hannaford7f34d8e2014-11-20 12:24:55 +0100167// rules of the group on the server.
Jon Perrittdb0ae142016-03-13 00:33:41 -0600168func AddServer(client *gophercloud.ServiceClient, serverID, groupName string) gophercloud.ErrResult {
169 var r gophercloud.ErrResult
170 _, r.Err = client.Post(serverActionURL(client, serverID), actionMap("add", groupName), &r.Body, nil)
171 return r
Jamie Hannaford740e4a32014-11-19 16:13:30 +0100172}
173
Jon Perrittdb0ae142016-03-13 00:33:41 -0600174// RemoveServer will disassociate a server from a security group.
175func RemoveServer(client *gophercloud.ServiceClient, serverID, groupName string) gophercloud.ErrResult {
176 var r gophercloud.ErrResult
177 _, r.Err = client.Post(serverActionURL(client, serverID), actionMap("remove", groupName), &r.Body, nil)
178 return r
Jamie Hannaford740e4a32014-11-19 16:13:30 +0100179}