diff --git a/pkg/compute/guestdrivers/managedvirtual.go b/pkg/compute/guestdrivers/managedvirtual.go index a02a0e3f1f..8648de0bdc 100644 --- a/pkg/compute/guestdrivers/managedvirtual.go +++ b/pkg/compute/guestdrivers/managedvirtual.go @@ -25,7 +25,6 @@ import ( "yunion.io/x/jsonutils" "yunion.io/x/log" - "yunion.io/x/pkg/util/compare" billing_api "yunion.io/x/onecloud/pkg/apis/billing" api "yunion.io/x/onecloud/pkg/apis/compute" @@ -776,50 +775,14 @@ func (self *SManagedVirtualizedGuestDriver) RequestSyncSecgroupsOnHost(ctx conte func (self *SManagedVirtualizedGuestDriver) RequestSyncConfigOnHost(ctx context.Context, guest *models.SGuest, host *models.SHost, task taskman.ITask) error { taskman.LocalTaskRun(task, func() (jsonutils.JSONObject, error) { - ihost, err := host.GetIHost() - if err != nil { - return nil, err - } - iVM, err := ihost.GetIVMById(guest.ExternalId) - if err != nil { - return nil, err - } if jsonutils.QueryBoolean(task.GetParams(), "fw_only", false) { - err = guest.GetDriver().RequestSyncSecgroupsOnHost(ctx, guest, host, task) + err := guest.GetDriver().RequestSyncSecgroupsOnHost(ctx, guest, host, task) if err != nil { return nil, err } } - iDisks, err := iVM.GetIDisks() - if err != nil { - return nil, err - } - disks := make([]models.SDisk, 0) - for _, guestdisk := range guest.GetDisks() { - disk := guestdisk.GetDisk() - disks = append(disks, *disk) - } - - added := make([]models.SDisk, 0) - commondb := make([]models.SDisk, 0) - commonext := make([]cloudprovider.ICloudDisk, 0) - removed := make([]cloudprovider.ICloudDisk, 0) - - if err := compare.CompareSets(disks, iDisks, &added, &commondb, &commonext, &removed); err != nil { - return nil, err - } - for _, disk := range removed { - if err := iVM.DetachDisk(ctx, disk.GetGlobalId()); err != nil { - return nil, err - } - } - for _, disk := range added { - if err := iVM.AttachDisk(ctx, disk.ExternalId); err != nil { - return nil, err - } - } return nil, nil }) return nil diff --git a/pkg/compute/models/guest_actions.go b/pkg/compute/models/guest_actions.go index ddf674f1bf..2eef974aea 100644 --- a/pkg/compute/models/guest_actions.go +++ b/pkg/compute/models/guest_actions.go @@ -1334,7 +1334,7 @@ func (self *SGuest) PerformCreatedisk(ctx context.Context, userCred mcclient.Tok lockman.LockObject(ctx, host) defer lockman.ReleaseObject(ctx, host) - err = self.CreateDisksOnHost(ctx, userCred, host, disksConf, pendingUsage, false, false, nil, nil) + err = self.CreateDisksOnHost(ctx, userCred, host, disksConf, pendingUsage, false, false, nil, nil, false) if err != nil { QuotaManager.CancelPendingUsage(ctx, userCred, rbacutils.ScopeProject, self.GetOwnerId(), nil, pendingUsage) logclient.AddActionLogWithContext(ctx, self, logclient.ACT_CREATE, err.Error(), userCred, false) @@ -2002,7 +2002,7 @@ func (self *SGuest) PerformChangeConfig(ctx context.Context, userCred mcclient.T } if len(newDisks) > 0 { - err := self.CreateDisksOnHost(ctx, userCred, host, newDisks, pendingUsage, false, false, nil, nil) + err := self.CreateDisksOnHost(ctx, userCred, host, newDisks, pendingUsage, false, false, nil, nil, false) if err != nil { QuotaManager.CancelPendingUsage(ctx, userCred, rbacutils.ScopeProject, self.GetOwnerId(), nil, pendingUsage) return nil, httperrors.NewBadRequestError("Create disk on host error: %s", err) @@ -3159,7 +3159,7 @@ func (self *SGuest) importDisks(ctx context.Context, userCred mcclient.TokenCred return httperrors.NewInputParameterError("Empty import disks") } for _, disk := range disks { - disk, err := self.createDiskOnHost(ctx, userCred, self.GetHost(), ToDiskConfig(&disk), nil, true, true, nil, nil) + disk, err := self.createDiskOnHost(ctx, userCred, self.GetHost(), ToDiskConfig(&disk), nil, true, true, nil, nil, true) if err != nil { return err } diff --git a/pkg/compute/models/guests.go b/pkg/compute/models/guests.go index 1655beaad8..b1f201cd54 100644 --- a/pkg/compute/models/guests.go +++ b/pkg/compute/models/guests.go @@ -2111,7 +2111,7 @@ func (self *SGuest) setOSProfile(ctx context.Context, userCred mcclient.TokenCre return self.SetMetadata(ctx, "__os_profile__", profile, userCred) } -func (self *SGuest) getOSProfile() osprofile.SOSProfile { +func (self *SGuest) GetOSProfile() osprofile.SOSProfile { osName := self.GetOS() osProf := osprofile.GetOSProfile(osName, self.Hypervisor) val := self.GetMetadata("__os_profile__", nil) @@ -2170,7 +2170,7 @@ func (self *SGuest) attach2NetworkOnce(ctx context.Context, userCred mcclient.To nicConf.Index = self.getMaxNicIndex() } if len(driver) == 0 { - osProf := self.getOSProfile() + osProf := self.GetOSProfile() driver = osProf.NetDriver } lockman.LockClass(ctx, QuotaManager, self.ProjectId) @@ -2339,6 +2339,10 @@ func (self *SGuest) SyncVMNics(ctx context.Context, userCred mcclient.TokenCrede return result } +func (self *SGuest) IsAttach2Disk(disk *SDisk) (bool, error) { + return self.isAttach2Disk(disk) +} + func (self *SGuest) isAttach2Disk(disk *SDisk) (bool, error) { q := GuestdiskManager.Query().Equals("disk_id", disk.Id).Equals("guest_id", self.Id) cnt, err := q.CountWithError() @@ -2386,7 +2390,7 @@ func (self *SGuest) attach2Disk(ctx context.Context, disk *SDisk, userCred mccli } if len(driver) == 0 { - osProf := self.getOSProfile() + osProf := self.GetOSProfile() driver = osProf.DiskDriver } guestdisk := SGuestdisk{} @@ -2604,7 +2608,7 @@ func totalGuestResourceCount( func (self *SGuest) getDefaultNetworkConfig() *api.NetworkConfig { netConf := api.NetworkConfig{} netConf.BwLimit = options.Options.DefaultBandwidth - osProf := self.getOSProfile() + osProf := self.GetOSProfile() netConf.Driver = osProf.NetDriver return &netConf } @@ -2714,6 +2718,7 @@ func (self *SGuest) CreateDisksOnHost( isWithServerCreate bool, candidateDisks []*schedapi.CandidateDisk, backupCandidateDisks []*schedapi.CandidateDisk, + autoAttach bool, ) error { for idx := 0; idx < len(disks); idx += 1 { diskConfig, err := parseDiskInfo(ctx, userCred, disks[idx]) @@ -2728,7 +2733,7 @@ func (self *SGuest) CreateDisksOnHost( if len(backupCandidateDisks) != 0 && len(backupCandidateDisks) > idx { backupCandidateDisk = backupCandidateDisks[idx] } - disk, err := self.createDiskOnHost(ctx, userCred, host, diskConfig, pendingUsage, inheritBilling, isWithServerCreate, candidateDisk, backupCandidateDisk) + disk, err := self.createDiskOnHost(ctx, userCred, host, diskConfig, pendingUsage, inheritBilling, isWithServerCreate, candidateDisk, backupCandidateDisk, autoAttach) if err != nil { return err } @@ -2790,6 +2795,7 @@ func (self *SGuest) createDiskOnHost( isWithServerCreate bool, candidate *schedapi.CandidateDisk, backupCandidate *schedapi.CandidateDisk, + autoAttach bool, ) (*SDisk, error) { var storage *SStorage if len(diskConfig.Storage) > 0 { @@ -2825,7 +2831,9 @@ func (self *SGuest) createDiskOnHost( } db.OpsLog.LogEvent(disk, db.ACT_UPDATE, diff, userCred) } - err = self.attach2Disk(ctx, disk, userCred, diskConfig.Driver, diskConfig.Cache, diskConfig.Mountpoint) + if autoAttach { + err = self.attach2Disk(ctx, disk, userCred, diskConfig.Driver, diskConfig.Cache, diskConfig.Mountpoint) + } return disk, err } diff --git a/pkg/compute/models/hosts.go b/pkg/compute/models/hosts.go index 33d0f9c66a..726bb9f822 100644 --- a/pkg/compute/models/hosts.go +++ b/pkg/compute/models/hosts.go @@ -3036,7 +3036,7 @@ func (self *SHost) PerformInitialize( caps := self.GetAttachedStorageCapacity() diskConfig := &api.DiskConfig{SizeMb: int(caps.GetFree())} - err = guest.CreateDisksOnHost(ctx, userCred, self, []*api.DiskConfig{diskConfig}, nil, true, true, nil, nil) + err = guest.CreateDisksOnHost(ctx, userCred, self, []*api.DiskConfig{diskConfig}, nil, true, true, nil, nil, true) if err != nil { log.Errorf("Host perform initialize failed on create disk %s", err) } diff --git a/pkg/compute/tasks/guest_batch_create_task.go b/pkg/compute/tasks/guest_batch_create_task.go index 702c294e4d..b0ea633d69 100644 --- a/pkg/compute/tasks/guest_batch_create_task.go +++ b/pkg/compute/tasks/guest_batch_create_task.go @@ -106,7 +106,8 @@ func (self *GuestBatchCreateTask) allocateGuestOnHost(ctx context.Context, guest if candidate.BackupCandidate != nil { backupCandidateDisks = candidate.BackupCandidate.Disks } - err = guest.CreateDisksOnHost(ctx, self.UserCred, host, input.Disks, &pendingUsage, true, true, candidate.Disks, backupCandidateDisks) + // 纳管的云需要有关联关系后,在做deploy时才有磁盘的信息 + err = guest.CreateDisksOnHost(ctx, self.UserCred, host, input.Disks, &pendingUsage, true, true, candidate.Disks, backupCandidateDisks, true) self.SetPendingUsage(&pendingUsage) if err != nil { diff --git a/pkg/compute/tasks/guest_create_disk_task.go b/pkg/compute/tasks/guest_create_disk_task.go index 958107919b..14ad54bdc5 100644 --- a/pkg/compute/tasks/guest_create_disk_task.go +++ b/pkg/compute/tasks/guest_create_disk_task.go @@ -19,6 +19,7 @@ import ( "fmt" "time" + "github.com/pkg/errors" "yunion.io/x/jsonutils" "yunion.io/x/log" @@ -115,6 +116,11 @@ func (self *KVMGuestCreateDiskTask) OnKvmDiskPrepared(ctx context.Context, obj d diskReady = false break } + err = self.attachDisk(ctx, disk, d.Driver, d.Cache, d.Mountpoint) + if err != nil { + self.SetStageFailed(ctx, err.Error()) + return + } } if diskReady { guest := obj.(*models.SGuest) @@ -144,6 +150,22 @@ func (self *SGuestCreateDiskBaseTask) GetInputDisks() ([]api.DiskConfig, error) return disks, err } +func (self *SGuestCreateDiskBaseTask) attachDisk(ctx context.Context, disk *models.SDisk, driver, cache, mountpoint string) error { + guest := self.getGuest() + attached, err := guest.IsAttach2Disk(disk) + if err != nil { + return errors.Wrapf(err, "IsAttach2Disk") + } + if attached { + return nil + } + err = guest.AttachDisk(ctx, disk, self.UserCred, driver, cache, mountpoint) + if err != nil { + return errors.Wrapf(err, "AttachDisk") + } + return nil +} + type ManagedGuestCreateDiskTask struct { SGuestCreateDiskBaseTask } @@ -203,7 +225,13 @@ func (self *ManagedGuestCreateDiskTask) OnManagedDiskPrepared(ctx context.Contex err = iVM.AttachDisk(ctx, disk.GetExternalId()) if err != nil { log.Debugf("Attach Disk %s to guest fail: %s", diskId, err) - self.SetStageFailed(ctx, "Attach Disk to guest fail") + self.SetStageFailed(ctx, fmt.Sprintf("Attach iDisk to guest fail error: %v", err)) + return + } + err = self.attachDisk(ctx, disk, d.Driver, d.Cache, d.Mountpoint) + if err != nil { + log.Debugf("Attach Disk %s to guest fail: %s", diskId, err) + self.SetStageFailed(ctx, fmt.Sprintf("Attach Disk to guest fail error: %v", err)) return } time.Sleep(time.Second * 5) @@ -237,28 +265,28 @@ func (self *ESXiGuestCreateDiskTask) OnInit(ctx context.Context, obj db.IStandal } for _, d := range disks { diskId := d.DiskId - guestDisk := guest.GetGuestDisk(diskId) - if guestDisk == nil { - self.SetStageFailed(ctx, "fail to find guestdisk") - return - } - disk := guestDisk.GetDisk() - if disk == nil { - self.SetStageFailed(ctx, fmt.Sprintf("Disk %s not found", diskId)) + iDisk, err := models.DiskManager.FetchById(diskId) + if err != nil { + self.SetStageFailed(ctx, err.Error()) return } + disk := iDisk.(*models.SDisk) if disk.Status != api.DISK_INIT { self.SetStageFailed(ctx, fmt.Sprintf("Disk %s already created??", diskId)) return } ivm, err := guest.GetIVM() if err != nil { - self.SetStageFailed(ctx, fmt.Sprintf("fail to find iVM for %s", guest.GetName())) + self.SetStageFailed(ctx, fmt.Sprintf("fail to find iVM for %s, error: %v", guest.GetName(), err)) return } - err = ivm.CreateDisk(ctx, disk.DiskSize, disk.Id, guestDisk.Driver) + if len(d.Driver) == 0 { + osProf := guest.GetOSProfile() + d.Driver = osProf.DiskDriver + } + err = ivm.CreateDisk(ctx, disk.DiskSize, disk.Id, d.Driver) if err != nil { - self.SetStageFailed(ctx, fmt.Sprintf("ivm.CreateDisk fail %s", guest.GetName())) + self.SetStageFailed(ctx, fmt.Sprintf("ivm.CreateDisk fail %s, error: %v", guest.GetName(), err)) return } idisks, err := ivm.GetIDisks() @@ -267,6 +295,12 @@ func (self *ESXiGuestCreateDiskTask) OnInit(ctx context.Context, obj db.IStandal return } + err = self.attachDisk(ctx, disk, d.Driver, d.Cache, d.Mountpoint) + if err != nil { + self.SetStageFailed(ctx, fmt.Sprintf("self.attachDisk fail %v", err)) + return + } + log.Debugf("diskcount after create: %d", len(idisks)) vdisk := idisks[len(idisks)-1]