From b876405c97ee588d1f10607808e08c3608cdcc52 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B1=88=E8=BD=A9?= Date: Tue, 9 Jun 2026 14:16:49 +0800 Subject: [PATCH] fix(region): vendor update (#24998) --- go.mod | 2 +- go.sum | 4 +- vendor/modules.txt | 2 +- .../pkg/apis/compute/storage_const.go | 5 + .../cloudmux/pkg/multicloud/rockbase/disk.go | 47 +++---- .../x/cloudmux/pkg/multicloud/rockbase/eip.go | 22 +-- .../cloudmux/pkg/multicloud/rockbase/host.go | 127 ++++++++---------- .../pkg/multicloud/rockbase/instance.go | 82 +++++------ .../pkg/multicloud/rockbase/instancetype.go | 6 +- .../pkg/multicloud/rockbase/network.go | 24 ++-- .../pkg/multicloud/rockbase/region.go | 45 ++++--- .../pkg/multicloud/rockbase/storage.go | 50 +++---- .../cloudmux/pkg/multicloud/rockbase/utils.go | 22 +-- .../cloudmux/pkg/multicloud/rockbase/zone.go | 6 + .../x/cloudmux/pkg/multicloud/ucloud/disk.go | 47 +++---- .../x/cloudmux/pkg/multicloud/ucloud/eip.go | 22 +-- .../x/cloudmux/pkg/multicloud/ucloud/host.go | 122 ++++++++--------- .../pkg/multicloud/ucloud/instance.go | 88 +++++------- .../pkg/multicloud/ucloud/instancetype.go | 6 +- .../cloudmux/pkg/multicloud/ucloud/network.go | 24 ++-- .../cloudmux/pkg/multicloud/ucloud/region.go | 44 +++--- .../cloudmux/pkg/multicloud/ucloud/storage.go | 47 +++---- .../x/cloudmux/pkg/multicloud/ucloud/utils.go | 22 +-- .../x/cloudmux/pkg/multicloud/ucloud/zone.go | 6 + 24 files changed, 402 insertions(+), 470 deletions(-) diff --git a/go.mod b/go.mod index fa414bff65..c1d96a77a2 100644 --- a/go.mod +++ b/go.mod @@ -108,7 +108,7 @@ require ( k8s.io/cri-api v0.28.15 k8s.io/klog/v2 v2.90.1 moul.io/http2curl/v2 v2.3.0 - yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260608093459-7789fd47ef2b + yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260609055727-275f3963d64c yunion.io/x/executor v0.0.0-20260312022053-f538abd2b005 yunion.io/x/jsonutils v1.0.1-0.20250507052344-1abcf4f443b1 yunion.io/x/log v1.0.1-0.20240305175729-7cf2d6cd5a91 diff --git a/go.sum b/go.sum index 4dfdfc2322..52d4615d9b 100644 --- a/go.sum +++ b/go.sum @@ -1785,8 +1785,8 @@ sigs.k8s.io/yaml v1.1.0/go.mod h1:UJmg0vDUVViEyp3mgSv9WPwZCDxu4rQW1olrI1uml+o= sigs.k8s.io/yaml v1.2.0/go.mod h1:yfXDCHCao9+ENCvLSE62v9VSji2MKu5jeNfTrofGhJc= sigs.k8s.io/yaml v1.3.0 h1:a2VclLzOGrwOHDiV8EfBGhvjHvP46CtW5j6POvhYGGo= sigs.k8s.io/yaml v1.3.0/go.mod h1:GeOyir5tyXNByN85N/dRIT9es5UQNerPYEKK56eTBm8= -yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260608093459-7789fd47ef2b h1:/ksenqUkmchwkBsE80p7RMzvsNyPNtPHQHHHJjUoumA= -yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260608093459-7789fd47ef2b/go.mod h1:TbMuTWxcTdyL2Usn+WQdIw0jdlBYO66SzPRY8LZ3Wj0= +yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260609055727-275f3963d64c h1:XucESU4LflBCCvfiW89YcdG58a0KQ9KPJK/ucFsQcww= +yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260609055727-275f3963d64c/go.mod h1:TbMuTWxcTdyL2Usn+WQdIw0jdlBYO66SzPRY8LZ3Wj0= yunion.io/x/executor v0.0.0-20260312022053-f538abd2b005 h1:3sWwcjGXGjG9mLBWa7AyLq+QSi0udTAx21pfVQRFMBE= yunion.io/x/executor v0.0.0-20260312022053-f538abd2b005/go.mod h1:Uxuou9WQIeJXNpy7t2fPLL0BYLvLiMvGQwY7Qc6aSws= yunion.io/x/jsonutils v0.0.0-20190625054549-a964e1e8a051/go.mod h1:4N0/RVzsYL3kH3WE/H1BjUQdFiWu50JGCFQuuy+Z634= diff --git a/vendor/modules.txt b/vendor/modules.txt index b5aa773b89..3e318f84a5 100644 --- a/vendor/modules.txt +++ b/vendor/modules.txt @@ -2603,7 +2603,7 @@ sigs.k8s.io/structured-merge-diff/v4/value # sigs.k8s.io/yaml v1.3.0 ## explicit; go 1.12 sigs.k8s.io/yaml -# yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260608093459-7789fd47ef2b +# yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20260609055727-275f3963d64c ## explicit; go 1.24 yunion.io/x/cloudmux/pkg/apis yunion.io/x/cloudmux/pkg/apis/billing diff --git a/vendor/yunion.io/x/cloudmux/pkg/apis/compute/storage_const.go b/vendor/yunion.io/x/cloudmux/pkg/apis/compute/storage_const.go index dfc1ecc97f..084296a48f 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/apis/compute/storage_const.go +++ b/vendor/yunion.io/x/cloudmux/pkg/apis/compute/storage_const.go @@ -207,6 +207,11 @@ var UCLOUD_STORAGES = []string{ STORAGE_UCLOUD_CLOUD_RSSD, } +var UCLOUD_LOCAL_STORAGES = []string{ + STORAGE_UCLOUD_LOCAL_SSD, + STORAGE_UCLOUD_LOCAL_NORMAL, +} + var KSYUN_STORAGES = []string{ STORAGE_KSYUN_ESSD_AUTO_PL, STORAGE_KSYUN_ESSD_PL1, diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/disk.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/disk.go index 2508f45b03..cf16acefd5 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/disk.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/disk.go @@ -23,8 +23,6 @@ import ( "github.com/pkg/errors" "yunion.io/x/jsonutils" - "yunion.io/x/log" - "yunion.io/x/pkg/utils" billing_api "yunion.io/x/cloudmux/pkg/apis/billing" api "yunion.io/x/cloudmux/pkg/apis/compute" @@ -163,11 +161,10 @@ func (self *SDisk) GetIsAutoDelete() bool { func (self *SDisk) GetTemplateId() string { if strings.Contains(self.DiskType, "SystemDisk") && len(self.UHostID) > 0 { - ins, err := self.storage.zone.region.GetInstanceByID(self.UHostID) + ins, err := self.storage.zone.region.GetInstance(self.UHostID) if err != nil { - log.Errorln(err) + return "" } - return ins.ImageID } @@ -303,27 +300,23 @@ func (self *SDisk) Rebuild(ctx context.Context) error { } func (self *SRegion) GetDisk(diskId string) (*SDisk, error) { - if len(diskId) == 0 { - return nil, fmt.Errorf("GetDisk id should not empty") - } - - disks, err := self.GetDisks("", "", []string{diskId}) + disks, err := self.GetDisks("", "", "", diskId) if err != nil { return nil, err } - if len(disks) == 1 { - return &disks[0], nil - } else if len(disks) == 0 { - return nil, cloudprovider.ErrNotFound - } else { - return nil, fmt.Errorf("GetDisk %s %d found", diskId, len(disks)) + for i := range disks { + if disks[i].UDiskID == diskId { + return &disks[i], nil + } } + + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "GetDisk %s", diskId) } // https://docs.ucloud.cn/api/udisk-api/describe_udisk // diskType DataDisk|SystemDisk (DataDisk表示数据盘,SystemDisk表示系统盘) -func (self *SRegion) GetDisks(zoneId string, diskType string, diskIds []string) ([]SDisk, error) { +func (self *SRegion) GetDisks(zoneId string, diskType string, isBoot string, diskId string) ([]SDisk, error) { disks := make([]SDisk, 0) params := NewRockbaseParams() if len(zoneId) > 0 { @@ -331,25 +324,23 @@ func (self *SRegion) GetDisks(zoneId string, diskType string, diskIds []string) } if len(diskType) > 0 { + params.Set("ProtocolVersion", "1") params.Set("DiskType", diskType) } + if len(diskId) > 0 { + params.Set("UDiskId", diskId) + } + + if len(isBoot) > 0 { + params.Set("IsBoot", isBoot) + } + err := self.DoListAll("DescribeUDisk", params, &disks) if err != nil { return nil, err } - if len(diskIds) > 0 { - filtedDisks := make([]SDisk, 0) - for i := range disks { - if utils.IsInStringArray(disks[i].UDiskID, diskIds) { - filtedDisks = append(filtedDisks, disks[i]) - } - } - - return filtedDisks, nil - } - return disks, nil } diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/eip.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/eip.go index 9e29460b76..dfa4a40958 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/eip.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/eip.go @@ -15,12 +15,12 @@ package rockbase import ( - "fmt" "strings" "time" "yunion.io/x/jsonutils" "yunion.io/x/log" + "yunion.io/x/pkg/errors" billing_api "yunion.io/x/cloudmux/pkg/apis/billing" api "yunion.io/x/cloudmux/pkg/apis/compute" @@ -99,7 +99,7 @@ func (self *SEip) GetGlobalId() string { func (self *SEip) GetStatus() string { switch self.Status { case "used": - return api.EIP_STATUS_ASSOCIATE // ? + return api.EIP_STATUS_READY case "free": return api.EIP_STATUS_READY case "freeze": @@ -113,9 +113,9 @@ func (self *SEip) Refresh() error { if self.IsEmulated() { return nil } - new, err := self.region.GetEipById(self.GetId()) + new, err := self.region.GetEip(self.GetId()) if err != nil { - return err + return errors.Wrapf(err, "Refresh") } return jsonutils.Update(self, new) } @@ -225,12 +225,15 @@ func (self *SRegion) CreateEIP(eip *cloudprovider.SEip) (cloudprovider.ICloudEIP params.Set("OperatorName", eip.BGPType) params.Set("Bandwidth", eip.BandwidthMbps) params.Set("Name", eip.Name) + params.Set("Region", self.GetId()) var payMode string switch eip.ChargeType { case api.EIP_CHARGE_TYPE_BY_TRAFFIC: payMode = "Traffic" case api.EIP_CHARGE_TYPE_BY_BANDWIDTH: payMode = "Bandwidth" + default: + payMode = "Bandwidth" } params.Set("PayMode", payMode) params.Set("ChargeType", "Dynamic") // 按需付费 @@ -241,14 +244,11 @@ func (self *SRegion) CreateEIP(eip *cloudprovider.SEip) (cloudprovider.ICloudEIP return nil, err } - if len(eips) == 1 { - eip := eips[0] - eip.region = self - eip.Refresh() - return &eip, nil - } else { - return nil, fmt.Errorf("CreateEIP %d eip created", len(eips)) + for i := range eips { + eips[i].region = self + return &eips[i], nil } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "CreateEIP %d eip created", len(eips)) } // https://docs.ucloud.cn/api/unet-api/release_eip diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/host.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/host.go index b5ac244683..a77ec5b879 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/host.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/host.go @@ -17,11 +17,10 @@ package rockbase import ( "encoding/base64" "fmt" + "regexp" "strconv" - "strings" "yunion.io/x/jsonutils" - "yunion.io/x/log" "yunion.io/x/pkg/errors" "yunion.io/x/pkg/util/billing" @@ -77,13 +76,13 @@ func (self *SHost) GetIVMs() ([]cloudprovider.ICloudVM, error) { } func (self *SHost) GetIVMById(id string) (cloudprovider.ICloudVM, error) { - vm, err := self.zone.region.GetInstanceByID(id) + vm, err := self.zone.region.GetInstance(id) if err != nil { return nil, err } vm.host = self - return &vm, nil + return vm, nil } func (self *SHost) GetIStorages() ([]cloudprovider.ICloudStorage, error) { @@ -162,19 +161,19 @@ func (self *SHost) GetVersion() string { // 不支持user data // 不支持指定keypair -func (self *SHost) CreateVM(desc *cloudprovider.SManagedVMCreateConfig) (cloudprovider.ICloudVM, error) { - vmId, err := self._createVM(desc.Name, desc.ExternalImageId, desc.SysDisk, desc.Cpu, desc.MemoryMB, desc.InstanceType, desc.ExternalNetworkId, desc.IpAddr, desc.Description, desc.Password, desc.DataDisks, desc.ExternalSecgroupIds, desc.BillingCycle) +func (self *SHost) CreateVM(opts *cloudprovider.SManagedVMCreateConfig) (cloudprovider.ICloudVM, error) { + vmId, err := self._createVM(opts) if err != nil { return nil, err } - vm, err := self.zone.region.GetInstanceByID(vmId) + vm, err := self.zone.region.GetInstance(vmId) if err != nil { return nil, err } vm.host = self - return &vm, err + return vm, err } func (host *SHost) GetIHostNics() ([]cloudprovider.ICloudHostNetInterface, error) { @@ -187,103 +186,92 @@ func (host *SHost) GetIHostNics() ([]cloudprovider.ICloudHostNetInterface, error type SInstanceType struct { UHostType string + GpuType string CPU int MemoryMB int GPU int } +// 格式: {机型}.c{cpu}.m{memGB}[.g{gpu}],机型支持 UCloud GpuType 如 T4S、2080Ti-4C、T4/4 +var instanceTypeRe = regexp.MustCompile(`^([A-Za-z0-9][A-Za-z0-9/_-]*)\.c(\d+)\.m(\d+)(?:\.g(\d+))?$`) + func ParseInstanceType(instanceType string) (SInstanceType, error) { i := SInstanceType{} - segs := strings.Split(instanceType, ".") - if len(segs) < 3 { + matches := instanceTypeRe.FindStringSubmatch(instanceType) + if matches == nil { return i, fmt.Errorf("invalid instance type %s", instanceType) - } else if len(segs) >= 4 { - gpu, err := strconv.Atoi(strings.TrimLeft(segs[3], "g")) + } + + hostType := matches[1] + cpu, err := strconv.Atoi(matches[2]) + if err != nil { + return i, err + } + memGB, err := strconv.Atoi(matches[3]) + if err != nil { + return i, err + } + + i.CPU = cpu + i.MemoryMB = memGB * 1024 + if len(matches[4]) > 0 { + gpu, err := strconv.Atoi(matches[4]) if err != nil { return i, err } - i.GPU = gpu + i.GpuType = hostType + i.UHostType = "G" + } else { + i.UHostType = hostType } - - cpu, err := strconv.Atoi(strings.TrimLeft(segs[1], "c")) - if err != nil { - return i, err - } - - mem, err := strconv.Atoi(strings.TrimLeft(segs[2], "m")) - if err != nil { - return i, err - } - - i.UHostType = segs[0] - i.CPU = cpu - i.MemoryMB = mem * 1024 return i, nil } -func (self *SHost) _createVM(name, imgId string, sysDisk cloudprovider.SDiskInfo, cpu, memMB int, instanceType string, - networkId, ipAddr, desc, passwd string, - dataDisks []cloudprovider.SDiskInfo, secgroupIds []string, bc *billing.SBillingCycle) (string, error) { - // 网络配置及安全组绑定 - net, _ := self.zone.region.getNetwork(networkId) - if net == nil { - return "", fmt.Errorf("invalid network ID %s", networkId) +func (self *SHost) _createVM(opts *cloudprovider.SManagedVMCreateConfig) (string, error) { + net, err := self.zone.region.getNetwork(opts.ExternalNetworkId) + if err != nil { + return "", errors.Wrapf(err, "getNetwork %s", opts.ExternalNetworkId) } - if net.wire == nil { - log.Errorf("network's wire is empty") - return "", fmt.Errorf("network's wire is empty") - } - - if net.wire.vpc == nil { - log.Errorf("wire's vpc is empty") - return "", fmt.Errorf("wire's vpc is empty") - } - - if len(passwd) == 0 { + if len(opts.Password) == 0 { return "", fmt.Errorf("CreateVM password should not be emtpty") } - // 镜像及硬盘配置 - img, err := self.zone.region.GetImage(imgId) + img, err := self.zone.region.GetImage(opts.ExternalImageId) if err != nil { - log.Errorf("GetImage %s fail %s", imgId, err) - return "", err + return "", errors.Wrapf(err, "GetImage %s", opts.ExternalImageId) } + if img.GetStatus() != api.CACHED_IMAGE_STATUS_ACTIVE { - log.Errorf("image %s status %s, expect %s", imgId, img.GetStatus(), api.CACHED_IMAGE_STATUS_ACTIVE) - return "", fmt.Errorf("image not ready") + return "", errors.Wrapf(cloudprovider.ErrInvalidStatus, "image %s status %s, expect %s", opts.ExternalImageId, img.GetStatus(), api.CACHED_IMAGE_STATUS_ACTIVE) } - disks := make([]SDisk, len(dataDisks)+1) + disks := make([]SDisk, len(opts.DataDisks)+1) disks[0].SizeGB = int(img.ImageSizeGB) - if sysDisk.SizeGB > 0 && sysDisk.SizeGB > int(img.ImageSizeGB) { - disks[0].SizeGB = sysDisk.SizeGB + if opts.SysDisk.SizeGB > 0 && opts.SysDisk.SizeGB > int(img.ImageSizeGB) { + disks[0].SizeGB = opts.SysDisk.SizeGB } - disks[0].DiskType = sysDisk.StorageType + disks[0].DiskType = opts.SysDisk.StorageType - for i, dataDisk := range dataDisks { + for i, dataDisk := range opts.DataDisks { disks[i+1].SizeGB = dataDisk.SizeGB disks[i+1].DiskType = dataDisk.StorageType } - // 创建实例 - // https://docs.ucloud.cn/api/uhost-api/uhost_type - // https://docs.ucloud.cn/compute/uhost/introduction/uhost/type var vmId string - i, err := ParseInstanceType(instanceType) + i, err := ParseInstanceType(opts.InstanceType) if err != nil { - if cpu <= 0 || memMB <= 0 { + if opts.Cpu <= 0 || opts.MemoryMB <= 0 { return "", err } else { - i.UHostType = "N2" - i.CPU = cpu - i.MemoryMB = memMB + i.UHostType = "O" + i.CPU = opts.Cpu + i.MemoryMB = opts.MemoryMB } } - vmId, err = self.zone.region.CreateInstance(name, imgId, i.UHostType, passwd, net.wire.vpc.GetId(), networkId, secgroupIds, self.zone.ZoneId, desc, ipAddr, i.CPU, i.MemoryMB, i.GPU, disks, bc) + vmId, err = self.zone.region.CreateInstance(opts.Name, opts.ExternalImageId, i.UHostType, opts.Password, net.wire.vpc.GetId(), opts.ExternalNetworkId, opts.ExternalSecgroupIds, self.zone.ZoneId, opts.Description, opts.IpAddr, i.CPU, i.MemoryMB, i.GPU, i.GpuType, disks, opts.BillingCycle) if err != nil { return "", fmt.Errorf("Failed to create: %v", err) } @@ -295,14 +283,14 @@ func (self *SHost) _createVM(name, imgId string, sysDisk cloudprovider.SDiskInfo // https://docs.ucloud.cn/api/uhost-api/specification // 支持8-30位字符, 不能包含[A-Z],[a-z],[0-9]和[()`~!@#$%^&*-+=_|{}[]:;'<>,.?/]之外的非法字符 func (self *SRegion) CreateInstance(name, imageId, hostType, password, vpcId, SubnetId string, securityGroupId []string, - zoneId, desc, ipAddr string, cpu, memMB, gpu int, disks []SDisk, bc *billing.SBillingCycle) (string, error) { + zoneId, desc, ipAddr string, cpu, memMB, gpu int, gpuType string, disks []SDisk, bc *billing.SBillingCycle) (string, error) { params := NewRockbaseParams() params.Set("Zone", zoneId) params.Set("ImageId", imageId) params.Set("Password", base64.StdEncoding.EncodeToString([]byte(password))) params.Set("LoginMode", "Password") params.Set("Name", name) - params.Set("UHostType", hostType) + params.Set("MachineType", hostType) params.Set("CPU", cpu) params.Set("Memory", memMB) params.Set("VPCId", vpcId) @@ -312,6 +300,9 @@ func (self *SRegion) CreateInstance(name, imageId, hostType, password, vpcId, Su } if gpu > 0 { params.Set("GPU", gpu) + if len(gpuType) > 0 { + params.Set("GpuType", gpuType) + } } if bc != nil && bc.GetMonths() >= 1 && bc.GetMonths() < 10 { @@ -347,7 +338,7 @@ func (self *SRegion) CreateInstance(name, imageId, hostType, password, vpcId, Su ret := Ret{} err := self.DoAction("CreateUHostInstance", params, &ret) if err != nil { - return "", err + return "", errors.Wrapf(err, "CreateUHostInstance") } if len(ret.UHostIds) == 1 { diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instance.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instance.go index df4cd9d703..b65fd8e59b 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instance.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instance.go @@ -55,6 +55,8 @@ type SInstance struct { State string `json:"State"` NetworkState string `json:"NetworkState"` HostType string `json:"HostType"` + MachineType string `json:"MachineType"` + GpuType string `json:"GpuType"` StorageType string `json:"StorageType"` TotalDiskSpace int `json:"TotalDiskSpace"` DiskSet []DiskSet `json:"DiskSet"` @@ -175,7 +177,7 @@ func (self *SInstance) GetStatus() string { } func (self *SInstance) Refresh() error { - new, err := self.host.zone.region.GetInstanceByID(self.GetId()) + new, err := self.host.zone.region.GetInstance(self.GetId()) if err != nil { return err } @@ -235,22 +237,17 @@ func (self *SInstance) GetLocalDisk(diskId, storageType string, sizeGB int, isBo func (self *SInstance) GetIDisks() ([]cloudprovider.ICloudDisk, error) { localDisks := make([]SDisk, 0) - diskIds := make([]string, 0) + disks := []SDisk{} for _, disk := range self.DiskSet { if utils.IsInStringArray(disk.DiskType, []string{api.STORAGE_ROCKBASE_LOCAL_NORMAL, api.STORAGE_ROCKBASE_LOCAL_SSD}) { localDisks = append(localDisks, self.GetLocalDisk(disk.DiskID, disk.DiskType, disk.Size, disk.IsBoot)) - } else { - diskIds = append(diskIds, disk.DiskID) + continue } - } - - disks := []SDisk{} - var err error - if len(diskIds) > 0 { - disks, err = self.host.zone.region.GetDisks("", "", diskIds) + disk, err := self.host.zone.region.GetDisk(disk.DiskID) if err != nil { return nil, err } + disks = append(disks, *disk) } disks = append(disks, localDisks...) @@ -302,12 +299,12 @@ func (self *SInstance) GetINics() ([]cloudprovider.ICloudNic, error) { func (self *SInstance) GetIEIP() (cloudprovider.ICloudEIP, error) { for _, ip := range self.IPSet { if len(ip.IPId) > 0 { - eip, err := self.host.zone.region.GetEipById(ip.IPId) + eip, err := self.host.zone.region.GetEip(ip.IPId) if err != nil { - return nil, err + return nil, errors.Wrapf(err, "GetEip %s", ip.IPId) } - return &eip, nil + return eip, nil } } @@ -374,13 +371,22 @@ func (self *SInstance) GetMachine() string { return "pc" } -func (self *SInstance) GetInstanceType() string { - // C1.c8.m24 - if strings.HasPrefix(self.HostType, "G") { - return fmt.Sprintf("%s.c%d.m%d.g%d", self.HostType, self.CPU, self.MemoryMB/1014, self.GPU) - } else { - return fmt.Sprintf("%s.c%d.m%d", self.HostType, self.CPU, self.MemoryMB/1014) +func (self *SInstance) instanceTypeHostPrefix() string { + if self.GPU > 0 && len(self.GpuType) > 0 { + return self.GpuType } + if len(self.UHostType) > 0 { + return self.UHostType + } + if len(self.MachineType) > 0 { + return self.MachineType + } + return self.HostType +} + +func (self *SInstance) GetInstanceType() string { + memGB := self.MemoryMB / 1024 + return formatInstanceSpec(self.instanceTypeHostPrefix(), self.CPU, memGB, self.GPU) } // https://docs.ucloud.cn/api/unet-api/grant_firewall @@ -437,34 +443,7 @@ func (self *SInstance) UpdateUserData(userData string) error { } // https://docs.ucloud.cn/api/uhost-api/reinstall_uhost_instance -// 1.请确认在重新安装之前,该实例已被关闭; -// 2.请确认该实例未挂载UDisk; -// todo:// 3.将原系统重装为不同类型的系统时(Linux->Windows),不可选择保留数据盘; -// 4.重装不同版本的系统时(CentOS6->CentOS7),若选择保留数据盘,请注意数据盘的文件系统格式; -// 5.若主机CPU低于2核,不可重装为Windows系统。 func (self *SInstance) RebuildRoot(ctx context.Context, desc *cloudprovider.SManagedVMRebuildRootConfig) (string, error) { - if len(desc.PublicKey) > 0 { - return "", fmt.Errorf("DeployVM not support assign ssh keypair") - } - - if self.GetStatus() != api.VM_READY { - return "", fmt.Errorf("DeployVM instance status %s , expected %s.", self.GetStatus(), api.VM_READY) - } - - if len(self.DiskSet) > 1 { - for _, disk := range self.DiskSet { - if disk.Type == "Data" { - err := self.host.zone.region.DetachDisk(self.host.zone.GetId(), self.GetId(), disk.DiskID) - if err != nil { - return "", fmt.Errorf("RebuildRoot detach disk %s", err) - } - - defer self.host.zone.region.AttachDisk(self.host.zone.GetId(), self.GetId(), disk.DiskID) - } - - } - } - err := self.host.zone.region.RebuildRoot(self.GetId(), desc.ImageId, desc.Password) if err != nil { return "", err @@ -475,12 +454,12 @@ func (self *SInstance) RebuildRoot(ctx context.Context, desc *cloudprovider.SMan return "", errors.Wrap(err, "RebuildRoot") } - disks, err := self.GetIDisks() - if len(disks) > 0 { - return disks[0].GetId(), nil - } else { - return "", fmt.Errorf("RebuildRoot %s", err) + for _, disk := range self.DiskSet { + if disk.Type == "SystemDisk" { + return disk.DiskID, nil + } } + return "", errors.Wrapf(cloudprovider.ErrNotFound, "SystemDisk not found") } func (self *SInstance) DeployVM(ctx context.Context, opts *cloudprovider.SInstanceDeployOptions) error { @@ -614,6 +593,7 @@ func (self *SRegion) DeleteVM(instanceId string) error { params := NewRockbaseParams() params.Set("UHostId", instanceId) params.Set("Destroy", 1) // 跳过回收站,直接删除 + params.Set("ReleaseUDisk", true) return self.DoAction("TerminateUHostInstance", params, nil) } diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instancetype.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instancetype.go index 01e6b8290a..e9188970ed 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instancetype.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/instancetype.go @@ -326,11 +326,7 @@ func (self *SRegion) GetZoneStorageTypes(zoneId string) ([]string, error) { if err != nil { return nil, err } - storageTypes := collectStorageTypesFromInstanceTypes(types, zoneId) - if len(storageTypes) == 0 { - return nil, fmt.Errorf("no storage types found for zone %s", zoneId) - } - return storageTypes, nil + return collectStorageTypesFromInstanceTypes(types, zoneId), nil } // GetAvailableInstanceTypes 获取地域/可用区下可售机型信息。 diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/network.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/network.go index d6d5e2c321..a33194539b 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/network.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/network.go @@ -19,6 +19,7 @@ import ( "yunion.io/x/jsonutils" "yunion.io/x/log" + "yunion.io/x/pkg/errors" "yunion.io/x/pkg/util/netutils" "yunion.io/x/pkg/util/rbacscope" @@ -142,9 +143,6 @@ func (self *SRegion) GetNetwork(networkId string) (*SNetwork, error) { } func (self *SRegion) getNetwork(networkId string) (*SNetwork, error) { - if len(networkId) == 0 { - return nil, fmt.Errorf("getNetwork network id should not be empty") - } networks := make([]SNetwork, 0) params := NewRockbaseParams() @@ -154,19 +152,17 @@ func (self *SRegion) getNetwork(networkId string) (*SNetwork, error) { return nil, err } - if len(networks) == 1 { - network := networks[0] - vpc, err := self.GetVpc(network.VpcId) - if err != nil { - return nil, err + for i := range networks { + if networks[i].SubnetID == networkId { + vpc, err := self.GetVpc(networks[i].VpcId) + if err != nil { + return nil, err + } + networks[i].wire = &SWire{vpc: vpc} + return &networks[i], nil } - network.wire = &SWire{vpc: vpc} - return &network, nil - } else if len(networks) == 0 { - return nil, cloudprovider.ErrNotFound - } else { - return nil, fmt.Errorf("getNetwork %s %d found", networkId, len(networks)) } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "getNetwork %s", networkId) } // https://docs.ucloud.cn/api/vpc2.0-api/delete_subnet diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/region.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/region.go index 574f29f3b4..8581476a70 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/region.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/region.go @@ -71,11 +71,11 @@ func (self *SRegion) GetGeographicInfo() cloudprovider.SGeographicInfo { } func (self *SRegion) GetIVMById(id string) (cloudprovider.ICloudVM, error) { - instance, err := self.GetInstanceByID(id) + instance, err := self.GetInstance(id) if err != nil { return nil, err } - return &instance, nil + return instance, nil } func (self *SRegion) GetIDiskById(id string) (cloudprovider.ICloudDisk, error) { @@ -144,29 +144,30 @@ func (self *SRegion) GetIZoneById(id string) (cloudprovider.ICloudZone, error) { return nil, cloudprovider.ErrNotFound } -func (self *SRegion) GetEipById(eipId string) (SEip, error) { +func (self *SRegion) GetEip(eipId string) (*SEip, error) { params := NewRockbaseParams() params.Set("EIPIds.0", eipId) eips := make([]SEip, 0) err := self.DoListAll("DescribeEIP", params, &eips) if err != nil { - return SEip{}, err + return nil, err } - if len(eips) == 1 { - eip := eips[0] - eip.region = self - return eip, nil - } else if len(eips) == 0 { - return SEip{}, cloudprovider.ErrNotFound - } else { - return SEip{}, fmt.Errorf("GetEipById %d eip found", len(eips)) + for i := range eips { + if eips[i].EIPID == eipId { + eips[i].region = self + return &eips[i], nil + } } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "GetEip %s", eipId) } func (self *SRegion) GetIEipById(id string) (cloudprovider.ICloudEIP, error) { - eip, err := self.GetEipById(id) - return &eip, err + eip, err := self.GetEip(id) + if err != nil { + return nil, err + } + return eip, nil } // https://docs.ucloud.cn/api/unet-api/delete_firewall @@ -386,22 +387,22 @@ func (self *SRegion) GetZones() ([]SZone, error) { return zones, err } -func (self *SRegion) GetInstanceByID(instanceId string) (SInstance, error) { +// https://docs.ucloud.cn/api/uhost-api/describe_uhost_instance +func (self *SRegion) GetInstance(instanceId string) (*SInstance, error) { params := NewRockbaseParams() params.Set("UHostIds.0", instanceId) instances := make([]SInstance, 0) err := self.DoAction("DescribeUHostInstance", params, &instances) if err != nil { - return SInstance{}, err + return nil, errors.Wrapf(err, "DescribeUHostInstance") } - if len(instances) == 1 { - return instances[0], nil - } else if len(instances) == 0 { - return SInstance{}, cloudprovider.ErrNotFound - } else { - return SInstance{}, fmt.Errorf("GetInstanceByID %s %d found.", instanceId, len(instances)) + for i := range instances { + if instances[i].UHostID == instanceId { + return &instances[i], nil + } } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "GetInstance %s", instanceId) } func (self *SRegion) GetClient() *SRockbaseClient { diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/storage.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/storage.go index 24d3c59968..1cf99aa344 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/storage.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/storage.go @@ -23,6 +23,7 @@ import ( api "yunion.io/x/cloudmux/pkg/apis/compute" "yunion.io/x/cloudmux/pkg/cloudprovider" "yunion.io/x/cloudmux/pkg/multicloud" + "yunion.io/x/pkg/utils" ) type SStorage struct { @@ -65,30 +66,18 @@ func (self *SStorage) GetIZone() cloudprovider.ICloudZone { } func (self *SStorage) GetIDisks() ([]cloudprovider.ICloudDisk, error) { - disks, err := self.zone.region.GetDisks(self.zone.GetId(), "", nil) - if err != nil { - return nil, err - } - - filtedDisks := make([]SDisk, 0) - for _, disk := range disks { - // ssd 盘 - if self.storageType == api.STORAGE_ROCKBASE_CLOUD_SSD && strings.Contains(disk.DiskType, "SSD") { - filtedDisks = append(filtedDisks, disk) + ret := []cloudprovider.ICloudDisk{} + for _, isBoot := range []string{"True", "False"} { + disks, err := self.zone.region.GetDisks(self.zone.GetId(), self.storageType, isBoot, "") + if err != nil { + return nil, err } - - // 普通盘 - if self.storageType == api.STORAGE_ROCKBASE_CLOUD_NORMAL && !strings.Contains(disk.DiskType, "SSD") { - filtedDisks = append(filtedDisks, disk) + for _, disk := range disks { + disk.storage = self + ret = append(ret, &disk) } } - - idisks := make([]cloudprovider.ICloudDisk, len(filtedDisks)) - for i := 0; i < len(filtedDisks); i += 1 { - filtedDisks[i].storage = self - idisks[i] = &filtedDisks[i] - } - return idisks, nil + return ret, nil } func (self *SStorage) GetStorageType() string { @@ -124,6 +113,10 @@ func (self *SStorage) CreateIDisk(opts *cloudprovider.DiskCreateConfig) (cloudpr switch self.storageType { case api.STORAGE_ROCKBASE_CLOUD_SSD: diskType = "SSDDataDisk" + case api.STORAGE_ROCKBASE_CLOUD_ESSD: + diskType = "ESSDDataDisk" + case api.STORAGE_ROCKBASE_CLOUD_RSSD: + diskType = "RSSDDataDisk" } diskId, err := self.zone.region.CreateDisk(self.zone.GetId(), diskType, opts) if err != nil { @@ -140,12 +133,12 @@ func (self *SStorage) CreateIDisk(opts *cloudprovider.DiskCreateConfig) (cloudpr } func (self *SStorage) GetIDiskById(idStr string) (cloudprovider.ICloudDisk, error) { - if disk, err := self.zone.region.GetDisk(idStr); err != nil { + disk, err := self.zone.region.GetDisk(idStr) + if err != nil { return nil, err - } else { - disk.storage = self - return disk, nil } + disk.storage = self + return disk, nil } func (self *SStorage) GetMountPoint() string { @@ -155,3 +148,10 @@ func (self *SStorage) GetMountPoint() string { func (self *SStorage) IsSysDiskStore() bool { return true } + +func (self *SStorage) DisableSync() bool { + return utils.IsInStringArray(self.storageType, []string{ + api.STORAGE_ROCKBASE_LOCAL_SSD, + api.STORAGE_ROCKBASE_LOCAL_NORMAL, + }) +} diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/utils.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/utils.go index 135980b6e5..6f684b5f6d 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/utils.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/utils.go @@ -20,6 +20,7 @@ import ( "yunion.io/x/jsonutils" "yunion.io/x/log" + "yunion.io/x/pkg/errors" ) var responseMetaKeys = map[string]bool{ @@ -99,24 +100,21 @@ func detectArrayResultKey(resp jsonutils.JSONObject) string { return candidates[0] } -func unmarshalResult(resp jsonutils.JSONObject, respErr error, result interface{}) error { - if respErr != nil { - return respErr - } - +func unmarshalResult(resp jsonutils.JSONObject, result interface{}) error { if result == nil { return nil } + var err error resultKey := detectResultKey(resp, result) if len(resultKey) > 0 { - respErr = resp.Unmarshal(result, resultKey) + err = resp.Unmarshal(result, resultKey) } else { - respErr = resp.Unmarshal(result) + err = resp.Unmarshal(result) } - if respErr != nil { - log.Errorf("unmarshal json error %s", respErr) + if err != nil { + return errors.Wrapf(err, "unmarshalResult") } return nil @@ -154,7 +152,11 @@ func doListPart(client *SRockbaseClient, action string, params SParams, result i func DoAction(client *SRockbaseClient, action string, params SParams, result interface{}) error { params.SetAction(action) resp, err := jsonRequest(client, params) - return unmarshalResult(resp, err, result) + if err != nil { + log.Debugf("DoAction %s %s error %s", action, params.PrettyString(), err) + return err + } + return unmarshalResult(resp, result) } // 遍历所有结果 diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/zone.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/zone.go index 58bf166c97..91da951dcc 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/zone.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/rockbase/zone.go @@ -18,6 +18,7 @@ import ( "fmt" "yunion.io/x/pkg/errors" + "yunion.io/x/pkg/utils" api "yunion.io/x/cloudmux/pkg/apis/compute" "yunion.io/x/cloudmux/pkg/cloudprovider" @@ -52,6 +53,11 @@ func (self *SZone) fetchStorages() error { if err != nil { return err } + for _, storageType := range []string{api.STORAGE_ROCKBASE_LOCAL_SSD, api.STORAGE_ROCKBASE_LOCAL_NORMAL} { + if !utils.IsInStringArray(storageType, storageTypes) { + storageTypes = append(storageTypes, storageType) + } + } self.storageTypes = storageTypes self.istorages = make([]cloudprovider.ICloudStorage, len(self.storageTypes)) for i, sc := range self.storageTypes { diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/disk.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/disk.go index de8f10b7d3..b48132824d 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/disk.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/disk.go @@ -23,8 +23,6 @@ import ( "github.com/pkg/errors" "yunion.io/x/jsonutils" - "yunion.io/x/log" - "yunion.io/x/pkg/utils" billing_api "yunion.io/x/cloudmux/pkg/apis/billing" api "yunion.io/x/cloudmux/pkg/apis/compute" @@ -163,11 +161,10 @@ func (self *SDisk) GetIsAutoDelete() bool { func (self *SDisk) GetTemplateId() string { if strings.Contains(self.DiskType, "SystemDisk") && len(self.UHostID) > 0 { - ins, err := self.storage.zone.region.GetInstanceByID(self.UHostID) + ins, err := self.storage.zone.region.GetInstance(self.UHostID) if err != nil { - log.Errorln(err) + return "" } - return ins.ImageID } @@ -303,27 +300,23 @@ func (self *SDisk) Rebuild(ctx context.Context) error { } func (self *SRegion) GetDisk(diskId string) (*SDisk, error) { - if len(diskId) == 0 { - return nil, fmt.Errorf("GetDisk id should not empty") - } - - disks, err := self.GetDisks("", "", []string{diskId}) + disks, err := self.GetDisks("", "", "", diskId) if err != nil { return nil, err } - if len(disks) == 1 { - return &disks[0], nil - } else if len(disks) == 0 { - return nil, cloudprovider.ErrNotFound - } else { - return nil, fmt.Errorf("GetDisk %s %d found", diskId, len(disks)) + for i := range disks { + if disks[i].UDiskID == diskId { + return &disks[i], nil + } } + + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "GetDisk %s", diskId) } // https://docs.ucloud.cn/api/udisk-api/describe_udisk // diskType DataDisk|SystemDisk (DataDisk表示数据盘,SystemDisk表示系统盘) -func (self *SRegion) GetDisks(zoneId string, diskType string, diskIds []string) ([]SDisk, error) { +func (self *SRegion) GetDisks(zoneId string, diskType string, isBoot string, diskId string) ([]SDisk, error) { disks := make([]SDisk, 0) params := NewUcloudParams() if len(zoneId) > 0 { @@ -331,25 +324,23 @@ func (self *SRegion) GetDisks(zoneId string, diskType string, diskIds []string) } if len(diskType) > 0 { + params.Set("ProtocolVersion", "1") params.Set("DiskType", diskType) } + if len(diskId) > 0 { + params.Set("UDiskId", diskId) + } + + if len(isBoot) > 0 { + params.Set("IsBoot", isBoot) + } + err := self.DoListAll("DescribeUDisk", params, &disks) if err != nil { return nil, err } - if len(diskIds) > 0 { - filtedDisks := make([]SDisk, 0) - for i := range disks { - if utils.IsInStringArray(disks[i].UDiskID, diskIds) { - filtedDisks = append(filtedDisks, disks[i]) - } - } - - return filtedDisks, nil - } - return disks, nil } diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/eip.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/eip.go index d096433969..61460d3952 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/eip.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/eip.go @@ -15,12 +15,12 @@ package ucloud import ( - "fmt" "strings" "time" "yunion.io/x/jsonutils" "yunion.io/x/log" + "yunion.io/x/pkg/errors" billing_api "yunion.io/x/cloudmux/pkg/apis/billing" api "yunion.io/x/cloudmux/pkg/apis/compute" @@ -99,7 +99,7 @@ func (self *SEip) GetGlobalId() string { func (self *SEip) GetStatus() string { switch self.Status { case "used": - return api.EIP_STATUS_ASSOCIATE // ? + return api.EIP_STATUS_READY case "free": return api.EIP_STATUS_READY case "freeze": @@ -113,9 +113,9 @@ func (self *SEip) Refresh() error { if self.IsEmulated() { return nil } - new, err := self.region.GetEipById(self.GetId()) + new, err := self.region.GetEip(self.GetId()) if err != nil { - return err + return errors.Wrapf(err, "Refresh") } return jsonutils.Update(self, new) } @@ -225,12 +225,15 @@ func (self *SRegion) CreateEIP(eip *cloudprovider.SEip) (cloudprovider.ICloudEIP params.Set("OperatorName", eip.BGPType) params.Set("Bandwidth", eip.BandwidthMbps) params.Set("Name", eip.Name) + params.Set("Region", self.GetId()) var payMode string switch eip.ChargeType { case api.EIP_CHARGE_TYPE_BY_TRAFFIC: payMode = "Traffic" case api.EIP_CHARGE_TYPE_BY_BANDWIDTH: payMode = "Bandwidth" + default: + payMode = "Bandwidth" } params.Set("PayMode", payMode) params.Set("ChargeType", "Dynamic") // 按需付费 @@ -241,14 +244,11 @@ func (self *SRegion) CreateEIP(eip *cloudprovider.SEip) (cloudprovider.ICloudEIP return nil, err } - if len(eips) == 1 { - eip := eips[0] - eip.region = self - eip.Refresh() - return &eip, nil - } else { - return nil, fmt.Errorf("CreateEIP %d eip created", len(eips)) + for i := range eips { + eips[i].region = self + return &eips[i], nil } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "CreateEIP %d eip created", len(eips)) } // https://docs.ucloud.cn/api/unet-api/release_eip diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/host.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/host.go index 1ef8838979..e449fca746 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/host.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/host.go @@ -17,11 +17,10 @@ package ucloud import ( "encoding/base64" "fmt" + "regexp" "strconv" - "strings" "yunion.io/x/jsonutils" - "yunion.io/x/log" "yunion.io/x/pkg/errors" "yunion.io/x/pkg/util/billing" @@ -77,13 +76,13 @@ func (self *SHost) GetIVMs() ([]cloudprovider.ICloudVM, error) { } func (self *SHost) GetIVMById(id string) (cloudprovider.ICloudVM, error) { - vm, err := self.zone.region.GetInstanceByID(id) + vm, err := self.zone.region.GetInstance(id) if err != nil { return nil, err } vm.host = self - return &vm, nil + return vm, nil } func (self *SHost) GetIStorages() ([]cloudprovider.ICloudStorage, error) { @@ -162,19 +161,19 @@ func (self *SHost) GetVersion() string { // 不支持user data // 不支持指定keypair -func (self *SHost) CreateVM(desc *cloudprovider.SManagedVMCreateConfig) (cloudprovider.ICloudVM, error) { - vmId, err := self._createVM(desc.Name, desc.ExternalImageId, desc.SysDisk, desc.Cpu, desc.MemoryMB, desc.InstanceType, desc.ExternalNetworkId, desc.IpAddr, desc.Description, desc.Password, desc.DataDisks, desc.ExternalSecgroupIds, desc.BillingCycle) +func (self *SHost) CreateVM(opts *cloudprovider.SManagedVMCreateConfig) (cloudprovider.ICloudVM, error) { + vmId, err := self._createVM(opts) if err != nil { return nil, err } - vm, err := self.zone.region.GetInstanceByID(vmId) + vm, err := self.zone.region.GetInstance(vmId) if err != nil { return nil, err } vm.host = self - return &vm, err + return vm, err } func (host *SHost) GetIHostNics() ([]cloudprovider.ICloudHostNetInterface, error) { @@ -187,83 +186,77 @@ func (host *SHost) GetIHostNics() ([]cloudprovider.ICloudHostNetInterface, error type SInstanceType struct { UHostType string + GpuType string CPU int MemoryMB int GPU int } +// 格式: {机型}.c{cpu}.m{memGB}[.g{gpu}],机型支持 UCloud GpuType 如 T4S、2080Ti-4C、T4/4 +var instanceTypeRe = regexp.MustCompile(`^([A-Za-z0-9][A-Za-z0-9/_-]*)\.c(\d+)\.m(\d+)(?:\.g(\d+))?$`) + func ParseInstanceType(instanceType string) (SInstanceType, error) { i := SInstanceType{} - segs := strings.Split(instanceType, ".") - if len(segs) < 3 { + matches := instanceTypeRe.FindStringSubmatch(instanceType) + if matches == nil { return i, fmt.Errorf("invalid instance type %s", instanceType) - } else if len(segs) >= 4 { - gpu, err := strconv.Atoi(strings.TrimLeft(segs[3], "g")) + } + + hostType := matches[1] + cpu, err := strconv.Atoi(matches[2]) + if err != nil { + return i, err + } + memGB, err := strconv.Atoi(matches[3]) + if err != nil { + return i, err + } + + i.CPU = cpu + i.MemoryMB = memGB * 1024 + if len(matches[4]) > 0 { + gpu, err := strconv.Atoi(matches[4]) if err != nil { return i, err } - i.GPU = gpu + i.GpuType = hostType + i.UHostType = "G" + } else { + i.UHostType = hostType } - - cpu, err := strconv.Atoi(strings.TrimLeft(segs[1], "c")) - if err != nil { - return i, err - } - - mem, err := strconv.Atoi(strings.TrimLeft(segs[2], "m")) - if err != nil { - return i, err - } - - i.UHostType = segs[0] - i.CPU = cpu - i.MemoryMB = mem * 1024 return i, nil } -func (self *SHost) _createVM(name, imgId string, sysDisk cloudprovider.SDiskInfo, cpu, memMB int, instanceType string, - networkId, ipAddr, desc, passwd string, - dataDisks []cloudprovider.SDiskInfo, secgroupIds []string, bc *billing.SBillingCycle) (string, error) { +func (self *SHost) _createVM(opts *cloudprovider.SManagedVMCreateConfig) (string, error) { // 网络配置及安全组绑定 - net, _ := self.zone.region.getNetwork(networkId) - if net == nil { - return "", fmt.Errorf("invalid network ID %s", networkId) + net, err := self.zone.region.getNetwork(opts.ExternalNetworkId) + if err != nil { + return "", errors.Wrapf(err, "getNetwork %s", opts.ExternalNetworkId) } - if net.wire == nil { - log.Errorf("network's wire is empty") - return "", fmt.Errorf("network's wire is empty") - } - - if net.wire.vpc == nil { - log.Errorf("wire's vpc is empty") - return "", fmt.Errorf("wire's vpc is empty") - } - - if len(passwd) == 0 { + if len(opts.Password) == 0 { return "", fmt.Errorf("CreateVM password should not be emtpty") } // 镜像及硬盘配置 - img, err := self.zone.region.GetImage(imgId) + img, err := self.zone.region.GetImage(opts.ExternalImageId) if err != nil { - log.Errorf("GetImage %s fail %s", imgId, err) - return "", err + return "", errors.Wrapf(err, "GetImage %s", opts.ExternalImageId) } + if img.GetStatus() != api.CACHED_IMAGE_STATUS_ACTIVE { - log.Errorf("image %s status %s, expect %s", imgId, img.GetStatus(), api.CACHED_IMAGE_STATUS_ACTIVE) - return "", fmt.Errorf("image not ready") + return "", errors.Wrapf(cloudprovider.ErrInvalidStatus, "image %s status %s, expect %s", opts.ExternalImageId, img.GetStatus(), api.CACHED_IMAGE_STATUS_ACTIVE) } - disks := make([]SDisk, len(dataDisks)+1) + disks := make([]SDisk, len(opts.DataDisks)+1) disks[0].SizeGB = int(img.ImageSizeGB) - if sysDisk.SizeGB > 0 && sysDisk.SizeGB > int(img.ImageSizeGB) { - disks[0].SizeGB = sysDisk.SizeGB + if opts.SysDisk.SizeGB > 0 && opts.SysDisk.SizeGB > int(img.ImageSizeGB) { + disks[0].SizeGB = opts.SysDisk.SizeGB } - disks[0].DiskType = sysDisk.StorageType + disks[0].DiskType = opts.SysDisk.StorageType - for i, dataDisk := range dataDisks { + for i, dataDisk := range opts.DataDisks { disks[i+1].SizeGB = dataDisk.SizeGB disks[i+1].DiskType = dataDisk.StorageType } @@ -272,18 +265,18 @@ func (self *SHost) _createVM(name, imgId string, sysDisk cloudprovider.SDiskInfo // https://docs.ucloud.cn/api/uhost-api/uhost_type // https://docs.ucloud.cn/compute/uhost/introduction/uhost/type var vmId string - i, err := ParseInstanceType(instanceType) + i, err := ParseInstanceType(opts.InstanceType) if err != nil { - if cpu <= 0 || memMB <= 0 { + if opts.Cpu <= 0 || opts.MemoryMB <= 0 { return "", err } else { - i.UHostType = "N2" - i.CPU = cpu - i.MemoryMB = memMB + i.UHostType = "O" + i.CPU = opts.Cpu + i.MemoryMB = opts.MemoryMB } } - vmId, err = self.zone.region.CreateInstance(name, imgId, i.UHostType, passwd, net.wire.vpc.GetId(), networkId, secgroupIds, self.zone.ZoneId, desc, ipAddr, i.CPU, i.MemoryMB, i.GPU, disks, bc) + vmId, err = self.zone.region.CreateInstance(opts.Name, opts.ExternalImageId, i.UHostType, opts.Password, net.wire.vpc.GetId(), opts.ExternalNetworkId, opts.ExternalSecgroupIds, self.zone.ZoneId, opts.Description, opts.IpAddr, i.CPU, i.MemoryMB, i.GPU, i.GpuType, disks, opts.BillingCycle) if err != nil { return "", fmt.Errorf("Failed to create: %v", err) } @@ -295,14 +288,14 @@ func (self *SHost) _createVM(name, imgId string, sysDisk cloudprovider.SDiskInfo // https://docs.ucloud.cn/api/uhost-api/specification // 支持8-30位字符, 不能包含[A-Z],[a-z],[0-9]和[()`~!@#$%^&*-+=_|{}[]:;'<>,.?/]之外的非法字符 func (self *SRegion) CreateInstance(name, imageId, hostType, password, vpcId, SubnetId string, securityGroupId []string, - zoneId, desc, ipAddr string, cpu, memMB, gpu int, disks []SDisk, bc *billing.SBillingCycle) (string, error) { + zoneId, desc, ipAddr string, cpu, memMB, gpu int, gpuType string, disks []SDisk, bc *billing.SBillingCycle) (string, error) { params := NewUcloudParams() params.Set("Zone", zoneId) params.Set("ImageId", imageId) params.Set("Password", base64.StdEncoding.EncodeToString([]byte(password))) params.Set("LoginMode", "Password") params.Set("Name", name) - params.Set("UHostType", hostType) + params.Set("MachineType", hostType) params.Set("CPU", cpu) params.Set("Memory", memMB) params.Set("VPCId", vpcId) @@ -312,6 +305,9 @@ func (self *SRegion) CreateInstance(name, imageId, hostType, password, vpcId, Su } if gpu > 0 { params.Set("GPU", gpu) + if len(gpuType) > 0 { + params.Set("GpuType", gpuType) + } } if bc != nil && bc.GetMonths() >= 1 && bc.GetMonths() < 10 { @@ -347,7 +343,7 @@ func (self *SRegion) CreateInstance(name, imageId, hostType, password, vpcId, Su ret := Ret{} err := self.DoAction("CreateUHostInstance", params, &ret) if err != nil { - return "", err + return "", errors.Wrapf(err, "CreateUHostInstance") } if len(ret.UHostIds) == 1 { diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instance.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instance.go index d3011f059c..2b1706c5d5 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instance.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instance.go @@ -55,6 +55,8 @@ type SInstance struct { State string `json:"State"` NetworkState string `json:"NetworkState"` HostType string `json:"HostType"` + MachineType string `json:"MachineType"` + GpuType string `json:"GpuType"` StorageType string `json:"StorageType"` TotalDiskSpace int `json:"TotalDiskSpace"` DiskSet []DiskSet `json:"DiskSet"` @@ -175,7 +177,7 @@ func (self *SInstance) GetStatus() string { } func (self *SInstance) Refresh() error { - new, err := self.host.zone.region.GetInstanceByID(self.GetId()) + new, err := self.host.zone.region.GetInstance(self.GetId()) if err != nil { return err } @@ -235,22 +237,17 @@ func (self *SInstance) GetLocalDisk(diskId, storageType string, sizeGB int, isBo func (self *SInstance) GetIDisks() ([]cloudprovider.ICloudDisk, error) { localDisks := make([]SDisk, 0) - diskIds := make([]string, 0) - for _, disk := range self.DiskSet { - if utils.IsInStringArray(disk.DiskType, []string{api.STORAGE_UCLOUD_LOCAL_NORMAL, api.STORAGE_UCLOUD_LOCAL_SSD}) { - localDisks = append(localDisks, self.GetLocalDisk(disk.DiskID, disk.DiskType, disk.Size, disk.IsBoot)) - } else { - diskIds = append(diskIds, disk.DiskID) - } - } - disks := []SDisk{} - var err error - if len(diskIds) > 0 { - disks, err = self.host.zone.region.GetDisks("", "", diskIds) + for _, disk := range self.DiskSet { + if utils.IsInStringArray(disk.DiskType, api.UCLOUD_LOCAL_STORAGES) { + localDisks = append(localDisks, self.GetLocalDisk(disk.DiskID, disk.DiskType, disk.Size, disk.IsBoot)) + continue + } + disk, err := self.host.zone.region.GetDisk(disk.DiskID) if err != nil { return nil, err } + disks = append(disks, *disk) } disks = append(disks, localDisks...) @@ -302,12 +299,12 @@ func (self *SInstance) GetINics() ([]cloudprovider.ICloudNic, error) { func (self *SInstance) GetIEIP() (cloudprovider.ICloudEIP, error) { for _, ip := range self.IPSet { if len(ip.IPId) > 0 { - eip, err := self.host.zone.region.GetEipById(ip.IPId) + eip, err := self.host.zone.region.GetEip(ip.IPId) if err != nil { - return nil, err + return nil, errors.Wrapf(err, "GetEip %s", ip.IPId) } - return &eip, nil + return eip, nil } } @@ -374,13 +371,22 @@ func (self *SInstance) GetMachine() string { return "pc" } -func (self *SInstance) GetInstanceType() string { - // C1.c8.m24 - if strings.HasPrefix(self.HostType, "G") { - return fmt.Sprintf("%s.c%d.m%d.g%d", self.HostType, self.CPU, self.MemoryMB/1014, self.GPU) - } else { - return fmt.Sprintf("%s.c%d.m%d", self.HostType, self.CPU, self.MemoryMB/1014) +func (self *SInstance) instanceTypeHostPrefix() string { + if self.GPU > 0 && len(self.GpuType) > 0 { + return self.GpuType } + if len(self.UHostType) > 0 { + return self.UHostType + } + if len(self.MachineType) > 0 { + return self.MachineType + } + return self.HostType +} + +func (self *SInstance) GetInstanceType() string { + memGB := self.MemoryMB / 1024 + return formatInstanceSpec(self.instanceTypeHostPrefix(), self.CPU, memGB, self.GPU) } // https://docs.ucloud.cn/api/unet-api/grant_firewall @@ -437,34 +443,7 @@ func (self *SInstance) UpdateUserData(userData string) error { } // https://docs.ucloud.cn/api/uhost-api/reinstall_uhost_instance -// 1.请确认在重新安装之前,该实例已被关闭; -// 2.请确认该实例未挂载UDisk; -// todo:// 3.将原系统重装为不同类型的系统时(Linux->Windows),不可选择保留数据盘; -// 4.重装不同版本的系统时(CentOS6->CentOS7),若选择保留数据盘,请注意数据盘的文件系统格式; -// 5.若主机CPU低于2核,不可重装为Windows系统。 func (self *SInstance) RebuildRoot(ctx context.Context, desc *cloudprovider.SManagedVMRebuildRootConfig) (string, error) { - if len(desc.PublicKey) > 0 { - return "", fmt.Errorf("DeployVM not support assign ssh keypair") - } - - if self.GetStatus() != api.VM_READY { - return "", fmt.Errorf("DeployVM instance status %s , expected %s.", self.GetStatus(), api.VM_READY) - } - - if len(self.DiskSet) > 1 { - for _, disk := range self.DiskSet { - if disk.Type == "Data" { - err := self.host.zone.region.DetachDisk(self.host.zone.GetId(), self.GetId(), disk.DiskID) - if err != nil { - return "", fmt.Errorf("RebuildRoot detach disk %s", err) - } - - defer self.host.zone.region.AttachDisk(self.host.zone.GetId(), self.GetId(), disk.DiskID) - } - - } - } - err := self.host.zone.region.RebuildRoot(self.GetId(), desc.ImageId, desc.Password) if err != nil { return "", err @@ -475,12 +454,12 @@ func (self *SInstance) RebuildRoot(ctx context.Context, desc *cloudprovider.SMan return "", errors.Wrap(err, "RebuildRoot") } - disks, err := self.GetIDisks() - if len(disks) > 0 { - return disks[0].GetId(), nil - } else { - return "", fmt.Errorf("RebuildRoot %s", err) + for _, disk := range self.DiskSet { + if disk.Type == "SystemDisk" { + return disk.DiskID, nil + } } + return "", errors.Wrapf(cloudprovider.ErrNotFound, "SystemDisk not found") } func (self *SInstance) DeployVM(ctx context.Context, opts *cloudprovider.SInstanceDeployOptions) error { @@ -614,6 +593,7 @@ func (self *SRegion) DeleteVM(instanceId string) error { params := NewUcloudParams() params.Set("UHostId", instanceId) params.Set("Destroy", 1) // 跳过回收站,直接删除 + params.Set("ReleaseUDisk", true) return self.DoAction("TerminateUHostInstance", params, nil) } diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instancetype.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instancetype.go index 0b3feed6b4..e5621b5aa5 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instancetype.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/instancetype.go @@ -326,11 +326,7 @@ func (self *SRegion) GetZoneStorageTypes(zoneId string) ([]string, error) { if err != nil { return nil, err } - storageTypes := collectStorageTypesFromInstanceTypes(types, zoneId) - if len(storageTypes) == 0 { - return nil, fmt.Errorf("no storage types found for zone %s", zoneId) - } - return storageTypes, nil + return collectStorageTypesFromInstanceTypes(types, zoneId), nil } // GetAvailableInstanceTypes 获取地域/可用区下可售机型信息。 diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/network.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/network.go index 1c72df5637..ed3619cc35 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/network.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/network.go @@ -19,6 +19,7 @@ import ( "yunion.io/x/jsonutils" "yunion.io/x/log" + "yunion.io/x/pkg/errors" "yunion.io/x/pkg/util/netutils" "yunion.io/x/pkg/util/rbacscope" @@ -142,9 +143,6 @@ func (self *SRegion) GetNetwork(networkId string) (*SNetwork, error) { } func (self *SRegion) getNetwork(networkId string) (*SNetwork, error) { - if len(networkId) == 0 { - return nil, fmt.Errorf("getNetwork network id should not be empty") - } networks := make([]SNetwork, 0) params := NewUcloudParams() @@ -154,19 +152,17 @@ func (self *SRegion) getNetwork(networkId string) (*SNetwork, error) { return nil, err } - if len(networks) == 1 { - network := networks[0] - vpc, err := self.GetVpc(network.VpcId) - if err != nil { - return nil, err + for i := range networks { + if networks[i].SubnetID == networkId { + vpc, err := self.GetVpc(networks[i].VpcId) + if err != nil { + return nil, err + } + networks[i].wire = &SWire{vpc: vpc} + return &networks[i], nil } - network.wire = &SWire{vpc: vpc} - return &network, nil - } else if len(networks) == 0 { - return nil, cloudprovider.ErrNotFound - } else { - return nil, fmt.Errorf("getNetwork %s %d found", networkId, len(networks)) } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "getNetwork %s", networkId) } // https://docs.ucloud.cn/api/vpc2.0-api/delete_subnet diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/region.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/region.go index 2af13c7c8e..c8fa515b82 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/region.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/region.go @@ -71,11 +71,11 @@ func (self *SRegion) GetGeographicInfo() cloudprovider.SGeographicInfo { } func (self *SRegion) GetIVMById(id string) (cloudprovider.ICloudVM, error) { - instance, err := self.GetInstanceByID(id) + instance, err := self.GetInstance(id) if err != nil { return nil, err } - return &instance, nil + return instance, nil } func (self *SRegion) GetIDiskById(id string) (cloudprovider.ICloudDisk, error) { @@ -144,29 +144,30 @@ func (self *SRegion) GetIZoneById(id string) (cloudprovider.ICloudZone, error) { return nil, cloudprovider.ErrNotFound } -func (self *SRegion) GetEipById(eipId string) (SEip, error) { +func (self *SRegion) GetEip(eipId string) (*SEip, error) { params := NewUcloudParams() params.Set("EIPIds.0", eipId) eips := make([]SEip, 0) err := self.DoListAll("DescribeEIP", params, &eips) if err != nil { - return SEip{}, err + return nil, err } - if len(eips) == 1 { - eip := eips[0] - eip.region = self - return eip, nil - } else if len(eips) == 0 { - return SEip{}, cloudprovider.ErrNotFound - } else { - return SEip{}, fmt.Errorf("GetEipById %d eip found", len(eips)) + for i := range eips { + if eips[i].EIPID == eipId { + eips[i].region = self + return &eips[i], nil + } } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "GetEip %s", eipId) } func (self *SRegion) GetIEipById(id string) (cloudprovider.ICloudEIP, error) { - eip, err := self.GetEipById(id) - return &eip, err + eip, err := self.GetEip(id) + if err != nil { + return nil, err + } + return eip, nil } // https://docs.ucloud.cn/api/unet-api/delete_firewall @@ -387,22 +388,21 @@ func (self *SRegion) GetZones() ([]SZone, error) { } // https://docs.ucloud.cn/api/uhost-api/describe_uhost_instance -func (self *SRegion) GetInstanceByID(instanceId string) (SInstance, error) { +func (self *SRegion) GetInstance(instanceId string) (*SInstance, error) { params := NewUcloudParams() params.Set("UHostIds.0", instanceId) instances := make([]SInstance, 0) err := self.DoAction("DescribeUHostInstance", params, &instances) if err != nil { - return SInstance{}, err + return nil, errors.Wrapf(err, "DescribeUHostInstance") } - if len(instances) == 1 { - return instances[0], nil - } else if len(instances) == 0 { - return SInstance{}, cloudprovider.ErrNotFound - } else { - return SInstance{}, fmt.Errorf("GetInstanceByID %s %d found.", instanceId, len(instances)) + for i := range instances { + if instances[i].UHostID == instanceId { + return &instances[i], nil + } } + return nil, errors.Wrapf(cloudprovider.ErrNotFound, "GetInstance %s", instanceId) } func (self *SRegion) GetClient() *SUcloudClient { diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/storage.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/storage.go index 440c95741b..142d0a8a6f 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/storage.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/storage.go @@ -23,6 +23,7 @@ import ( api "yunion.io/x/cloudmux/pkg/apis/compute" "yunion.io/x/cloudmux/pkg/cloudprovider" "yunion.io/x/cloudmux/pkg/multicloud" + "yunion.io/x/pkg/utils" ) type SStorage struct { @@ -65,30 +66,18 @@ func (self *SStorage) GetIZone() cloudprovider.ICloudZone { } func (self *SStorage) GetIDisks() ([]cloudprovider.ICloudDisk, error) { - disks, err := self.zone.region.GetDisks(self.zone.GetId(), "", nil) - if err != nil { - return nil, err - } - - filtedDisks := make([]SDisk, 0) - for _, disk := range disks { - // ssd 盘 - if self.storageType == api.STORAGE_UCLOUD_CLOUD_SSD && strings.Contains(disk.DiskType, "SSD") { - filtedDisks = append(filtedDisks, disk) + ret := []cloudprovider.ICloudDisk{} + for _, isBoot := range []string{"True", "False"} { + disks, err := self.zone.region.GetDisks(self.zone.GetId(), self.storageType, isBoot, "") + if err != nil { + return nil, err } - - // 普通盘 - if self.storageType == api.STORAGE_UCLOUD_CLOUD_NORMAL && !strings.Contains(disk.DiskType, "SSD") { - filtedDisks = append(filtedDisks, disk) + for _, disk := range disks { + disk.storage = self + ret = append(ret, &disk) } } - - idisks := make([]cloudprovider.ICloudDisk, len(filtedDisks)) - for i := 0; i < len(filtedDisks); i += 1 { - filtedDisks[i].storage = self - idisks[i] = &filtedDisks[i] - } - return idisks, nil + return ret, nil } func (self *SStorage) GetStorageType() string { @@ -124,6 +113,10 @@ func (self *SStorage) CreateIDisk(opts *cloudprovider.DiskCreateConfig) (cloudpr switch self.storageType { case api.STORAGE_UCLOUD_CLOUD_SSD: diskType = "SSDDataDisk" + case api.STORAGE_UCLOUD_CLOUD_ESSD: + diskType = "ESSDDataDisk" + case api.STORAGE_UCLOUD_CLOUD_RSSD: + diskType = "RSSDDataDisk" } diskId, err := self.zone.region.CreateDisk(self.zone.GetId(), diskType, opts) if err != nil { @@ -140,12 +133,12 @@ func (self *SStorage) CreateIDisk(opts *cloudprovider.DiskCreateConfig) (cloudpr } func (self *SStorage) GetIDiskById(idStr string) (cloudprovider.ICloudDisk, error) { - if disk, err := self.zone.region.GetDisk(idStr); err != nil { + disk, err := self.zone.region.GetDisk(idStr) + if err != nil { return nil, err - } else { - disk.storage = self - return disk, nil } + disk.storage = self + return disk, nil } func (self *SStorage) GetMountPoint() string { @@ -155,3 +148,7 @@ func (self *SStorage) GetMountPoint() string { func (self *SStorage) IsSysDiskStore() bool { return true } + +func (self *SStorage) DisableSync() bool { + return utils.IsInStringArray(self.storageType, api.UCLOUD_LOCAL_STORAGES) +} diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/utils.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/utils.go index ebf6a9d69d..36d311cdea 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/utils.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/utils.go @@ -20,6 +20,7 @@ import ( "yunion.io/x/jsonutils" "yunion.io/x/log" + "yunion.io/x/pkg/errors" ) var responseMetaKeys = map[string]bool{ @@ -99,24 +100,21 @@ func detectArrayResultKey(resp jsonutils.JSONObject) string { return candidates[0] } -func unmarshalResult(resp jsonutils.JSONObject, respErr error, result interface{}) error { - if respErr != nil { - return respErr - } - +func unmarshalResult(resp jsonutils.JSONObject, result interface{}) error { if result == nil { return nil } + var err error resultKey := detectResultKey(resp, result) if len(resultKey) > 0 { - respErr = resp.Unmarshal(result, resultKey) + err = resp.Unmarshal(result, resultKey) } else { - respErr = resp.Unmarshal(result) + err = resp.Unmarshal(result) } - if respErr != nil { - log.Errorf("unmarshal json error %s", respErr) + if err != nil { + return errors.Wrapf(err, "unmarshalResult") } return nil @@ -154,7 +152,11 @@ func doListPart(client *SUcloudClient, action string, params SParams, result int func DoAction(client *SUcloudClient, action string, params SParams, result interface{}) error { params.SetAction(action) resp, err := jsonRequest(client, params) - return unmarshalResult(resp, err, result) + if err != nil { + log.Debugf("DoAction %s %s error %s", action, params.PrettyString(), err) + return err + } + return unmarshalResult(resp, result) } // 遍历所有结果 diff --git a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/zone.go b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/zone.go index 66c8165cb9..b6b162ac42 100644 --- a/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/zone.go +++ b/vendor/yunion.io/x/cloudmux/pkg/multicloud/ucloud/zone.go @@ -18,6 +18,7 @@ import ( "fmt" "yunion.io/x/pkg/errors" + "yunion.io/x/pkg/utils" api "yunion.io/x/cloudmux/pkg/apis/compute" "yunion.io/x/cloudmux/pkg/cloudprovider" @@ -52,6 +53,11 @@ func (self *SZone) fetchStorages() error { if err != nil { return err } + for _, storageType := range api.UCLOUD_LOCAL_STORAGES { + if !utils.IsInStringArray(storageType, storageTypes) { + storageTypes = append(storageTypes, storageType) + } + } self.storageTypes = storageTypes self.istorages = make([]cloudprovider.ICloudStorage, len(self.storageTypes)) for i, sc := range self.storageTypes {