Merge pull request #15903 from ioito/automated-cherry-pick-of-#15902-upstream-release-3.10

Automated cherry pick of #15902: fix(region): cdn domain config
This commit is contained in:
Zexi Li
2023-02-06 23:40:03 +08:00
committed by GitHub
32 changed files with 1767 additions and 130 deletions
+1 -1
View File
@@ -81,7 +81,7 @@ require (
k8s.io/client-go v0.19.3
k8s.io/cluster-bootstrap v0.19.3
moul.io/http2curl/v2 v2.3.0
yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230131095206-0d758294026e
yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230206033907-593ed22677c6
yunion.io/x/executor v0.0.0-20211018100936-39a2cd966656
yunion.io/x/jsonutils v1.0.1-0.20220819091305-3bab322ab4fd
yunion.io/x/log v1.0.0
+2 -2
View File
@@ -1158,8 +1158,8 @@ sigs.k8s.io/structured-merge-diff/v4 v4.0.1/go.mod h1:bJZC9H9iH24zzfZ/41RGcq60oK
sigs.k8s.io/yaml v1.1.0/go.mod h1:UJmg0vDUVViEyp3mgSv9WPwZCDxu4rQW1olrI1uml+o=
sigs.k8s.io/yaml v1.2.0 h1:kr/MCeFWJWTwyaHoR9c8EjH9OumOmoF9YGiZd7lFm/Q=
sigs.k8s.io/yaml v1.2.0/go.mod h1:yfXDCHCao9+ENCvLSE62v9VSji2MKu5jeNfTrofGhJc=
yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230131095206-0d758294026e h1:5YrzMsfD+p+wWvmHCWxIrwRqCJDpz8uliRAuY7hieT8=
yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230131095206-0d758294026e/go.mod h1:yEMFtIKPyIdIfPzsw7oTcH41JXc8G5StUAQw3ZoGj5I=
yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230206033907-593ed22677c6 h1:S3ZxAAae4qmlWYLDKJCQCUeUEOT3LhdvDB18h0oPqQI=
yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230206033907-593ed22677c6/go.mod h1:yEMFtIKPyIdIfPzsw7oTcH41JXc8G5StUAQw3ZoGj5I=
yunion.io/x/executor v0.0.0-20211018100936-39a2cd966656 h1:0zlZD5uhZoIHgLVAWCz2aHaYk2ZrNsACCYD7R6EIBII=
yunion.io/x/executor v0.0.0-20211018100936-39a2cd966656/go.mod h1:Uxuou9WQIeJXNpy7t2fPLL0BYLvLiMvGQwY7Qc6aSws=
yunion.io/x/jsonutils v0.0.0-20190625054549-a964e1e8a051/go.mod h1:4N0/RVzsYL3kH3WE/H1BjUQdFiWu50JGCFQuuy+Z634=
+43
View File
@@ -75,6 +75,20 @@ type SCDNDomain struct {
ServiceType string `list:"user" width:"32" create:"domain_required"`
// 加速区域
Area string `list:"user" width:"32" update:"domain" create:"domain_required"`
// 是否忽略参数
CacheKeys *cloudprovider.SCDNCacheKeys `list:"user" create:"domain_optional"`
// 是否分片回源
RangeOriginPull *cloudprovider.SCDNRangeOriginPull `list:"user" create:"domain_optional"`
// 缓存配置
Cache *cloudprovider.SCDNCache `list:"user" create:"domain_optional"`
// https配置
HTTPS *cloudprovider.SCDNHttps `list:"user" create:"domain_optional"`
// 强制跳转
ForceRedirect *cloudprovider.SCDNForceRedirect `list:"user" create:"domain_optional"`
// 防盗链配置
Referer *cloudprovider.SCDNReferer `list:"user" create:"domain_optional"`
// 浏览器缓存配置
MaxAge *cloudprovider.SCDNMaxAge `list:"user" create:"domain_optional"`
}
func (manager *SCDNDomainManager) GetContextManagers() [][]db.IModelManager {
@@ -215,6 +229,28 @@ func (self *SCDNDomain) SyncWithCloudCDNDomain(ctx context.Context, userCred mcc
self.ServiceType = ext.GetServiceType()
self.Cname = ext.GetCname()
self.Origins = ext.GetOrigins()
cacheKeys, err := ext.GetCacheKeys()
if err == nil {
self.CacheKeys = cacheKeys
}
if rangeOrigin, err := ext.GetRangeOriginPull(); err == nil {
self.RangeOriginPull = rangeOrigin
}
if cache, err := ext.GetCache(); err == nil {
self.Cache = cache
}
if https, err := ext.GetHTTPS(); err == nil {
self.HTTPS = https
}
if fr, err := ext.GetForceRedirect(); err == nil {
self.ForceRedirect = fr
}
if referer, err := ext.GetReferer(); err == nil {
self.Referer = referer
}
if maxAge, err := ext.GetMaxAge(); err == nil {
self.MaxAge = maxAge
}
return nil
})
if err != nil {
@@ -249,6 +285,13 @@ func (self *SCloudprovider) newFromCloudCDNDomain(ctx context.Context, userCred
domain.ServiceType = ext.GetServiceType()
domain.Cname = ext.GetCname()
domain.Origins = ext.GetOrigins()
domain.CacheKeys, _ = ext.GetCacheKeys()
domain.RangeOriginPull, _ = ext.GetRangeOriginPull()
domain.Cache, _ = ext.GetCache()
domain.HTTPS, _ = ext.GetHTTPS()
domain.ForceRedirect, _ = ext.GetForceRedirect()
domain.Referer, _ = ext.GetReferer()
domain.MaxAge, _ = ext.GetMaxAge()
err := CDNDomainManager.TableSpec().Insert(ctx, &domain)
if err != nil {
+1 -1
View File
@@ -1439,7 +1439,7 @@ sigs.k8s.io/structured-merge-diff/v4/value
# sigs.k8s.io/yaml v1.2.0
## explicit; go 1.12
sigs.k8s.io/yaml
# yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230131095206-0d758294026e
# yunion.io/x/cloudmux v0.3.10-0-alpha.1.0.20230206033907-593ed22677c6
## explicit; go 1.18
yunion.io/x/cloudmux/pkg/apis
yunion.io/x/cloudmux/pkg/apis/billing
+224 -6
View File
@@ -57,6 +57,14 @@ type SCdnOrigin struct {
Priority int
}
type CdnCreateOptions struct {
Domain string
ServiceType string
Area string
Origins SCdnOrigins
}
// +onecloud:model-api-gen
type SCdnOrigins []SCdnOrigin
@@ -68,16 +76,226 @@ func (self SCdnOrigins) String() string {
return jsonutils.Marshal(self).String()
}
// 是否忽略参数
type SCDNCacheKeys struct {
// 开启关闭忽略参数
Enabled *bool
// 是否忽略大小
IgnoreCase *bool
// 分路径缓存键配置
KeyRules []CacheKeyRule
}
type CacheKeyRule struct {
RulePaths []string
RuleType string
FullUrlCache bool
IgnoreCase bool
QueryString CacheKeyRuleQueryString
RuleTag string
}
type CacheKeyRuleQueryString struct {
Enabled bool
Action string
Value string
}
func (self SCDNCacheKeys) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNCacheKeys{})
}
func (self SCDNCacheKeys) String() string {
return jsonutils.Marshal(self).String()
}
// 是否分片回源
type SCDNRangeOriginPull struct {
Enabled *bool
RangeOriginPullRules []SRangeOriginPullRule
}
type SRangeOriginPullRule struct {
Enabled bool
RuleType string
RulePaths []string
}
func (self SCDNRangeOriginPull) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNRangeOriginPull{})
}
func (self SCDNRangeOriginPull) String() string {
return jsonutils.Marshal(self).String()
}
type CacheRule struct {
// 规则类型:
// all:所有文件生效
// file:指定文件后缀生效
// directory:指定路径生效
// path:指定绝对路径生效
// index:首页
CacheType string
// CacheType 对应类型下的匹配内容
CacheContents []string
// 过期时间: 秒
CacheTime int
}
type SCDNCache struct {
RuleCache []SCacheRuleCache
}
type SCacheRuleCache struct {
RulePaths []string
RuleType string
Priority int
CacheConfig *RuleCacheConfig
}
type RuleCacheConfig struct {
Cache *struct {
Enabled bool
CacheTime int
CompareMaxAge bool
IgnoreCacheControl bool
IgnoreSetCookie bool
}
NoCache *struct {
Enabled bool
Revalidate bool
}
FollowOrigin *struct {
Enabled bool
HeuristicCache struct {
Enabled bool
CacheConfig struct {
HeuristicCacheTimeSwitch bool
HeuristicCacheTime int
}
}
}
}
func (self SCDNCache) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNCache{})
}
func (self SCDNCache) String() string {
return jsonutils.Marshal(self).String()
}
type SCDNHttps struct {
// https 配置开关
Enabled *bool
// http2 配置开关
Http2 *bool
}
func (self SCDNHttps) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNHttps{})
}
func (self SCDNHttps) String() string {
return jsonutils.Marshal(self).String()
}
type SCDNForceRedirect struct {
// 访问强制跳转配置开关
Enabled *bool
// 访问强制跳转类型
// enmu: http, https
RedirectType string
}
func (self SCDNForceRedirect) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNForceRedirect{})
}
func (self SCDNForceRedirect) String() string {
return jsonutils.Marshal(self).String()
}
type RefererRule struct {
// 规则类型:
// all:所有文件生效
// file:指定文件后缀生效
// directory:指定路径生效
// path:指定绝对路径生效
RuleType string
RulePaths []string
RefererType string
Referers []string
AllowEmpty *bool
}
type SCDNReferer struct {
// 是否开启防盗链
Enabled *bool
RefererRules []RefererRule
}
func (self SCDNReferer) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNReferer{})
}
func (self SCDNReferer) String() string {
return jsonutils.Marshal(self).String()
}
type SMaxAgeRule struct {
MaxAgeType string
MaxAgeContents []string
MaxAgeTime int
FollowOrigin bool
}
// 浏览器缓存配置
type SCDNMaxAge struct {
Enabled *bool
MaxAgeRules []SMaxAgeRule
}
func (self SCDNMaxAge) IsZero() bool {
return jsonutils.Marshal(self) == jsonutils.Marshal(&SCDNMaxAge{})
}
func (self SCDNMaxAge) String() string {
return jsonutils.Marshal(self).String()
}
func init() {
gotypes.RegisterSerializable(reflect.TypeOf(&SCdnOrigins{}), func() gotypes.ISerializable {
return &SCdnOrigins{}
})
}
type CdnCreateOptions struct {
Domain string
ServiceType string
Area string
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNCacheKeys{}), func() gotypes.ISerializable {
return &SCDNCacheKeys{}
})
Origins SCdnOrigins
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNRangeOriginPull{}), func() gotypes.ISerializable {
return &SCDNRangeOriginPull{}
})
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNCache{}), func() gotypes.ISerializable {
return &SCDNCache{}
})
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNHttps{}), func() gotypes.ISerializable {
return &SCDNHttps{}
})
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNForceRedirect{}), func() gotypes.ISerializable {
return &SCDNForceRedirect{}
})
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNReferer{}), func() gotypes.ISerializable {
return &SCDNReferer{}
})
gotypes.RegisterSerializable(reflect.TypeOf(&SCDNMaxAge{}), func() gotypes.ISerializable {
return &SCDNMaxAge{}
})
}
+2
View File
@@ -37,4 +37,6 @@ const (
ErrNotImplemented = errors.ErrNotImplemented
ErrNotSupported = errors.ErrNotSupported
ErrAccountReadOnly = errors.ErrAccountReadOnly
ErrUnknown = errors.Error("UnknownError")
)
+15
View File
@@ -1585,6 +1585,21 @@ type ICloudCDNDomain interface {
GetCname() string
GetOrigins() *SCdnOrigins
// 是否忽略参数
GetCacheKeys() (*SCDNCacheKeys, error)
// 是否分片回源
GetRangeOriginPull() (*SCDNRangeOriginPull, error)
// 缓存配置
GetCache() (*SCDNCache, error)
// https配置
GetHTTPS() (*SCDNHttps, error)
// 强制跳转
GetForceRedirect() (*SCDNForceRedirect, error)
// 防盗链配置
GetReferer() (*SCDNReferer, error)
// 浏览器缓存配置
GetMaxAge() (*SCDNMaxAge, error)
Delete() error
}
+5
View File
@@ -132,6 +132,11 @@ type SecurityGroupCreateInput struct {
Rules []secrules.SecurityRule
}
type SecurityGroupCreateOutput struct {
Return bool
GroupId string
}
type SecurityRule struct {
minPriority int
maxPriority int
+1 -1
View File
@@ -65,7 +65,7 @@ type SCdnSources struct {
}
type SCdnDomain struct {
multicloud.SResourceBase
multicloud.SCDNDomainBase
client *SAliyunClient
+5 -5
View File
@@ -21,7 +21,7 @@ import (
"crypto/sha256"
"encoding/base64"
"fmt"
"io/ioutil"
"io"
"net/http"
"net/url"
"sort"
@@ -236,14 +236,14 @@ func (self *SBingoCloudClient) invoke(action string, params map[string]string) (
query += "&" + encode("SignatureVersion", "2")
query += "&" + encode("SignatureMethod", "HmacSHA256")
query += "&" + encode("Signature", self.sign(query))
client := self.getDefaultClient(0)
client := self.getDefaultClient(time.Minute * 5)
resp, err := httputils.Request(client, context.Background(), httputils.POST, self.endpoint, nil, strings.NewReader(query), self.debug)
if err != nil {
return nil, err
}
defer resp.Body.Close()
data, err := ioutil.ReadAll(resp.Body)
data, err := io.ReadAll(resp.Body)
if err != nil {
return nil, err
}
@@ -265,7 +265,7 @@ func (self *SBingoCloudClient) invoke(action string, params map[string]string) (
}
be := &sBingoError{}
obj.Unmarshal(be)
_ = obj.Unmarshal(be)
if len(be.Response.Errors.Error.Code) > 0 {
return nil, be
}
@@ -293,7 +293,7 @@ func (self *SBingoCloudClient) GetSubAccounts() ([]cloudprovider.SSubAccount, er
}
func (self *SBingoCloudClient) GetIRegions() []cloudprovider.ICloudRegion {
ret := []cloudprovider.ICloudRegion{}
var ret []cloudprovider.ICloudRegion
for i := range self.regions {
self.regions[i].client = self
ret = append(ret, &self.regions[i])
+2 -2
View File
@@ -74,7 +74,7 @@ func (self *SRegion) GetIZones() ([]cloudprovider.ICloudZone, error) {
if err != nil {
return nil, errors.Wrapf(err, "GetClusters")
}
ret := []cloudprovider.ICloudZone{}
var ret []cloudprovider.ICloudZone
for i := range clusters {
clusters[i].region = self
ret = append(ret, &clusters[i])
@@ -100,6 +100,6 @@ func (self *SRegion) GetClusters() ([]SCluster, error) {
if err != nil {
return nil, err
}
ret := []SCluster{}
var ret []SCluster
return ret, resp.Unmarshal(&ret, "clusterSet")
}
+30 -11
View File
@@ -61,6 +61,19 @@ type SDisk struct {
VolumeName string `json:"volumeName"`
}
func (self *SDisk) GetISnapshots() ([]cloudprovider.ICloudSnapshot, error) {
snapshots, err := self.storage.cluster.region.getSnapshots("", "")
if err != nil {
return nil, err
}
iSnapshots := make([]cloudprovider.ICloudSnapshot, len(snapshots))
for i := 0; i < len(snapshots); i++ {
snapshots[i].region = self.storage.cluster.region
iSnapshots[i] = &snapshots[i]
}
return iSnapshots, nil
}
type AttachmentSet struct {
AttachTime string `json:"attachTime"`
Cache string `json:"cache"`
@@ -142,15 +155,19 @@ func (self *SDisk) GetAccessPath() string {
}
func (self *SDisk) Delete(ctx context.Context) error {
return cloudprovider.ErrNotImplemented
params := map[string]string{}
params["VolumeId"] = self.VolumeId
_, err := self.storage.cluster.region.invoke("DeleteVolume", params)
return err
}
func (self *SDisk) CreateISnapshot(ctx context.Context, name string, desc string) (cloudprovider.ICloudSnapshot, error) {
return nil, cloudprovider.ErrNotImplemented
}
func (self *SDisk) GetISnapshots() ([]cloudprovider.ICloudSnapshot, error) {
return nil, cloudprovider.ErrNotImplemented
snapshotId, err := self.storage.cluster.region.createSnapshot(self.VolumeId, name, desc)
if err != nil {
return nil, err
}
return self.storage.cluster.region.GetISnapshotById(snapshotId)
}
func (self *SDisk) GetExtSnapshotPolicyIds() ([]string, error) {
@@ -188,11 +205,12 @@ func (self *SRegion) GetDisks(id string, maxResult int, nextToken string) ([]SDi
}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
if maxResult > 0 {
params["maxRecords"] = fmt.Sprintf("%d", maxResult)
params["MaxRecords"] = fmt.Sprintf("%d", maxResult)
}
resp, err := self.invoke("DescribeVolumes", params)
if err != nil {
return nil, "", err
@@ -201,7 +219,8 @@ func (self *SRegion) GetDisks(id string, maxResult int, nextToken string) ([]SDi
NextToken string
VolumeSet []SDisk
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.VolumeSet, ret.NextToken, nil
}
@@ -210,7 +229,7 @@ func (self *SStorage) GetIDisks() ([]cloudprovider.ICloudDisk, error) {
if err != nil {
return nil, err
}
disks := []SDisk{}
var disks []SDisk
disks = append(disks, part...)
for len(nextToken) > 0 {
part, nextToken, err = self.cluster.region.GetDisks("", MAX_RESULT, nextToken)
@@ -219,7 +238,7 @@ func (self *SStorage) GetIDisks() ([]cloudprovider.ICloudDisk, error) {
}
disks = append(disks, part...)
}
ret := []cloudprovider.ICloudDisk{}
var ret []cloudprovider.ICloudDisk
for i := range disks {
if disks[i].StorageId == self.StorageId {
disks[i].storage = self
+17 -7
View File
@@ -90,11 +90,20 @@ func (self *SEip) Delete() error {
}
func (self *SEip) Associate(conf *cloudprovider.AssociateConfig) error {
return cloudprovider.ErrNotImplemented
params := map[string]string{}
params["PublicIp"] = self.PublicIp
params["InstanceId"] = conf.InstanceId
_, err := self.region.invoke("AssociateAddress", params)
return err
}
func (self *SEip) Dissociate() error {
return cloudprovider.ErrNotImplemented
params := map[string]string{}
params["PublicIp"] = self.PublicIp
_, err := self.region.invoke("DisassociateAddress", params)
return err
}
func (self *SEip) ChangeBandwidth(bw int) error {
@@ -112,10 +121,10 @@ func (self *SEip) GetStatus() string {
func (self *SRegion) GetEips(ip, instanceId, nextToken string) ([]SEip, string, error) {
params := map[string]string{}
if len(ip) > 0 {
params["publicIp"] = ip
params["PublicIp"] = ip
}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
idx := 1
@@ -133,7 +142,8 @@ func (self *SRegion) GetEips(ip, instanceId, nextToken string) ([]SEip, string,
AddressesSet []SEip
NextToken string
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.AddressesSet, ret.NextToken, nil
}
@@ -142,7 +152,7 @@ func (self *SRegion) GetIEips() ([]cloudprovider.ICloudEIP, error) {
if err != nil {
return nil, err
}
eips := []SEip{}
var eips []SEip
eips = append(eips, part...)
for len(nextToken) > 0 {
part, nextToken, err = self.GetEips("", "", nextToken)
@@ -151,7 +161,7 @@ func (self *SRegion) GetIEips() ([]cloudprovider.ICloudEIP, error) {
}
eips = append(eips, part...)
}
ret := []cloudprovider.ICloudEIP{}
var ret []cloudprovider.ICloudEIP
for i := range eips {
eips[i].region = self
ret = append(ret, &eips[i])
+3 -2
View File
@@ -55,7 +55,7 @@ type SHost struct {
func (self *SRegion) GetHosts(nextToken string) ([]SHost, string, error) {
params := map[string]string{}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
resp, err := self.invoke("DescribePhysicalHosts", params)
if err != nil {
@@ -67,6 +67,7 @@ func (self *SRegion) GetHosts(nextToken string) ([]SHost, string, error) {
}
NextToken string
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.DescribePhysicalHostsResult.PhysicalHostSet, ret.NextToken, nil
}
+23 -9
View File
@@ -94,6 +94,10 @@ func (self *SImage) GetSizeByte() int64 {
return self.ImageSize
}
func (self *SImage) GetSizeGB() int64 {
return self.ImageSize / 1073741824
}
func (self *SImage) GetImageType() cloudprovider.TImageType {
if self.IsPublic {
return cloudprovider.ImageTypeSystem
@@ -102,7 +106,7 @@ func (self *SImage) GetImageType() cloudprovider.TImageType {
}
func (self *SImage) GetImageStatus() string {
return ""
return "active"
}
func (i *SImage) getNormalizedImageInfo() *imagetools.ImageInfo {
@@ -142,11 +146,11 @@ func (i *SImage) GetBios() cloudprovider.TBiosType {
}
func (self *SImage) GetMinOsDiskSizeGb() int {
return 0
return 4
}
func (self *SImage) GetMinRamSizeMb() int {
return 0
return 1024
}
func (self *SImage) GetImageFormat() string {
@@ -188,10 +192,10 @@ func (self *SImage) GetStatus() string {
func (self *SRegion) GetImages(id, nextToken string) ([]SImage, string, error) {
params := map[string]string{}
if len(id) > 0 {
params["imageId"] = id
params["ImageId.1"] = id
}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
resp, err := self.invoke("DescribeImages", params)
if err != nil {
@@ -201,16 +205,27 @@ func (self *SRegion) GetImages(id, nextToken string) ([]SImage, string, error) {
NextToken string
ImagesSet []SImage
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.ImagesSet, ret.NextToken, nil
}
func (self *SRegion) GetImageById(id string) (*SImage, error) {
imgs, _, err := self.GetImages(id, "")
if err != nil {
return nil, err
}
if len(imgs) == 0 {
return nil, errors.Wrapf(cloudprovider.ErrNotFound, id)
}
return &imgs[0], nil
}
func (self *SStoragecache) GetICloudImages() ([]cloudprovider.ICloudImage, error) {
part, nextToken, err := self.region.GetImages("", "")
if err != nil {
return nil, err
}
images := []SImage{}
var images []SImage
images = append(images, part...)
for len(nextToken) > 0 {
part, nextToken, err = self.region.GetImages("", nextToken)
@@ -219,7 +234,7 @@ func (self *SStoragecache) GetICloudImages() ([]cloudprovider.ICloudImage, error
}
images = append(images, part...)
}
ret := []cloudprovider.ICloudImage{}
var ret []cloudprovider.ICloudImage
for i := range images {
if images[i].StorageId == self.storageId {
images[i].cache = self
@@ -240,6 +255,5 @@ func (self *SStoragecache) GetIImageById(id string) (cloudprovider.ICloudImage,
return &images[i], nil
}
}
return nil, errors.Wrapf(cloudprovider.ErrNotFound, id)
}
+61 -23
View File
@@ -144,7 +144,7 @@ func (self *SInstance) GetName() string {
}
func (self *SInstance) GetSecurityGroupIds() ([]string, error) {
ret := []string{}
var ret []string
for _, sec := range self.GroupSet {
ret = append(ret, sec.GroupId)
}
@@ -152,19 +152,19 @@ func (self *SInstance) GetSecurityGroupIds() ([]string, error) {
}
func (self *SInstance) AssignSecurityGroup(secgroupId string) error {
return cloudprovider.ErrNotImplemented
return nil
}
func (self *SInstance) SetSecurityGroups(secgroupIds []string) error {
return cloudprovider.ErrNotImplemented
return nil
}
func (self *SInstance) AttachDisk(ctx context.Context, diskId string) error {
return cloudprovider.ErrNotImplemented
return nil
}
func (self *SInstance) DetachDisk(ctx context.Context, diskId string) error {
return cloudprovider.ErrNotImplemented
return nil
}
func (self *SInstance) ChangeConfig(ctx context.Context, config *cloudprovider.SManagedVMChangeConfig) error {
@@ -176,7 +176,11 @@ func (self *SInstance) DeployVM(ctx context.Context, name string, username strin
}
func (self *SInstance) DeleteVM(ctx context.Context) error {
return cloudprovider.ErrNotImplemented
params := map[string]string{}
params["InstanceId.1"] = self.InstancesSet.InstanceId
_, err := self.node.cluster.region.invoke("TerminateInstances", params)
return err
}
func (self *SInstance) GetVcpuCount() int {
@@ -271,7 +275,7 @@ func (self *SInstance) GetIDisks() ([]cloudprovider.ICloudDisk, error) {
for i := range storages {
storageMaps[storages[i].StorageId] = storages[i]
}
ret := []cloudprovider.ICloudDisk{}
var ret []cloudprovider.ICloudDisk
for _, _disk := range self.InstancesSet.BlockDeviceMapping {
disk, err := self.node.cluster.region.GetDisk(_disk.Ebs.VolumeId)
if err != nil {
@@ -292,7 +296,7 @@ func (self *SInstance) GetINics() ([]cloudprovider.ICloudNic, error) {
if err != nil {
return nil, err
}
ret := []cloudprovider.ICloudNic{}
var ret []cloudprovider.ICloudNic
for i := range nics {
ret = append(ret, &nics[i])
}
@@ -316,14 +320,14 @@ func (self *SInstance) GetProjectId() string {
}
func (self *SInstance) Refresh() error {
new, _, err := self.node.cluster.region.GetInstances(self.InstancesSet.InstanceId, self.node.NodeId, MAX_RESULT, "")
newInstances, _, err := self.node.cluster.region.GetInstances(self.InstancesSet.InstanceId, self.node.NodeId, MAX_RESULT, "")
if err != nil {
return err
}
if len(new) == 1 {
return jsonutils.Update(self, &new[0])
if len(newInstances) == 1 {
return jsonutils.Update(self, &newInstances[0])
}
return nil
return cloudprovider.ErrNotFound
}
func (self *SInstance) GetStatus() string {
@@ -337,7 +341,7 @@ func (self *SInstance) GetStatus() string {
func (self *SInstance) GetVNCInfo(input *cloudprovider.ServerVncInput) (*cloudprovider.ServerVncOutput, error) {
params := map[string]string{}
params["instanceId"] = self.InstancesSet.InstanceId
params["InstanceId"] = self.InstancesSet.InstanceId
resp, err := self.node.cluster.region.invoke("GetVncInfo", params)
if err != nil {
@@ -347,10 +351,7 @@ func (self *SInstance) GetVNCInfo(input *cloudprovider.ServerVncInput) (*cloudpr
result := struct {
GetVncInfoResult *cloudprovider.ServerVncOutput `json:"getVncInfoResult"`
}{}
err = resp.Unmarshal(&result)
if err != nil {
return nil, err
}
_ = resp.Unmarshal(&result)
result.GetVncInfoResult.InstanceId = self.InstancesSet.InstanceId
result.GetVncInfoResult.Hypervisor = self.GetHypervisor()
@@ -384,13 +385,52 @@ func (self *SInstance) UpdateVM(ctx context.Context, name string) error {
return cloudprovider.ErrNotImplemented
}
func (self *SInstance) CreateInstanceSnapshot(ctx context.Context, name string, desc string) (cloudprovider.ICloudInstanceSnapshot, error) {
newId, err := self.node.cluster.region.createInstanceSnapshot(self.InstancesSet.InstanceId, name, desc)
if err != nil {
return nil, err
}
return self.GetInstanceSnapshot(newId)
}
func (self *SInstance) GetInstanceSnapshot(id string) (cloudprovider.ICloudInstanceSnapshot, error) {
snapshots, err := self.node.cluster.region.getInstanceSnapshots(self.InstancesSet.InstanceId, id)
if err != nil {
return nil, err
}
for i := range snapshots {
if snapshots[i].GetGlobalId() == id {
snapshots[i].region = self.node.cluster.region
return &snapshots[i], nil
}
}
return nil, cloudprovider.ErrNotFound
}
func (self *SInstance) GetInstanceSnapshots() ([]cloudprovider.ICloudInstanceSnapshot, error) {
snapshots, err := self.node.cluster.region.getInstanceSnapshots(self.InstancesSet.InstanceId, "")
if err != nil {
return nil, err
}
var ret []cloudprovider.ICloudInstanceSnapshot
for i := range snapshots {
snapshots[i].region = self.node.cluster.region
ret = append(ret, &snapshots[i])
}
return ret, nil
}
func (self *SInstance) ResetToInstanceSnapshot(ctx context.Context, idStr string) error {
return self.node.cluster.region.revertInstanceSnapshot(idStr)
}
func (self *SRegion) GetInstances(id, nodeId string, maxResult int, nextToken string) ([]SInstance, string, error) {
params := map[string]string{}
if maxResult > 0 {
params["maxRecords"] = fmt.Sprintf("%d", maxResult)
params["MaxRecords"] = fmt.Sprintf("%d", maxResult)
}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
idx := 1
@@ -414,9 +454,7 @@ func (self *SRegion) GetInstances(id, nodeId string, maxResult int, nextToken st
NextToken string
ReservationSet []SInstance
}{}
err = resp.Unmarshal(&result)
if err != nil {
return nil, "", err
}
_ = resp.Unmarshal(&result)
return result.ReservationSet, result.NextToken, nil
}
@@ -0,0 +1,132 @@
package bingocloud
import (
"time"
"yunion.io/x/jsonutils"
"yunion.io/x/cloudmux/pkg/cloudprovider"
)
type SInstanceSnapshot struct {
region *SRegion
InstanceSnapshotId string
InstanceSnapshotName string
InstanceId string
DiskOnly bool
Size int64
Status string
StatusReason string
CreateTime string
}
func (self SInstanceSnapshot) GetId() string {
return self.InstanceSnapshotId
}
func (self SInstanceSnapshot) GetName() string {
return self.InstanceSnapshotName
}
func (self SInstanceSnapshot) GetGlobalId() string {
return self.InstanceSnapshotId
}
func (self SInstanceSnapshot) GetCreatedAt() time.Time {
ct, _ := time.Parse("2006-01-02T15:04:05.000Z", self.CreateTime)
return ct
}
func (self SInstanceSnapshot) GetStatus() string {
return self.Status
}
func (self SInstanceSnapshot) Refresh() error {
newSnapshot, err := self.region.getInstanceSnapshots(self.InstanceId, self.InstanceSnapshotId)
if err != nil {
return err
}
if len(newSnapshot) == 1 {
return jsonutils.Update(self, &newSnapshot[0])
}
return cloudprovider.ErrNotFound
}
func (self SInstanceSnapshot) IsEmulated() bool {
return false
}
func (self SInstanceSnapshot) GetSysTags() map[string]string {
return nil
}
func (self SInstanceSnapshot) GetTags() (map[string]string, error) {
return nil, nil
}
func (self SInstanceSnapshot) SetTags(tags map[string]string, replace bool) error {
return nil
}
func (self SInstanceSnapshot) GetProjectId() string {
return ""
}
func (self SInstanceSnapshot) GetDescription() string {
return ""
}
func (self SInstanceSnapshot) Delete() error {
return self.region.deleteInstanceSnapshot(self.InstanceSnapshotId)
}
func (self *SRegion) createInstanceSnapshot(instanceId, name string, desc string) (string, error) {
params := map[string]string{}
params["InstanceId"] = instanceId
params["InstanceSnapshotName"] = name
params["Description"] = desc
params["DiskOnly"] = "false"
resp, err := self.client.invoke("CreateInstanceSnapshot", params)
if err != nil {
return "", err
}
newId := ""
err = resp.Unmarshal(&newId, "instanceSnapshotId")
return newId, err
}
func (self *SRegion) getInstanceSnapshots(instanceId, snapshotId string) ([]SInstanceSnapshot, error) {
params := map[string]string{}
if instanceId != "" {
params["InstanceId"] = instanceId
}
if snapshotId != "" {
params["InstanceSnapshotId.1"] = snapshotId
}
resp, err := self.client.invoke("DescribeInstanceSnapshots", params)
if err != nil {
return nil, err
}
var ret []SInstanceSnapshot
_ = resp.Unmarshal(&ret, "instanceSnapshotSet")
return ret, err
}
func (self *SRegion) deleteInstanceSnapshot(id string) error {
params := map[string]string{}
params["InstanceSnapshotId"] = id
_, err := self.client.invoke("DeleteInstanceSnapshots", params)
return err
}
func (self *SRegion) revertInstanceSnapshot(id string) error {
params := map[string]string{}
params["InstanceSnapshotId"] = id
_, err := self.client.invoke("RevertInstanceSnapshot", params)
return err
}
+209
View File
@@ -0,0 +1,209 @@
package bingocloud
import (
"strings"
"time"
"yunion.io/x/cloudmux/pkg/apis"
"yunion.io/x/cloudmux/pkg/cloudprovider"
)
var INSTANCE_CATEGORY_MAP = map[string]string{
"m1": "M1代",
"m2": "M2代",
"m3": "M3代",
"c1": "C1代",
"c2": "C2代",
"c3": "C3代",
"t1": "T1代",
"t2": "T2代",
"t3": "T3代",
}
func getInstanceCategory(family string) string {
ret, ok := INSTANCE_CATEGORY_MAP[family]
if ok {
return ret
}
return family
}
type SInstanceType struct {
cloudprovider.SServerSku
region *SRegion
InstanceType string
DisplayName string
Cpu int
Ram int
Max int
Available int
Description string
}
func (self *SInstanceType) GetCreatedAt() time.Time {
return time.Time{}
}
func (self *SInstanceType) GetId() string {
return self.InstanceType
}
func (self *SInstanceType) GetName() string {
return self.InstanceType
}
func (self *SInstanceType) GetGlobalId() string {
return self.InstanceType
}
func (self *SInstanceType) GetStatus() string {
return ""
}
func (self *SInstanceType) Refresh() error {
return nil
}
func (self *SInstanceType) IsEmulated() bool {
return false
}
func (self *SInstanceType) GetSysTags() map[string]string {
return nil
}
func (self *SInstanceType) GetTags() (map[string]string, error) {
return nil, nil
}
func (self *SInstanceType) SetTags(tags map[string]string, replace bool) error {
return nil
}
func (self *SInstanceType) GetInstanceTypeFamily() string {
return strings.Split(self.InstanceType, ".")[0]
}
func (self *SInstanceType) GetInstanceTypeCategory() string {
return getInstanceCategory(self.GetInstanceTypeFamily())
}
func (self *SInstanceType) GetPrepaidStatus() string {
return "available"
}
func (self *SInstanceType) GetPostpaidStatus() string {
return "available"
}
// https://support.huaweicloud.com/productdesc-ecs/ecs_01_0066.html
// https://support.huaweicloud.com/ecs_faq/ecs_faq_0105.html
func (self *SInstanceType) GetCpuArch() string {
return apis.OS_ARCH_X86
}
func (self *SInstanceType) GetCpuCoreCount() int {
return self.Cpu
}
func (self *SInstanceType) GetMemorySizeMB() int {
return self.Ram
}
func (self *SInstanceType) GetOsName() string {
return ""
}
func (self *SInstanceType) GetSysDiskResizable() bool {
return false
}
func (self *SInstanceType) GetSysDiskType() string {
return ""
}
func (self *SInstanceType) GetSysDiskMinSizeGB() int {
return 0
}
func (self *SInstanceType) GetSysDiskMaxSizeGB() int {
return 0
}
func (self *SInstanceType) GetAttachedDiskType() string {
return ""
}
func (self *SInstanceType) GetAttachedDiskSizeGB() int {
return 0
}
func (self *SInstanceType) GetAttachedDiskCount() int {
return 0
}
func (self *SInstanceType) GetDataDiskTypes() string {
return ""
}
func (self *SInstanceType) GetDataDiskMaxCount() int {
return 0
}
func (self *SInstanceType) GetNicType() string {
return ""
}
func (self *SInstanceType) GetNicMaxCount() int {
return 0
}
func (self *SInstanceType) GetGpuAttachable() bool {
return false
}
func (self *SInstanceType) GetGpuSpec() string {
return ""
}
func (self *SInstanceType) GetGpuCount() int {
return 0
}
func (self *SInstanceType) GetGpuMaxCount() int {
return 0
}
func (self *SInstanceType) Delete() error {
return nil
}
func (self *SRegion) GetInstanceTypes() ([]SInstanceType, error) {
resp, err := self.invoke("DescribeInstanceTypes", nil)
if err != nil {
return nil, err
}
result := struct {
InstanceTypeInfo []SInstanceType
}{}
_ = resp.Unmarshal(&result)
return result.InstanceTypeInfo, err
}
func (self *SRegion) GetISkus() ([]cloudprovider.ICloudSku, error) {
instanceTypes, err := self.GetInstanceTypes()
if err != nil {
return nil, err
}
iskus := make([]cloudprovider.ICloudSku, len(instanceTypes))
for i := 0; i < len(instanceTypes); i++ {
instanceTypes[i].region = self
iskus[i] = &instanceTypes[i]
}
return iskus, nil
}
+6 -3
View File
@@ -75,7 +75,7 @@ func (self *SInstanceNic) GetINetworkId() string {
}
func (self *SInstanceNic) GetSubAddress() ([]string, error) {
ret := []string{}
var ret []string
for _, ip := range self.PrivateIPAddressesSet {
if ip.PrivateIPAddress != self.PrivateIPAddress {
ret = append(ret, ip.PrivateIPAddress)
@@ -99,15 +99,18 @@ func (self *SInstanceNic) UnassignAddress(ipAddrs []string) error {
func (self *SRegion) GetInstanceNics(insId string) ([]SInstanceNic, error) {
params := map[string]string{}
if len(insId) > 0 {
params["instanceId"] = insId
params["InstanceId"] = insId
}
resp, err := self.invoke("DescribeNetworkInterfaces", params)
if err != nil {
return nil, err
}
ret := struct {
NetworkInterfaceSet []SInstanceNic
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.NetworkInterfaceSet, nil
}
+4 -4
View File
@@ -81,10 +81,10 @@ func (self *SBingoCloudClient) GetMetrics(opts *cloudprovider.MetricListOptions)
}
func (self *SBingoCloudClient) GetEcsMetrics(opts *cloudprovider.MetricListOptions) ([]cloudprovider.MetricValues, error) {
ret := []cloudprovider.MetricValues{}
var ret []cloudprovider.MetricValues
for metricType, metricName := range map[cloudprovider.TMetricType]string{
cloudprovider.VM_METRIC_TYPE_CPU_USAGE: "CPUUtilization",
cloudprovider.VM_METRIC_TYPE_MEM_USAGE: "MemeryUsage",
cloudprovider.VM_METRIC_TYPE_MEM_USAGE: "MemoryUsage",
cloudprovider.VM_METRIC_TYPE_NET_BPS_RX: "NetworkIn",
cloudprovider.VM_METRIC_TYPE_NET_BPS_TX: "NetworkOut",
cloudprovider.VM_METRIC_TYPE_DISK_IO_READ_BPS: "DiskReadBytes",
@@ -112,10 +112,10 @@ func (self *SBingoCloudClient) GetEcsMetrics(opts *cloudprovider.MetricListOptio
}
func (self *SBingoCloudClient) GetHostMetrics(opts *cloudprovider.MetricListOptions) ([]cloudprovider.MetricValues, error) {
ret := []cloudprovider.MetricValues{}
var ret []cloudprovider.MetricValues
for metricType, metricName := range map[cloudprovider.TMetricType]string{
cloudprovider.VM_METRIC_TYPE_CPU_USAGE: "CPUUtilization",
cloudprovider.VM_METRIC_TYPE_MEM_USAGE: "MemeryUsage",
cloudprovider.VM_METRIC_TYPE_MEM_USAGE: "MemoryUsage",
cloudprovider.VM_METRIC_TYPE_NET_BPS_RX: "NetworkIn",
cloudprovider.VM_METRIC_TYPE_NET_BPS_TX: "NetworkOut",
cloudprovider.VM_METRIC_TYPE_DISK_IO_READ_BPS: "DiskReadBytes",
+3 -3
View File
@@ -153,7 +153,7 @@ func (self *SWire) GetINetworks() ([]cloudprovider.ICloudNetwork, error) {
if err != nil {
return nil, err
}
ret := []cloudprovider.ICloudNetwork{}
var ret []cloudprovider.ICloudNetwork
for i := range networks {
networks[i].wire = self
ret = append(ret, &networks[i])
@@ -177,7 +177,7 @@ func (self *SWire) GetINetworkById(id string) (cloudprovider.ICloudNetwork, erro
func (self *SRegion) GetNetworks(id, clusterId, vpcId string) ([]SNetwork, error) {
params := map[string]string{}
if len(id) > 0 {
params["subnetId"] = id
params["SubnetId"] = id
}
idx := 1
if len(clusterId) > 0 {
@@ -194,6 +194,6 @@ func (self *SRegion) GetNetworks(id, clusterId, vpcId string) ([]SNetwork, error
if err != nil {
return nil, err
}
networks := []SNetwork{}
var networks []SNetwork
return networks, resp.Unmarshal(&networks, "subnetSet")
}
+113 -11
View File
@@ -15,9 +15,12 @@
package bingocloud
import (
"fmt"
"strconv"
"strings"
"yunion.io/x/jsonutils"
"yunion.io/x/log"
"yunion.io/x/pkg/errors"
api "yunion.io/x/cloudmux/pkg/apis/compute"
@@ -53,16 +56,16 @@ type SNode struct {
func (self *SRegion) GetNodes(clusterId, nodeId string) ([]SNode, error) {
params := map[string]string{}
if len(clusterId) > 0 {
params["clusterId"] = clusterId
params["ClusterId"] = clusterId
}
if len(clusterId) > 0 {
params["nodeId"] = nodeId
params["NodeId"] = nodeId
}
resp, err := self.invoke("DescribeNodes", params)
if err != nil {
return nil, err
}
ret := []SNode{}
var ret []SNode
return ret, resp.Unmarshal(&ret, "nodeSet")
}
@@ -151,10 +154,6 @@ func (self *SNode) GetNodeType() string {
return api.HOST_TYPE_BINGO_CLOUD
}
func (self *SNode) CreateVM(desc *cloudprovider.SManagedVMCreateConfig) (cloudprovider.ICloudVM, error) {
return nil, cloudprovider.ErrNotImplemented
}
func (self *SNode) GetIStorages() ([]cloudprovider.ICloudStorage, error) {
return self.cluster.GetIStorages()
}
@@ -179,7 +178,7 @@ func (self *SNode) GetIHostNics() ([]cloudprovider.ICloudHostNetInterface, error
}
func (self *SNode) GetIVMs() ([]cloudprovider.ICloudVM, error) {
vms := []SInstance{}
var vms []SInstance
part, nextToken, err := self.cluster.region.GetInstances("", self.NodeId, MAX_RESULT, "")
vms = append(vms, part...)
for len(nextToken) > 0 {
@@ -189,7 +188,7 @@ func (self *SNode) GetIVMs() ([]cloudprovider.ICloudVM, error) {
}
vms = append(vms, part...)
}
ret := []cloudprovider.ICloudVM{}
var ret []cloudprovider.ICloudVM
for i := range vms {
vms[i].node = self
ret = append(ret, &vms[i])
@@ -212,7 +211,19 @@ func (self *SNode) GetIVMById(id string) (cloudprovider.ICloudVM, error) {
}
func (self *SNode) GetIWires() ([]cloudprovider.ICloudWire, error) {
return nil, cloudprovider.ErrNotImplemented
vpcs, err := self.cluster.region.GetIVpcs()
if err != nil {
return nil, err
}
var ret []cloudprovider.ICloudWire
for _, vpc := range vpcs {
wires, err := vpc.GetIWires()
if err != nil {
return nil, err
}
ret = append(ret, wires...)
}
return ret, nil
}
func (self *SNode) GetSchedtags() ([]string, error) {
@@ -261,10 +272,101 @@ func (self *SCluster) GetIHosts() ([]cloudprovider.ICloudHost, error) {
if err != nil {
return nil, err
}
ret := []cloudprovider.ICloudHost{}
var ret []cloudprovider.ICloudHost
for i := range nodes {
nodes[i].cluster = self
ret = append(ret, &nodes[i])
}
return ret, nil
}
func (self *SNode) CreateVM(desc *cloudprovider.SManagedVMCreateConfig) (cloudprovider.ICloudVM, error) {
var err error
log.Debugf("Try instancetype : %s", desc.InstanceType)
img, err := self.cluster.region.GetImageById(desc.ExternalImageId)
if err != nil {
log.Errorf("get image %s fail %s", desc.ExternalImageId, err)
return nil, err
}
params := map[string]string{}
params["InstanceName"] = desc.Name
params["ImageId"] = desc.ExternalImageId
params["MinCount"] = "1"
params["MaxCount"] = "1"
if len(desc.ExternalSecgroupIds) > 0 {
for i := range desc.ExternalSecgroupIds {
secGroup, err := self.cluster.region.GetISecurityGroupById(desc.ExternalSecgroupIds[i])
if err != nil {
return nil, err
}
params[fmt.Sprintf("SecurityGroup.%v", i+1)] = secGroup.GetName()
}
}
disks := make([]SDisk, len(desc.DataDisks)+1)
disks[0].Size = int(img.GetSizeGB())
if desc.SysDisk.SizeGB > 0 && desc.SysDisk.SizeGB > int(img.GetSizeGB()) {
disks[0].Size = desc.SysDisk.SizeGB
}
for i, dataDisk := range desc.DataDisks {
disks[i+1].Size = dataDisk.SizeGB
}
for i, disk := range disks {
var deviceName string
var err error
if i == 0 {
params[fmt.Sprintf("BlockDeviceMapping.%v.Ebs.DeleteOnTermination", i+1)] = "true"
params[fmt.Sprintf("BlockDeviceMapping.%v.Ebs.VolumeSize", i+1)] = strconv.Itoa(disk.Size)
if len(img.RootDeviceName) > 0 {
deviceName = img.RootDeviceName
} else {
deviceName = fmt.Sprintf("/dev/vda")
}
} else {
params[fmt.Sprintf("BlockDeviceMapping.%v.Ebs.DeleteOnTermination", i+1)] = "true"
params[fmt.Sprintf("BlockDeviceMapping.%v.Ebs.VolumeSize", i+1)] = strconv.Itoa(disk.Size)
deviceName, err = nextDeviceName([]string{deviceName})
if err != nil {
return nil, errors.Wrap(err, "nextDeviceName")
}
}
params[fmt.Sprintf("BlockDeviceMapping.%v.DeviceName", i+1)] = deviceName
}
params["InstanceType"] = desc.InstanceType
params["Password"] = desc.Password
params["NetworkInterface.1.VpcId"] = desc.ExternalVpcId
params["NetworkInterface.1.SubnetId"] = desc.ExternalNetworkId
params["AllowNodes.1"] = self.NodeId
resp, err := self.cluster.region.invoke("RunInstances", params)
if err != nil {
return nil, err
}
if err != nil {
return nil, errors.Wrap(err, "CreateVM")
}
var tmpInst = struct {
InstancesSet struct {
InstanceId string
}
}{}
_ = resp.Unmarshal(&tmpInst)
insets, _, err := self.cluster.region.GetInstances(tmpInst.InstancesSet.InstanceId, "", MAX_RESULT, "")
if err != nil {
log.Errorf("GetInstance %s: %s", "", err)
return nil, errors.Wrap(err, "CreateVM")
}
if len(insets) > 0 {
insets[0].node = self
return &insets[0], nil
}
return nil, errors.Wrap(cloudprovider.ErrUnknown, "CreateVM")
}
+43 -6
View File
@@ -92,16 +92,26 @@ func (self *SBingoCloudClient) GetRegions() ([]SRegion, error) {
if err != nil {
return nil, err
}
ret := []SRegion{}
err = resp.Unmarshal(&ret, "regionInfo")
var ret []SRegion
return ret, resp.Unmarshal(&ret, "regionInfo")
}
func (self *SRegion) GetIStorageById(id string) (cloudprovider.ICloudStorage, error) {
storages, err := self.getStorages()
if err != nil {
return nil, err
}
return ret, nil
for i := range storages {
if storages[i].GetGlobalId() == id {
storages[i].cluster = &SCluster{region: self}
return &storages[i], nil
}
}
return nil, errors.Wrapf(cloudprovider.ErrNotFound, id)
}
func (self *SRegion) GetIStoragecaches() ([]cloudprovider.ICloudStoragecache, error) {
storages := []SStorage{}
var storages []SStorage
part, nextToken, err := self.GetStorages("")
if err != nil {
return nil, err
@@ -114,7 +124,7 @@ func (self *SRegion) GetIStoragecaches() ([]cloudprovider.ICloudStoragecache, er
}
storages = append(storages, part...)
}
ret := []cloudprovider.ICloudStoragecache{}
var ret []cloudprovider.ICloudStoragecache
for i := range storages {
cache := SStoragecache{
region: self,
@@ -144,7 +154,7 @@ func (self *SRegion) GetIHosts() ([]cloudprovider.ICloudHost, error) {
if err != nil {
return nil, err
}
ret := []cloudprovider.ICloudHost{}
var ret []cloudprovider.ICloudHost
for i := range zones {
hosts, err := zones[i].GetIHosts()
if err != nil {
@@ -173,3 +183,30 @@ func (self *SRegion) GetIHostById(id string) (cloudprovider.ICloudHost, error) {
}
return nil, errors.Wrapf(cloudprovider.ErrNotFound, id)
}
func (self *SRegion) GetISnapshots() ([]cloudprovider.ICloudSnapshot, error) {
snapshots, err := self.getSnapshots("", "")
if err != nil {
return nil, err
}
iSnapshots := make([]cloudprovider.ICloudSnapshot, len(snapshots))
for i := 0; i < len(snapshots); i++ {
snapshots[i].region = self
iSnapshots[i] = snapshots[i]
}
return iSnapshots, nil
}
func (self *SRegion) GetISnapshotById(id string) (cloudprovider.ICloudSnapshot, error) {
snapshots, err := self.getSnapshots(id, "")
if err != nil {
return nil, err
}
for i := range snapshots {
if snapshots[i].GetGlobalId() == id {
snapshots[i].region = self
return &snapshots[i], nil
}
}
return nil, cloudprovider.ErrNotFound
}
@@ -15,6 +15,10 @@
package bingocloud
import (
"encoding/json"
"strings"
"yunion.io/x/log"
"yunion.io/x/pkg/errors"
"yunion.io/x/pkg/util/secrules"
@@ -28,19 +32,19 @@ type SSecurityGroup struct {
BingoTags
region *SRegion
ComplexIPPermissions string `json:"complexIpPermissions"`
ComplexIPPermissionsEgress string `json:"complexIpPermissionsEgress"`
DisplayName string `json:"displayName"`
GroupDescription string `json:"groupDescription"`
GroupId string `json:"groupId"`
GroupName string `json:"groupName"`
IPPermissionType string `json:"ipPermissionType"`
IPPermissions string `json:"ipPermissions"`
IPPermissionsEgress []IPPermissionsEgress `json:"ipPermissionsEgress"`
OwnerId string `json:"ownerId"`
ComplexIPPermissions string `json:"complexIpPermissions"`
ComplexIPPermissionsEgress string `json:"complexIpPermissionsEgress"`
DisplayName string `json:"displayName"`
GroupDescription string `json:"groupDescription"`
GroupId string `json:"groupId"`
GroupName string `json:"groupName"`
IPPermissionType string `json:"ipPermissionType"`
IPPermissions []IPPermissions `json:"ipPermissions"`
IPPermissionsEgress []IPPermissions `json:"ipPermissionsEgress"`
OwnerId string `json:"ownerId"`
}
type IPPermissionsEgress struct {
type IPPermissions struct {
BoundType string `json:"boundType"`
Description string `json:"description"`
FromPort int `json:"fromPort"`
@@ -70,10 +74,6 @@ func (self *SSecurityGroup) GetName() string {
return self.GroupName
}
func (self *SSecurityGroup) Delete() error {
return cloudprovider.ErrNotImplemented
}
func (self *SSecurityGroup) GetDescription() string {
return self.GroupDescription
}
@@ -87,8 +87,8 @@ func (self *SSecurityGroup) GetReferences() ([]cloudprovider.SecurityGroupRefere
}
func (self *SSecurityGroup) GetRules() ([]cloudprovider.SecurityRule, error) {
ret := []cloudprovider.SecurityRule{}
for _, _rule := range self.IPPermissionsEgress {
var ret []cloudprovider.SecurityRule
for _, _rule := range append(self.IPPermissionsEgress, self.IPPermissions...) {
if len(_rule.Groups) > 0 {
continue
}
@@ -135,20 +135,82 @@ func (self *SSecurityGroup) GetStatus() string {
}
func (self *SSecurityGroup) SyncRules(common, inAdds, outAdds, inDels, outDels []cloudprovider.SecurityRule) error {
return cloudprovider.ErrNotImplemented
for _, r := range append(inDels, outDels...) {
err := self.region.deleteSecurityGroupRule(self.GroupId, r)
if err != nil {
if strings.Contains(err.Error(), "InvalidPermission.NotFound") {
continue
}
return errors.Wrapf(err, "deleteSecurityGroupRule %s %d %s", r.Name, r.Priority, r.String())
}
}
for _, r := range append(inAdds, outAdds...) {
err := self.region.addSecurityGroupRules(self.GroupId, r)
if err != nil {
return errors.Wrapf(err, "addSecurityGroupRules %d %s", r.Priority, r.String())
}
}
return nil
}
func (self *SSecurityGroup) Delete() error {
return self.region.deleteSecurityGroup(self.GroupId)
}
func (self *SRegion) deleteSecurityGroupRule(secGrpId string, rule cloudprovider.SecurityRule) error {
allInputs := securityRuleToBingoCloud(secGrpId, rule)
for _, input := range allInputs {
data, _ := json.Marshal(&input)
params := make(map[string]string)
_ = json.Unmarshal(data, &params)
_, err := self.invoke("RevokeSecurityGroupIngress", params)
if err != nil {
log.Debugf("deleteSecurityGroupRule %s %s", rule.Direction, err.Error())
return err
}
}
return nil
}
func (self *SRegion) addSecurityGroupRules(secGrpId string, rule cloudprovider.SecurityRule) error {
allInputs := securityRuleToBingoCloud(secGrpId, rule)
for _, input := range allInputs {
data, _ := json.Marshal(&input)
params := make(map[string]string)
_ = json.Unmarshal(data, &params)
_, err := self.invoke("AuthorizeSecurityGroupIngress", params)
if err == nil {
continue
}
if err != nil && strings.Contains(err.Error(), "InvalidPermission.Duplicate") {
log.Debugf("addSecurityGroupRule %s %s", rule.Direction, err.Error())
continue
} else {
return err
}
}
return nil
}
func (self *SRegion) GetSecurityGroups(id, name, nextToken string) ([]SSecurityGroup, string, error) {
params := map[string]string{}
if len(id) > 0 {
params["groupId"] = id
params["GroupId.1"] = id
}
if len(name) > 0 {
params["groupName"] = name
params["Filter.1.Name"] = "group-name"
params["Filter.1.Value.1"] = name
}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
resp, err := self.invoke("DescribeSecurityGroups", params)
if err != nil {
return nil, "", err
@@ -157,7 +219,7 @@ func (self *SRegion) GetSecurityGroups(id, name, nextToken string) ([]SSecurityG
SecurityGroupInfo []SSecurityGroup
NextToken string
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.SecurityGroupInfo, ret.NextToken, nil
}
@@ -188,3 +250,49 @@ func (self *SRegion) GetISecurityGroupByName(opts *cloudprovider.SecurityGroupFi
}
return nil, cloudprovider.ErrNotFound
}
func (self *SRegion) deleteSecurityGroup(id string) error {
params := map[string]string{}
params["GroupId"] = id
_, err := self.invoke("DeleteSecurityGroup", params)
return err
}
func (self *SRegion) CreateISecurityGroup(conf *cloudprovider.SecurityGroupCreateInput) (cloudprovider.ICloudSecurityGroup, error) {
params := map[string]string{}
if len(conf.Name) > 0 {
params["GroupName"] = conf.Name
}
resp, err := self.invoke("CreateSecurityGroup", params)
if err != nil {
return nil, err
}
ret := &cloudprovider.SecurityGroupCreateOutput{}
_ = resp.Unmarshal(&ret)
if ret.Return {
//rule := cloudprovider.SecurityRule{
// ExternalId: ret.GroupId,
// SecurityRule: secrules.SecurityRule{
// Action: secrules.SecurityRuleAllow,
// Protocol: secrules.PROTO_ANY,
// Direction: secrules.DIR_IN,
// Priority: 1,
// Ports: []int{},
// PortStart: 1,
// PortEnd: 65535,
// },
//}
//rule.ParseCIDR("0.0.0.0/0")
//err = self.addSecurityGroupRules(ret.GroupId, rule)
//if err != nil {
// _ = self.deleteSecurityGroup(ret.GroupId)
// return nil, err
//}
return self.GetISecurityGroupById(ret.GroupId)
}
return nil, errors.Wrap(cloudprovider.ErrUnknown, "CreateSecurityGroup")
}
+135
View File
@@ -0,0 +1,135 @@
package bingocloud
import (
"strconv"
"time"
"yunion.io/x/jsonutils"
"yunion.io/x/cloudmux/pkg/cloudprovider"
)
type SSnapshot struct {
region *SRegion
SnapshotId string
SnapshotName string
VolumeId string
Status string
StartTime string
Progress string
OwnerId string
VolumeSize string
Description string
}
func (self SSnapshot) GetId() string {
return self.SnapshotId
}
func (self SSnapshot) GetName() string {
return self.SnapshotName
}
func (self SSnapshot) GetGlobalId() string {
return self.SnapshotId
}
func (self SSnapshot) GetCreatedAt() time.Time {
ct, _ := time.Parse("2006-01-02T15:04:05.000Z", self.StartTime)
return ct
}
func (self SSnapshot) GetStatus() string {
return self.Status
}
func (self SSnapshot) Refresh() error {
newSnapshot, err := self.region.getSnapshots(self.SnapshotId, "")
if err != nil {
return err
}
if len(newSnapshot) == 1 {
return jsonutils.Update(self, &newSnapshot[0])
}
return cloudprovider.ErrNotFound
}
func (self SSnapshot) IsEmulated() bool {
return false
}
func (self SSnapshot) GetSysTags() map[string]string {
return nil
}
func (self SSnapshot) GetTags() (map[string]string, error) {
return nil, nil
}
func (self SSnapshot) SetTags(tags map[string]string, replace bool) error {
return nil
}
func (self SSnapshot) GetProjectId() string {
return ""
}
func (self SSnapshot) GetSizeMb() int32 {
size, _ := strconv.Atoi(self.VolumeSize)
return int32(size * 1024)
}
func (self SSnapshot) GetDiskId() string {
return self.VolumeId
}
func (self SSnapshot) GetDiskType() string {
return ""
}
func (self SSnapshot) Delete() error {
return self.region.deleteSnapshot(self.SnapshotId)
}
func (self *SRegion) createSnapshot(volumeId, name string, desc string) (string, error) {
params := map[string]string{}
params["VolumeId"] = volumeId
params["SnapshotName"] = name
params["Description"] = desc
resp, err := self.client.invoke("CreateSnapshot", params)
if err != nil {
return "", err
}
newId := ""
err = resp.Unmarshal(&newId, "snapshotId")
return newId, err
}
func (self *SRegion) getSnapshots(id, name string) ([]SSnapshot, error) {
params := map[string]string{}
if id != "" {
params["SnapshotId.1"] = id
}
if name != "" {
params["Filter.1.Name"] = name
}
resp, err := self.client.invoke("DescribeSnapshots", params)
if err != nil {
return nil, err
}
var ret []SSnapshot
_ = resp.Unmarshal(&ret, "snapshotSet")
return ret, err
}
func (self *SRegion) deleteSnapshot(id string) error {
params := map[string]string{}
params["SnapshotId"] = id
_, err := self.client.invoke("DeleteSnapshot", params)
return err
}
+6 -4
View File
@@ -115,8 +115,9 @@ func (self *SStorage) IsSysDiskStore() bool {
func (self *SRegion) GetStorages(nextToken string) ([]SStorage, string, error) {
params := map[string]string{}
if len(nextToken) > 0 {
params["nextToken"] = nextToken
params["NextToken"] = nextToken
}
resp, err := self.invoke("DescribeStorages", params)
if err != nil {
return nil, "", err
@@ -125,7 +126,8 @@ func (self *SRegion) GetStorages(nextToken string) ([]SStorage, string, error) {
NextToken string
StorageSet []SStorage
}{}
resp.Unmarshal(&ret)
_ = resp.Unmarshal(&ret)
return ret.StorageSet, ret.NextToken, nil
}
@@ -147,7 +149,7 @@ func (self *SCluster) GetIStorages() ([]cloudprovider.ICloudStorage, error) {
if err != nil {
return nil, err
}
ret := []cloudprovider.ICloudStorage{}
var ret []cloudprovider.ICloudStorage
for i := range storages {
storages[i].cluster = self
ret = append(ret, &storages[i])
@@ -156,7 +158,7 @@ func (self *SCluster) GetIStorages() ([]cloudprovider.ICloudStorage, error) {
}
func (self *SRegion) getStorages() ([]SStorage, error) {
storages := []SStorage{}
var storages []SStorage
part, nextToken, err := self.GetStorages("")
if err != nil {
return nil, err
+113
View File
@@ -0,0 +1,113 @@
package bingocloud
import (
"fmt"
"strconv"
"strings"
"yunion.io/x/pkg/util/secrules"
"yunion.io/x/cloudmux/pkg/cloudprovider"
)
type portRange struct {
Start int64
End int64
}
type securityGroupInput struct {
GroupId string `json:"GroupId,omitempty"`
IpProtocol string `json:"IpProtocol,omitempty"`
CidrIp string `json:"CidrIp,omitempty"`
FromPort string `json:"FromPort,omitempty"`
ToPort string `json:"ToPort,omitempty"`
BoundType string `json:"BoundType,omitempty"`
SourceSecurityGroupOwnerId string `json:"SourceSecurityGroupOwnerId,omitempty"`
SourceSecurityGroupName string `json:"SourceSecurityGroupName,omitempty"`
Policy string `json:"Policy,omitempty"`
}
func securityRuleToBingoCloud(secGroupId string, rule cloudprovider.SecurityRule) []securityGroupInput {
var portRanges []portRange
if len(rule.Ports) == 0 {
var start, end = 0, 0
if rule.PortStart <= 0 {
start = 1
} else {
start = rule.PortStart
}
if rule.PortEnd <= 0 {
end = 65535
} else {
end = rule.PortEnd
}
portRanges = append(portRanges, portRange{int64(start), int64(end)})
}
for i := range rule.Ports {
port := rule.Ports[i]
if port <= 0 {
portRanges = append(portRanges, portRange{1, 65535})
} else {
portRanges = append(portRanges, portRange{int64(port), int64(port)})
}
}
protocol := ""
if rule.Protocol == secrules.PROTO_ANY {
protocol = "all"
} else {
protocol = rule.Protocol
}
var boundType = "In"
var policy = "DROP"
var allInputs []securityGroupInput
if rule.Direction == secrules.SecurityRuleEgress {
boundType = "Out"
}
if rule.Action == secrules.SecurityRuleAllow {
policy = "ACCEPT"
}
for _, port := range portRanges {
input := securityGroupInput{
GroupId: secGroupId,
IpProtocol: protocol,
CidrIp: rule.IPNet.String(),
FromPort: strconv.FormatInt(port.Start, 10),
ToPort: strconv.FormatInt(port.End, 10),
BoundType: boundType,
Policy: policy,
}
allInputs = append(allInputs, input)
}
return allInputs
}
func nextDeviceName(curDeviceNames []string) (string, error) {
var currents []string
for _, item := range curDeviceNames {
currents = append(currents, strings.ToLower(item))
}
for i := 0; i < 25; i++ {
device := fmt.Sprintf("/dev/vd%c", byte(98+i))
found := false
for _, item := range currents {
if strings.HasPrefix(item, device) {
found = true
}
}
if !found {
return device, nil
}
}
return "", fmt.Errorf("disk devicename out of index, current deivces: %s", currents)
}
+7 -5
View File
@@ -81,7 +81,7 @@ func (self *SVpc) GetISecurityGroups() ([]cloudprovider.ICloudSecurityGroup, err
if err != nil {
return nil, err
}
groups := []SSecurityGroup{}
var groups []SSecurityGroup
groups = append(groups, part...)
for len(nextToken) > 0 {
part, nextToken, err = self.region.GetSecurityGroups("", "", nextToken)
@@ -90,7 +90,7 @@ func (self *SVpc) GetISecurityGroups() ([]cloudprovider.ICloudSecurityGroup, err
}
groups = append(groups, part...)
}
ret := []cloudprovider.ICloudSecurityGroup{}
var ret []cloudprovider.ICloudSecurityGroup
for i := range groups {
groups[i].region = self.region
ret = append(ret, &groups[i])
@@ -118,13 +118,15 @@ func (self *SVpc) GetStatus() string {
func (self *SRegion) GetVpcs(id string) ([]SVpc, error) {
params := map[string]string{}
if len(id) > 0 {
params["vpcId"] = id
params["VpcId"] = id
}
resp, err := self.invoke("DescribeVpcs", params)
if err != nil {
return nil, err
}
vpcs := []SVpc{}
var vpcs []SVpc
return vpcs, resp.Unmarshal(&vpcs, "vpcSet")
}
@@ -133,7 +135,7 @@ func (self *SRegion) GetIVpcs() ([]cloudprovider.ICloudVpc, error) {
if err != nil {
return nil, errors.Wrapf(err, "GetVpcs")
}
ret := []cloudprovider.ICloudVpc{}
var ret []cloudprovider.ICloudVpc
for i := range vpcs {
vpcs[i].region = self
ret = append(ret, &vpcs[i])
+1 -1
View File
@@ -82,7 +82,7 @@ func (self *SVpc) GetIWires() ([]cloudprovider.ICloudWire, error) {
if err != nil {
return nil, err
}
ret := []cloudprovider.ICloudWire{}
var ret []cloudprovider.ICloudWire
for i := range clusters {
wire := &SWire{
vpc: self,
+1 -1
View File
@@ -25,6 +25,6 @@ func (self *SRegion) GetZones() ([]SZone, error) {
if err != nil {
return nil, err
}
ret := []SZone{}
var ret []SZone
return ret, resp.Unmarshal(&ret, "availabilityZoneInfo")
}
+52
View File
@@ -0,0 +1,52 @@
// Copyright 2019 Yunion
//
// 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 multicloud
import (
"yunion.io/x/cloudmux/pkg/cloudprovider"
"yunion.io/x/pkg/errors"
)
type SCDNDomainBase struct {
SResourceBase
}
func (self *SCDNDomainBase) GetCacheKeys() (*cloudprovider.SCDNCacheKeys, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetCacheKeys")
}
func (self *SCDNDomainBase) GetRangeOriginPull() (*cloudprovider.SCDNRangeOriginPull, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetRangeOriginPull")
}
func (self *SCDNDomainBase) GetCache() (*cloudprovider.SCDNCache, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetCache")
}
func (self *SCDNDomainBase) GetHTTPS() (*cloudprovider.SCDNHttps, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetHTTPS")
}
func (self *SCDNDomainBase) GetForceRedirect() (*cloudprovider.SCDNForceRedirect, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetForceRedirect")
}
func (self *SCDNDomainBase) GetReferer() (*cloudprovider.SCDNReferer, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetReferer")
}
func (self *SCDNDomainBase) GetMaxAge() (*cloudprovider.SCDNMaxAge, error) {
return nil, errors.Wrapf(cloudprovider.ErrNotImplemented, "GetMaxAge")
}
+377
View File
@@ -55,6 +55,134 @@ type SCdnDomain struct {
ServiceType string `json:"ServiceType"`
Status string `json:"Status"`
UpdateTime string `json:"UpdateTime"`
config *SCdnConfig
}
func (self *SCdnDomain) GetConfig() (*SCdnConfig, error) {
var err error = nil
if self.config == nil {
self.config, err = self.client.GetCdnConfig(self.ResourceID)
}
return self.config, err
}
type SCacheKey struct {
FullUrlCache string
IgnoreCase string
KeyRules []struct {
RulePaths []string
RuleType string
FullUrlCache string
IgnoreCase string
QueryString struct {
Switch string
Action string
Value string
}
RuleTag string
}
}
type SCache struct {
RuleCache []CdnCache
}
type CdnCache struct {
CdnCacheCacheConfig CdnCacheCacheConfig `json:"CacheConfig"`
RulePaths []string `json:"RulePaths"`
RuleType string `json:"RuleType"`
}
type CdnCacheCacheConfig struct {
CdnCacheCacheConfigCache CdnCacheCacheConfigCache `json:"Cache"`
CdnCacheCacheConfigFollowOrigin CdnCacheCacheConfigFollowOrigin `json:"FollowOrigin"`
CdnCacheCacheConfigNoCache CdnCacheCacheConfigNoCache `json:"NoCache"`
}
type CdnCacheCacheConfigFollowOrigin struct {
CdnCacheCacheConfigFollowOriginHeuristicCache CdnCacheCacheConfigFollowOriginHeuristicCache `json:"HeuristicCache"`
Switch string `json:"Switch"`
}
type CdnCacheCacheConfigFollowOriginHeuristicCache struct {
CdnCacheCacheConfigFollowOriginHeuristicCacheCacheConfig CdnCacheCacheConfigFollowOriginHeuristicCacheCacheConfig `json:"CacheConfig"`
Switch string `json:"Switch"`
}
type CdnCacheCacheConfigFollowOriginHeuristicCacheCacheConfig struct {
HeuristicCacheTime int `json:"HeuristicCacheTime"`
HeuristicCacheTimeSwitch string `json:"HeuristicCacheTimeSwitch"`
}
type CdnCacheCacheConfigNoCache struct {
Revalidate string `json:"Revalidate"`
Switch string `json:"Switch"`
}
type CdnCacheCacheConfigCache struct {
CacheTime int `json:"CacheTime"`
CompareMaxAge string `json:"CompareMaxAge"`
IgnoreCacheControl string `json:"IgnoreCacheControl"`
IgnoreSetCookie string `json:"IgnoreSetCookie"`
Switch string `json:"Switch"`
}
type SRangeOriginPull struct {
Switch string
RangeRules []struct {
Switch string
RuleType string
RulePaths []string
}
Cache *SCache
}
type SCdnHttps struct {
Switch string
Http2 string
}
type SForceRedirect struct {
Switch string
RedirectType string
}
type SCdnReferer struct {
Switch string
RefererRules []struct {
RuleType string
RulePaths []string
RefererType string
Referers []string
AllowEmpty bool
}
}
type SMaxAge struct {
Switch string
MaxAgeRules []struct {
MaxAgeType string
MaxAgeContents []string
MaxAgeTime int
FollowOrigin string
}
}
type SCdnConfig struct {
CacheKey *SCacheKey
RangeOriginPull *SRangeOriginPull
Cache *SCache
Https *SCdnHttps
ForceRedirect *SForceRedirect
Referer *SCdnReferer
MaxAge *SMaxAge
}
func (self *SCdnDomain) GetName() string {
@@ -319,3 +447,252 @@ func (self *SQcloudClient) CreateCDNDomain(opts *cloudprovider.CdnCreateOptions)
}
return self.GetCdnDomain(opts.Domain)
}
func (self *SQcloudClient) GetCdnConfig(resourceId string) (*SCdnConfig, error) {
params := map[string]string{
"Filters.0.Name": "resourceId",
"Filters.0.Value.0": resourceId,
"Limit": "1",
}
resp, err := self.cdnRequest("DescribeDomainsConfig", params)
if err != nil {
return nil, errors.Wrapf(err, "DescribeDomainsConfig")
}
result := struct {
Domains []SCdnConfig
TotalNumber int
}{}
err = resp.Unmarshal(&result)
if err != nil {
return nil, errors.Wrapf(err, "resp.Unmarshal")
}
for i := range result.Domains {
return &result.Domains[i], nil
}
return nil, errors.Wrapf(cloudprovider.ErrNotFound, resourceId)
}
func (self *SCdnDomain) GetCacheKeys() (*cloudprovider.SCDNCacheKeys, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.CacheKey == nil {
return nil, nil
}
enabled, ignoreCase := false, false
ret := &cloudprovider.SCDNCacheKeys{
KeyRules: []cloudprovider.CacheKeyRule{},
}
if config.CacheKey.FullUrlCache == "on" {
enabled = true
}
if config.CacheKey.IgnoreCase == "on" {
ignoreCase = true
}
ret.Enabled, ret.IgnoreCase = &enabled, &ignoreCase
for _, r := range config.CacheKey.KeyRules {
rule := cloudprovider.CacheKeyRule{
RulePaths: r.RulePaths,
RuleType: r.RuleType,
FullUrlCache: r.FullUrlCache == "on",
IgnoreCase: r.IgnoreCase == "on",
RuleTag: r.RuleTag,
QueryString: cloudprovider.CacheKeyRuleQueryString{
Enabled: r.QueryString.Switch == "on",
Action: r.QueryString.Action,
Value: r.QueryString.Value,
},
}
ret.KeyRules = append(ret.KeyRules, rule)
}
return ret, nil
}
func (self *SCdnDomain) GetRangeOriginPull() (*cloudprovider.SCDNRangeOriginPull, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.RangeOriginPull == nil {
return nil, nil
}
ret := &cloudprovider.SCDNRangeOriginPull{RangeOriginPullRules: []cloudprovider.SRangeOriginPullRule{}}
enabled := false
if config.RangeOriginPull.Switch == "on" {
enabled = true
}
ret.Enabled = &enabled
for _, obj := range config.RangeOriginPull.RangeRules {
rule := cloudprovider.SRangeOriginPullRule{
Enabled: false,
RuleType: obj.RuleType,
RulePaths: obj.RulePaths,
}
if obj.Switch == "on" {
rule.Enabled = true
}
ret.RangeOriginPullRules = append(ret.RangeOriginPullRules, rule)
}
return ret, nil
}
func (self *SCdnDomain) GetCache() (*cloudprovider.SCDNCache, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.Cache == nil {
return nil, nil
}
ret := &cloudprovider.SCDNCache{
RuleCache: []cloudprovider.SCacheRuleCache{},
}
for i, r := range config.Cache.RuleCache {
rule := cloudprovider.SCacheRuleCache{
Priority: i + 1,
RulePaths: r.RulePaths,
RuleType: r.RuleType,
CacheConfig: &cloudprovider.RuleCacheConfig{},
}
if r.CdnCacheCacheConfig.CdnCacheCacheConfigCache.Switch == "on" {
rule.CacheConfig.Cache = &struct {
Enabled bool
CacheTime int
CompareMaxAge bool
IgnoreCacheControl bool
IgnoreSetCookie bool
}{
Enabled: true,
CacheTime: r.CdnCacheCacheConfig.CdnCacheCacheConfigCache.CacheTime,
CompareMaxAge: r.CdnCacheCacheConfig.CdnCacheCacheConfigCache.CompareMaxAge == "on",
IgnoreCacheControl: r.CdnCacheCacheConfig.CdnCacheCacheConfigCache.IgnoreCacheControl == "on",
IgnoreSetCookie: r.CdnCacheCacheConfig.CdnCacheCacheConfigCache.IgnoreSetCookie == "on",
}
} else if r.CdnCacheCacheConfig.CdnCacheCacheConfigNoCache.Switch == "on" {
rule.CacheConfig.NoCache = &struct {
Enabled bool
Revalidate bool
}{
Enabled: true,
Revalidate: r.CdnCacheCacheConfig.CdnCacheCacheConfigNoCache.Revalidate == "on",
}
} else if r.CdnCacheCacheConfig.CdnCacheCacheConfigFollowOrigin.Switch == "on" {
follow := r.CdnCacheCacheConfig.CdnCacheCacheConfigFollowOrigin
rule.CacheConfig.FollowOrigin = &struct {
Enabled bool
HeuristicCache struct {
Enabled bool
CacheConfig struct {
HeuristicCacheTimeSwitch bool
HeuristicCacheTime int
}
}
}{
Enabled: true,
}
rule.CacheConfig.FollowOrigin.HeuristicCache.Enabled = follow.Switch == "on"
rule.CacheConfig.FollowOrigin.HeuristicCache.CacheConfig.HeuristicCacheTimeSwitch = follow.CdnCacheCacheConfigFollowOriginHeuristicCache.Switch == "on"
rule.CacheConfig.FollowOrigin.HeuristicCache.CacheConfig.HeuristicCacheTime = follow.CdnCacheCacheConfigFollowOriginHeuristicCache.CdnCacheCacheConfigFollowOriginHeuristicCacheCacheConfig.HeuristicCacheTime
}
ret.RuleCache = append(ret.RuleCache, rule)
}
return ret, nil
}
func (self *SCdnDomain) GetHTTPS() (*cloudprovider.SCDNHttps, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.Https == nil {
return nil, nil
}
ret := &cloudprovider.SCDNHttps{}
enabled, enableHttp2 := false, false
if config.Https.Switch == "on" {
enabled = true
}
if config.Https.Http2 == "on" {
enableHttp2 = true
}
ret.Enabled, ret.Http2 = &enabled, &enableHttp2
return ret, nil
}
func (self *SCdnDomain) GetForceRedirect() (*cloudprovider.SCDNForceRedirect, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.ForceRedirect == nil {
return nil, nil
}
ret := &cloudprovider.SCDNForceRedirect{
RedirectType: config.ForceRedirect.RedirectType,
}
enabled := false
if config.ForceRedirect.Switch == "on" {
enabled = true
}
ret.Enabled = &enabled
return ret, nil
}
func (self *SCdnDomain) GetReferer() (*cloudprovider.SCDNReferer, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.Referer == nil {
return nil, nil
}
ret := &cloudprovider.SCDNReferer{
RefererRules: []cloudprovider.RefererRule{},
}
enabled := false
if config.Referer.Switch == "on" {
enabled = true
}
ret.Enabled = &enabled
for _, r := range config.Referer.RefererRules {
rule := cloudprovider.RefererRule{
RuleType: r.RuleType,
RulePaths: r.RulePaths,
RefererType: r.RuleType,
Referers: r.Referers,
AllowEmpty: &r.AllowEmpty,
}
ret.RefererRules = append(ret.RefererRules, rule)
}
return ret, nil
}
func (self *SCdnDomain) GetMaxAge() (*cloudprovider.SCDNMaxAge, error) {
config, err := self.GetConfig()
if err != nil {
return nil, err
}
if config.MaxAge == nil {
return nil, nil
}
ret := &cloudprovider.SCDNMaxAge{}
enabled := false
if config.MaxAge.Switch == "on" {
enabled = true
}
ret.Enabled = &enabled
for _, r := range config.MaxAge.MaxAgeRules {
rule := cloudprovider.SMaxAgeRule{
MaxAgeType: r.MaxAgeType,
MaxAgeContents: r.MaxAgeContents,
MaxAgeTime: r.MaxAgeTime,
FollowOrigin: false,
}
if r.FollowOrigin == "on" {
rule.FollowOrigin = true
}
ret.MaxAgeRules = append(ret.MaxAgeRules, rule)
}
return ret, nil
}