Eldan Shachar has uploaded a new change for review. Change subject: userportal\webadmin: Editing of template version for stateless VMs and pools ......................................................................
userportal\webadmin: Editing of template version for stateless VMs and pools This patch will allow a user to change a template version for an existing stateless VM / Pool. The main issues handled are: - VM \ Pool object - added support for changing of the template field. - Frontend - Added support for editing of this field and introduced some limitations to avoid non-supported behaviors. - UpdateVmVersion Command - added support for any template versions. - Pools - Until now pools haven't supported changes affecting the actual VMs and some logic that depended on this assumption needed change. - Running VMs - Changes were required in the next-run logic on multiple locations. Change-Id: I53686dae694f6ff826bdbeaada1e28fc55fd8d30 Bug-Url: https://bugzilla.redhat.com/1140569 Signed-off-by: Eldan Shachar <[email protected]> --- M frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/dialog/tab/DialogTab.java M frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/AbstractVmPopupWidget.java M frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/pool/PoolEditPopupWidget.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/dataprovider/AsyncDataProvider.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/pools/PoolListModel.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingPoolModelBehavior.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingVmModelBehavior.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/NewVmModelBehavior.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/UnitVmModel.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmListModel.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmModelBehaviorBase.java M frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/instancetypes/InstanceTypeManager.java M frontend/webadmin/modules/uicommonweb/src/test/java/org/ovirt/engine/ui/uicommonweb/models/vms/BaseVmListModelTest.java M frontend/webadmin/modules/uicompat/src/main/java/org/ovirt/engine/ui/uicompat/UIConstants.java 14 files changed, 418 insertions(+), 141 deletions(-) git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/10/36510/1 diff --git a/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/dialog/tab/DialogTab.java b/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/dialog/tab/DialogTab.java index b1e472a..fe938f3 100644 --- a/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/dialog/tab/DialogTab.java +++ b/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/dialog/tab/DialogTab.java @@ -24,6 +24,7 @@ import org.ovirt.engine.ui.common.widget.HasValidation; import java.util.ArrayList; +import java.util.HashMap; import java.util.List; public class DialogTab extends AbstractValidatedWidget implements HasClickHandlers, HasLabel, HasElementId, HasKeyUpHandlers, FocusableComponentsContainer { @@ -125,6 +126,24 @@ disable(getContent()); } + public void setContentState(HashMap<Widget, Boolean> originalState) { + setState(getContent(), originalState); + } + + public void getContentState(HashMap<Widget, Boolean> originalState) { + getState(getContent(), originalState); + } + + private void getState(Widget content, HashMap<Widget, Boolean> originalState) { + if (content instanceof IndexedPanel) { + for (int i = 0; i < ((IndexedPanel) content).getWidgetCount(); i++) { + getState(((IndexedPanel) content).getWidget(i), originalState); + } + } else if (content instanceof HasEnabled) { + originalState.put(content, ((HasEnabled) content).isEnabled()); + } + } + private void disable(Widget content) { if (content instanceof IndexedPanel) { for (int i = 0; i < ((IndexedPanel) content).getWidgetCount(); i++) { @@ -135,6 +154,18 @@ } } + private void setState(Widget content, HashMap<Widget, Boolean> originalState) { + if (content instanceof IndexedPanel) { + for (int i = 0; i < ((IndexedPanel) content).getWidgetCount(); i++) { + setState(((IndexedPanel) content).getWidget(i), originalState); + } + } else if (content instanceof HasEnabled) { + if (originalState != null && originalState.containsKey(content)) { + ((HasEnabled) content).setEnabled(originalState.get(content)); + } + } + } + public List<HasValidation> getInvalidWidgets() { return getInvalidWidgets(getContent()); } diff --git a/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/AbstractVmPopupWidget.java b/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/AbstractVmPopupWidget.java index 5e2c248..9571a6d 100644 --- a/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/AbstractVmPopupWidget.java +++ b/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/AbstractVmPopupWidget.java @@ -868,6 +868,8 @@ private final Map<TabName, DialogTab> tabMap = new HashMap<TabName, DialogTab>(); + private HashMap<Widget, Boolean> tabsState = null; + @SuppressWarnings({ "unchecked", "rawtypes" }) public AbstractVmPopupWidget(CommonApplicationConstants constants, CommonApplicationResources resources, @@ -1640,6 +1642,22 @@ } }); + object.getTemplateChanged().getEntityChangedEvent().addListener(new IEventListener<EventArgs>() { + @Override + public void eventRaised(Event<? extends EventArgs> ev, Object sender, EventArgs args) { + Boolean enabled = object.getTemplateChanged().getEntity(); + if (Boolean.TRUE.equals(enabled)) { + tabsState = getAllTabsState(); + disableAllTabs(); + templateEditor.setEnabled(tabsState.get(templateEditor)); // if template editing was allowed -> keep it enabled + generalWarningMessage.setText(object.getTemplateChanged().getMessage()); + } else { + setAllTabsState(tabsState); + generalWarningMessage.setText(null); + } + } + }); + object.getCpuSharesAmountSelection().getPropertyChangedEvent().addListener(new IEventListener<PropertyChangedEventArgs>() { @Override public void eventRaised(Event<? extends PropertyChangedEventArgs> ev, Object sender, PropertyChangedEventArgs args) { @@ -2116,6 +2134,22 @@ ); } + private HashMap<Widget, Boolean> getAllTabsState() { + HashMap<Widget, Boolean> originalState = new HashMap<Widget, Boolean>(); + for (DialogTab dialogTab : allDialogTabs()) { + dialogTab.getContentState(originalState); + } + originalState.put(oSTypeEditor, oSTypeEditor.isEnabled()); + originalState.put(quotaEditor, quotaEditor.isEnabled()); + originalState.put(dataCenterWithClusterEditor, dataCenterWithClusterEditor.isEnabled()); + originalState.put(templateEditor, templateEditor.isEnabled()); + originalState.put(baseTemplateEditor, baseTemplateEditor.isEnabled()); + originalState.put(vmTypeEditor, vmTypeEditor.isEnabled()); + originalState.put(instanceTypesEditor, instanceTypesEditor.isEnabled()); + + return originalState; + } + protected void disableAllTabs() { for (DialogTab dialogTab : allDialogTabs()) { dialogTab.disableContent(); @@ -2132,6 +2166,24 @@ customCpu.setEnabled(false); } + protected void setAllTabsState(HashMap<Widget, Boolean> originalState) { + if (originalState != null) { + for (DialogTab dialogTab : allDialogTabs()) { + dialogTab.setContentState(originalState); + } + + oSTypeEditor.setEnabled(originalState.get(oSTypeEditor)); + quotaEditor.setEnabled(originalState.get(quotaEditor)); + dataCenterWithClusterEditor.setEnabled(originalState.get(dataCenterWithClusterEditor)); + templateEditor.setEnabled(originalState.get(templateEditor)); + baseTemplateEditor.setEnabled(originalState.get(baseTemplateEditor)); + vmTypeEditor.setEnabled(originalState.get(vmTypeEditor)); + instanceTypesEditor.setEnabled(originalState.get(instanceTypesEditor)); + emulatedMachine.setEnabled(originalState.get(emulatedMachine)); + customCpu.setEnabled(originalState.get(customCpu)); + } + } + private List<DialogTab> allDialogTabs() { return Arrays.asList( generalTab, diff --git a/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/pool/PoolEditPopupWidget.java b/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/pool/PoolEditPopupWidget.java index 1541139..de0f61b 100644 --- a/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/pool/PoolEditPopupWidget.java +++ b/frontend/webadmin/modules/gwt-common/src/main/java/org/ovirt/engine/ui/common/widget/uicommon/popup/pool/PoolEditPopupWidget.java @@ -85,6 +85,8 @@ editMaxAssignedVmsPerUserEditor.setEnabled(true); spiceProxyEditor.setEnabled(model.getSpiceProxyEnabled().getEntity()); + + templateEditor.setEnabled(true); } @Override diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/dataprovider/AsyncDataProvider.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/dataprovider/AsyncDataProvider.java index af2f059..f063843 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/dataprovider/AsyncDataProvider.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/dataprovider/AsyncDataProvider.java @@ -3895,11 +3895,9 @@ public void getSupportedCpuList(AsyncQuery aQuery, String cpuName) { aQuery.converterCallback = new IAsyncConverter() { @Override - public Object Convert(Object source, AsyncQuery _asyncQuery) - { - if (source != null) - { - ArrayList<ServerCpu> cpuList = Linq.<ServerCpu> cast((ArrayList<ServerCpu>) source); + public Object Convert(Object source, AsyncQuery _asyncQuery) { + if (source != null) { + ArrayList<ServerCpu> cpuList = Linq.<ServerCpu>cast((ArrayList<ServerCpu>) source); return cpuList; } @@ -3907,6 +3905,23 @@ } }; - Frontend.getInstance().runQuery(VdcQueryType.GetSupportedCpuList, new GetSupportedCpuListParameters(cpuName), aQuery); + Frontend.getInstance() + .runQuery(VdcQueryType.GetSupportedCpuList, new GetSupportedCpuListParameters(cpuName), aQuery); + } + + public void getVmTemplatesByBaseTemplateId(AsyncQuery asyncQuery, Guid baseTemplate) { + asyncQuery.converterCallback = new IAsyncConverter() { + + @Override + public Object Convert(Object source, AsyncQuery asyncQuery) { + if (source == null) { + return new ArrayList<VmTemplate>(); + } + return source; + } + }; + Frontend.getInstance().runQuery(VdcQueryType.GetVmTemplatesByBaseTemplateId, + new GetVmTemplateParameters(baseTemplate), + asyncQuery); } } diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/pools/PoolListModel.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/pools/PoolListModel.java index 43afffb..137e7af 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/pools/PoolListModel.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/pools/PoolListModel.java @@ -448,6 +448,8 @@ pool.setComment(model.getComment().getEntity()); pool.setPrestartedVms(model.getPrestartedVms().getEntity()); pool.setMaxAssignedVmsPerUser(model.getMaxAssignedVmsPerUser().getEntity()); + pool.setVmtGuid(model.getTemplate().getSelectedItem().getId()); + pool.setUseLatestVersion(model.getTemplate().getSelectedItem() instanceof LatestVmTemplate); EntityModel<VmPoolType> poolTypeSelectedItem = model.getPoolType().getSelectedItem(); pool.setVmPoolType(poolTypeSelectedItem.getEntity()); diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingPoolModelBehavior.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingPoolModelBehavior.java index e28f223..806660d 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingPoolModelBehavior.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingPoolModelBehavior.java @@ -8,12 +8,15 @@ import org.ovirt.engine.core.common.businessentities.StoragePool; import org.ovirt.engine.core.common.businessentities.VDSGroup; import org.ovirt.engine.core.common.businessentities.VM; +import org.ovirt.engine.core.common.businessentities.VmBase; import org.ovirt.engine.core.common.businessentities.VmTemplate; import org.ovirt.engine.core.compat.Guid; import org.ovirt.engine.core.compat.StringHelper; import org.ovirt.engine.ui.frontend.AsyncQuery; import org.ovirt.engine.ui.frontend.INewAsyncCallback; import org.ovirt.engine.ui.uicommonweb.Linq; +import org.ovirt.engine.ui.uicommonweb.builders.BuilderExecutor; +import org.ovirt.engine.ui.uicommonweb.builders.vm.HwOnlyVmBaseToUnitBuilder; import org.ovirt.engine.ui.uicommonweb.dataprovider.AsyncDataProvider; import org.ovirt.engine.ui.uicommonweb.models.SystemTreeItemModel; import org.ovirt.engine.ui.uicommonweb.models.storage.DisksAllocationModel; @@ -27,6 +30,8 @@ private final VM pool; private InstanceTypeManager instanceTypeManager; + + boolean templateVersionWasChanged; public ExistingPoolModelBehavior(VM pool) { this.pool = pool; @@ -76,15 +81,47 @@ } public void initTemplate() { - setupTemplate(pool.getVmtGuid(), pool.isUseLatestVersion()); + setupTemplate(pool.getVmtGuid(), pool.isUseLatestVersion(), true); } @Override public void template_SelectedItemChanged() { getModel().setIsDisksAvailable(true); VmTemplate template = getModel().getTemplate().getSelectedItem(); + if (template == null) { + return; + } updateRngDevice(template.getId()); getModel().getCustomPropertySheet().deserialize(template.getCustomProperties()); + + if (!pool.getVmtGuid().equals(template.getId())) { + if (!templateVersionWasChanged) { + deactivateInstanceTypeManager(new InstanceTypeManager.ActivatedListener() { + @Override + public void activated() { + getInstanceTypeManager().updateAll(); + } + }); + } + templateVersionWasChanged = true; + doChangeDefautlHost(template.getDedicatedVmForVds()); + setupWindowModelFrom(template); + + } else { + if (templateVersionWasChanged) { + activateInstanceTypeManager(); + } + templateVersionWasChanged = false; + } + } + + @Override + protected void buildModel(VmBase vm) { + super.buildModel(vm); + if (templateVersionWasChanged) { // instanceManager is disabled and the regular buildModel copies unwanted fields + BuilderExecutor.build(vm, getModel(), + new HwOnlyVmBaseToUnitBuilder()); + } } @Override @@ -92,6 +129,12 @@ } @Override + public void updateIsDisksAvailable() + { + getModel().setIsDisksAvailable(getModel().getDisks() != null); + } + + @Override protected void postInitStorageDomains() { ArrayList<DiskModel> disks = (ArrayList<DiskModel>) getModel().getDisks(); if (disks == null) { diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingVmModelBehavior.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingVmModelBehavior.java index 7f36f6d..61108af 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingVmModelBehavior.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/ExistingVmModelBehavior.java @@ -14,6 +14,7 @@ import org.ovirt.engine.core.common.businessentities.VmDevice; import org.ovirt.engine.core.common.businessentities.VmBase; import org.ovirt.engine.core.common.businessentities.VmNumaNode; +import org.ovirt.engine.core.common.businessentities.VmTemplate; import org.ovirt.engine.core.common.queries.ConfigurationValues; import org.ovirt.engine.core.common.queries.IdQueryParameters; import org.ovirt.engine.core.common.queries.VdcQueryReturnValue; @@ -27,11 +28,15 @@ import org.ovirt.engine.ui.uicommonweb.builders.BuilderExecutor; import org.ovirt.engine.ui.uicommonweb.builders.vm.CommentVmBaseToUnitBuilder; import org.ovirt.engine.ui.uicommonweb.builders.vm.CommonVmBaseToUnitBuilder; +import org.ovirt.engine.ui.uicommonweb.builders.vm.CoreVmBaseToUnitBuilder; +import org.ovirt.engine.ui.uicommonweb.builders.vm.HwOnlyVmBaseToUnitBuilder; import org.ovirt.engine.ui.uicommonweb.builders.vm.NameAndDescriptionVmBaseToUnitBuilder; import org.ovirt.engine.ui.uicommonweb.dataprovider.AsyncDataProvider; import org.ovirt.engine.ui.uicommonweb.models.SystemTreeItemModel; +import org.ovirt.engine.ui.uicommonweb.models.templates.LatestVmTemplate; import org.ovirt.engine.ui.uicommonweb.models.vms.instancetypes.ExistingVmInstanceTypeManager; import org.ovirt.engine.ui.uicommonweb.models.vms.instancetypes.InstanceTypeManager; +import org.ovirt.engine.ui.uicompat.ConstantsManager; public class ExistingVmModelBehavior extends VmModelBehaviorBase { @@ -41,10 +46,18 @@ private int hostCpu; private VDS runningOnHost; + private VM oldVm; + boolean templateVersionWasChanged; public ExistingVmModelBehavior(VM vm) { this.vm = vm; + } + + public ExistingVmModelBehavior(VM vm, VM oldVm) + { + this.vm = vm; + this.oldVm = oldVm; } public VM getVm() { @@ -59,8 +72,6 @@ public void initialize(SystemTreeItemModel systemTreeSelectedItem) { super.initialize(systemTreeSelectedItem); - getModel().getVmInitEnabled().setEntity(getVm().getVmInit() != null); - getModel().getVmInitModel().init(getVm().getStaticData()); getModel().getVmType().setIsChangable(true); getModel().getIsSoundcardEnabled().setIsChangable(true); getModel().getInstanceTypes().setIsChangable(!vm.isRunning()); @@ -91,37 +102,38 @@ private void loadDataCenter() { AsyncDataProvider.getInstance().getDataCenterById(new AsyncQuery(getModel(), - new INewAsyncCallback() { - @Override - public void onSuccess(Object target, Object returnValue) { + new INewAsyncCallback() { + @Override + public void onSuccess(Object target, Object returnValue) { - UnitVmModel model = (UnitVmModel) target; - if (returnValue != null) { - StoragePool dataCenter = (StoragePool) returnValue; - final List<StoragePool> dataCenters = - new ArrayList<StoragePool>(Arrays.asList(new StoragePool[]{dataCenter})); + UnitVmModel model = (UnitVmModel) target; + if (returnValue != null) { + StoragePool dataCenter = (StoragePool) returnValue; + final List<StoragePool> dataCenters = + new ArrayList<StoragePool>(Arrays.asList(new StoragePool[] { dataCenter })); - initClusters(dataCenters); - } else { - ExistingVmModelBehavior behavior = (ExistingVmModelBehavior) model.getBehavior(); - VM currentVm = behavior.vm; - VDSGroup tempVar = new VDSGroup(); - tempVar.setId(currentVm.getVdsGroupId()); - tempVar.setName(currentVm.getVdsGroupName()); - tempVar.setcompatibility_version(currentVm.getVdsGroupCompatibilityVersion()); - tempVar.setStoragePoolId(currentVm.getStoragePoolId()); - VDSGroup cluster = tempVar; - DataCenterWithCluster dataCenterWithCluster = - new DataCenterWithCluster(null, cluster); - model.getDataCenterWithClustersList().setItems(Arrays.asList(dataCenterWithCluster)); - model.getDataCenterWithClustersList().setSelectedItem(dataCenterWithCluster); - behavior.initTemplate(); - behavior.initCdImage(); - } + initClusters(dataCenters); + } else { + ExistingVmModelBehavior behavior = (ExistingVmModelBehavior) model.getBehavior(); + VM currentVm = behavior.vm; + VDSGroup tempVar = new VDSGroup(); + tempVar.setId(currentVm.getVdsGroupId()); + tempVar.setName(currentVm.getVdsGroupName()); + tempVar.setcompatibility_version(currentVm.getVdsGroupCompatibilityVersion()); + tempVar.setStoragePoolId(currentVm.getStoragePoolId()); + VDSGroup cluster = tempVar; + DataCenterWithCluster dataCenterWithCluster = + new DataCenterWithCluster(null, cluster); + model.getDataCenterWithClustersList() + .setItems(Arrays.asList(dataCenterWithCluster)); + model.getDataCenterWithClustersList().setSelectedItem(dataCenterWithCluster); + behavior.initTemplate(); + behavior.initCdImage(); + } - } - }, - getModel().getHash()), + } + }, + getModel().getHash()), vm.getStoragePoolId()); } @@ -155,10 +167,51 @@ @Override public void template_SelectedItemChanged() { - // This method will be called even if a VM created from Blank template. + BuilderExecutor.build(vm.getStaticData(), getModel(), + new NameAndDescriptionVmBaseToUnitBuilder()); // while vm is running, if a template version was changed in a previous edit, then this will load base fields from the original vm + VmTemplate template = getModel().getTemplate().getSelectedItem(); + // disable editing if template version was changed + if (!oldVm.getVmtGuid().equals(template.getId()) || ((template instanceof LatestVmTemplate) != oldVm.isUseLatestVersion())) { + String msg; + if (vm.getStatus() == VMStatus.Down) { + msg = ConstantsManager.getInstance().getConstants().templateChangeMessage(); + } else { + msg = ConstantsManager.getInstance().getConstants().templateChangeRunningMessage(); + } + getModel().getTemplateChanged().setMessage(msg); + getModel().getTemplateChanged().setEntity(true); + + if (!templateVersionWasChanged) { + templateVersionWasChanged = true; + deactivateInstanceTypeManager(new InstanceTypeManager.ActivatedListener() { + @Override + public void activated() { + getInstanceTypeManager().updateAll(); + } + }); + } + updateModelFromTemplate(template); + + } else { // template wasn't changed (called during init) + if (templateVersionWasChanged) { + templateVersionWasChanged = false; + activateInstanceTypeManager(); + } + + getModel().getTemplateChanged().setEntity(false); + + loadModelFromVM(); + } + } + + private void loadModelFromVM() { // Update model state according to VM properties. buildModel(vm.getStaticData()); + + getModel().getVmInitEnabled().setEntity(getVm().getVmInit() != null); + getModel().getVmInitModel().init(getVm().getStaticData()); + updateDefaultHost(); getModel().getIsStateless().setIsAvailable(vm.getVmPoolId() == null); @@ -199,15 +252,21 @@ }), vm.getRunOnVds()); } - updateCpuProfile(vm.getVdsGroupId(), vm.getVdsGroupCompatibilityVersion(), vm.getCpuProfileId()); + updateCpuProfile(vm.getVdsGroupId(), vm.getVdsGroupCompatibilityVersion(), vm.getCpuProfileId()); } @Override protected void buildModel(VmBase vm) { - BuilderExecutor.build(vm, getModel(), - new NameAndDescriptionVmBaseToUnitBuilder(), - new CommentVmBaseToUnitBuilder(), - new CommonVmBaseToUnitBuilder()); + if (templateVersionWasChanged) { // instanceManager is disabled and the regular buildModel copies unwanted fields + BuilderExecutor.build(vm, getModel(), + new CoreVmBaseToUnitBuilder(), + new HwOnlyVmBaseToUnitBuilder()); + } else { + BuilderExecutor.build(vm, getModel(), + new NameAndDescriptionVmBaseToUnitBuilder(), + new CommentVmBaseToUnitBuilder(), + new CommonVmBaseToUnitBuilder()); + } } private void updateGraphics() { @@ -320,7 +379,9 @@ protected void initTemplate() { - setupTemplate(vm.getVmtGuid(), vm.isUseLatestVersion()); + setupTemplate(vm.getVmtGuid(), + vm.isUseLatestVersion(), + (vm.isStateless() || (vm.getVmPoolId() != null)) && (!Guid.Empty.equals(vm.getVmtGuid()))); } public void initCdImage() @@ -431,4 +492,5 @@ getModel().getNumaNodeCount().setEntity(getModel().getVmNumaNodes().size()); } } + } diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/NewVmModelBehavior.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/NewVmModelBehavior.java index 4a29c3b..10126d0 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/NewVmModelBehavior.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/NewVmModelBehavior.java @@ -2,7 +2,6 @@ import java.util.ArrayList; import java.util.List; -import org.ovirt.engine.core.common.businessentities.InstanceType; import org.ovirt.engine.core.common.businessentities.StorageDomain; import org.ovirt.engine.core.common.businessentities.StoragePool; import org.ovirt.engine.core.common.businessentities.StoragePoolStatus; @@ -12,7 +11,6 @@ import org.ovirt.engine.core.common.businessentities.VmType; import org.ovirt.engine.core.common.businessentities.network.VnicProfileView; import org.ovirt.engine.core.compat.Guid; -import org.ovirt.engine.core.compat.StringHelper; import org.ovirt.engine.ui.frontend.AsyncQuery; import org.ovirt.engine.ui.frontend.INewAsyncCallback; import org.ovirt.engine.ui.uicommonweb.Linq; @@ -85,71 +83,7 @@ public void template_SelectedItemChanged() { VmTemplate template = getModel().getTemplate().getSelectedItem(); - - if (template != null) - { - // Copy VM parameters from template. - buildModel(template); - - setSelectedOSType(template, getModel().getSelectedCluster().getArchitecture()); - doChangeDefautlHost(template.getDedicatedVmForVds()); - - getModel().getIsStateless().setEntity(template.isStateless()); - - boolean hasCd = !StringHelper.isNullOrEmpty(template.getIsoPath()); - - getModel().getCdImage().setIsChangable(hasCd); - getModel().getCdAttached().setEntity(hasCd); - if (hasCd) { - getModel().getCdImage().setSelectedItem(template.getIsoPath()); - } - - updateTimeZone(template.getTimeZone()); - - if (!template.getId().equals(Guid.Empty)) - { - getModel().getStorageDomain().setIsChangable(true); - getModel().getProvisioning().setIsChangable(true); - - getModel().getVmType().setSelectedItem(template.getVmType()); - getModel().setIsBlankTemplate(false); - getModel().getCopyPermissions().setIsAvailable(true); - getModel().getAllowConsoleReconnect().setEntity(template.isAllowConsoleReconnect()); - initDisks(); - updateRngDevice(template.getId()); - } - else - { - getModel().getStorageDomain().setIsChangable(false); - getModel().getProvisioning().setIsChangable(false); - - getModel().setIsBlankTemplate(true); - getModel().setIsDisksAvailable(false); - getModel().getCopyPermissions().setIsAvailable(false); - getModel().setDisks(null); - } - - initStorageDomains(); - - InstanceType selectedInstanceType = getModel().getInstanceTypes().getSelectedItem(); - int instanceTypeMinAllocatedMemory = selectedInstanceType != null ? selectedInstanceType.getMinAllocatedMem() : 0; - - // do not update if specified on template or instance type - if (template.getMinAllocatedMem() == 0 && instanceTypeMinAllocatedMemory == 0) { - updateMinAllocatedMemory(); - } - - updateQuotaByCluster(template.getQuotaId(), template.getQuotaName()); - getModel().getCustomPropertySheet().deserialize(template.getCustomProperties()); - - getModel().getVmInitModel().init(template); - getModel().getVmInitEnabled().setEntity(template.getVmInit() != null); - - if (getModel().getSelectedCluster() != null) { - updateCpuProfile(getModel().getSelectedCluster().getId(), - getClusterCompatibilityVersion(), template.getCpuProfileId()); - } - } + updateModelFromTemplate(template); } @Override diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/UnitVmModel.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/UnitVmModel.java index 1760199..22d175e 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/UnitVmModel.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/UnitVmModel.java @@ -147,6 +147,16 @@ this.spiceProxyEnabled = spiceProxyEnabled; } + private EntityModel<Boolean> templateChanged; + + public EntityModel<Boolean> getTemplateChanged() { + return templateChanged; + } + + public void setTemplateChanged(EntityModel<Boolean> templateChanged) { + this.templateChanged = templateChanged; + } + private EntityModel<Boolean> editingEnabled; public EntityModel<Boolean> getEditingEnabled() { @@ -1486,7 +1496,8 @@ VdcQueryType.GetPermittedStorageDomainsByStoragePoolId, VdcQueryType.GetHostsByClusterId, VdcQueryType.OsRepository, VdcQueryType.Search, - VdcQueryType.GetSupportedCpuList}); + VdcQueryType.GetSupportedCpuList, VdcQueryType.GetVmTemplatesByBaseTemplateId + }); this.behavior = behavior; this.behavior.setModel(this); @@ -1729,6 +1740,9 @@ setEditingEnabled(new EntityModel<Boolean>()); getEditingEnabled().setEntity(true); + setTemplateChanged(new EntityModel<Boolean>()); + getTemplateChanged().setEntity(false); + setCpuProfiles(new NotChangableForVmInPoolListModel<CpuProfile>()); getCpuProfiles().setIsAvailable(false); diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmListModel.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmListModel.java index 753917b..9df3d7b 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmListModel.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmListModel.java @@ -442,15 +442,15 @@ private VM privatecurrentVm; + public void setcurrentVm(VM value) + { + privatecurrentVm = value; + } + public VM getcurrentVm() { return privatecurrentVm; - } - - public void setcurrentVm(VM value) - { - privatecurrentVm = value; } private final ConsoleModelsCache consoleModelsCache; @@ -824,7 +824,7 @@ } private void edit() { - VM vm = (VM) getSelectedItem(); + final VM vm = (VM) getSelectedItem(); if (vm == null) { return; @@ -841,7 +841,7 @@ @Override public void onSuccess(Object model, Object result) { editedVm = (VM) result; - vmInitLoaded(editedVm); + vmInitLoaded(editedVm, vm); } }; if (vm.isNextRunConfigurationExists()) { @@ -852,8 +852,8 @@ } - private void vmInitLoaded(VM vm) { - UnitVmModel model = new UnitVmModel(new ExistingVmModelBehavior(vm)); + private void vmInitLoaded(VM vm, VM oldVm) { + UnitVmModel model = new UnitVmModel(new ExistingVmModelBehavior(vm, oldVm)); model.getVmType().setSelectedItem(vm.getVmType()); model.setVmAttachedToPool(vm.getVmPoolId() != null); model.setIsAdvancedModeLocalStorageKey("wa_vm_dialog"); //$NON-NLS-1$ @@ -1988,19 +1988,24 @@ final UnitVmModel model = (UnitVmModel) getWindow(); // Save changes. - buildVmOnSave(model, getcurrentVm()); + if (!model.getIsNew() && model.getTemplateChanged().getEntity()) { // template version change -> ignore other values + getcurrentVm().setVmtGuid(model.getTemplate().getSelectedItem().getId()); + } else { + buildVmOnSave(model, getcurrentVm()); - getcurrentVm().setBalloonEnabled(balloonEnabled(model)); + getcurrentVm().setBalloonEnabled(balloonEnabled(model)); - getcurrentVm().setCpuPinning(model.getCpuPinning().getEntity()); + getcurrentVm().setCpuPinning(model.getCpuPinning().getEntity()); - if (model.getCpuSharesAmount().getIsAvailable() && model.getCpuSharesAmount().getEntity() != null) { // $NON-NLS-1$ - getcurrentVm().setCpuShares(model.getCpuSharesAmount().getEntity()); + if (model.getCpuSharesAmount().getIsAvailable() + && model.getCpuSharesAmount().getEntity() != null) { // $NON-NLS-1$ + getcurrentVm().setCpuShares(model.getCpuSharesAmount().getEntity()); + } + + getcurrentVm().setUseHostCpuFlags(model.getHostCpu().getEntity()); + + getcurrentVm().setVmInit(model.getVmInitModel().buildCloudInitParameters(model)); } - - getcurrentVm().setUseHostCpuFlags(model.getHostCpu().getEntity()); - - getcurrentVm().setVmInit(model.getVmInitModel().buildCloudInitParameters(model)); if (model.getIsNew()) { @@ -2063,7 +2068,7 @@ VM selectedItem = (VM) getSelectedItem(); Guid oldClusterID = selectedItem.getVdsGroupId(); Guid newClusterID = model.getSelectedCluster().getId(); - if (oldClusterID.equals(newClusterID) == false) + if (oldClusterID.equals(newClusterID) == false && !model.getTemplateChanged().getEntity()) { ChangeVMClusterParameters parameters = new ChangeVMClusterParameters(newClusterID, getcurrentVm().getId()); @@ -2097,7 +2102,21 @@ { model.startProgress(null); VmManagementParametersBase updateVmParams = getUpdateVmParameters(applyCpuChangesLater); - Frontend.getInstance().runAction(VdcActionType.UpdateVm, updateVmParams, new UnitVmModelNetworkAsyncCallback(model, defaultNetworkCreatingManager, getcurrentVm().getId()), this); + IFrontendActionAsyncCallback updateCallback; + // if the change is a template version change -> no network changes are required -> no callback. + if (!model.getTemplateChanged().getEntity()) { + updateCallback = new UnitVmModelNetworkAsyncCallback(model, + defaultNetworkCreatingManager, + getcurrentVm().getId()); + } else { + updateCallback = new IFrontendActionAsyncCallback() { + @Override public void executed(FrontendActionAsyncResult result) { + getWindow().stopProgress(); + cancel(); + } + }; + } + Frontend.getInstance().runAction(VdcActionType.UpdateVm, updateVmParams, updateCallback, this); } } diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmModelBehaviorBase.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmModelBehaviorBase.java index 05c2578..59ed05a 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmModelBehaviorBase.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/VmModelBehaviorBase.java @@ -582,7 +582,7 @@ VmTemplate template = getModel().getTemplate().getSelectedItem(); - if (template != null && !template.getId().equals(Guid.Empty)) + if (template != null && !template.getId().equals(Guid.Empty) && !getModel().getTemplateChanged().getEntity()) { postInitStorageDomains(); } @@ -742,7 +742,7 @@ getModel().getIsVirtioScsiEnabled().setIsAvailable(isVirtioScsiEnabled); } - protected void setupTemplate(Guid templateId, final boolean useLatest) { + protected void setupTemplate(final Guid templateId, final boolean useLatest, final boolean isThinStateless) { AsyncDataProvider.getInstance().getTemplateById(new AsyncQuery(getModel(), new INewAsyncCallback() { @Override @@ -751,15 +751,41 @@ UnitVmModel model = (UnitVmModel) target; VmTemplate template = (VmTemplate) returnValue; - if (useLatest) { - template = new LatestVmTemplate(template); - } - setupBaseTemplate(template.getBaseTemplateId()); - model.getTemplate().setItems(Collections.singletonList(template)); - model.getTemplate().setSelectedItem(template); - model.getTemplate().setIsChangable(false); + if (isThinStateless) { + AsyncDataProvider.getInstance().getVmTemplatesByBaseTemplateId( + new AsyncQuery(getModel(), new INewAsyncCallback() { + @Override + public void onSuccess(Object target, Object returnValue) { + UnitVmModel model = (UnitVmModel) target; + VmTemplate selectedTemplate = null; + ArrayList<VmTemplate> templatesChain = new ArrayList<VmTemplate>((List<VmTemplate>)returnValue); + + for (VmTemplate template : templatesChain) { // find current selected item by id + if (template.getId().equals(templateId)) { + selectedTemplate = template; + } + } + + VmTemplate latestTemplate = new LatestVmTemplate(templatesChain.get(0)); + templatesChain.add(0, latestTemplate); + + if (useLatest) { + selectedTemplate = latestTemplate; + } + model.getTemplate().setItems(templatesChain, selectedTemplate); + } + }, getModel().getHash() + ), template.getBaseTemplateId()); + } else { + if (useLatest) { + template = new LatestVmTemplate(template); + } + model.getTemplate().setItems(Collections.singletonList(template)); + model.getTemplate().setSelectedItem(template); + model.getTemplate().setIsChangable(false); + } } }, getModel().getHash() @@ -768,6 +794,73 @@ ); } + protected void updateModelFromTemplate(VmTemplate template) { + if (template != null) + { + // Copy VM parameters from template. + buildModel(template); + + setSelectedOSType(template, getModel().getSelectedCluster().getArchitecture()); + doChangeDefautlHost(template.getDedicatedVmForVds()); + + getModel().getIsStateless().setEntity(template.isStateless()); + + boolean hasCd = !StringHelper.isNullOrEmpty(template.getIsoPath()); + + getModel().getCdImage().setIsChangable(hasCd); + getModel().getCdAttached().setEntity(hasCd); + if (hasCd) { + getModel().getCdImage().setSelectedItem(template.getIsoPath()); + } + + updateTimeZone(template.getTimeZone()); + + if (!template.getId().equals(Guid.Empty)) + { + getModel().getStorageDomain().setIsChangable(true); + getModel().getProvisioning().setIsChangable(true); + + getModel().getVmType().setSelectedItem(template.getVmType()); + getModel().setIsBlankTemplate(false); + getModel().getCopyPermissions().setIsAvailable(true); + getModel().getAllowConsoleReconnect().setEntity(template.isAllowConsoleReconnect()); + initDisks(); + updateRngDevice(template.getId()); + } + else + { + getModel().getStorageDomain().setIsChangable(false); + getModel().getProvisioning().setIsChangable(false); + + getModel().setIsBlankTemplate(true); + getModel().setIsDisksAvailable(false); + getModel().getCopyPermissions().setIsAvailable(false); + getModel().setDisks(null); + } + + initStorageDomains(); + + InstanceType selectedInstanceType = getModel().getInstanceTypes().getSelectedItem(); + int instanceTypeMinAllocatedMemory = selectedInstanceType != null ? selectedInstanceType.getMinAllocatedMem() : 0; + + // do not update if specified on template or instance type + if (template.getMinAllocatedMem() == 0 && instanceTypeMinAllocatedMemory == 0) { + updateMinAllocatedMemory(); + } + + updateQuotaByCluster(template.getQuotaId(), template.getQuotaName()); + getModel().getCustomPropertySheet().deserialize(template.getCustomProperties()); + + getModel().getVmInitModel().init(template); + getModel().getVmInitEnabled().setEntity(template.getVmInit() != null); + + if (getModel().getSelectedCluster() != null) { + updateCpuProfile(getModel().getSelectedCluster().getId(), + getClusterCompatibilityVersion(), template.getCpuProfileId()); + } + } + } + protected void setupBaseTemplate(Guid baseTemplateId) { AsyncDataProvider.getInstance().getTemplateById(new AsyncQuery(getModel(), new INewAsyncCallback() { diff --git a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/instancetypes/InstanceTypeManager.java b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/instancetypes/InstanceTypeManager.java index b4ca8e8..984107f 100644 --- a/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/instancetypes/InstanceTypeManager.java +++ b/frontend/webadmin/modules/uicommonweb/src/main/java/org/ovirt/engine/ui/uicommonweb/models/vms/instancetypes/InstanceTypeManager.java @@ -417,6 +417,9 @@ private void updateVirtioScsi(VmBase vmBase) { if (isNextRunConfigurationExists()) { getModel().getIsVirtioScsiEnabled().setEntity(isVmDeviceExists(vmBase.getManagedDeviceMap(), VmDeviceType.VIRTIOSCSI.getName())); + + // when changing template version for a running vm with a next-run config -> finish progress + model.stopProgress(); return; } diff --git a/frontend/webadmin/modules/uicommonweb/src/test/java/org/ovirt/engine/ui/uicommonweb/models/vms/BaseVmListModelTest.java b/frontend/webadmin/modules/uicommonweb/src/test/java/org/ovirt/engine/ui/uicommonweb/models/vms/BaseVmListModelTest.java index 821a5e1..35cfd3f 100644 --- a/frontend/webadmin/modules/uicommonweb/src/test/java/org/ovirt/engine/ui/uicommonweb/models/vms/BaseVmListModelTest.java +++ b/frontend/webadmin/modules/uicommonweb/src/test/java/org/ovirt/engine/ui/uicommonweb/models/vms/BaseVmListModelTest.java @@ -82,6 +82,7 @@ when(model.getNumaTuneMode().getSelectedItem()).thenReturn(NumaTuneMode.INTERLEAVE); when(model.getAutoConverge().getSelectedItem()).thenReturn(true); when(model.getMigrateCompressed().getSelectedItem()).thenReturn(true); + when(model.getTemplateChanged().getEntity()).thenReturn(false); } protected void setUpOrigVm(VM origVm) { diff --git a/frontend/webadmin/modules/uicompat/src/main/java/org/ovirt/engine/ui/uicompat/UIConstants.java b/frontend/webadmin/modules/uicompat/src/main/java/org/ovirt/engine/ui/uicompat/UIConstants.java index 5c0b532..54b5743 100644 --- a/frontend/webadmin/modules/uicompat/src/main/java/org/ovirt/engine/ui/uicompat/UIConstants.java +++ b/frontend/webadmin/modules/uicompat/src/main/java/org/ovirt/engine/ui/uicompat/UIConstants.java @@ -2487,4 +2487,10 @@ @DefaultStringValue("This field is not a valid Guid (use 0-9,A-F format: 00000000-0000-0000-0000-000000000000)") String invalidGuidMsg(); + + @DefaultStringValue("Template version was changed, confirm change for further editing") + String templateChangeMessage(); + + @DefaultStringValue("New template version will be applied on the next vm start, no more changes are possible") + String templateChangeRunningMessage(); } -- To view, visit http://gerrit.ovirt.org/36510 To unsubscribe, visit http://gerrit.ovirt.org/settings Gerrit-MessageType: newchange Gerrit-Change-Id: I53686dae694f6ff826bdbeaada1e28fc55fd8d30 Gerrit-PatchSet: 1 Gerrit-Project: ovirt-engine Gerrit-Branch: master Gerrit-Owner: Eldan Shachar <[email protected]> _______________________________________________ Engine-patches mailing list [email protected] http://lists.ovirt.org/mailman/listinfo/engine-patches
