| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743 |
- // 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 models
- import (
- "context"
- "fmt"
- "yunion.io/x/cloudmux/pkg/cloudprovider"
- "yunion.io/x/jsonutils"
- "yunion.io/x/log"
- "yunion.io/x/pkg/errors"
- "yunion.io/x/pkg/gotypes"
- "yunion.io/x/pkg/util/compare"
- "yunion.io/x/sqlchemy"
- api "yunion.io/x/onecloud/pkg/apis/compute"
- "yunion.io/x/onecloud/pkg/cloudcommon/db"
- "yunion.io/x/onecloud/pkg/cloudcommon/db/lockman"
- "yunion.io/x/onecloud/pkg/cloudcommon/validators"
- "yunion.io/x/onecloud/pkg/httperrors"
- "yunion.io/x/onecloud/pkg/mcclient"
- "yunion.io/x/onecloud/pkg/util/stringutils2"
- )
- type SRouteTableManager struct {
- db.SStatusInfrasResourceBaseManager
- db.SExternalizedResourceBaseManager
- SVpcResourceBaseManager
- }
- var RouteTableManager *SRouteTableManager
- func init() {
- RouteTableManager = &SRouteTableManager{
- SStatusInfrasResourceBaseManager: db.NewStatusInfrasResourceBaseManager(
- SRouteTable{},
- "route_tables_tbl",
- "route_table",
- "route_tables",
- ),
- }
- RouteTableManager.SetVirtualObject(RouteTableManager)
- }
- type SRouteTable struct {
- db.SStatusInfrasResourceBase
- db.SExternalizedResourceBase
- SVpcResourceBase `create:"required"`
- Type string `width:"16" charset:"ascii" nullable:"false" list:"user"`
- Routes *api.SRoutes `list:"user" update:"user" create:"required"`
- }
- // VPC虚拟路由表列表
- func (man *SRouteTableManager) ListItemFilter(
- ctx context.Context,
- q *sqlchemy.SQuery,
- userCred mcclient.TokenCredential,
- query api.RouteTableListInput,
- ) (*sqlchemy.SQuery, error) {
- var err error
- q, err = man.SStatusInfrasResourceBaseManager.ListItemFilter(ctx, q, userCred, query.StatusInfrasResourceBaseListInput)
- if err != nil {
- return nil, errors.Wrap(err, "SStatusInfrasResourceBaseManager.ListItemFilter")
- }
- q, err = man.SExternalizedResourceBaseManager.ListItemFilter(ctx, q, userCred, query.ExternalizedResourceBaseListInput)
- if err != nil {
- return nil, errors.Wrap(err, "SExternalizedResourceBaseManager.ListItemFilter")
- }
- q, err = man.SVpcResourceBaseManager.ListItemFilter(ctx, q, userCred, query.VpcFilterListInput)
- if err != nil {
- return nil, errors.Wrap(err, "SVpcResourceBaseManager.ListItemFilter")
- }
- if len(query.Type) > 0 {
- q = q.In("type", query.Type)
- }
- return q, nil
- }
- func (man *SRouteTableManager) OrderByExtraFields(
- ctx context.Context,
- q *sqlchemy.SQuery,
- userCred mcclient.TokenCredential,
- query api.RouteTableListInput,
- ) (*sqlchemy.SQuery, error) {
- var err error
- q, err = man.SStatusInfrasResourceBaseManager.OrderByExtraFields(ctx, q, userCred, query.StatusInfrasResourceBaseListInput)
- if err != nil {
- return nil, errors.Wrap(err, "SStatusInfrasResourceBaseManager.OrderByExtraFields")
- }
- q, err = man.SVpcResourceBaseManager.OrderByExtraFields(ctx, q, userCred, query.VpcFilterListInput)
- if err != nil {
- return nil, errors.Wrap(err, "SVpcResourceBaseManager.OrderByExtraFields")
- }
- return q, nil
- }
- func (man *SRouteTableManager) QueryDistinctExtraField(q *sqlchemy.SQuery, field string) (*sqlchemy.SQuery, error) {
- var err error
- q, err = man.SInfrasResourceBaseManager.QueryDistinctExtraField(q, field)
- if err == nil {
- return q, nil
- }
- q, err = man.SVpcResourceBaseManager.QueryDistinctExtraField(q, field)
- if err == nil {
- return q, nil
- }
- return q, httperrors.ErrNotFound
- }
- func (man *SRouteTableManager) validateRoutes(ctx context.Context, data *jsonutils.JSONDict, update bool) (*jsonutils.JSONDict, error) {
- routes := api.SRoutes{}
- routesV := validators.NewStructValidator("routes", &routes)
- if update {
- routesV.Optional(true)
- }
- err := routesV.Validate(ctx, data)
- if err != nil {
- return nil, err
- }
- return data, nil
- }
- func (man *SRouteTableManager) ValidateCreateData(
- ctx context.Context,
- userCred mcclient.TokenCredential,
- ownerId mcclient.IIdentityProvider,
- query jsonutils.JSONObject,
- input api.RouteTableCreateInput,
- ) (api.RouteTableCreateInput, error) {
- _, err := man.validateRoutes(ctx, jsonutils.Marshal(input).(*jsonutils.JSONDict), false)
- if err != nil {
- return input, errors.Wrap(err, "validateRoutes")
- }
- _, err = validators.ValidateModel(ctx, userCred, VpcManager, &input.VpcId)
- if err != nil {
- return input, err
- }
- input.StatusInfrasResourceBaseCreateInput, err = man.SStatusInfrasResourceBaseManager.ValidateCreateData(ctx, userCred, ownerId, query, input.StatusInfrasResourceBaseCreateInput)
- if err != nil {
- return input, errors.Wrap(err, "SStatusInfrasResourceBaseManager.ValidateCreateData")
- }
- return input, nil
- }
- func (rt *SRouteTable) PerformPurge(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, data jsonutils.JSONObject) (jsonutils.JSONObject, error) {
- err := rt.ValidateDeleteCondition(ctx, nil)
- if err != nil {
- return nil, err
- }
- provider := rt.GetCloudprovider()
- if provider != nil {
- if provider.GetEnabled() {
- return nil, httperrors.NewInvalidStatusError("Cannot purge route_table on enabled cloud provider")
- }
- }
- err = rt.RealDelete(ctx, userCred)
- return nil, err
- }
- func (rt *SRouteTable) RealDelete(ctx context.Context, userCred mcclient.TokenCredential) error {
- routeSets, err := rt.GetRouteTableRouteSets()
- if err != nil {
- return errors.Wrapf(err, "GetRouteTableRouteSets for %s(%s)", rt.Name, rt.Id)
- }
- for i := range routeSets {
- err = routeSets[i].RealDelete(ctx, userCred)
- if err != nil {
- return errors.Wrapf(err, "Delete routeSet %s(%s)", routeSets[i].Name, routeSets[i].Id)
- }
- }
- associations, err := rt.GetRouteTableAssociations()
- if err != nil {
- return errors.Wrapf(err, "GetRouteTableAssociations for %s(%s)", rt.Name, rt.Id)
- }
- for i := range associations {
- err = associations[i].RealDelete(ctx, userCred)
- if err != nil {
- return errors.Wrapf(err, "Delete routetable associations %s(%s)", associations[i].Name, associations[i].Id)
- }
- }
- return rt.SStatusInfrasResourceBase.Delete(ctx, userCred)
- }
- func (rt *SRouteTable) ValidateUpdateData(
- ctx context.Context,
- userCred mcclient.TokenCredential,
- query jsonutils.JSONObject,
- input api.RouteTableUpdateInput,
- ) (api.RouteTableUpdateInput, error) {
- _, err := RouteTableManager.validateRoutes(ctx, jsonutils.Marshal(input).(*jsonutils.JSONDict), true)
- if err != nil {
- return input, errors.Wrap(err, "RouteTableManager.validateRoutes")
- }
- input.StatusInfrasResourceBaseUpdateInput, err = rt.SStatusInfrasResourceBase.ValidateUpdateData(ctx, userCred, query, input.StatusInfrasResourceBaseUpdateInput)
- if err != nil {
- return input, errors.Wrap(err, "SStatusInfrasResourceBase.ValidateUpdateData")
- }
- return input, nil
- }
- // PerformAddRoutes patches acl entries by adding then deleting the specified acls.
- // This is intended mainly for command line operations.
- func (rt *SRouteTable) PerformAddRoutes(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, data *jsonutils.JSONDict) (*jsonutils.JSONDict, error) {
- var routes api.SRoutes
- if rt.Routes != nil {
- routes_ := gotypes.DeepCopy(rt.Routes).(*api.SRoutes)
- routes = *routes_
- }
- {
- adds := api.SRoutes{}
- addsV := validators.NewStructValidator("routes", &adds)
- addsV.Optional(true)
- err := addsV.Validate(ctx, data)
- if err != nil {
- return nil, err
- }
- for _, add := range adds {
- found := false
- for _, route := range routes {
- if route.Cidr == add.Cidr {
- found = true
- break
- }
- }
- if !found {
- routes = append(routes, add)
- }
- }
- }
- _, err := db.Update(rt, func() error {
- rt.Routes = &routes
- return nil
- })
- if err != nil {
- return nil, err
- }
- return nil, nil
- }
- func (rt *SRouteTable) PerformDelRoutes(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, data *jsonutils.JSONDict) (*jsonutils.JSONDict, error) {
- var routes api.SRoutes
- if rt.Routes != nil {
- routes_ := gotypes.DeepCopy(rt.Routes).(*api.SRoutes)
- routes = *routes_
- }
- {
- cidrs := []string{}
- err := data.Unmarshal(&cidrs, "cidrs")
- if err != nil {
- return nil, httperrors.NewInputParameterError("unmarshaling cidrs failed: %s", err)
- }
- for _, cidr := range cidrs {
- for i := len(routes) - 1; i >= 0; i-- {
- route := routes[i]
- if route.Type == "system" {
- continue
- }
- if route.Cidr == cidr {
- routes = append(routes[:i], routes[i+1:]...)
- break
- }
- }
- }
- }
- _, err := db.Update(rt, func() error {
- rt.Routes = &routes
- return nil
- })
- if err != nil {
- return nil, err
- }
- return nil, nil
- }
- func (manager *SRouteTableManager) FetchCustomizeColumns(
- ctx context.Context,
- userCred mcclient.TokenCredential,
- query jsonutils.JSONObject,
- objs []interface{},
- fields stringutils2.SSortedStrings,
- isList bool,
- ) []api.RouteTableDetails {
- rows := make([]api.RouteTableDetails, len(objs))
- routeTableIds := make([]string, len(objs))
- virtRows := manager.SStatusInfrasResourceBaseManager.FetchCustomizeColumns(ctx, userCred, query, objs, fields, isList)
- vpcRows := manager.SVpcResourceBaseManager.FetchCustomizeColumns(ctx, userCred, query, objs, fields, isList)
- for i := range rows {
- rows[i] = api.RouteTableDetails{
- StatusInfrasResourceBaseDetails: virtRows[i],
- VpcResourceInfo: vpcRows[i],
- }
- routeTable := objs[i].(*SRouteTable)
- routeTableIds[i] = routeTable.GetId()
- }
- routeSets := []SRouteTableRouteSet{}
- q := RouteTableRouteSetManager.Query().In("route_table_id", routeTableIds)
- err := db.FetchModelObjects(RouteTableRouteSetManager, q, &routeSets)
- if err != nil {
- return rows
- }
- routeSetMap := map[string][]string{}
- for i := range routeSets {
- if _, ok := routeSetMap[routeSets[i].RouteTableId]; !ok {
- routeSetMap[routeSets[i].RouteTableId] = []string{}
- }
- routeSetMap[routeSets[i].RouteTableId] = append(routeSetMap[routeSets[i].RouteTableId], routeSets[i].Id)
- }
- associations := []SRouteTableAssociation{}
- q = RouteTableAssociationManager.Query().In("route_table_id", routeTableIds)
- err = db.FetchModelObjects(RouteTableAssociationManager, q, &associations)
- if err != nil {
- return rows
- }
- associationMap := map[string][]string{}
- for i := range associations {
- if _, ok := associationMap[associations[i].RouteTableId]; !ok {
- associationMap[associations[i].RouteTableId] = []string{}
- }
- associationMap[associations[i].RouteTableId] = append(associationMap[associations[i].RouteTableId], associations[i].Id)
- }
- for i := range rows {
- rows[i].RouteSetCount = len(routeSetMap[routeTableIds[i]])
- rows[i].AccociationCount = len(associationMap[routeTableIds[i]])
- }
- return rows
- }
- func (man *SRouteTableManager) SyncRouteTables(
- ctx context.Context,
- userCred mcclient.TokenCredential,
- vpc *SVpc,
- cloudRouteTables []cloudprovider.ICloudRouteTable,
- provider *SCloudprovider,
- xor bool,
- ) ([]SRouteTable, []cloudprovider.ICloudRouteTable, compare.SyncResult) {
- lockman.LockRawObject(ctx, man.Keyword(), vpc.Id)
- defer lockman.ReleaseRawObject(ctx, man.Keyword(), vpc.Id)
- localRouteTables := make([]SRouteTable, 0)
- remoteRouteTables := make([]cloudprovider.ICloudRouteTable, 0)
- syncResult := compare.SyncResult{}
- dbRouteTables := []SRouteTable{}
- if err := db.FetchModelObjects(man, man.Query().Equals("vpc_id", vpc.Id), &dbRouteTables); err != nil {
- syncResult.Error(err)
- return nil, nil, syncResult
- }
- removed := make([]SRouteTable, 0)
- commondb := make([]SRouteTable, 0)
- commonext := make([]cloudprovider.ICloudRouteTable, 0)
- added := make([]cloudprovider.ICloudRouteTable, 0)
- if err := compare.CompareSets(dbRouteTables, cloudRouteTables, &removed, &commondb, &commonext, &added); err != nil {
- syncResult.Error(err)
- return nil, nil, syncResult
- }
- for i := 0; i < len(removed); i += 1 {
- err := removed[i].syncRemoveCloudRouteTable(ctx, userCred)
- if err != nil {
- syncResult.DeleteError(err)
- } else {
- syncResult.Delete()
- }
- }
- if !xor {
- for i := 0; i < len(commondb); i += 1 {
- err := commondb[i].SyncWithCloudRouteTable(ctx, userCred, vpc, commonext[i], provider)
- if err != nil {
- syncResult.UpdateError(err)
- continue
- }
- localRouteTables = append(localRouteTables, commondb[i])
- remoteRouteTables = append(remoteRouteTables, commonext[i])
- syncResult.Update()
- }
- }
- for i := 0; i < len(added); i += 1 {
- routeTableNew, err := man.insertFromCloud(ctx, userCred, vpc, added[i], provider)
- if err != nil {
- syncResult.AddError(err)
- continue
- }
- syncMetadata(ctx, userCred, routeTableNew, added[i], false)
- localRouteTables = append(localRouteTables, *routeTableNew)
- remoteRouteTables = append(remoteRouteTables, added[i])
- syncResult.Add()
- }
- return localRouteTables, remoteRouteTables, syncResult
- }
- func (man *SRouteTableManager) newRouteTableFromCloud(ctx context.Context, userCred mcclient.TokenCredential, vpc *SVpc, cloudRouteTable cloudprovider.ICloudRouteTable) (*SRouteTable, error) {
- routes := api.SRoutes{}
- {
- cloudRoutes, err := cloudRouteTable.GetIRoutes()
- if err != nil {
- return nil, err
- }
- for _, cloudRoute := range cloudRoutes {
- route := &api.SRoute{
- Type: cloudRoute.GetType(),
- Cidr: cloudRoute.GetCidr(),
- NextHopType: cloudRoute.GetNextHopType(),
- NextHopId: cloudRoute.GetNextHop(),
- }
- routes = append(routes, route)
- }
- }
- routeTable := &SRouteTable{
- Type: string(cloudRouteTable.GetType()),
- Routes: &routes,
- }
- routeTable.VpcId = vpc.Id
- {
- basename := routeTableBasename(cloudRouteTable.GetName(), vpc.Name)
- newName, err := db.GenerateName(ctx, man, userCred, basename)
- if err != nil {
- return nil, err
- }
- routeTable.Name = newName
- }
- // routeTable.ManagerId = vpc.ManagerId
- routeTable.Status = cloudRouteTable.GetStatus()
- routeTable.ExternalId = cloudRouteTable.GetGlobalId()
- routeTable.Description = cloudRouteTable.GetDescription()
- // routeTable.ProjectId = userCred.GetProjectId()
- // routeTable.DomainId = userCred.GetProjectDomainId()
- routeTable.SetModelManager(man, routeTable)
- return routeTable, nil
- }
- func routeTableBasename(name, vpcName string) string {
- if name != "" {
- return name
- } else if vpcName != "" {
- return "rtbl-" + vpcName
- } else {
- return "rtbl"
- }
- }
- func (man *SRouteTableManager) insertFromCloud(ctx context.Context, userCred mcclient.TokenCredential, vpc *SVpc, cloudRouteTable cloudprovider.ICloudRouteTable, provider *SCloudprovider) (*SRouteTable, error) {
- var routeTable *SRouteTable
- var err error
- err = func() error {
- lockman.LockRawObject(ctx, man.Keyword(), "name")
- defer lockman.ReleaseRawObject(ctx, man.Keyword(), "name")
- routeTable, err = man.newRouteTableFromCloud(ctx, userCred, vpc, cloudRouteTable)
- if err != nil {
- return err
- }
- return man.TableSpec().Insert(ctx, routeTable)
- }()
- if err != nil {
- return nil, err
- }
- if provider != nil {
- SyncCloudDomain(userCred, routeTable, provider.GetOwnerId())
- routeTable.SyncShareState(ctx, userCred, provider.getAccountShareInfo())
- }
- db.OpsLog.LogEvent(routeTable, db.ACT_CREATE, routeTable.GetShortDesc(ctx), userCred)
- return routeTable, nil
- }
- func (self *SRouteTable) syncRemoveCloudRouteTable(ctx context.Context, userCred mcclient.TokenCredential) error {
- lockman.LockObject(ctx, self)
- defer lockman.ReleaseObject(ctx, self)
- err := self.ValidateDeleteCondition(ctx, nil)
- if err != nil {
- return err
- }
- err = self.RealDelete(ctx, userCred)
- return err
- }
- func (self *SRouteTable) SyncWithCloudRouteTable(ctx context.Context, userCred mcclient.TokenCredential, vpc *SVpc, cloudRouteTable cloudprovider.ICloudRouteTable, provider *SCloudprovider) error {
- man := self.GetModelManager().(*SRouteTableManager)
- routeTable, err := man.newRouteTableFromCloud(ctx, userCred, vpc, cloudRouteTable)
- if err != nil {
- return err
- }
- diff, err := db.UpdateWithLock(ctx, self, func() error {
- // self.CloudregionId = routeTable.CloudregionId
- self.Status = routeTable.GetStatus()
- self.VpcId = vpc.Id
- self.Type = routeTable.Type
- self.Routes = routeTable.Routes
- return nil
- })
- if err != nil {
- return err
- }
- if provider != nil {
- SyncCloudDomain(userCred, self, provider.GetOwnerId())
- self.SyncShareState(ctx, userCred, provider.getAccountShareInfo())
- if account, _ := provider.GetCloudaccount(); account != nil {
- syncMetadata(ctx, userCred, self, cloudRouteTable, account.ReadOnly)
- }
- }
- db.OpsLog.LogSyncUpdate(self, diff, userCred)
- return nil
- }
- func (self *SRouteTable) SyncRouteTableRouteSets(
- ctx context.Context,
- userCred mcclient.TokenCredential,
- ext cloudprovider.ICloudRouteTable,
- provider *SCloudprovider,
- xor bool,
- ) compare.SyncResult {
- lockman.LockRawObject(ctx, self.Keyword(), fmt.Sprintf("%s-records", self.Id))
- defer lockman.ReleaseRawObject(ctx, self.Keyword(), fmt.Sprintf("%s-records", self.Id))
- syncResult := compare.SyncResult{}
- iRoutes, err := ext.GetIRoutes()
- if err != nil {
- syncResult.Error(errors.Wrapf(err, "GetIRoutes"))
- return syncResult
- }
- dbRouteSets, err := self.GetRouteTableRouteSets()
- if err != nil {
- syncResult.Error(errors.Wrapf(err, "GetRouteTableRouteSets"))
- return syncResult
- }
- removed := make([]SRouteTableRouteSet, 0)
- commondb := make([]SRouteTableRouteSet, 0)
- commonext := make([]cloudprovider.ICloudRoute, 0)
- added := make([]cloudprovider.ICloudRoute, 0)
- if err := compare.CompareSets(dbRouteSets, iRoutes, &removed, &commondb, &commonext, &added); err != nil {
- syncResult.Error(err)
- return syncResult
- }
- for i := range dbRouteSets {
- if len(dbRouteSets[i].ExternalId) == 0 {
- removed = append(removed, dbRouteSets[i])
- }
- }
- for i := 0; i < len(removed); i++ {
- err := removed[i].syncRemoveRouteSet(ctx, userCred)
- if err != nil {
- syncResult.DeleteError(err)
- } else {
- syncResult.Delete()
- }
- }
- if !xor {
- for i := 0; i < len(commondb); i++ {
- err := commondb[i].syncWithCloudRouteSet(ctx, userCred, provider, commonext[i])
- if err != nil {
- syncResult.UpdateError(err)
- continue
- }
- syncResult.Update()
- }
- }
- for i := 0; i < len(added); i++ {
- _, err := RouteTableRouteSetManager.newRouteSetFromCloud(ctx, userCred, self, provider, added[i])
- if err != nil {
- syncResult.AddError(err)
- continue
- }
- syncResult.Add()
- }
- return syncResult
- }
- func (self *SRouteTable) GetRouteTableRouteSets() ([]SRouteTableRouteSet, error) {
- routes := []SRouteTableRouteSet{}
- q := RouteTableRouteSetManager.Query().Equals("route_table_id", self.Id)
- err := db.FetchModelObjects(RouteTableRouteSetManager, q, &routes)
- if err != nil {
- return nil, errors.Wrapf(err, "db.FetchModelObjects")
- }
- return routes, nil
- }
- func (self *SRouteTable) SyncRouteTableAssociations(
- ctx context.Context,
- userCred mcclient.TokenCredential,
- ext cloudprovider.ICloudRouteTable,
- provider *SCloudprovider,
- xor bool,
- ) compare.SyncResult {
- lockman.LockRawObject(ctx, self.Keyword(), fmt.Sprintf("%s-records", self.Id))
- defer lockman.ReleaseRawObject(ctx, self.Keyword(), fmt.Sprintf("%s-records", self.Id))
- syncResult := compare.SyncResult{}
- extAssociations := ext.GetAssociations()
- dbAssociation, err := self.GetRouteTableAssociations()
- if err != nil {
- syncResult.Error(errors.Wrapf(err, "GetRouteTableRouteSets"))
- return syncResult
- }
- removed := make([]SRouteTableAssociation, 0)
- commondb := make([]SRouteTableAssociation, 0)
- commonext := make([]cloudprovider.RouteTableAssociation, 0)
- added := make([]cloudprovider.RouteTableAssociation, 0)
- if err := compare.CompareSets(dbAssociation, extAssociations, &removed, &commondb, &commonext, &added); err != nil {
- syncResult.Error(err)
- return syncResult
- }
- for i := range dbAssociation {
- if len(dbAssociation[i].ExternalId) == 0 {
- removed = append(removed, dbAssociation[i])
- }
- }
- for i := 0; i < len(removed); i++ {
- err := removed[i].syncRemoveAssociation(ctx, userCred)
- if err != nil {
- syncResult.DeleteError(err)
- } else {
- syncResult.Delete()
- }
- }
- if !xor {
- for i := 0; i < len(commondb); i++ {
- err := commondb[i].syncWithCloudAssociation(ctx, userCred, provider, commonext[i])
- if err != nil {
- syncResult.UpdateError(err)
- continue
- }
- syncResult.Update()
- }
- }
- for i := 0; i < len(added); i++ {
- _, err := RouteTableAssociationManager.newAssociationFromCloud(ctx, userCred, self, provider, added[i])
- if err != nil {
- syncResult.AddError(err)
- continue
- }
- syncResult.Add()
- }
- return syncResult
- }
- func (self *SRouteTable) GetRouteTableAssociations() ([]SRouteTableAssociation, error) {
- association := []SRouteTableAssociation{}
- q := RouteTableAssociationManager.Query().Equals("route_table_id", self.Id)
- err := db.FetchModelObjects(RouteTableAssociationManager, q, &association)
- if err != nil {
- return nil, errors.Wrapf(err, "db.FetchModelObjects")
- }
- return association, nil
- }
- func (self *SRouteTable) getVpc() (*SVpc, error) {
- val, err := VpcManager.FetchById(self.VpcId)
- if err != nil {
- log.Errorf("VpcManager.FetchById fail %s", err)
- return nil, err
- }
- return val.(*SVpc), nil
- }
- func (self *SRouteTable) getRegion() (*SCloudregion, error) {
- vpc, err := self.getVpc()
- if err != nil {
- return nil, err
- }
- return vpc.GetRegion()
- }
- func (self *SRouteTable) getCloudProviderInfo() SCloudProviderInfo {
- region, _ := self.getRegion()
- provider := self.GetCloudprovider()
- return MakeCloudProviderInfo(region, nil, provider)
- }
- func (self *SRouteTable) PerformSyncstatus(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, input api.VpcSyncstatusInput) (jsonutils.JSONObject, error) {
- return nil, StartResourceSyncStatusTask(ctx, userCred, self, "RouteTableSyncStatusTask", "")
- }
- func (self *SRouteTable) GetICloudRouteTable(ctx context.Context) (cloudprovider.ICloudRouteTable, error) {
- vpc, err := self.getVpc()
- if err != nil {
- return nil, errors.Wrap(err, "self.getVpc()")
- }
- ivpc, err := vpc.GetIVpc(ctx)
- if err != nil {
- return nil, errors.Wrap(err, "self.GetIVpc()")
- }
- if len(self.ExternalId) == 0 {
- return nil, errors.Wrap(errors.ErrNotFound, "ExternalId not found")
- }
- iRouteTable, err := ivpc.GetIRouteTableById(self.ExternalId)
- if err != nil {
- return nil, errors.Wrapf(err, "ivpc.GetIRouteTableById(%s)", self.ExternalId)
- }
- return iRouteTable, nil
- }
|