yunion.io/x/cloudmux@v0.3.10-0-alpha.1/pkg/multicloud/aliyun/filesystem.go (about) 1 // Copyright 2019 Yunion 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package aliyun 16 17 import ( 18 "fmt" 19 "strings" 20 "time" 21 22 "yunion.io/x/jsonutils" 23 "yunion.io/x/pkg/errors" 24 "yunion.io/x/pkg/utils" 25 26 billing_api "yunion.io/x/cloudmux/pkg/apis/billing" 27 api "yunion.io/x/cloudmux/pkg/apis/compute" 28 "yunion.io/x/cloudmux/pkg/cloudprovider" 29 "yunion.io/x/cloudmux/pkg/multicloud" 30 ) 31 32 type SupportedFeatures struct { 33 SupportedFeature []string 34 } 35 36 type MountTargets struct { 37 MountTarget []SMountTarget 38 } 39 40 type Package struct { 41 } 42 43 type Packages struct { 44 Package []Package 45 } 46 47 type SFileSystem struct { 48 multicloud.SNasBase 49 AliyunTags 50 region *SRegion 51 52 Status string 53 Description string 54 StorageType string 55 MountTargetCountLimit int 56 Ldap string 57 ZoneId string 58 // 2021-03-22T10:08:15CST 59 CreateTime string 60 MeteredIASize int 61 SupportedFeatures SupportedFeatures 62 MountTargets MountTargets 63 AutoSnapshotPolicyId string 64 MeteredSize int64 65 EncryptType int 66 Capacity int64 67 ProtocolType string 68 ChargeType string 69 Packages Packages 70 ExpiredTime string 71 FileSystemType string 72 FileSystemId string 73 RegionId string 74 } 75 76 func (self *SFileSystem) GetId() string { 77 return self.FileSystemId 78 } 79 80 func (self *SFileSystem) GetGlobalId() string { 81 return self.FileSystemId 82 } 83 84 func (self *SFileSystem) GetName() string { 85 if len(self.Description) > 0 { 86 return self.Description 87 } 88 return self.FileSystemId 89 } 90 91 func (self *SFileSystem) GetFileSystemType() string { 92 return self.FileSystemType 93 } 94 95 func (self *SFileSystem) GetMountTargetCountLimit() int { 96 return self.MountTargetCountLimit 97 } 98 99 func (self *SFileSystem) GetStatus() string { 100 switch self.Status { 101 case "", "Running": 102 return api.NAS_STATUS_AVAILABLE 103 case "Extending": 104 return api.NAS_STATUS_EXTENDING 105 case "Stopping", "Stopped": 106 return api.NAS_STATUS_UNAVAILABLE 107 case "Pending": 108 return api.NAS_STATUS_CREATING 109 default: 110 return api.NAS_STATUS_UNKNOWN 111 } 112 } 113 114 func (self *SFileSystem) GetBillintType() string { 115 if self.ChargeType == "PayAsYouGo" { 116 return billing_api.BILLING_TYPE_POSTPAID 117 } 118 return billing_api.BILLING_TYPE_PREPAID 119 } 120 121 func (self *SFileSystem) GetStorageType() string { 122 return strings.ToLower(self.StorageType) 123 } 124 125 func (self *SFileSystem) GetProtocol() string { 126 return self.ProtocolType 127 } 128 129 func (self *SFileSystem) GetCapacityGb() int64 { 130 return self.Capacity 131 } 132 133 func (self *SFileSystem) GetUsedCapacityGb() int64 { 134 return self.MeteredSize 135 } 136 137 func (self *SFileSystem) GetZoneId() string { 138 return self.ZoneId 139 } 140 141 func (self *SFileSystem) Delete() error { 142 return self.region.DeleteFileSystem(self.FileSystemId) 143 } 144 145 func (self *SFileSystem) GetCreatedAt() time.Time { 146 ret, _ := time.Parse("2006-01-02T15:04:05CST", self.CreateTime) 147 if !ret.IsZero() { 148 ret = ret.Add(time.Hour * 8) 149 } 150 return ret 151 } 152 153 func (self *SFileSystem) GetExpiredAt() time.Time { 154 ret, _ := time.Parse("2006-01-02T15:04:05CST", self.ExpiredTime) 155 if !ret.IsZero() { 156 ret = ret.Add(time.Hour * 8) 157 } 158 return ret 159 } 160 161 func (self *SFileSystem) Refresh() error { 162 fs, err := self.region.GetFileSystem(self.FileSystemId) 163 if err != nil { 164 return errors.Wrapf(err, "GetFileSystem(%s)", self.FileSystemId) 165 } 166 return jsonutils.Update(self, fs) 167 } 168 169 func (self *SRegion) GetFileSystems(id string, pageSize, pageNum int) ([]SFileSystem, int, error) { 170 if pageSize < 1 || pageSize > 100 { 171 pageSize = 50 172 } 173 if pageNum < 1 { 174 pageNum = 1 175 } 176 params := map[string]string{ 177 "RegionId": self.RegionId, 178 "PageSize": fmt.Sprintf("%d", pageSize), 179 "PageNumber": fmt.Sprintf("%d", pageNum), 180 } 181 if len(id) > 0 { 182 params["FileSystemId"] = id 183 } 184 resp, err := self.nasRequest("DescribeFileSystems", params) 185 if err != nil { 186 return nil, 0, errors.Wrapf(err, "DescribeFileSystems") 187 } 188 ret := struct { 189 TotalCount int 190 FileSystems struct { 191 FileSystem []SFileSystem 192 } 193 }{} 194 err = resp.Unmarshal(&ret) 195 if err != nil { 196 return nil, 0, errors.Wrapf(err, "resp.Unmarshal") 197 } 198 return ret.FileSystems.FileSystem, ret.TotalCount, nil 199 } 200 201 func (self *SRegion) GetICloudFileSystems() ([]cloudprovider.ICloudFileSystem, error) { 202 nas := []SFileSystem{} 203 num := 1 204 for { 205 part, total, err := self.GetFileSystems("", 100, num) 206 if err != nil { 207 return nil, errors.Wrapf(err, "GetFileSystems") 208 } 209 nas = append(nas, part...) 210 if total <= len(nas) { 211 break 212 } 213 num++ 214 } 215 216 ret := []cloudprovider.ICloudFileSystem{} 217 for i := range nas { 218 nas[i].region = self 219 ret = append(ret, &nas[i]) 220 } 221 return ret, nil 222 } 223 224 func (self *SRegion) GetFileSystem(id string) (*SFileSystem, error) { 225 if len(id) == 0 { 226 return nil, errors.Wrapf(cloudprovider.ErrNotFound, "empty id") 227 } 228 nas, total, err := self.GetFileSystems(id, 1, 1) 229 if err != nil { 230 return nil, errors.Wrapf(err, "GetFileSystems") 231 } 232 if total == 1 { 233 nas[0].region = self 234 return &nas[0], nil 235 } 236 if total == 0 { 237 return nil, errors.Wrapf(cloudprovider.ErrNotFound, id) 238 } 239 return nil, errors.Wrapf(cloudprovider.ErrDuplicateId, id) 240 } 241 242 func (self *SRegion) GetICloudFileSystemById(id string) (cloudprovider.ICloudFileSystem, error) { 243 fs, err := self.GetFileSystem(id) 244 if err != nil { 245 return nil, errors.Wrapf(err, "self.GetFileSystem") 246 } 247 return fs, nil 248 } 249 250 func (self *SRegion) CreateMountTarget(opts *cloudprovider.SMountTargetCreateOptions) (*SMountTarget, error) { 251 params := map[string]string{ 252 "RegionId": self.RegionId, 253 "FileSystemId": opts.FileSystemId, 254 "AccessGroupName": strings.TrimPrefix(strings.TrimPrefix(opts.AccessGroupId, "extreme/"), "standard/"), 255 "NetworkType": utils.Capitalize(opts.NetworkType), 256 "VpcId": opts.VpcId, 257 "VSwitchId": opts.NetworkId, 258 } 259 resp, err := self.nasRequest("CreateMountTarget", params) 260 if err != nil { 261 return nil, errors.Wrapf(err, "CreateMountTarget") 262 } 263 ret := struct { 264 MountTargetDomain string 265 }{} 266 err = resp.Unmarshal(&ret) 267 if err != nil { 268 return nil, errors.Wrapf(err, "resp.Unmarshal") 269 } 270 mts, _, err := self.GetMountTargets(opts.FileSystemId, ret.MountTargetDomain, 10, 1) 271 if err != nil { 272 return nil, errors.Wrapf(err, "self.GetMountTargets") 273 } 274 for i := range mts { 275 if mts[i].MountTargetDomain == ret.MountTargetDomain { 276 return &mts[i], nil 277 } 278 } 279 return nil, errors.Wrapf(cloudprovider.ErrNotFound, "afeter create with mount domain %s", ret.MountTargetDomain) 280 } 281 282 func (self *SFileSystem) CreateMountTarget(opts *cloudprovider.SMountTargetCreateOptions) (cloudprovider.ICloudMountTarget, error) { 283 mt, err := self.region.CreateMountTarget(opts) 284 if err != nil { 285 return nil, errors.Wrapf(err, "CreateMountTarget") 286 } 287 mt.fs = self 288 return mt, nil 289 } 290 291 func (self *SRegion) DeleteFileSystem(id string) error { 292 params := map[string]string{ 293 "RegionId": self.RegionId, 294 "FileSystemId": id, 295 } 296 _, err := self.nasRequest("DeleteFileSystem", params) 297 return errors.Wrapf(err, "DeleteFileSystem") 298 } 299 300 func (self *SRegion) CreateICloudFileSystem(opts *cloudprovider.FileSystemCraeteOptions) (cloudprovider.ICloudFileSystem, error) { 301 fs, err := self.CreateFileSystem(opts) 302 if err != nil { 303 return nil, errors.Wrapf(err, "self.CreateFileSystem") 304 } 305 return fs, nil 306 } 307 308 func (self *SRegion) CreateFileSystem(opts *cloudprovider.FileSystemCraeteOptions) (*SFileSystem, error) { 309 params := map[string]string{ 310 "RegionId": self.RegionId, 311 "ProtocolType": opts.Protocol, 312 "ZoneId": opts.ZoneId, 313 "EncryptType": "0", 314 "FileSystemType": opts.FileSystemType, 315 "StorageType": opts.StorageType, 316 "ClientToken": utils.GenRequestId(20), 317 "Description": opts.Name, 318 } 319 320 if self.GetCloudEnv() == ALIYUN_FINANCE_CLOUDENV { 321 if opts.FileSystemType == "standard" { 322 opts.ZoneId = strings.Replace(opts.ZoneId, "cn-shanghai-finance-1", "jr-cn-shanghai-", 1) 323 opts.ZoneId = strings.Replace(opts.ZoneId, "cn-shenzhen-finance-1", "jr-cn-shenzhen-", 1) 324 params["ZoneId"] = opts.ZoneId 325 } 326 } 327 328 switch opts.FileSystemType { 329 case "standard": 330 params["StorageType"] = utils.Capitalize(opts.StorageType) 331 case "cpfs": 332 params["ProtocolType"] = "cpfs" 333 switch opts.StorageType { 334 case "advance_100": 335 params["Bandwidth"] = "100" 336 case "advance_200": 337 params["Bandwidth"] = "200" 338 } 339 case "extreme": 340 params["Capacity"] = fmt.Sprintf("%d", opts.Capacity) 341 } 342 if len(opts.VpcId) > 0 { 343 params["VpcId"] = opts.VpcId 344 } 345 if len(opts.NetworkId) > 0 { 346 params["VSwitchId"] = opts.NetworkId 347 } 348 if opts.BillingCycle != nil { 349 params["ChargeType"] = "Subscription" 350 params["Duration"] = fmt.Sprintf("%d", opts.BillingCycle.GetMonths()) 351 } 352 resp, err := self.nasRequest("CreateFileSystem", params) 353 if err != nil { 354 return nil, errors.Wrapf(err, "CreateFileSystem") 355 } 356 fsId, _ := resp.GetString("FileSystemId") 357 return self.GetFileSystem(fsId) 358 } 359 360 func (self *SFileSystem) SetTags(tags map[string]string, replace bool) error { 361 return self.region.SetResourceTags(ALIYUN_SERVICE_NAS, "filesystem", self.FileSystemId, tags, replace) 362 }