Martin Sivák has uploaded a new change for review.

Change subject: Add VdsPowerDown command and use it in Power saving policy
......................................................................

Add VdsPowerDown command and use it in Power saving policy

This adds a new command that can shut a host down in a nice
way. It first tries to use SSH to execute /sbin/poweroff and
if that fails it falls back to power management and cuts the
power.

Change-Id: Iccb9064dcfc9c20901d32a550354d66bbb0cc863
Bug-Url: https://bugzilla.redhat.com/show_bug.cgi?id=1035238
Signed-off-by: Martin Sivak <msi...@redhat.com>
---
A 
backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/VdsPowerDownCommand.java
M 
backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/scheduling/policyunits/PowerSavingBalancePolicyUnit.java
M 
backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdcActionType.java
A 
backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdsPowerDownParameters.java
M 
backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/config/ConfigValues.java
5 files changed, 165 insertions(+), 2 deletions(-)


  git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/20/22520/1

diff --git 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/VdsPowerDownCommand.java
 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/VdsPowerDownCommand.java
new file mode 100644
index 0000000..2d09b25
--- /dev/null
+++ 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/VdsPowerDownCommand.java
@@ -0,0 +1,114 @@
+package org.ovirt.engine.core.bll;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+
+import org.ovirt.engine.core.bll.job.ExecutionHandler;
+import org.ovirt.engine.core.bll.utils.EngineSSHClient;
+import org.ovirt.engine.core.common.action.FenceVdsActionParameters;
+import org.ovirt.engine.core.common.action.VdsPowerDownParameters;
+import org.ovirt.engine.core.common.action.VdcActionType;
+import org.ovirt.engine.core.common.businessentities.FenceActionType;
+import org.ovirt.engine.core.common.businessentities.VDSStatus;
+import org.ovirt.engine.core.common.config.Config;
+import org.ovirt.engine.core.common.config.ConfigValues;
+
+/**
+ * Tries to shutdown a host using SSH connection. The host has to be in 
maintenance mode.
+ */
+@NonTransactiveCommandAttribute
+public class VdsPowerDownCommand<T extends VdsPowerDownParameters> extends 
VdsCommand<T> {
+    public VdsPowerDownCommand(T parameters) {
+        super(parameters);
+    }
+
+    @Override
+    protected boolean canDoAction() {
+        return getVds().getStatus() == VDSStatus.Maintenance && 
super.canDoAction();
+    }
+
+    /**
+     * Try to shut down the host using a clean ssh poweroff method
+     */
+    @Override
+    protected void executeCommand() {
+        setVds(null);
+        if (getVds() == null) {
+            setCommandShouldBeLogged(false);
+            log.infoFormat("SSH powerdown will not be executed on host 
{0}({1}) since it doesn't exist anymore.",
+                    getVdsName(),
+                    getVdsId());
+            getReturnValue().setSucceeded(false);
+            return;
+        }
+
+        /* Try this only when the Host is in maintenance state */
+        if (getVds().getStatus() != VDSStatus.Maintenance) {
+            setCommandShouldBeLogged(false);
+            log.infoFormat("SSH powerdown will not be executed on host 
{0}({1}) since it is not in Maintenance.",
+                    getVdsName(),
+                    getVdsId());
+            getReturnValue().setSucceeded(false);
+            return;
+        }
+
+        boolean result = 
executeSshPowerdown(getVds().getVdsGroupCompatibilityVersion().toString());
+        if (result) {
+            // SSH powerdown executed without errors set the status to down
+            getVds().setStatus(VDSStatus.Down);
+
+            // clear the automatic PM flag unless instructed otherwise
+            if (!getParameters().getKeepPolicyPMEnabled()) {
+                getVds().setPowerManagementControlledByPolicy(false);
+            }
+            getDbFacade().getVdsDynamicDao().update(getVds().getDynamicData());
+
+        } else if (getParameters().getFallbackToPowerManagement() && 
getVds().getpm_enabled()) {
+            FenceVdsActionParameters parameters = new 
FenceVdsActionParameters(getVds().getId(), FenceActionType.Stop);
+            
parameters.setKeepPolicyPMEnabled(getParameters().getKeepPolicyPMEnabled());
+            Backend.getInstance().runInternalAction(VdcActionType.StopVds,
+                    parameters,
+                    ExecutionHandler.createInternalJobContext());
+        }
+
+        getReturnValue().setSucceeded(result);
+    }
+
+    /**
+     * Executes SSH shutdown command
+     *
+     * @returns {@code true} if command has been executed successfully, {@code 
false} otherwise
+     */
+    private boolean executeSshPowerdown(String version) {
+        boolean ret = false;
+        try (
+                final EngineSSHClient sshClient = new EngineSSHClient();
+                final ByteArrayOutputStream cmdOut = new 
ByteArrayOutputStream();
+                final ByteArrayOutputStream cmdErr = new 
ByteArrayOutputStream();
+        ) {
+            try {
+                log.infoFormat("Opening SSH powerdown session on host {0}", 
getVds().getHostName());
+                sshClient.setVds(getVds());
+                sshClient.useDefaultKeyPair();
+                sshClient.connect();
+                sshClient.authenticate();
+
+                log.infoFormat("Executing SSH powerdown command on host {0}", 
getVds().getHostName());
+                sshClient.executeCommand(
+                        Config.<String> 
getValue(ConfigValues.SshVdsPowerdownCommand, version),
+                        null,
+                        cmdOut,
+                        cmdErr
+                );
+                ret = true;
+            } catch (Exception ex) {
+                log.errorFormat("SSH powerdown command failed on host {0}: 
{1}\nStdout: {2}\nStderr: {3}\nStacktrace: {4}",
+                        getVds().getHostName(), ex.getMessage(), 
cmdOut.toString(), cmdErr.toString(), ex);
+            }
+        }
+        catch(IOException e) {
+            log.error("IOException", e);
+        }
+        return ret;
+    }
+}
diff --git 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/scheduling/policyunits/PowerSavingBalancePolicyUnit.java
 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/scheduling/policyunits/PowerSavingBalancePolicyUnit.java
