From 97becc364ec188797f17dbdcd9a3ef66cd5cfab4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B1=88=E8=BD=A9?= Date: Wed, 7 Oct 2026 12:44:44 +0800 Subject: [PATCH] fix(region): skip sync rds sku when network is empty (#25783) --- pkg/compute/models/cloudregions.go | 44 +++++++++++++++++++ pkg/compute/models/cloudsync.go | 38 ++++++++++------ pkg/compute/models/dbinstance_skus.go | 10 ++++- pkg/compute/models/elasticcache_skus.go | 10 ++++- pkg/compute/models/networks.go | 12 +++++ pkg/compute/models/server_skus.go | 10 ++++- .../tasks/network/network_create_task.go | 3 ++ 7 files changed, 108 insertions(+), 19 deletions(-) diff --git a/pkg/compute/models/cloudregions.go b/pkg/compute/models/cloudregions.go index 0a7c62f4fa..e6a6f8b6f4 100644 --- a/pkg/compute/models/cloudregions.go +++ b/pkg/compute/models/cloudregions.go @@ -1334,6 +1334,50 @@ func (self *SCloudregion) StartSyncSkusTask(ctx context.Context, userCred mcclie return task.ScheduleRun(nil) } +// skipSkuSyncWithoutNetwork 当前 region 没有可用子网时跳过虚拟机、RDS、Redis 套餐同步。 +func (self *SCloudregion) skipSkuSyncWithoutNetwork(ctx context.Context) bool { + cnt, err := self.GetNetworkCount(ctx) + if err != nil { + log.Errorf("region %s(%s) GetNetworkCount fail %s, skip sku sync", self.Name, self.Id, err) + return true + } + if cnt > 0 { + return false + } + log.Debugf("region %s(%s) has no available network, skip sku sync", self.Name, self.Id) + return true +} + +// TriggerSkuSyncOnFirstNetwork 公有云区域出现第一个可用子网时触发虚拟机、RDS、Redis 套餐同步。 +func (self *SCloudregion) TriggerSkuSyncOnFirstNetwork(ctx context.Context, userCred mcclient.TokenCredential) { + if self.GetCloudEnv() != cloudprovider.CLOUD_ENV_PUBLIC_CLOUD { + return + } + cnt, err := self.GetNetworkCount(ctx) + if err != nil { + log.Errorf("region %s(%s) GetNetworkCount fail %s", self.Name, self.Id, err) + return + } + if cnt != 1 { + return + } + log.Infof("first available network ready in public region %s(%s), trigger sku sync", self.Name, self.Id) + if err := self.StartSyncSkusTask(ctx, userCred, ServerSkuManager.Keyword()); err != nil { + log.Errorf("start server sku sync for region %s fail %s", self.Name, err) + } + driver := self.GetDriver() + if driver != nil && driver.IsSupportedElasticcache() { + if err := self.StartSyncSkusTask(ctx, userCred, ElasticcacheSkuManager.Keyword()); err != nil { + log.Errorf("start elasticcache sku sync for region %s fail %s", self.Name, err) + } + } + if driver != nil && driver.IsSupportedDBInstance() { + if err := self.StartSyncSkusTask(ctx, userCred, DBInstanceSkuManager.Keyword()); err != nil { + log.Errorf("start dbinstance sku sync for region %s fail %s", self.Name, err) + } + } +} + func (self *SCloudregion) GetCloudproviders() ([]SCloudprovider, error) { sq := CloudproviderRegionManager.Query().Equals("cloudregion_id", self.Id).SubQuery() q := CloudproviderManager.Query() diff --git a/pkg/compute/models/cloudsync.go b/pkg/compute/models/cloudsync.go index dbdb70f222..e9ec0f6b3f 100644 --- a/pkg/compute/models/cloudsync.go +++ b/pkg/compute/models/cloudsync.go @@ -161,19 +161,22 @@ func syncRegionSkus(ctx context.Context, userCred mcclient.TokenCredential, loca return } - cnt, err := ServerSkuManager.GetSkuCountByRegion(regionId) - if err != nil { - log.Errorf("GetSkuCountByRegion fail %s", err) - return + skipSku := localRegion.skipSkuSyncWithoutNetwork(ctx) + if !skipSku { + cnt, err := ServerSkuManager.GetSkuCountByRegion(regionId) + if err != nil { + log.Errorf("GetSkuCountByRegion fail %s", err) + return + } + + if cnt == 0 { + // 提前同步instance type.如果同步失败可能导致vm 内存显示为0 + localRegion.StartSyncSkusTask(ctx, userCred, ServerSkuManager.Keyword()) + } } - if cnt == 0 { - // 提前同步instance type.如果同步失败可能导致vm 内存显示为0 - localRegion.StartSyncSkusTask(ctx, userCred, ServerSkuManager.Keyword()) - } - - if localRegion.GetDriver().IsSupportedElasticcache() { - cnt, err = ElasticcacheSkuManager.GetSkuCountByRegion(regionId) + if localRegion.GetDriver().IsSupportedElasticcache() && !skipSku { + cnt, err := ElasticcacheSkuManager.GetSkuCountByRegion(regionId) if err != nil { log.Errorf("ElasticcacheSkuManager.GetSkuCountByRegion fail %s", err) return @@ -184,8 +187,8 @@ func syncRegionSkus(ctx context.Context, userCred mcclient.TokenCredential, loca } } - if localRegion.GetDriver().IsSupportedDBInstance() { - cnt, err = DBInstanceSkuManager.GetSkuCountByRegion(regionId) + if localRegion.GetDriver().IsSupportedDBInstance() && !skipSku { + cnt, err := DBInstanceSkuManager.GetSkuCountByRegion(regionId) if err != nil { log.Errorf("DBInstanceSkuManager.GetSkuCountByRegion fail %s", err) return @@ -1543,6 +1546,9 @@ func syncSkusFromPrivateCloud( remoteRegion cloudprovider.ICloudRegion, xor bool, ) { + if region.skipSkuSyncWithoutNetwork(ctx) { + return + } skus, err := remoteRegion.GetISkus() if err != nil { msg := fmt.Sprintf("GetISkus for region %s(%s) failed %v", region.Name, region.Id, err) @@ -1614,6 +1620,9 @@ func syncRegionDBInstances( } func syncDBInstanceSkus(ctx context.Context, userCred mcclient.TokenCredential, syncResults SSyncResultSet, provider *SCloudprovider, localRegion *SCloudregion, remoteRegion cloudprovider.ICloudRegion, syncRange *SSyncRange) { + if localRegion.skipSkuSyncWithoutNetwork(ctx) { + return + } skus, err := func() ([]cloudprovider.ICloudDBInstanceSku, error) { defer syncResults.AddRequestCost(DBInstanceSkuManager)() return remoteRegion.GetIDBInstanceSkus() @@ -1672,6 +1681,9 @@ func syncNATSkus(ctx context.Context, userCred mcclient.TokenCredential, syncRes } func syncCacheSkus(ctx context.Context, userCred mcclient.TokenCredential, syncResults SSyncResultSet, provider *SCloudprovider, localRegion *SCloudregion, remoteRegion cloudprovider.ICloudRegion, syncRange *SSyncRange) { + if localRegion.skipSkuSyncWithoutNetwork(ctx) { + return + } skus, err := func() ([]cloudprovider.ICloudElasticcacheSku, error) { defer syncResults.AddRequestCost(ElasticcacheSkuManager)() return remoteRegion.GetIElasticcacheSkus() diff --git a/pkg/compute/models/dbinstance_skus.go b/pkg/compute/models/dbinstance_skus.go index 908d360194..ec6ccddf79 100644 --- a/pkg/compute/models/dbinstance_skus.go +++ b/pkg/compute/models/dbinstance_skus.go @@ -496,11 +496,14 @@ func (manager *SDBInstanceSkuManager) SyncDBInstanceSkus( region *SCloudregion, xor bool, ) compare.SyncResult { + result := compare.SyncResult{} + if region.skipSkuSyncWithoutNetwork(ctx) { + return result + } + lockman.LockRawObject(ctx, manager.Keyword(), region.Id) defer lockman.ReleaseRawObject(ctx, manager.Keyword(), region.Id) - result := compare.SyncResult{} - meta, err := yunionmeta.FetchYunionmeta(ctx) if err != nil { result.Error(errors.Wrapf(err, "FetchYunionmeta")) @@ -674,6 +677,9 @@ func SyncRegionDBInstanceSkus(ctx context.Context, userCred mcclient.TokenCreden log.Debugf("region %s(%s) not support dbinstance, skip sync", region.Name, region.Id) continue } + if region.skipSkuSyncWithoutNetwork(ctx) { + continue + } skuMeta := &SDBInstanceSku{} skuMeta.SetModelManager(DBInstanceSkuManager, skuMeta) skuMeta.Id = region.ExternalId diff --git a/pkg/compute/models/elasticcache_skus.go b/pkg/compute/models/elasticcache_skus.go index 2aa7575569..8a5d1b83eb 100644 --- a/pkg/compute/models/elasticcache_skus.go +++ b/pkg/compute/models/elasticcache_skus.go @@ -364,11 +364,14 @@ func (self *SElasticcacheSku) GetElasticcacheCount() (int, error) { } func (manager *SElasticcacheSkuManager) SyncElasticcacheSkus(ctx context.Context, userCred mcclient.TokenCredential, region *SCloudregion, xor bool) compare.SyncResult { + syncResult := compare.SyncResult{} + if region.skipSkuSyncWithoutNetwork(ctx) { + return syncResult + } + lockman.LockRawObject(ctx, manager.Keyword(), region.Id) defer lockman.ReleaseRawObject(ctx, manager.Keyword(), region.Id) - syncResult := compare.SyncResult{} - meta, err := yunionmeta.FetchYunionmeta(ctx) if err != nil { return syncResult @@ -831,6 +834,9 @@ func SyncElasticCacheSkus(ctx context.Context, userCred mcclient.TokenCredential if !region.GetDriver().IsSupportedElasticcache() { continue } + if region.skipSkuSyncWithoutNetwork(ctx) { + continue + } skuMeta := &SElasticcacheSku{} skuMeta.SetModelManager(ElasticcacheSkuManager, skuMeta) diff --git a/pkg/compute/models/networks.go b/pkg/compute/models/networks.go index 6d5941adac..18e6d072b6 100644 --- a/pkg/compute/models/networks.go +++ b/pkg/compute/models/networks.go @@ -850,10 +850,22 @@ func (manager *SNetworkManager) newFromCloudNetwork(ctx context.Context, userCre Obj: net, Action: notifyclient.ActionSyncCreate, }) + if net.Status == api.NETWORK_STATUS_AVAILABLE { + net.TriggerPublicCloudSkuSync(ctx, userCred) + } return net, nil } +func (snet *SNetwork) TriggerPublicCloudSkuSync(ctx context.Context, userCred mcclient.TokenCredential) { + region, err := snet.GetRegion() + if err != nil { + log.Errorf("network %s(%s) get region for sku sync fail %s", snet.Name, snet.Id, err) + return + } + region.TriggerSkuSyncOnFirstNetwork(ctx, userCred) +} + func (net *SNetwork) IsAddressInRange(address netutils.IPV4Addr) bool { ipRange := net.getIPRange() if ipRange == nil { diff --git a/pkg/compute/models/server_skus.go b/pkg/compute/models/server_skus.go index ad628cd2e5..46a260c8aa 100644 --- a/pkg/compute/models/server_skus.go +++ b/pkg/compute/models/server_skus.go @@ -1582,11 +1582,14 @@ func (manager *SServerSkuManager) GetLocalSkus() (map[string]bool, error) { } func (region *SCloudregion) SyncServerSkus(ctx context.Context, userCred mcclient.TokenCredential, xor bool) compare.SyncResult { + result := compare.SyncResult{} + if region.skipSkuSyncWithoutNetwork(ctx) { + return result + } + lockman.LockRawObject(ctx, ServerSkuManager.Keyword(), region.Id) defer lockman.ReleaseRawObject(ctx, ServerSkuManager.Keyword(), region.Id) - result := compare.SyncResult{} - meta, err := yunionmeta.FetchYunionmeta(ctx) if err != nil { result.Error(errors.Wrapf(err, "FetchYunionmeta")) @@ -2041,6 +2044,9 @@ func SyncServerSkus(ctx context.Context, userCred mcclient.TokenCredential, isSt for i := range cloudregions { region := &cloudregions[i] + if region.skipSkuSyncWithoutNetwork(ctx) { + continue + } skuMeta := &SServerSku{} skuMeta.SetModelManager(ServerSkuManager, skuMeta) diff --git a/pkg/compute/tasks/network/network_create_task.go b/pkg/compute/tasks/network/network_create_task.go index c16a1da177..fdd89f76ca 100644 --- a/pkg/compute/tasks/network/network_create_task.go +++ b/pkg/compute/tasks/network/network_create_task.go @@ -65,6 +65,9 @@ func (self *NetworkCreateTask) OnInit(ctx context.Context, obj db.IStandaloneMod self.taskFailed(ctx, net, errors.Wrapf(err, "RequestCreateNetwork")) return } + if net.Status == api.NETWORK_STATUS_AVAILABLE { + net.TriggerPublicCloudSkuSync(ctx, self.UserCred) + } net.ClearSchedDescCache() logclient.AddActionLogWithStartable(self, net, logclient.ACT_CREATE, "", self.UserCred, true)