Add the ability to create, delete, list, and get networks, ports and subnets
Partially implements network-v2 Updated to use Session Change-Id: I9c57cbe524712313892868c0fb38eb6f6062d362
This commit is contained in:

committed by
Dean Troyer

parent
4141ca3ed3
commit
c42cbe79a0
252
examples/40-network-v2.go
Normal file
252
examples/40-network-v2.go
Normal file
@@ -0,0 +1,252 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net/http"
|
||||
"reflect"
|
||||
"time"
|
||||
|
||||
"git.openstack.org/openstack/golang-client.git/network/v2"
|
||||
"git.openstack.org/openstack/golang-client.git/openstack"
|
||||
)
|
||||
|
||||
func main() {
|
||||
config := getConfig()
|
||||
|
||||
// Authenticate with a username, password, tenant id.
|
||||
creds := openstack.AuthOpts{
|
||||
AuthUrl: config.Host,
|
||||
Project: config.ProjectName,
|
||||
Username: config.Username,
|
||||
Password: config.Password,
|
||||
}
|
||||
auth, err := openstack.DoAuthRequest(creds)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("There was an error authenticating:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
if !auth.GetExpiration().After(time.Now()) {
|
||||
panic("There was an error. The auth token has an invalid expiration.")
|
||||
}
|
||||
|
||||
// Find the endpoint for the network service.
|
||||
url, err := auth.GetEndpoint("network", "")
|
||||
if url == "" || err != nil {
|
||||
panic("v2 network service url not found during authentication")
|
||||
}
|
||||
|
||||
// Make a new client with these creds
|
||||
sess, err := openstack.NewSession(nil, auth, nil)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error crating new Session:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
networkService := network.Service{
|
||||
Session: *sess,
|
||||
Client: *http.DefaultClient,
|
||||
URL: url + "/v2.0", // We're forcing Network v2.0 for now
|
||||
}
|
||||
|
||||
networkName := "OtherNetwork"
|
||||
activeNetwork := CreateNewNetworkVerifyExistsAndActive(networkService, networkName)
|
||||
|
||||
// Create list, get and delete a subnet
|
||||
activeSubnet := CreateSubnetAndVerify(networkService, activeNetwork)
|
||||
activePort := CreatePortAndVerify(networkService, activeSubnet, activeNetwork)
|
||||
DeletePortAndVerify(networkService, activePort)
|
||||
DeleteSubnetAndVerify(networkService, activeSubnet)
|
||||
DeleteNetworkAndVerify(networkService, activeNetwork)
|
||||
}
|
||||
|
||||
func CreatePortAndVerify(networkService network.Service, subnet network.SubnetResponse, activeNetwork network.Response) network.PortResponse {
|
||||
var portToCreate = network.CreatePortParameters{AdminStateUp: false, Name: "testPort", NetworkID: activeNetwork.ID}
|
||||
|
||||
portCreated, err := networkService.CreatePort(portToCreate)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in creating port:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
foundPorts, err := networkService.Ports()
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in getting list of subnets:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
foundCreatedPort := false
|
||||
for _, portFound := range foundPorts {
|
||||
if reflect.DeepEqual(portCreated, portFound) {
|
||||
foundCreatedPort = true
|
||||
}
|
||||
}
|
||||
|
||||
if !foundCreatedPort {
|
||||
panic("Cannot find the newly created port.")
|
||||
}
|
||||
|
||||
return portCreated
|
||||
}
|
||||
|
||||
func DeletePortAndVerify(networkService network.Service, port network.PortResponse) {
|
||||
err := networkService.DeletePort(port.ID)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in deleting port:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
ports, err := networkService.Ports()
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("There was an error getting a list of ports to verify the port was deleted:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
portDeleted := true
|
||||
for _, portFound := range ports {
|
||||
if reflect.DeepEqual(portFound, port) {
|
||||
portDeleted = false
|
||||
}
|
||||
}
|
||||
|
||||
if !portDeleted {
|
||||
panic("port was not deleted.")
|
||||
}
|
||||
}
|
||||
|
||||
func CreateSubnetAndVerify(networkService network.Service, activeNetwork network.Response) network.SubnetResponse {
|
||||
var allocationPools = []network.AllocationPool{network.AllocationPool{Start: "10.1.2.5", End: "10.1.2.15"}}
|
||||
subnetToCreate := network.CreateSubnetParameters{NetworkID: activeNetwork.ID, IPVersion: network.IPV4,
|
||||
CIDR: "10.1.2.1/25", AllocationPools: allocationPools}
|
||||
|
||||
subnetCreated, err := networkService.CreateSubnet(subnetToCreate)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in creating subnet:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
foundSubnets, err := networkService.Subnets()
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in getting list of subnets:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
foundCreatedSubnet := false
|
||||
for _, subnetFound := range foundSubnets {
|
||||
if reflect.DeepEqual(subnetCreated, subnetFound) {
|
||||
foundCreatedSubnet = true
|
||||
}
|
||||
}
|
||||
|
||||
if !foundCreatedSubnet {
|
||||
panic("Cannot find the newly created subnet.")
|
||||
}
|
||||
|
||||
return subnetCreated
|
||||
}
|
||||
|
||||
func DeleteSubnetAndVerify(networkService network.Service, subnet network.SubnetResponse) {
|
||||
err := networkService.DeleteSubnet(subnet.ID)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in deleting subnet:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
subnets, err := networkService.Subnets()
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("There was an error getting a list of networks to verify the network was deleted:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
subnetDeleted := true
|
||||
for _, subnetFound := range subnets {
|
||||
if reflect.DeepEqual(subnetFound, subnet) {
|
||||
subnetDeleted = false
|
||||
}
|
||||
}
|
||||
|
||||
if !subnetDeleted {
|
||||
panic("subnet was not deleted.")
|
||||
}
|
||||
}
|
||||
|
||||
func DeleteNetworkAndVerify(networkService network.Service, activeNetwork network.Response) {
|
||||
err := networkService.DeleteNetwork(activeNetwork.ID)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("Error in deleting 'OtherNetwork'", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
networks, err := networkService.Networks()
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("There was an error getting a list of networks to verify the network was deleted:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
networkDeleted := true
|
||||
for _, networkFound := range networks {
|
||||
if reflect.DeepEqual(activeNetwork, networkFound) {
|
||||
networkDeleted = false
|
||||
}
|
||||
}
|
||||
|
||||
if !networkDeleted {
|
||||
panic("network was not deleted.")
|
||||
}
|
||||
|
||||
}
|
||||
func CreateNewNetworkVerifyExistsAndActive(networkService network.Service, networkName string) network.Response {
|
||||
createdNetwork, err := networkService.CreateNetwork(true, networkName, false)
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("There was an error creating a network:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
networks, err := networkService.Networks()
|
||||
if err != nil {
|
||||
panicString := fmt.Sprint("There was an error getting a list of networks:", err)
|
||||
panic(panicString)
|
||||
}
|
||||
|
||||
foundCreatedNetwork := false
|
||||
for _, networkFound := range networks {
|
||||
if reflect.DeepEqual(createdNetwork, networkFound) {
|
||||
foundCreatedNetwork = true
|
||||
}
|
||||
}
|
||||
|
||||
if !foundCreatedNetwork {
|
||||
panic("Cannot find network called 'OtherNetwork' when getting a list of networks.")
|
||||
}
|
||||
|
||||
// Might be nice to have some sugar api that can do this easily for a developer...
|
||||
// Keep iterating until active or until more than 5 tries has been exceeded.
|
||||
//numTries := 0
|
||||
//activeNetwork := createdNetwork
|
||||
//for activeNetwork.Status != "ACTIVE" && numTries < 5 {
|
||||
// activeNetwork, _ = networkService.Network(createdNetwork.ID)
|
||||
// numTries++
|
||||
// fmt.Println("Sleeping 50ms on try:" + string(numTries) + " with status currently " + activeNetwork.Status)
|
||||
// sleepDuration, _ := time.ParseDuration("50ms")
|
||||
// time.Sleep(sleepDuration)
|
||||
//}
|
||||
|
||||
//if activeNetwork.Status != "ACTIVE" {
|
||||
// panic("The network is not in the active state and cannot be deleted")
|
||||
//}
|
||||
|
||||
return createdNetwork
|
||||
}
|
94
network/v2/network.go
Normal file
94
network/v2/network.go
Normal file
@@ -0,0 +1,94 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
// Package network is used to create, delete, and query, networks, ports and subnets
|
||||
package network
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
|
||||
"git.openstack.org/openstack/golang-client.git/openstack"
|
||||
)
|
||||
|
||||
// Service holds state that is use to make requests and get responses for networks,
|
||||
// ports and subnets
|
||||
type Service struct {
|
||||
Client http.Client
|
||||
Session openstack.Session
|
||||
URL string
|
||||
}
|
||||
|
||||
// Response returns a set of values of the a network response.
|
||||
type Response struct {
|
||||
ID string `json:"id"`
|
||||
Name string `json:"name"`
|
||||
Status string `json:"status"`
|
||||
Subnets []string `json:"subnets"`
|
||||
TenantID string `json:"tenant_id"`
|
||||
RouterExternal bool `json:"router:external"`
|
||||
AdminStateUp bool `json:"admin_state_up"`
|
||||
Shared bool `json:"shared"`
|
||||
PortSecurityEnabled bool `json:"port_security_enabled"`
|
||||
}
|
||||
|
||||
// Networks will issue a get query that returns a list of networks
|
||||
func (networkService Service) Networks() ([]Response, error) {
|
||||
reqURL := networkService.URL + "/networks"
|
||||
nwContainer := networksResp{}
|
||||
_, err := networkService.Session.GetJSON(reqURL, nil, nil, &nwContainer)
|
||||
return nwContainer.Networks, err
|
||||
}
|
||||
|
||||
// Network will issue a get request for a specific network.
|
||||
func (networkService Service) Network(id string) (Response, error) {
|
||||
reqURL := networkService.URL + "/networks/" + id
|
||||
nwContainer := networkResp{}
|
||||
_, err := networkService.Session.GetJSON(reqURL, nil, nil, &nwContainer)
|
||||
return nwContainer.Network, err
|
||||
}
|
||||
|
||||
// CreateNetwork will send a POST request to create a new network with the specified parameters.
|
||||
func (networkService Service) CreateNetwork(adminStateUp bool, name string, shared bool) (Response, error) {
|
||||
createParameters := createNetworkValuesContainer{createNetworkValues{Name: name, AdminStateUp: adminStateUp, Shared: shared, TenantID: ""}}
|
||||
reqURL := networkService.URL + "/networks"
|
||||
nwContainer := networkResp{}
|
||||
_, err := networkService.Session.PostJSON(reqURL, nil, nil, &createParameters, &nwContainer)
|
||||
return nwContainer.Network, err
|
||||
}
|
||||
|
||||
// DeleteNetwork will delete the specified network.
|
||||
func (networkService Service) DeleteNetwork(name string) (err error) {
|
||||
reqURL := networkService.URL + "/networks/" + name
|
||||
_, err = networkService.Session.Delete(reqURL, nil, nil)
|
||||
return err
|
||||
}
|
||||
|
||||
type createNetworkValues struct {
|
||||
Name string `json:"name"`
|
||||
AdminStateUp bool `json:"admin_state_up"`
|
||||
Shared bool `json:"shared"`
|
||||
TenantID string `json:"tenant_id"`
|
||||
}
|
||||
|
||||
type createNetworkValuesContainer struct {
|
||||
Network createNetworkValues `json:"network"`
|
||||
}
|
||||
|
||||
type networksResp struct {
|
||||
Networks []Response `json:"networks"`
|
||||
}
|
||||
|
||||
type networkResp struct {
|
||||
Network Response `json:"network"`
|
||||
}
|
107
network/v2/network_test.go
Normal file
107
network/v2/network_test.go
Normal file
@@ -0,0 +1,107 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package network_test
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"git.openstack.org/openstack/golang-client.git/network/v2"
|
||||
"git.openstack.org/openstack/golang-client.git/testutil"
|
||||
"net/http"
|
||||
"testing"
|
||||
)
|
||||
|
||||
var tokn = "eaaafd18-0fed-4b3a-81b4-663c99ec1cbb"
|
||||
var subnets = []string{"10.3.5.2", "12.34.1.4"}
|
||||
var sampleNetworkResponse = network.Response{
|
||||
ID: "16470140hb",
|
||||
Name: "networkName",
|
||||
Status: "active",
|
||||
Subnets: subnets,
|
||||
TenantID: "tenantID",
|
||||
RouterExternal: true,
|
||||
AdminStateUp: false,
|
||||
Shared: true,
|
||||
PortSecurityEnabled: false}
|
||||
|
||||
func TestGetNetworks(t *testing.T) {
|
||||
mockResponseObject := networksContainer{Networks: []network.Response{sampleNetworkResponse}}
|
||||
apiServer := testUtil.CreateGetJSONTestRequestServerWithMockObject(t, tokn, mockResponseObject, "/networks")
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
networks, err := networkService.Networks()
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
if len(networks) != 1 {
|
||||
t.Error(errors.New("Error: Expected 2 networks to be listed"))
|
||||
}
|
||||
testUtil.Equals(t, sampleNetworkResponse, networks[0])
|
||||
}
|
||||
|
||||
func TestGetNetwork(t *testing.T) {
|
||||
mockResponseObject := networkContainer{Network: sampleNetworkResponse}
|
||||
apiServer := testUtil.CreateGetJSONTestRequestServerWithMockObject(t, tokn, mockResponseObject, "/networks/5270u2tg0")
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
network, err := networkService.Network("5270u2tg0")
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
testUtil.Equals(t, sampleNetworkResponse, network)
|
||||
}
|
||||
|
||||
func TestDeleteNetwork(t *testing.T) {
|
||||
name := "networkName"
|
||||
apiServer := testUtil.CreateDeleteTestRequestServer(t, tokn, "/networks/"+name)
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
err := networkService.DeleteNetwork(name)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestCreateNetwork(t *testing.T) {
|
||||
mockResponse, _ := json.Marshal(networkContainer{sampleNetworkResponse})
|
||||
apiServer := testUtil.CreatePostJSONTestRequestServer(t, tokn, string(mockResponse), "/networks",
|
||||
`{"network":{"name":"networkName","admin_state_up":false,"shared":true,"tenant_id":"tenantId"}}`)
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
actualNetwork, err := networkService.CreateNetwork(false, "networkName", true)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
testUtil.Equals(t, sampleNetworkResponse, actualNetwork)
|
||||
}
|
||||
|
||||
func CreateNetworkService(url string) network.Service {
|
||||
return network.Service{TokenID: tokn, TenantID: "tenantId", Client: *http.DefaultClient, URL: url}
|
||||
}
|
||||
|
||||
type networksContainer struct {
|
||||
Networks []network.Response `json:"networks"`
|
||||
}
|
||||
|
||||
type networkContainer struct {
|
||||
Network network.Response `json:"network"`
|
||||
}
|
109
network/v2/port.go
Normal file
109
network/v2/port.go
Normal file
@@ -0,0 +1,109 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package network
|
||||
|
||||
import (
|
||||
// "git.openstack.org/openstack/golang-client.git/openstack"
|
||||
)
|
||||
|
||||
// PortResponse returns a set of values of the a port response.
|
||||
type PortResponse struct {
|
||||
ID string `json:"id"`
|
||||
Name string `json:"name"`
|
||||
Status string `json:"status"`
|
||||
AdminStateUp bool `json:"admin_state_up"`
|
||||
PortSecurityEnabled bool `json:"port_security_enabled"`
|
||||
DeviceID string `json:"device_id"`
|
||||
DeviceOwner string `json:"device_owner"`
|
||||
NetworkID string `json:"network_id"`
|
||||
TenantID string `json:"tenant_id"`
|
||||
MacAddress string `json:"mac_address"`
|
||||
FixedIPs []FixedIP `json:"fixed_ips"`
|
||||
SecurityGroups []string `json:"security_groups"`
|
||||
}
|
||||
|
||||
// CreatePortParameters holds a set of values that specify how
|
||||
// to create a new port.
|
||||
type CreatePortParameters struct {
|
||||
AdminStateUp bool `json:"admin_state_up,omitempty"`
|
||||
Name string `json:"name,omitempty"`
|
||||
NetworkID string `json:"network_id"`
|
||||
DeviceID string `json:"device_id,omitempty"`
|
||||
MacAddress string `json:"mac_address,omitempty"`
|
||||
FixedIPs []FixedIP `json:"fixed_ips,omitempty"`
|
||||
SecurityGroups []string `json:"security_groups,omitempty"`
|
||||
}
|
||||
|
||||
// PortResponses is a type for a slice of PortResponses.
|
||||
type PortResponses []PortResponse
|
||||
|
||||
func (a PortResponses) Len() int { return len(a) }
|
||||
func (a PortResponses) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||
func (a PortResponses) Less(i, j int) bool { return a[i].Name < a[j].Name }
|
||||
|
||||
// FixedIP is holds data that specifies a fixed IP.
|
||||
type FixedIP struct {
|
||||
SubnetID string `json:"subnet_id"`
|
||||
IPAddress string `json:"ip_address,omitempty"`
|
||||
}
|
||||
|
||||
// Ports issues a GET request that returns the found port responses
|
||||
func (networkService Service) Ports() ([]PortResponse, error) {
|
||||
reqURL := networkService.URL + "/ports"
|
||||
var portResponse = portsResp{}
|
||||
_, err := networkService.Session.GetJSON(reqURL, nil, nil, &portResponse)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return portResponse.Ports, nil
|
||||
}
|
||||
|
||||
// Port issues a GET request that returns a specific port response.
|
||||
func (networkService Service) Port(id string) (PortResponse, error) {
|
||||
reqURL := networkService.URL + "/ports/" + id
|
||||
portResponse := portResp{}
|
||||
_, err := networkService.Session.GetJSON(reqURL, nil, nil, &portResponse)
|
||||
return portResponse.Port, err
|
||||
}
|
||||
|
||||
// DeletePort issues a DELETE to the specified port url to delete it.
|
||||
func (networkService Service) DeletePort(id string) error {
|
||||
reqURL := networkService.URL + "/ports/" + id
|
||||
_, err := networkService.Session.Delete(reqURL, nil, nil)
|
||||
return err
|
||||
}
|
||||
|
||||
// CreatePort issues a POST to create the specified port and return a PortResponse.
|
||||
func (networkService Service) CreatePort(parameters CreatePortParameters) (PortResponse, error) {
|
||||
reqURL := networkService.URL + "/ports"
|
||||
parametersContainer := createPortContainer{Port: parameters}
|
||||
portResponse := portResp{}
|
||||
|
||||
_, err := networkService.Session.PostJSON(reqURL, nil, nil, ¶metersContainer, &portResponse)
|
||||
return portResponse.Port, err
|
||||
}
|
||||
|
||||
type portsResp struct {
|
||||
Ports []PortResponse `json:"ports"`
|
||||
}
|
||||
|
||||
type portResp struct {
|
||||
Port PortResponse `json:"port"`
|
||||
}
|
||||
|
||||
type createPortContainer struct {
|
||||
Port CreatePortParameters `json:"port"`
|
||||
}
|
104
network/v2/port_test.go
Normal file
104
network/v2/port_test.go
Normal file
@@ -0,0 +1,104 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package network_test
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"git.openstack.org/openstack/golang-client.git/network/v2"
|
||||
"git.openstack.org/openstack/golang-client.git/testutil"
|
||||
"testing"
|
||||
)
|
||||
|
||||
var fixedIps = []network.FixedIP{network.FixedIP{SubnetID: "125071206726"}, network.FixedIP{SubnetID: "15615526", IPAddress: "132.145.15.11"}}
|
||||
var samplePortResponse = network.PortResponse{
|
||||
ID: "2490640zbg",
|
||||
Name: "Port14",
|
||||
Status: "active",
|
||||
AdminStateUp: true,
|
||||
PortSecurityEnabled: true,
|
||||
DeviceID: "deviceid",
|
||||
DeviceOwner: "deviceowner",
|
||||
NetworkID: "networkid",
|
||||
TenantID: "tenantid",
|
||||
MacAddress: "macAddress",
|
||||
FixedIPs: fixedIps,
|
||||
SecurityGroups: []string{"sec1", "sec2"}}
|
||||
|
||||
func TestGetPorts(t *testing.T) {
|
||||
mockResponseObject := portsContainer{Ports: []network.PortResponse{samplePortResponse}}
|
||||
apiServer := testUtil.CreateGetJSONTestRequestServerWithMockObject(t, tokn, mockResponseObject, "/ports")
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
ports, err := networkService.Ports()
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
if len(ports) != 1 {
|
||||
t.Error(errors.New("Error: Expected 2 networks to be listed"))
|
||||
}
|
||||
testUtil.Equals(t, samplePortResponse, ports[0])
|
||||
}
|
||||
|
||||
func TestGetPort(t *testing.T) {
|
||||
mockResponseObject := portContainer{Port: samplePortResponse}
|
||||
apiServer := testUtil.CreateGetJSONTestRequestServerWithMockObject(t, tokn, mockResponseObject, "/ports/23507256")
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
port, err := networkService.Port("23507256")
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
testUtil.Equals(t, samplePortResponse, port)
|
||||
}
|
||||
|
||||
func TestDeletePort(t *testing.T) {
|
||||
portName := "portName"
|
||||
apiServer := testUtil.CreateDeleteTestRequestServer(t, tokn, "/ports/"+portName)
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
err := networkService.DeletePort(portName)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestCreatePort(t *testing.T) {
|
||||
mockResponse, _ := json.Marshal(portContainer{Port: samplePortResponse})
|
||||
apiServer := testUtil.CreatePostJSONTestRequestServer(t, tokn, string(mockResponse), "/ports",
|
||||
`{"port":{"admin_state_up":true,"name":"name","network_id":"networkid","fixed_ips":[{"subnet_id":"125071206726"},{"subnet_id":"15615526","ip_address":"132.145.15.11"}]}}`)
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
createPortParameters := network.CreatePortParameters{AdminStateUp: true, Name: "name", NetworkID: "networkid", FixedIPs: fixedIps}
|
||||
actualPort, err := networkService.CreatePort(createPortParameters)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
testUtil.Equals(t, samplePortResponse, actualPort)
|
||||
}
|
||||
|
||||
type portsContainer struct {
|
||||
Ports []network.PortResponse `json:"ports"`
|
||||
}
|
||||
|
||||
type portContainer struct {
|
||||
Port network.PortResponse `json:"port"`
|
||||
}
|
106
network/v2/subnet.go
Normal file
106
network/v2/subnet.go
Normal file
@@ -0,0 +1,106 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package network
|
||||
|
||||
import (
|
||||
// "git.openstack.org/openstack/golang-client.git/openstack"
|
||||
)
|
||||
|
||||
// SubnetResponse returns a set of values of the a Subnet response
|
||||
type SubnetResponse struct {
|
||||
ID string `json:"id"`
|
||||
Name string `json:"name"`
|
||||
NetworkID string `json:"network_id"`
|
||||
TenantID string `json:"tenant_id"`
|
||||
EnableDHCP bool `json:"enable_dhcp"`
|
||||
DNSNameserver []string `json:"dns_nameservers"`
|
||||
AllocationPools []AllocationPool `json:"allocation_pools"`
|
||||
HostRoutes []string `json:"host_routes"`
|
||||
IPVersion IPVersion `json:"ip_version"`
|
||||
GatewayIP string `json:"gateway_ip"`
|
||||
CIDR string `json:"cidr"`
|
||||
}
|
||||
|
||||
// CreateSubnetParameters is a set of values to create a new subnet.
|
||||
type CreateSubnetParameters struct {
|
||||
NetworkID string `json:"network_id"`
|
||||
IPVersion IPVersion `json:"ip_version"`
|
||||
CIDR string `json:"cidr"`
|
||||
AllocationPools []AllocationPool `json:"allocation_pools"`
|
||||
}
|
||||
|
||||
// AllocationPool is a set of values for an allocation pool of ip addresses.
|
||||
type AllocationPool struct {
|
||||
Start string `json:"start"`
|
||||
End string `json:"end"`
|
||||
}
|
||||
|
||||
// IPVersion type indicates whether an ip address is IPV4 or IPV6.
|
||||
type IPVersion int
|
||||
|
||||
const (
|
||||
// IPV4 indicates its an ip address version 4.
|
||||
IPV4 IPVersion = 4
|
||||
// IPV6 indicates its an ip address version 6
|
||||
IPV6 IPVersion = 6
|
||||
)
|
||||
|
||||
// Subnets issues a GET request to return all subnets.
|
||||
func (networkService Service) Subnets() ([]SubnetResponse, error) {
|
||||
reqURL := networkService.URL + "/subnets"
|
||||
var subnetResponse = subnetsResp{}
|
||||
_, err := networkService.Session.GetJSON(reqURL, nil, nil, &subnetResponse)
|
||||
return subnetResponse.Subnets, err
|
||||
}
|
||||
|
||||
// Subnet issues a GET request to a specific url of a subnet and returns a subnet response.
|
||||
func (networkService Service) Subnet(id string) (SubnetResponse, error) {
|
||||
reqURL := networkService.URL + "/subnets/" + id
|
||||
|
||||
subnetResponse := subnetResp{}
|
||||
_, err := networkService.Session.GetJSON(reqURL, nil, nil, &subnetResponse)
|
||||
return subnetResponse.Subnet, err
|
||||
}
|
||||
|
||||
// DeleteSubnet issues a DELETE request to remove the subnet.
|
||||
func (networkService Service) DeleteSubnet(id string) error {
|
||||
reqURL := networkService.URL + "/subnets/" + id
|
||||
_, err := networkService.Session.Delete(reqURL, nil, nil)
|
||||
return err
|
||||
}
|
||||
|
||||
// CreateSubnet issues a GET request to add a Subnet with the specified parameters
|
||||
// and returns the Subnet created.
|
||||
func (networkService Service) CreateSubnet(parameters CreateSubnetParameters) (SubnetResponse, error) {
|
||||
|
||||
reqURL := networkService.URL + "/subnets"
|
||||
parametersContainer := createSubnetContainer{Subnet: parameters}
|
||||
subnetResponse := subnetResp{}
|
||||
|
||||
_, err := networkService.Session.PostJSON(reqURL, nil, nil, ¶metersContainer, &subnetResponse)
|
||||
return subnetResponse.Subnet, err
|
||||
}
|
||||
|
||||
type subnetResp struct {
|
||||
Subnet SubnetResponse `json:"subnet"`
|
||||
}
|
||||
|
||||
type subnetsResp struct {
|
||||
Subnets []SubnetResponse `json:"subnets"`
|
||||
}
|
||||
|
||||
type createSubnetContainer struct {
|
||||
Subnet CreateSubnetParameters `json:"subnet"`
|
||||
}
|
107
network/v2/subnet_test.go
Normal file
107
network/v2/subnet_test.go
Normal file
@@ -0,0 +1,107 @@
|
||||
// Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
// not use this file except in compliance with the License. You may obtain
|
||||
// a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
// License for the specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package network_test
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"git.openstack.org/openstack/golang-client.git/network/v2"
|
||||
"git.openstack.org/openstack/golang-client.git/testutil"
|
||||
"testing"
|
||||
)
|
||||
|
||||
var allocationPool1 = network.AllocationPool{Start: "13.14.14.15", End: "13.14.14.15"}
|
||||
var allocationPools = []network.AllocationPool{allocationPool1}
|
||||
var sampleSubNetResponse = network.SubnetResponse{
|
||||
ID: "subnet",
|
||||
Name: "name",
|
||||
NetworkID: "networkid",
|
||||
TenantID: "tenantid",
|
||||
EnableDHCP: true,
|
||||
DNSNameserver: []string{"13.14.14.15"},
|
||||
AllocationPools: allocationPools,
|
||||
HostRoutes: []string{"35.15.15.15"},
|
||||
IPVersion: network.IPV4,
|
||||
GatewayIP: "35.15.15.1",
|
||||
CIDR: "35.15.15.3"}
|
||||
|
||||
func TestGetSubnets(t *testing.T) {
|
||||
mockResponseObject := subnetsResp{Subnets: []network.SubnetResponse{sampleSubNetResponse}}
|
||||
apiServer := testUtil.CreateGetJSONTestRequestServerWithMockObject(t, tokn, mockResponseObject, "/subnets")
|
||||
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
subnets, err := networkService.Subnets()
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
if len(subnets) != 1 {
|
||||
t.Error(errors.New("Error: Expected 1 subnet to be listed"))
|
||||
}
|
||||
testUtil.Equals(t, sampleSubNetResponse, subnets[0])
|
||||
}
|
||||
|
||||
func TestGetSubnet(t *testing.T) {
|
||||
mockResponseObject := subnetResp{Subnet: sampleSubNetResponse}
|
||||
apiServer := testUtil.CreateGetJSONTestRequestServerWithMockObject(t, tokn, mockResponseObject, "/subnets/5270u2tg0")
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
subnet, err := networkService.Subnet("5270u2tg0")
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
testUtil.Equals(t, sampleSubNetResponse, subnet)
|
||||
}
|
||||
|
||||
func TestDeleteSubnet(t *testing.T) {
|
||||
name := "subnetName"
|
||||
apiServer := testUtil.CreateDeleteTestRequestServer(t, tokn, "/subnets/"+name)
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
err := networkService.DeleteSubnet(name)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestCreateSubnet(t *testing.T) {
|
||||
mockResponse, err := json.Marshal(subnetResp{Subnet: sampleSubNetResponse})
|
||||
|
||||
apiServer := testUtil.CreatePostJSONTestRequestServer(t, tokn, string(mockResponse), "/subnets",
|
||||
`{"subnet":{"network_id":"subnetid","ip_version":4,"cidr":"12.14.76.87","allocation_pools":[{"start":"13.14.14.15","end":"13.14.14.15"}]}}`)
|
||||
defer apiServer.Close()
|
||||
|
||||
networkService := CreateNetworkService(apiServer.URL)
|
||||
createSubnetParameters := network.CreateSubnetParameters{NetworkID: "subnetid", AllocationPools: allocationPools, CIDR: "12.14.76.87", IPVersion: 4}
|
||||
actualPort, err := networkService.CreateSubnet(createSubnetParameters)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
testUtil.Equals(t, sampleSubNetResponse, actualPort)
|
||||
}
|
||||
|
||||
type subnetsResp struct {
|
||||
Subnets []network.SubnetResponse `json:"subnets"`
|
||||
}
|
||||
|
||||
type subnetResp struct {
|
||||
Subnet network.SubnetResponse `json:"subnet"`
|
||||
}
|
@@ -16,6 +16,7 @@
|
||||
package testUtil
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net/http"
|
||||
@@ -101,6 +102,22 @@ func CreateGetJSONTestRequestServer(t *testing.T, expectedAuthTokenValue string,
|
||||
}))
|
||||
}
|
||||
|
||||
// CreateGetJSONTestRequestServerWithMockObject a http.Server that can be used to test PostJson requests. Specify the token,
|
||||
// response object which will be marshaled to a json payload and the expected ending url.
|
||||
func CreateGetJSONTestRequestServerWithMockObject(t *testing.T, token string, mockResponseObject interface{}, urlEndsWith string) *httptest.Server {
|
||||
mockResponse, err := json.Marshal(mockResponseObject)
|
||||
if err != nil {
|
||||
t.Error("Test failed to marshal mockResponseObject:", err)
|
||||
}
|
||||
anon := func(req *http.Request) {
|
||||
reqURL := req.URL.String()
|
||||
if !strings.HasSuffix(reqURL, urlEndsWith) {
|
||||
t.Error(errors.New("Incorrect url created, expected:" + urlEndsWith + " at the end, actual url:" + reqURL))
|
||||
}
|
||||
}
|
||||
return CreateGetJSONTestRequestServer(t, token, string(mockResponse), anon)
|
||||
}
|
||||
|
||||
// CreatePostJSONTestRequestServer creates a http.Server that can be used to test PostJson requests. Specify the token,
|
||||
// response json payload and the url and request body that is expected.
|
||||
func CreatePostJSONTestRequestServer(t *testing.T, expectedAuthTokenValue string, outputResponseJSONPayload string, expectedRequestURLEndsWith string, expectedRequestBody string) *httptest.Server {
|
||||
|
Reference in New Issue
Block a user