index b4db756..46e5556 100644
--- 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/scheduling/policyunits/PowerSavingBalancePolicyUnit.java
+++ 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/scheduling/policyunits/PowerSavingBalancePolicyUnit.java
@@ -12,6 +12,7 @@
 import org.ovirt.engine.core.common.AuditLogType;
 import org.ovirt.engine.core.common.action.FenceVdsActionParameters;
 import org.ovirt.engine.core.common.action.MaintenanceNumberOfVdssParameters;
+import org.ovirt.engine.core.common.action.VdsPowerDownParameters;
 import org.ovirt.engine.core.common.action.VdcActionType;
 import org.ovirt.engine.core.common.action.VdsActionParameters;
 import org.ovirt.engine.core.common.businessentities.FenceActionType;
@@ -83,8 +84,9 @@
             logAction(vds, AuditLogType.PM_POLICY_MAINTENANCE_TO_DOWN);
 
             /* Maint -> Down */
-            FenceVdsActionParameters parameters = new 
FenceVdsActionParameters(vds.getId(), FenceActionType.Stop, true);
-            Backend.getInstance().runInternalAction(VdcActionType.StopVds,
+            VdsPowerDownParameters parameters = new 
VdsPowerDownParameters(vds.getId());
+            parameters.setKeepPolicyPMEnabled(true);
+            Backend.getInstance().runInternalAction(VdcActionType.VdsPowerDown,
                     parameters,
                     ExecutionHandler.createInternalJobContext());
         }
diff --git 
a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdcActionType.java
 
b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdcActionType.java
index 0f990b8..835885c 100644
--- 
a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdcActionType.java
+++ 
b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdcActionType.java
@@ -73,6 +73,7 @@
     ChangeVDSCluster(125, ActionGroup.EDIT_HOST_CONFIGURATION, false, 
QuotaDependency.NONE),
     RefreshHostCapabilities(126, ActionGroup.MANIPUTLATE_HOST, false, 
QuotaDependency.NONE),
     SshSoftFencing(127, QuotaDependency.NONE),
+    VdsPowerDown(128, QuotaDependency.NONE),
 
     // Network
     UpdateNetworkToVdsInterface(149, ActionGroup.CONFIGURE_HOST_NETWORK, 
QuotaDependency.NONE),
diff --git 
a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdsPowerDownParameters.java
 
b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdsPowerDownParameters.java
new file mode 100644
index 0000000..5ce310d
--- /dev/null
+++ 
b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdsPowerDownParameters.java
@@ -0,0 +1,42 @@
+package org.ovirt.engine.core.common.action;
+
+import org.ovirt.engine.core.compat.Guid;
+
+public class VdsPowerDownParameters extends VdsActionParameters {
+    /*
+     * If the power management policy is responsible for this action
+     * pass true so we keep the powerManagementControlledByPolicy flag set.
+     *
+     * If the user triggered this action, clear the flag.
+     */
+    private boolean keepPolicyPMEnabled = false;
+
+    /*
+     * If this flag is set and ssh fails, then the command
+     * tries the standard power management procedures to cut the power.
+     */
+    private boolean fallbackToPowerManagement = true;
+
+    public VdsPowerDownParameters(Guid vdsId) {
+        super(vdsId);
+    }
+
+    public VdsPowerDownParameters() {
+    }
+
+    public boolean getKeepPolicyPMEnabled() {
+        return keepPolicyPMEnabled;
+    }
+
+    public void setKeepPolicyPMEnabled(boolean keepPolicyPMEnabled) {
+        this.keepPolicyPMEnabled = keepPolicyPMEnabled;
+    }
+
+    public boolean getFallbackToPowerManagement() {
+        return fallbackToPowerManagement;
+    }
+
+    public void setFallbackToPowerManagement(boolean 
fallbackToPowerManagement) {
+        this.fallbackToPowerManagement = fallbackToPowerManagement;
+    }
+}
diff --git 
a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/config/ConfigValues.java
 
b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/config/ConfigValues.java
index 2cbc461..acd1e30 100644
--- 
a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/config/ConfigValues.java
+++ 
b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/config/ConfigValues.java
@@ -1430,6 +1430,10 @@
     @DefaultValueAttribute("/usr/bin/vdsm-tool service-restart vdsmd")
     SshSoftFencingCommand,
 
+    @TypeConverterAttribute(String.class)
+    @DefaultValueAttribute("/sbin/poweroff")
+    SshVdsPowerdownCommand,
+
     @TypeConverterAttribute(java.util.List.class)
     @DefaultValueAttribute("rhel6.2.0,pc-1.0")
     @OptionBehaviourAttribute(behaviour = 
OptionBehaviour.CommaSeparatedStringArray)


-- 
To view, visit http://gerrit.ovirt.org/22520
To unsubscribe, visit http://gerrit.ovirt.org/settings

Gerrit-MessageType: newchange
Gerrit-Change-Id: Iccb9064dcfc9c20901d32a550354d66bbb0cc863
Gerrit-PatchSet: 1
Gerrit-Project: ovirt-engine
Gerrit-Branch: master
Gerrit-Owner: Martin Sivák <msi...@redhat.com>
_______________________________________________
Engine-patches mailing list
Engine-patches@ovirt.org
http://lists.ovirt.org/mailman/listinfo/engine-patches

Reply via email to