fix: cleanup tap flows and services for deleted guest and host (#14503)

Co-authored-by: Qiu Jian <qiujian@yunionyun.com>
This commit is contained in:
Jian Qiu
2022-06-22 23:10:07 +08:00
committed by GitHub
co-authored by Qiu Jian
parent cb58c16f59
commit 9e099cf451
6 changed files with 99 additions and 25 deletions
+12 -9
View File
@@ -4071,19 +4071,22 @@ func (self *SGuest) Delete(ctx context.Context, userCred mcclient.TokenCredentia
return nil
}
func (self *SGuest) RealDelete(ctx context.Context, userCred mcclient.TokenCredential) error {
func (self *SGuest) CleanTapRecords(ctx context.Context, userCred mcclient.TokenCredential) error {
// delete tap devices
if srvs, err := NetTapServiceManager.getTapServicesByGuestId(self.Id, false); err != nil {
if err := NetTapServiceManager.removeTapServicesByGuestId(ctx, userCred, self.Id); err != nil {
return errors.Wrap(err, "NetTapServiceManager.getTapServicesByGuestId")
} else {
for _, srv := range srvs {
err := srv.cleanup(ctx, userCred)
if err != nil {
return errors.Wrap(err, "srv.Delete")
}
}
}
if err := NetTapFlowManager.removeTapFlowsByGuestId(ctx, userCred, self.Id); err != nil {
return errors.Wrap(err, "NetTapFlowManager.getTapServicesByGuestId")
}
return nil
}
func (self *SGuest) RealDelete(ctx context.Context, userCred mcclient.TokenCredential) error {
err := self.CleanTapRecords(ctx, userCred)
if err != nil {
return errors.Wrap(err, "CleanTapRecords")
}
return self.SVirtualResourceBase.Delete(ctx, userCred)
}
+5 -1
View File
@@ -34,7 +34,11 @@ func (h *SHost) GetDetailsTapConfig(ctx context.Context, userCred mcclient.Token
for _, flow := range flows {
mirror, err := flow.getMirrorConfig(true)
if err != nil {
return conf, errors.Wrap(err, "flow.getMirrorConfig")
if errors.Cause(err) == errors.ErrNotFound {
continue
} else {
return conf, errors.Wrap(err, "flow.getMirrorConfig")
}
}
mirrors = append(mirrors, mirror)
}
+4 -8
View File
@@ -782,15 +782,11 @@ func (self *SHost) RealDelete(ctx context.Context, userCred mcclient.TokenCreden
DeleteResourceJointSchedtags(self, ctx, userCred)
// delete tap devices
if srvs, err := NetTapServiceManager.getTapServicesByHostId(self.Id, false); err != nil {
if err := NetTapServiceManager.removeTapServicesByHostId(ctx, userCred, self.Id); err != nil {
return errors.Wrap(err, "NetTapServiceManager.getTapServicesByHostId")
} else {
for _, srv := range srvs {
err := srv.cleanup(ctx, userCred)
if err != nil {
return errors.Wrap(err, "srv.Delete")
}
}
}
if err := NetTapFlowManager.removeTapFlowsByHostId(ctx, userCred, self.Id); err != nil {
return errors.Wrap(err, "NetTapFlowManager.getTapFlowsByHostId")
}
IsolatedDeviceManager.DeleteDevicesByHost(ctx, userCred, self)
+53 -7
View File
@@ -210,17 +210,25 @@ func (flow *SNetTapFlow) getMoreDetails(ctx context.Context, details api.NetTapF
switch flow.Type {
case api.TapFlowVSwitch:
host := HostManager.FetchHostById(flow.SourceId)
details.Source = host.Name
details.SourceIps = host.AccessIp
if host != nil {
details.Source = host.Name
details.SourceIps = host.AccessIp
}
wire := WireManager.FetchWireById(flow.NetId)
details.Net = wire.Name
if wire != nil {
details.Net = wire.Name
}
case api.TapFlowGuestNic:
guest := GuestManager.FetchGuestById(flow.SourceId)
details.Source = guest.Name
ret := fetchGuestIPs([]string{flow.SourceId}, tristate.False)
details.SourceIps = strings.Join(ret[flow.SourceId], ",")
if guest != nil {
details.Source = guest.Name
ret := fetchGuestIPs([]string{flow.SourceId}, tristate.False)
details.SourceIps = strings.Join(ret[flow.SourceId], ",")
}
netObj, _ := NetworkManager.FetchById(flow.NetId)
details.Net = netObj.GetName()
if netObj != nil {
details.Net = netObj.GetName()
}
}
return details
}
@@ -432,6 +440,10 @@ func (flow *SNetTapFlow) getMirrorConfig(needTapHostIp bool) (api.SMirrorConfig,
wireId = flow.NetId
case api.TapFlowGuestNic:
guest := GuestManager.FetchGuestById(flow.SourceId)
if guest == nil {
// guest has been deleted?
return ret, errors.Wrap(errors.ErrNotFound, "source not found")
}
gn, err := guest.GetGuestnetworkByMac(flow.MacAddr)
if err != nil {
return ret, errors.Wrap(err, "GetGuestnetworkByMac")
@@ -463,3 +475,37 @@ func (flow *SNetTapFlow) getMirrorConfig(needTapHostIp bool) (api.SMirrorConfig,
ret.Direction = flow.Direction
return ret, nil
}
func (manager *SNetTapFlowManager) removeTapFlowsByGuestId(ctx context.Context, userCred mcclient.TokenCredential, sourceId string) error {
return manager.removeTapFlows(ctx, userCred, api.TapFlowGuestNic, sourceId)
}
func (manager *SNetTapFlowManager) removeTapFlowsByHostId(ctx context.Context, userCred mcclient.TokenCredential, sourceId string) error {
return manager.removeTapFlows(ctx, userCred, api.TapFlowVSwitch, sourceId)
}
func (manager *SNetTapFlowManager) removeTapFlows(ctx context.Context, userCred mcclient.TokenCredential, srvType string, targetId string) error {
srvs, err := manager.getTapFlows(srvType, targetId)
if err != nil {
return errors.Wrap(err, "getTapServicesByHostId")
}
for i := range srvs {
err := srvs[i].Delete(ctx, userCred)
if err != nil {
return errors.Wrap(err, "Delete")
}
}
return nil
}
func (manager *SNetTapFlowManager) getTapFlows(srvType string, sourceId string) ([]SNetTapFlow, error) {
q := manager.Query()
q = q.Equals("type", srvType)
q = q.Equals("source_id", sourceId)
ret := make([]SNetTapFlow, 0)
err := db.FetchModelObjects(manager, q, &ret)
if err != nil {
return nil, errors.Wrap(err, "FetchModelObjects")
}
return ret, nil
}
+22
View File
@@ -548,3 +548,25 @@ func (srv *SNetTapService) cleanup(ctx context.Context, userCred mcclient.TokenC
}
return nil
}
func (manager *SNetTapServiceManager) removeTapServicesByGuestId(ctx context.Context, userCred mcclient.TokenCredential, targetId string) error {
return manager.removeTapServices(ctx, userCred, api.TapServiceGuest, targetId)
}
func (manager *SNetTapServiceManager) removeTapServicesByHostId(ctx context.Context, userCred mcclient.TokenCredential, targetId string) error {
return manager.removeTapServices(ctx, userCred, api.TapServiceHost, targetId)
}
func (manager *SNetTapServiceManager) removeTapServices(ctx context.Context, userCred mcclient.TokenCredential, srvType string, targetId string) error {
srvs, err := manager.getTapServices(srvType, targetId, false)
if err != nil {
return errors.Wrap(err, "getTapServicesByHostId")
}
for i := range srvs {
err := srvs[i].cleanup(ctx, userCred)
if err != nil {
return errors.Wrap(err, "cleanup")
}
}
return nil
}
+3
View File
@@ -203,6 +203,9 @@ func (self *GuestDeleteTask) OnSyncConfigComplete(ctx context.Context, obj db.IS
// try to leave all groups
guest.LeaveAllGroups(ctx, self.UserCred)
// cleanup tap services and flows
guest.CleanTapRecords(ctx, self.UserCred)
isPurge := jsonutils.QueryBoolean(self.Params, "purge", false)
overridePendingDelete := jsonutils.QueryBoolean(self.Params, "override_pending_delete", false)