From f051583681a7db36320a8f80f09934b2cea0fb07 Mon Sep 17 00:00:00 2001 From: Rui Ling <82846950+rling-equinix@users.noreply.github.com> Date: Thu, 14 Dec 2023 14:59:47 -0800 Subject: [PATCH] NFV-26837: introduce core field for device PATCH API (#26) --- client.go | 83 ++++++++++++++++++++++-------------------- internal/api/device.go | 43 +++++++++++----------- rest_device.go | 46 ++++++++++++++--------- 3 files changed, 94 insertions(+), 78 deletions(-) diff --git a/client.go b/client.go index dbfe122..87878f6 100644 --- a/client.go +++ b/client.go @@ -1,4 +1,4 @@ -//Package ne implements Network Edge client +// Package ne implements Network Edge client package ne import ( @@ -27,6 +27,10 @@ const ( DeviceStateDeprovisioning = "DEPROVISIONING" //DeviceStateDeprovisioned Network Edge device was successfully deprovisioned DeviceStateDeprovisioned = "DEPROVISIONED" + //DeviceStateResourceUpgradeInProgress Network Edge device is in process of resource upgrade + DeviceStateResourceUpgradeInProgress = "RESOURCE_UPGRADE_IN_PROGRESS" + //DeviceStateResourceUpgradeFailed Network Edge device resource upgrade has failed + DeviceStateResourceUpgradeFailed = "RESOURCE_UPGRADE_FAILED" //DeviceLicenseStateApplying license is in registration process DeviceLicenseStateApplying = "APPLYING_LICENSE" @@ -89,7 +93,7 @@ const ( DeviceLinkGroupStatusDeprovisioned = "DEPROVISIONED" ) -//Client interface describes operations provided by Network Edge client library +// Client interface describes operations provided by Network Edge client library type Client interface { GetAccounts(metroCode string) ([]Account, error) GetDeviceTypes() ([]DeviceType, error) @@ -138,25 +142,26 @@ type Client interface { DeleteDeviceLinkGroup(uuid string) error } -//DeviceUpdateRequest describes composite request to update given Network Edge device +// DeviceUpdateRequest describes composite request to update given Network Edge device type DeviceUpdateRequest interface { WithDeviceName(deviceName string) DeviceUpdateRequest WithTermLength(termLength int) DeviceUpdateRequest WithNotifications(notifications []string) DeviceUpdateRequest + WithCore(core int) DeviceUpdateRequest WithAdditionalBandwidth(additionalBandwidth int) DeviceUpdateRequest WithACLTemplate(templateID string) DeviceUpdateRequest WithMgmtAclTemplate(mgmtAclTemplateUuid string) DeviceUpdateRequest Execute() error } -//SSHUserUpdateRequest describes composite request to update given Network Edge SSH user +// SSHUserUpdateRequest describes composite request to update given Network Edge SSH user type SSHUserUpdateRequest interface { WithNewPassword(password string) SSHUserUpdateRequest WithDeviceChange(old []string, new []string) SSHUserUpdateRequest Execute() error } -//BGPUpdateRequest describes request to update given BGP configuration +// BGPUpdateRequest describes request to update given BGP configuration type BGPUpdateRequest interface { WithLocalIPAddress(localIPAddress string) BGPUpdateRequest WithLocalASN(localASN int) BGPUpdateRequest @@ -166,7 +171,7 @@ type BGPUpdateRequest interface { Execute() error } -//DeviceLinkUpdateRequest descrobes request to update given Device Link Group +// DeviceLinkUpdateRequest descrobes request to update given Device Link Group type DeviceLinkUpdateRequest interface { WithGroupName(name string) DeviceLinkUpdateRequest WithSubnet(subnet string) DeviceLinkUpdateRequest @@ -175,7 +180,7 @@ type DeviceLinkUpdateRequest interface { Execute() error } -//Error describes Network Edge error that occurs during API call processing +// Error describes Network Edge error that occurs during API call processing type Error struct { //ErrorCode is short error identifier ErrorCode string @@ -183,7 +188,7 @@ type Error struct { ErrorMessage string } -//ChangeError describes single error that occurred during update of selected target property +// ChangeError describes single error that occurred during update of selected target property type ChangeError struct { Type string Target string @@ -195,12 +200,12 @@ func (e ChangeError) Error() string { return fmt.Sprintf("change type '%s', target '%s', value '%s', cause: '%s'", e.Type, e.Target, e.Value, e.Cause) } -//UpdateError describes error that occurred during composite update request and consists of multiple atomic change errors +// UpdateError describes error that occurred during composite update request and consists of multiple atomic change errors type UpdateError struct { Failed []ChangeError } -//AddChangeError functions add new atomic change error to update error structure +// AddChangeError functions add new atomic change error to update error structure func (e *UpdateError) AddChangeError(changeType string, target string, value interface{}, cause error) { e.Failed = append(e.Failed, ChangeError{ Type: changeType, @@ -209,7 +214,7 @@ func (e *UpdateError) AddChangeError(changeType string, target string, value int Cause: cause}) } -//ChangeErrorsCount returns number of atomic change errors in a given composite update error +// ChangeErrorsCount returns number of atomic change errors in a given composite update error func (e UpdateError) ChangeErrorsCount() int { return len(e.Failed) } @@ -222,7 +227,7 @@ func (e UpdateError) Error() string { return str } -//Account describes Network Edge customer account details +// Account describes Network Edge customer account details type Account struct { Name *string Number *string @@ -230,7 +235,7 @@ type Account struct { UCMID *string } -//Device describes Network Edge device +// Device describes Network Edge device type Device struct { UUID *string Name *string @@ -276,7 +281,7 @@ type Device struct { ClusterDetails *ClusterDetails } -//DeviceInterface describes Network Edge device interface +// DeviceInterface describes Network Edge device interface type DeviceInterface struct { ID *int Name *string @@ -288,14 +293,14 @@ type DeviceInterface struct { Type *string } -//DeviceUserPublicKey describes public SSH key along with username that is -//provisioned on a network device. +// DeviceUserPublicKey describes public SSH key along with username that is +// provisioned on a network device. type DeviceUserPublicKey struct { Username *string KeyName *string } -//DeviceType describes Network Edge device type +// DeviceType describes Network Edge device type type DeviceType struct { Name *string Code *string @@ -305,8 +310,8 @@ type DeviceType struct { MetroCodes []string } -//DevicePlatform describes Network Edge platform configurations -//available for a given device type +// DevicePlatform describes Network Edge platform configurations +// available for a given device type type DevicePlatform struct { Flavor *string CoreCount *int @@ -317,7 +322,7 @@ type DevicePlatform struct { LicenseOptions []string } -//DeviceSoftwareVersion describes available software packages and versions for a Network Edge device +// DeviceSoftwareVersion describes available software packages and versions for a Network Edge device type DeviceSoftwareVersion struct { Version *string ImageName *string @@ -328,7 +333,7 @@ type DeviceSoftwareVersion struct { PackageCodes []string } -//SSHUser describes Network Edge SSH user +// SSHUser describes Network Edge SSH user type SSHUser struct { UUID *string Username *string @@ -336,7 +341,7 @@ type SSHUser struct { DeviceUUIDs []string } -//BGPConfiguration describes Network Edge BGP configuration +// BGPConfiguration describes Network Edge BGP configuration type BGPConfiguration struct { UUID *string ConnectionUUID *string @@ -350,7 +355,7 @@ type BGPConfiguration struct { ProvisioningStatus *string } -//SSHPublicKey describes Network Edge SSH user public key +// SSHPublicKey describes Network Edge SSH user public key type SSHPublicKey struct { UUID *string Name *string @@ -358,7 +363,7 @@ type SSHPublicKey struct { Type *string } -//ACLTemplate describes Network Edge device ACL template +// ACLTemplate describes Network Edge device ACL template type ACLTemplate struct { UUID *string Name *string @@ -370,8 +375,8 @@ type ACLTemplate struct { DeviceDetails []ACLTemplateDeviceDetails } -//ACLTemplateInboundRule describes inbound ACL rule that is part of -//Network Edge device ACL template +// ACLTemplateInboundRule describes inbound ACL rule that is part of +// Network Edge device ACL template type ACLTemplateInboundRule struct { SeqNo *int FQDN *string // Deprecated: FQDN is no longer supported @@ -384,27 +389,27 @@ type ACLTemplateInboundRule struct { Description *string } -//ACLTemplateDeviceDetails describes Device Details this template applied to +// ACLTemplateDeviceDetails describes Device Details this template applied to type ACLTemplateDeviceDetails struct { UUID *string Name *string ACLStatus *string } -//DeviceAdditionalBandwidthDetails describes details of a device -//additional badwidth +// DeviceAdditionalBandwidthDetails describes details of a device +// additional badwidth type DeviceAdditionalBandwidthDetails struct { AdditionalBandwidth *int Status *string } -//DeviceACLDetails describes details of a device -//additional badwidth +// DeviceACLDetails describes details of a device +// additional badwidth type DeviceACLDetails struct { Status *string } -//DeviceLinkGroup describes details of a device link group +// DeviceLinkGroup describes details of a device link group type DeviceLinkGroup struct { UUID *string Name *string @@ -414,8 +419,8 @@ type DeviceLinkGroup struct { Links []DeviceLinkGroupLink } -//DeviceLinkGroupDevice describes details of a device within device -//link group +// DeviceLinkGroupDevice describes details of a device within device +// link group type DeviceLinkGroupDevice struct { DeviceID *string ASN *int @@ -424,8 +429,8 @@ type DeviceLinkGroupDevice struct { IPAddress *string } -//DeviceLinkGroupLink describes details if a link (connection) within -//device link group +// DeviceLinkGroupLink describes details if a link (connection) within +// device link group type DeviceLinkGroupLink struct { AccountNumber *string Throughput *string @@ -436,7 +441,7 @@ type DeviceLinkGroupLink struct { DestinationZoneCode *string } -//ClusterDetails describes Network Edge cluster device details +// ClusterDetails describes Network Edge cluster device details type ClusterDetails struct { ClusterName *string NumOfNodes *int @@ -447,7 +452,7 @@ type ClusterDetails struct { Node1 *ClusterNodeDetail } -//ClusterNodeDetail describes Network Edge cluster node details +// ClusterNodeDetail describes Network Edge cluster node details type ClusterNodeDetail struct { UUID *string Name *string @@ -464,7 +469,7 @@ type ClusterNode struct { // Deprecated: Use ClusterNodeDetail instead VendorConfiguration map[string]string } -//File describes Network Edge uploaded file +// File describes Network Edge uploaded file type File struct { UUID *string FileName *string diff --git a/internal/api/device.go b/internal/api/device.go index 3b80e02..fa330ab 100644 --- a/internal/api/device.go +++ b/internal/api/device.go @@ -1,6 +1,6 @@ package api -//Device describes network edge device +// Device describes network edge device type Device struct { UUID *string `json:"uuid,omitempty"` Name *string `json:"name,omitempty"` @@ -44,7 +44,7 @@ type Device struct { Connectivity *string `json:"connectivity,omitempty"` } -//DeviceRequest describes network edge device creation request +// DeviceRequest describes network edge device creation request type DeviceRequest struct { Throughput *int `json:"throughput,omitempty,string"` ThroughputUnit *string `json:"throughputUnit,omitempty"` @@ -77,7 +77,7 @@ type DeviceRequest struct { Connectivity *string `json:"connectivity,omitempty"` } -//SecondaryDeviceRequest describes secondary device part of device creation request +// SecondaryDeviceRequest describes secondary device part of device creation request type SecondaryDeviceRequest struct { MetroCode *string `json:"metroCode,omitempty"` LicenseToken *string `json:"licenseToken,omitempty"` @@ -95,7 +95,7 @@ type SecondaryDeviceRequest struct { UserPublicKey *DeviceUserPublicKeyRequest `json:"userPublicKey,omitempty"` } -//DeviceInterface describes device network interface +// DeviceInterface describes device network interface type DeviceInterface struct { ID *int `json:"id,omitempty"` Name *string `json:"name,omitempty"` @@ -107,30 +107,30 @@ type DeviceInterface struct { Type *string `json:"type,omitempty"` } -//DeviceUserPublicKey describes public SSH key along with username that is -//provisioned on a network device +// DeviceUserPublicKey describes public SSH key along with username that is +// provisioned on a network device type DeviceUserPublicKey struct { Username *string `json:"username,omitempty"` KeyName *string `json:"publicKeyName,omitempty"` Key *string `json:"publicKey,omitempty"` } -//DeviceUserPublicKeyRequest describes public SSH key along with username that -//will be provisioned on a network device. SSH key has to be created beforehand -//and referred by its name +// DeviceUserPublicKeyRequest describes public SSH key along with username that +// will be provisioned on a network device. SSH key has to be created beforehand +// and referred by its name type DeviceUserPublicKeyRequest struct { Username *string `json:"username,omitempty"` KeyName *string `json:"keyName,omitempty"` } -//DeviceCoreInformation describes device core and memory information +// DeviceCoreInformation describes device core and memory information type DeviceCoreInformation struct { Core *int `json:"core,omitempty"` Memory *int `json:"memory,omitempty"` Unit *string `json:"unit,omitempty"` } -//DeviceRequestResponse describes response for device creation request +// DeviceRequestResponse describes response for device creation request type DeviceRequestResponse struct { UUID *string `json:"uuid,omitempty"` SecondaryUUID *string `json:"secondaryUuid,omitempty"` @@ -138,32 +138,33 @@ type DeviceRequestResponse struct { ClusterID *string `json:"clusterId,omitempty"` } -//DeviceUpdateRequest describes network device update request +// DeviceUpdateRequest describes network device update request type DeviceUpdateRequest struct { Notifications []string `json:"notifications"` TermLength *int `json:"termLength,omitempty"` VirtualDeviceName *string `json:"virtualDeviceName,omitempty"` + Core *int `json:"core,omitempty"` } -//DeviceAdditionalBandwidthUpdateRequest describes network device additional bandwidth update request +// DeviceAdditionalBandwidthUpdateRequest describes network device additional bandwidth update request type DeviceAdditionalBandwidthUpdateRequest struct { AdditionalBandwidth *int `json:"additionalBandwidth"` } -//DevicesResponse describes response for a get device list request +// DevicesResponse describes response for a get device list request type DevicesResponse struct { Pagination Pagination `json:"pagination,omitempty"` Data []Device `json:"data,omitempty"` } -//DeviceACLTemplateRequest describes request for updating device ACL template +// DeviceACLTemplateRequest describes request for updating device ACL template type DeviceACLTemplateRequest struct { TemplateUUID *string `json:"aclTemplateUuid,omitempty"` MgmtAclTemplateUUID *string `json:"mgmtAclTemplateUuid,omitempty"` } -//DeviceAdditionalBandwidthResponse describes response for device additional -//bandwidth get request +// DeviceAdditionalBandwidthResponse describes response for device additional +// bandwidth get request type DeviceAdditionalBandwidthResponse struct { AdditionalBandwidth *int `json:"additionalBandwidth,omitempty"` Status *string `json:"status,omitempty"` @@ -173,20 +174,20 @@ type DeviceACLResponse struct { Status *string `json:"status,omitempty"` } -//ClusterDetailsRequest describes cluster details of device creation request +// ClusterDetailsRequest describes cluster details of device creation request type ClusterDetailsRequest struct { ClusterName *string `json:"clusterName,omitempty"` ClusterNodeDetails map[string]ClusterNodeDetailRequest `json:"clusterNodeDetails,omitempty"` } -//ClusterNodeDetailRequest describes cluster node configuration of device creation request +// ClusterNodeDetailRequest describes cluster node configuration of device creation request type ClusterNodeDetailRequest struct { VendorConfiguration map[string]string `json:"vendorConfig,omitempty"` LicenseFileID *string `json:"licenseFileId,omitempty"` LicenseToken *string `json:"licenseToken,omitempty"` } -//ClusterDetails describes cluster details for device response +// ClusterDetails describes cluster details for device response type ClusterDetails struct { ClusterID *string `json:"clusterId,omitempty"` ClusterName *string `json:"clusterName,omitempty"` @@ -194,7 +195,7 @@ type ClusterDetails struct { Nodes []ClusterNode `json:"nodes,omitempty"` } -//ClusterNode describes cluster node details for device response +// ClusterNode describes cluster node details for device response type ClusterNode struct { UUID *string `json:"uuid,omitempty"` Name *string `json:"name,omitempty"` diff --git a/rest_device.go b/rest_device.go index 850ba7c..65edb4f 100644 --- a/rest_device.go +++ b/rest_device.go @@ -35,7 +35,7 @@ type restDeviceUpdateRequest struct { c RestClient } -//CreateDevice creates given Network Edge device and returns its UUID upon successful creation +// CreateDevice creates given Network Edge device and returns its UUID upon successful creation func (c RestClient) CreateDevice(device Device) (*string, error) { path := "/ne/v1/devices" reqBody := createDeviceRequest(device) @@ -47,8 +47,8 @@ func (c RestClient) CreateDevice(device Device) (*string, error) { return respBody.UUID, nil } -//CreateRedundantDevice creates HA device setup from given primary and secondary devices and -//returns their UUIDS upon successful creation +// CreateRedundantDevice creates HA device setup from given primary and secondary devices and +// returns their UUIDS upon successful creation func (c RestClient) CreateRedundantDevice(primary Device, secondary Device) (*string, *string, error) { path := "/ne/v1/devices" reqBody := createRedundantDeviceRequest(primary, secondary) @@ -60,7 +60,7 @@ func (c RestClient) CreateRedundantDevice(primary Device, secondary Device) (*st return respBody.UUID, respBody.SecondaryUUID, nil } -//GetDevice fetches details of a device with a given UUID +// GetDevice fetches details of a device with a given UUID func (c RestClient) GetDevice(uuid string) (*Device, error) { path := "/ne/v1/devices/" + url.PathEscape(uuid) result := api.Device{} @@ -71,7 +71,7 @@ func (c RestClient) GetDevice(uuid string) (*Device, error) { return mapDeviceAPIToDomain(result), nil } -//GetDevices retrieves list of devices (along with their details) with given list of statuses +// GetDevices retrieves list of devices (along with their details) with given list of statuses func (c RestClient) GetDevices(statuses []string) ([]Device, error) { path := "/ne/v1/devices" content, err := c.GetOffsetPaginated(path, &api.DevicesResponse{}, @@ -87,7 +87,7 @@ func (c RestClient) GetDevices(statuses []string) ([]Device, error) { return transformed, nil } -//GetDeviceAdditionalBandwidthDetails retrives details of given device's additional bandwidth +// GetDeviceAdditionalBandwidthDetails retrives details of given device's additional bandwidth func (c RestClient) GetDeviceAdditionalBandwidthDetails(uuid string) (*DeviceAdditionalBandwidthDetails, error) { path := fmt.Sprintf("/ne/v1/devices/%s/additionalBandwidths", url.PathEscape(uuid)) result := api.DeviceAdditionalBandwidthResponse{} @@ -98,7 +98,7 @@ func (c RestClient) GetDeviceAdditionalBandwidthDetails(uuid string) (*DeviceAdd return mapDeviceAdditionalBandwidthAPIToDomain(result), nil } -//GetDeviceACLDetails retrives device acl template provisioning status +// GetDeviceACLDetails retrives device acl template provisioning status func (c RestClient) GetDeviceACLDetails(uuid string) (*DeviceACLDetails, error) { path := fmt.Sprintf("/ne/v1/devices/%s/acl", url.PathEscape(uuid)) result := api.DeviceACLResponse{} @@ -109,7 +109,7 @@ func (c RestClient) GetDeviceACLDetails(uuid string) (*DeviceACLDetails, error) return mapDeviceACLAPIToDomain(result), nil } -//NewDeviceUpdateRequest creates new composite update request for a device with a given UUID +// NewDeviceUpdateRequest creates new composite update request for a device with a given UUID func (c RestClient) NewDeviceUpdateRequest(uuid string) DeviceUpdateRequest { return &restDeviceUpdateRequest{ uuid: uuid, @@ -117,7 +117,7 @@ func (c RestClient) NewDeviceUpdateRequest(uuid string) DeviceUpdateRequest { c: c} } -//DeleteDevice deletes device with a given UUID +// DeleteDevice deletes device with a given UUID func (c RestClient) DeleteDevice(uuid string) error { path := "/ne/v1/devices/" + url.PathEscape(uuid) req := c.R().SetQueryParam("deleteRedundantDevice", "true") @@ -127,45 +127,51 @@ func (c RestClient) DeleteDevice(uuid string) error { return nil } -//WithDeviceName sets new device name in a composite device update request +// WithDeviceName sets new device name in a composite device update request func (req *restDeviceUpdateRequest) WithDeviceName(deviceName string) DeviceUpdateRequest { req.deviceFields["deviceName"] = deviceName return req } -//WithTermLength sets new term length in a composite device update request +// WithTermLength sets new term length in a composite device update request func (req *restDeviceUpdateRequest) WithTermLength(termLength int) DeviceUpdateRequest { req.deviceFields["termLength"] = termLength return req } -//WithNotifications sets new notifications in a composite device update request +// WithNotifications sets new notifications in a composite device update request func (req *restDeviceUpdateRequest) WithNotifications(notifications []string) DeviceUpdateRequest { req.deviceFields["notifications"] = notifications return req } -//WithAdditionalBandwidth sets new additional bandwidth in a composite device update request +// WithCore sets new core count in a composite device update request +func (req *restDeviceUpdateRequest) WithCore(core int) DeviceUpdateRequest { + req.deviceFields["core"] = core + return req +} + +// WithAdditionalBandwidth sets new additional bandwidth in a composite device update request func (req *restDeviceUpdateRequest) WithAdditionalBandwidth(additionalBandwidth int) DeviceUpdateRequest { req.additionalBandwidth = &additionalBandwidth return req } -//WithACLTemplate sets new ACL template identifier in a composite device update request +// WithACLTemplate sets new ACL template identifier in a composite device update request func (req *restDeviceUpdateRequest) WithACLTemplate(templateID string) DeviceUpdateRequest { req.aclTemplateID = &templateID return req } -//WithMgmtAclTemplate sets new MGMT ACL template identifier in a composite device update request +// WithMgmtAclTemplate sets new MGMT ACL template identifier in a composite device update request func (req *restDeviceUpdateRequest) WithMgmtAclTemplate(mgmtAclTemplateUuid string) DeviceUpdateRequest { req.mgmtAclTemplateUuid = &mgmtAclTemplateUuid return req } -//Execute attempts to update device according new data set in composite update request. -//This is not atomic operation and if any update will fail, other changes won't be reverted. -//UpdateError will be returned if any of requested data failed to update +// Execute attempts to update device according new data set in composite update request. +// This is not atomic operation and if any update will fail, other changes won't be reverted. +// UpdateError will be returned if any of requested data failed to update func (req *restDeviceUpdateRequest) Execute() error { updateErr := UpdateError{} if err := req.c.replaceDeviceFields(req.uuid, req.deviceFields); err != nil { @@ -456,6 +462,10 @@ func (c RestClient) replaceDeviceFields(uuid string, fields map[string]interface reqBody.Notifications = v.([]string) okToSend = true } + if v, ok := fields["core"]; ok { + reqBody.Core = Int(v.(int)) + okToSend = true + } if okToSend { path := "/ne/v1/devices/" + uuid req := c.R().SetBody(&reqBody)