yunion.io/x/cloudmux@v0.3.10-0-alpha.1/pkg/multicloud/aliyun/vpc.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 "strings" 19 "time" 20 21 "yunion.io/x/jsonutils" 22 "yunion.io/x/log" 23 "yunion.io/x/pkg/errors" 24 25 "yunion.io/x/cloudmux/pkg/cloudprovider" 26 "yunion.io/x/cloudmux/pkg/multicloud" 27 ) 28 29 const ( 30 VpcAvailable = "Available" 31 VpcPending = "Pending" 32 ) 33 34 // "CidrBlock":"172.31.0.0/16","CreationTime":"2017-03-19T13:37:40Z","Description":"System created default VPC.","IsDefault":true,"RegionId":"cn-hongkong","Status":"Available","UserCidrs":{"UserCidr":[]},"VRouterId":"vrt-j6c00qrol733dg36iq4qj","VSwitchIds":{"VSwitchId":["vsw-j6c3gig5ub4fmi2veyrus"]},"VpcId":"vpc-j6c86z3sh8ufhgsxwme0q","VpcName":"" 35 36 type SUserCIDRs struct { 37 UserCidr []string 38 } 39 40 type SVSwitchIds struct { 41 VSwitchId []string 42 } 43 44 type SVpc struct { 45 multicloud.SVpc 46 AliyunTags 47 48 region *SRegion 49 50 iwires []cloudprovider.ICloudWire 51 52 secgroups []cloudprovider.ICloudSecurityGroup 53 routeTables []cloudprovider.ICloudRouteTable 54 55 CidrBlock string 56 CreationTime time.Time 57 Description string 58 IsDefault bool 59 RegionId string 60 Status string 61 UserCidrs SUserCIDRs 62 VRouterId string 63 VSwitchIds SVSwitchIds 64 VpcId string 65 VpcName string 66 } 67 68 func (self *SVpc) GetId() string { 69 return self.VpcId 70 } 71 72 func (self *SVpc) GetName() string { 73 if len(self.VpcName) > 0 { 74 return self.VpcName 75 } 76 return self.VpcId 77 } 78 79 func (self *SVpc) GetGlobalId() string { 80 return self.VpcId 81 } 82 83 func (self *SVpc) IsEmulated() bool { 84 return false 85 } 86 87 func (self *SVpc) GetIsDefault() bool { 88 return self.IsDefault 89 } 90 91 func (self *SVpc) GetCidrBlock() string { 92 return self.CidrBlock 93 } 94 95 func (self *SVpc) GetStatus() string { 96 return strings.ToLower(self.Status) 97 } 98 99 func (self *SVpc) Refresh() error { 100 new, err := self.region.getVpc(self.VpcId) 101 if err != nil { 102 return err 103 } 104 return jsonutils.Update(self, new) 105 } 106 107 func (self *SVpc) GetRegion() cloudprovider.ICloudRegion { 108 return self.region 109 } 110 111 func (self *SVpc) addWire(wire *SWire) { 112 if self.iwires == nil { 113 self.iwires = make([]cloudprovider.ICloudWire, 0) 114 } 115 self.iwires = append(self.iwires, wire) 116 } 117 118 func (self *SVpc) getWireByZoneId(zoneId string) *SWire { 119 for i := 0; i < len(self.iwires); i += 1 { 120 wire := self.iwires[i].(*SWire) 121 if wire.zone.ZoneId == zoneId { 122 return wire 123 } 124 } 125 return nil 126 } 127 128 func (self *SVpc) fetchVSwitches() error { 129 switches, total, err := self.region.GetVSwitches(nil, self.VpcId, 0, 50) 130 if err != nil { 131 return err 132 } 133 if total > len(switches) { 134 switches, _, err = self.region.GetVSwitches(nil, self.VpcId, 0, total) 135 if err != nil { 136 return err 137 } 138 } 139 for i := 0; i < len(switches); i += 1 { 140 wire := self.getWireByZoneId(switches[i].ZoneId) 141 if wire != nil { 142 switches[i].wire = wire 143 wire.addNetwork(&switches[i]) 144 } 145 } 146 return nil 147 } 148 149 func (self *SVpc) GetIWires() ([]cloudprovider.ICloudWire, error) { 150 if self.iwires == nil { 151 err := self.fetchVSwitches() 152 if err != nil { 153 return nil, err 154 } 155 } 156 return self.iwires, nil 157 } 158 159 func (self *SVpc) GetIWireById(wireId string) (cloudprovider.ICloudWire, error) { 160 if self.iwires == nil { 161 err := self.fetchVSwitches() 162 if err != nil { 163 return nil, err 164 } 165 } 166 for i := 0; i < len(self.iwires); i += 1 { 167 if self.iwires[i].GetGlobalId() == wireId { 168 return self.iwires[i], nil 169 } 170 } 171 return nil, cloudprovider.ErrNotFound 172 } 173 174 func (self *SVpc) fetchSecurityGroups() error { 175 secgroups := make([]SSecurityGroup, 0) 176 for { 177 parts, total, err := self.region.GetSecurityGroups(self.VpcId, "", []string{}, len(secgroups), 50) 178 if err != nil { 179 return err 180 } 181 secgroups = append(secgroups, parts...) 182 if len(secgroups) >= total { 183 break 184 } 185 } 186 self.secgroups = make([]cloudprovider.ICloudSecurityGroup, len(secgroups)) 187 for i := 0; i < len(secgroups); i++ { 188 secgroups[i].vpc = self 189 self.secgroups[i] = &secgroups[i] 190 } 191 return nil 192 } 193 194 func (self *SVpc) GetISecurityGroups() ([]cloudprovider.ICloudSecurityGroup, error) { 195 if self.secgroups == nil { 196 err := self.fetchSecurityGroups() 197 if err != nil { 198 return nil, err 199 } 200 } 201 return self.secgroups, nil 202 } 203 204 func (self *SVpc) fetchRouteTables() error { 205 routeTables := make([]*SRouteTable, 0) 206 for { 207 parts, total, err := self.RemoteGetRouteTableList(len(routeTables), 50) 208 if err != nil { 209 return err 210 } 211 routeTables = append(routeTables, parts...) 212 if len(routeTables) >= total { 213 break 214 } 215 } 216 self.routeTables = make([]cloudprovider.ICloudRouteTable, len(routeTables)) 217 for i := 0; i < len(routeTables); i++ { 218 routeTables[i].vpc = self 219 self.routeTables[i] = routeTables[i] 220 } 221 return nil 222 } 223 224 func (self *SVpc) GetIRouteTables() ([]cloudprovider.ICloudRouteTable, error) { 225 if self.routeTables == nil { 226 err := self.fetchRouteTables() 227 if err != nil { 228 return nil, err 229 } 230 } 231 return self.routeTables, nil 232 } 233 234 func (self *SVpc) GetIRouteTableById(routeTableId string) (cloudprovider.ICloudRouteTable, error) { 235 tables, err := self.GetIRouteTables() 236 if err != nil { 237 return nil, errors.Wrapf(err, "GetIRouteTables") 238 } 239 for i := range tables { 240 if tables[i].GetGlobalId() == routeTableId { 241 return tables[i], nil 242 } 243 } 244 return nil, errors.Wrapf(cloudprovider.ErrNotFound, routeTableId) 245 } 246 247 func (self *SVpc) Delete() error { 248 err := self.fetchSecurityGroups() 249 if err != nil { 250 log.Errorf("fetchSecurityGroup for VPC delete fail %s", err) 251 return err 252 } 253 for i := 0; i < len(self.secgroups); i += 1 { 254 secgroup := self.secgroups[i].(*SSecurityGroup) 255 err := self.region.DeleteSecurityGroup(secgroup.SecurityGroupId) 256 if err != nil { 257 log.Errorf("deleteSecurityGroup for VPC delete fail %s", err) 258 return err 259 } 260 } 261 return self.region.DeleteVpc(self.VpcId) 262 } 263 264 func (self *SVpc) getNatGateways() ([]SNatGateway, error) { 265 natgatways := make([]SNatGateway, 0) 266 gwTotal := -1 267 for gwTotal < 0 || len(natgatways) < gwTotal { 268 parts, total, err := self.region.GetNatGateways(self.VpcId, "", len(natgatways), 50) 269 if err != nil { 270 return nil, err 271 } 272 if len(parts) > 0 { 273 natgatways = append(natgatways, parts...) 274 } 275 gwTotal = total 276 } 277 for i := 0; i < len(natgatways); i += 1 { 278 natgatways[i].vpc = self 279 } 280 return natgatways, nil 281 } 282 283 func (self *SVpc) GetINatGateways() ([]cloudprovider.ICloudNatGateway, error) { 284 nats := []SNatGateway{} 285 for { 286 parts, total, err := self.region.GetNatGateways(self.VpcId, "", len(nats), 50) 287 if err != nil { 288 return nil, err 289 } 290 nats = append(nats, parts...) 291 if len(nats) >= total { 292 break 293 } 294 } 295 inats := []cloudprovider.ICloudNatGateway{} 296 for i := 0; i < len(nats); i++ { 297 nats[i].vpc = self 298 inats = append(inats, &nats[i]) 299 } 300 return inats, nil 301 } 302 303 func (self *SVpc) GetAuthorityOwnerId() string { 304 return self.region.client.ownerId 305 } 306 307 func (self *SRegion) GrantInstanceToCen(opts *cloudprovider.SVpcJointInterVpcNetworkOption, instance SCenAttachInstanceInput) error { 308 params := make(map[string]string) 309 params["CenId"] = opts.InterVpcNetworkId 310 params["CenOwnerId"] = opts.NetworkAuthorityOwnerId 311 312 params["InstanceId"] = instance.InstanceId 313 params["InstanceType"] = instance.InstanceType 314 params["RegionId"] = instance.InstanceRegion 315 _, err := self.vpcRequest("GrantInstanceToCen", params) 316 if err != nil { 317 return errors.Wrapf(err, `self.vpcRequest("GrantInstanceToCen", %s)`, jsonutils.Marshal(params).String()) 318 } 319 return nil 320 } 321 322 func (self *SVpc) ProposeJoinICloudInterVpcNetwork(opts *cloudprovider.SVpcJointInterVpcNetworkOption) error { 323 instance := SCenAttachInstanceInput{ 324 InstanceType: "VPC", 325 InstanceId: self.GetId(), 326 InstanceRegion: self.region.GetId(), 327 } 328 err := self.region.GrantInstanceToCen(opts, instance) 329 if err != nil { 330 return errors.Wrapf(err, "self.region.GrantInstanceToCen(%s,%s)", self.GetId(), jsonutils.Marshal(opts).String()) 331 } 332 return nil 333 }