github.com/gophercloud/gophercloud@v1.11.0/openstack/networking/v2/ports/results.go (about) 1 package ports 2 3 import ( 4 "encoding/json" 5 "time" 6 7 "github.com/gophercloud/gophercloud" 8 "github.com/gophercloud/gophercloud/pagination" 9 ) 10 11 type commonResult struct { 12 gophercloud.Result 13 } 14 15 // Extract is a function that accepts a result and extracts a port resource. 16 func (r commonResult) Extract() (*Port, error) { 17 var s Port 18 err := r.ExtractInto(&s) 19 return &s, err 20 } 21 22 func (r commonResult) ExtractInto(v interface{}) error { 23 return r.Result.ExtractIntoStructPtr(v, "port") 24 } 25 26 // CreateResult represents the result of a create operation. Call its Extract 27 // method to interpret it as a Port. 28 type CreateResult struct { 29 commonResult 30 } 31 32 // GetResult represents the result of a get operation. Call its Extract 33 // method to interpret it as a Port. 34 type GetResult struct { 35 commonResult 36 } 37 38 // UpdateResult represents the result of an update operation. Call its Extract 39 // method to interpret it as a Port. 40 type UpdateResult struct { 41 commonResult 42 } 43 44 // DeleteResult represents the result of a delete operation. Call its 45 // ExtractErr method to determine if the request succeeded or failed. 46 type DeleteResult struct { 47 gophercloud.ErrResult 48 } 49 50 // IP is a sub-struct that represents an individual IP. 51 type IP struct { 52 SubnetID string `json:"subnet_id"` 53 IPAddress string `json:"ip_address,omitempty"` 54 } 55 56 // AddressPair contains the IP Address and the MAC address. 57 type AddressPair struct { 58 IPAddress string `json:"ip_address,omitempty"` 59 MACAddress string `json:"mac_address,omitempty"` 60 } 61 62 // Port represents a Neutron port. See package documentation for a top-level 63 // description of what this is. 64 type Port struct { 65 // UUID for the port. 66 ID string `json:"id"` 67 68 // Network that this port is associated with. 69 NetworkID string `json:"network_id"` 70 71 // Human-readable name for the port. Might not be unique. 72 Name string `json:"name"` 73 74 // Describes the port. 75 Description string `json:"description"` 76 77 // Administrative state of port. If false (down), port does not forward 78 // packets. 79 AdminStateUp bool `json:"admin_state_up"` 80 81 // Indicates whether network is currently operational. Possible values include 82 // `ACTIVE', `DOWN', `BUILD', or `ERROR'. Plug-ins might define additional 83 // values. 84 Status string `json:"status"` 85 86 // Mac address to use on this port. 87 MACAddress string `json:"mac_address"` 88 89 // Specifies IP addresses for the port thus associating the port itself with 90 // the subnets where the IP addresses are picked from 91 FixedIPs []IP `json:"fixed_ips"` 92 93 // TenantID is the project owner of the port. 94 TenantID string `json:"tenant_id"` 95 96 // ProjectID is the project owner of the port. 97 ProjectID string `json:"project_id"` 98 99 // Identifies the entity (e.g.: dhcp agent) using this port. 100 DeviceOwner string `json:"device_owner"` 101 102 // Specifies the IDs of any security groups associated with a port. 103 SecurityGroups []string `json:"security_groups"` 104 105 // Identifies the device (e.g., virtual server) using this port. 106 DeviceID string `json:"device_id"` 107 108 // Identifies the list of IP addresses the port will recognize/accept 109 AllowedAddressPairs []AddressPair `json:"allowed_address_pairs"` 110 111 // Tags optionally set via extensions/attributestags 112 Tags []string `json:"tags"` 113 114 // PropagateUplinkStatus enables/disables propagate uplink status on the port. 115 PropagateUplinkStatus bool `json:"propagate_uplink_status"` 116 117 // Extra parameters to include in the request. 118 ValueSpecs map[string]string `json:"value_specs"` 119 120 // RevisionNumber optionally set via extensions/standard-attr-revisions 121 RevisionNumber int `json:"revision_number"` 122 123 // Timestamp when the port was created 124 CreatedAt time.Time `json:"created_at"` 125 126 // Timestamp when the port was last updated 127 UpdatedAt time.Time `json:"updated_at"` 128 } 129 130 func (r *Port) UnmarshalJSON(b []byte) error { 131 type tmp Port 132 133 // Support for older neutron time format 134 var s1 struct { 135 tmp 136 CreatedAt gophercloud.JSONRFC3339NoZ `json:"created_at"` 137 UpdatedAt gophercloud.JSONRFC3339NoZ `json:"updated_at"` 138 } 139 140 err := json.Unmarshal(b, &s1) 141 if err == nil { 142 *r = Port(s1.tmp) 143 r.CreatedAt = time.Time(s1.CreatedAt) 144 r.UpdatedAt = time.Time(s1.UpdatedAt) 145 146 return nil 147 } 148 149 // Support for newer neutron time format 150 var s2 struct { 151 tmp 152 CreatedAt time.Time `json:"created_at"` 153 UpdatedAt time.Time `json:"updated_at"` 154 } 155 156 err = json.Unmarshal(b, &s2) 157 if err != nil { 158 return err 159 } 160 161 *r = Port(s2.tmp) 162 r.CreatedAt = time.Time(s2.CreatedAt) 163 r.UpdatedAt = time.Time(s2.UpdatedAt) 164 165 return nil 166 } 167 168 // PortPage is the page returned by a pager when traversing over a collection 169 // of network ports. 170 type PortPage struct { 171 pagination.LinkedPageBase 172 } 173 174 // NextPageURL is invoked when a paginated collection of ports has reached 175 // the end of a page and the pager seeks to traverse over a new one. In order 176 // to do this, it needs to construct the next page's URL. 177 func (r PortPage) NextPageURL() (string, error) { 178 var s struct { 179 Links []gophercloud.Link `json:"ports_links"` 180 } 181 err := r.ExtractInto(&s) 182 if err != nil { 183 return "", err 184 } 185 return gophercloud.ExtractNextURL(s.Links) 186 } 187 188 // IsEmpty checks whether a PortPage struct is empty. 189 func (r PortPage) IsEmpty() (bool, error) { 190 if r.StatusCode == 204 { 191 return true, nil 192 } 193 194 is, err := ExtractPorts(r) 195 return len(is) == 0, err 196 } 197 198 // ExtractPorts accepts a Page struct, specifically a PortPage struct, 199 // and extracts the elements into a slice of Port structs. In other words, 200 // a generic collection is mapped into a relevant slice. 201 func ExtractPorts(r pagination.Page) ([]Port, error) { 202 var s []Port 203 err := ExtractPortsInto(r, &s) 204 return s, err 205 } 206 207 func ExtractPortsInto(r pagination.Page, v interface{}) error { 208 return r.(PortPage).Result.ExtractIntoSlicePtr(v, "ports") 209 }