You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by ko...@apache.org on 2015/05/19 18:20:58 UTC

[12/50] [abbrv] git commit: updated refs/heads/CLOUDSTACK-8301 to 8ff9000

Refactoring the LibvirtComputingResource
  - Adding LibvirtCheckOnHostCommandWrapper and LibvirtOvsCreateTunnelCommandWrapper
  - 4 unit tests added
  - KVM hypervisor plugin with 16.2% coverage


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/3c8b2172
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/3c8b2172
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/3c8b2172

Branch: refs/heads/CLOUDSTACK-8301
Commit: 3c8b217262e08053fd59329f7466b65b150a18c2
Parents: 6748a73
Author: wilderrodrigues <wr...@schubergphilis.com>
Authored: Fri May 1 19:17:30 2015 +0200
Committer: wilderrodrigues <wr...@schubergphilis.com>
Committed: Wed May 6 19:24:12 2015 +0200

----------------------------------------------------------------------
 .../kvm/resource/LibvirtComputingResource.java  |  89 +--------------
 .../LibvirtCheckOnHostCommandWrapper.java       |  64 +++++++++++
 .../LibvirtOvsCreateTunnelCommandWrapper.java   |  68 +++++++++++
 .../resource/wrapper/LibvirtRequestWrapper.java |   4 +
 .../resource/LibvirtComputingResourceTest.java  | 112 +++++++++++++++++++
 5 files changed, 252 insertions(+), 85 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/3c8b2172/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
index 9c1a6b4..6d13ce6 100644
--- a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
+++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
@@ -85,7 +85,6 @@ import com.ceph.rbd.RbdImage;
 import com.cloud.agent.api.Answer;
 import com.cloud.agent.api.BackupSnapshotAnswer;
 import com.cloud.agent.api.BackupSnapshotCommand;
-import com.cloud.agent.api.CheckOnHostCommand;
 import com.cloud.agent.api.Command;
 import com.cloud.agent.api.CreatePrivateTemplateFromSnapshotCommand;
 import com.cloud.agent.api.CreatePrivateTemplateFromVolumeCommand;
@@ -98,8 +97,6 @@ import com.cloud.agent.api.ManageSnapshotAnswer;
 import com.cloud.agent.api.ManageSnapshotCommand;
 import com.cloud.agent.api.NetworkUsageAnswer;
 import com.cloud.agent.api.NetworkUsageCommand;
-import com.cloud.agent.api.OvsCreateTunnelAnswer;
-import com.cloud.agent.api.OvsCreateTunnelCommand;
 import com.cloud.agent.api.PingCommand;
 import com.cloud.agent.api.PingRoutingCommand;
 import com.cloud.agent.api.PingRoutingWithNwGroupsCommand;
@@ -430,6 +427,10 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
         return _ovsTunnelPath;
     }
 
+    public KVMHAMonitor getMonitor() {
+        return _monitor;
+    }
+
     private static final class KeyValueInterpreter extends OutputInterpreter {
         private final Map<String, String> map = new HashMap<String, String>();
 
@@ -1309,10 +1310,6 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
                 return storageHandler.handleStorageCommands((StorageSubSystemCommand)cmd);
             } else if (cmd instanceof PvlanSetupCommand) {
                 return execute((PvlanSetupCommand)cmd);
-            } else if (cmd instanceof CheckOnHostCommand) {
-                return execute((CheckOnHostCommand)cmd);
-            } else if (cmd instanceof OvsCreateTunnelCommand) {
-                return execute((OvsCreateTunnelCommand)cmd);
             } else {
                 s_logger.warn("Unsupported command ");
                 return Answer.createUnsupportedCommandAnswer(cmd);
@@ -1398,39 +1395,6 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
         return true;
     }
 
-    private OvsCreateTunnelAnswer execute(final OvsCreateTunnelCommand cmd) {
-        final String bridge = cmd.getNetworkName();
-        try {
-            if (!findOrCreateTunnelNetwork(bridge)) {
-                s_logger.debug("Error during bridge setup");
-                return new OvsCreateTunnelAnswer(cmd, false,
-                        "Cannot create network", bridge);
-            }
-
-            configureTunnelNetwork(cmd.getNetworkId(), cmd.getFrom(),
-                    cmd.getNetworkName());
-            final Script command = new Script(_ovsTunnelPath, _timeout, s_logger);
-            command.add("create_tunnel");
-            command.add("--bridge", bridge);
-            command.add("--remote_ip", cmd.getRemoteIp());
-            command.add("--key", cmd.getKey().toString());
-            command.add("--src_host", cmd.getFrom().toString());
-            command.add("--dst_host", cmd.getTo().toString());
-
-            final String result = command.execute();
-            if (result != null) {
-                return new OvsCreateTunnelAnswer(cmd, true, result, null,
-                        bridge);
-            } else {
-                return new OvsCreateTunnelAnswer(cmd, false, result, bridge);
-            }
-        } catch (final Exception e) {
-            s_logger.debug("Error during tunnel setup");
-            s_logger.warn("Caught execption when creating ovs tunnel", e);
-            return new OvsCreateTunnelAnswer(cmd, false, e.getMessage(), bridge);
-        }
-    }
-
     private CopyVolumeAnswer execute(final CopyVolumeCommand cmd) {
         /**
              This method is only used for copying files from Primary Storage TO Secondary Storage
@@ -1508,26 +1472,6 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
 
     }
 
-    protected Answer execute(final CheckOnHostCommand cmd) {
-        final ExecutorService executors = Executors.newSingleThreadExecutor();
-        final List<NfsStoragePool> pools = _monitor.getStoragePools();
-        final KVMHAChecker ha = new KVMHAChecker(pools, cmd.getHost().getPrivateNetwork().getIp());
-        final Future<Boolean> future = executors.submit(ha);
-        try {
-            final Boolean result = future.get();
-            if (result) {
-                return new Answer(cmd, false, "Heart is still beating...");
-            } else {
-                return new Answer(cmd);
-            }
-        } catch (final InterruptedException e) {
-            return new Answer(cmd, false, "can't get status of host:");
-        } catch (final ExecutionException e) {
-            return new Answer(cmd, false, "can't get status of host:");
-        }
-
-    }
-
     protected Storage.StorageResourceType getStorageResourceType() {
         return Storage.StorageResourceType.STORAGE_POOL;
     }
@@ -3795,28 +3739,6 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
         return parser.getEmulator();
     }
 
-    private String getGuestType(final Connect conn, final String vmName) {
-        final LibvirtDomainXMLParser parser = new LibvirtDomainXMLParser();
-        Domain dm = null;
-        try {
-            dm = conn.domainLookupByName(vmName);
-            final String xmlDesc = dm.getXMLDesc(0);
-            parser.parseDomainXML(xmlDesc);
-            return parser.getDescription();
-        } catch (final LibvirtException e) {
-            s_logger.trace("Ignoring libvirt error.", e);
-            return null;
-        } finally {
-            try {
-                if (dm != null) {
-                    dm.free();
-                }
-            } catch (final LibvirtException l) {
-                s_logger.trace("Ignoring libvirt error.", l);
-            }
-        }
-    }
-
     boolean isGuestPVEnabled(final String guestOSName) {
         if (guestOSName == null) {
             return false;
@@ -4304,13 +4226,11 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
     @Override
     public void setName(final String name) {
         // TODO Auto-generated method stub
-
     }
 
     @Override
     public void setConfigParams(final Map<String, Object> params) {
         // TODO Auto-generated method stub
-
     }
 
     @Override
@@ -4328,7 +4248,6 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
     @Override
     public void setRunLevel(final int level) {
         // TODO Auto-generated method stub
-
     }
 
     public HypervisorType getHypervisorType(){

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/3c8b2172/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtCheckOnHostCommandWrapper.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtCheckOnHostCommandWrapper.java b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtCheckOnHostCommandWrapper.java
new file mode 100644
index 0000000..5e56023
--- /dev/null
+++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtCheckOnHostCommandWrapper.java
@@ -0,0 +1,64 @@
+//
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you 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 com.cloud.hypervisor.kvm.resource.wrapper;
+
+import java.util.List;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.Future;
+
+import com.cloud.agent.api.Answer;
+import com.cloud.agent.api.CheckOnHostCommand;
+import com.cloud.agent.api.to.HostTO;
+import com.cloud.agent.api.to.NetworkTO;
+import com.cloud.hypervisor.kvm.resource.KVMHABase.NfsStoragePool;
+import com.cloud.hypervisor.kvm.resource.KVMHAChecker;
+import com.cloud.hypervisor.kvm.resource.KVMHAMonitor;
+import com.cloud.hypervisor.kvm.resource.LibvirtComputingResource;
+import com.cloud.resource.CommandWrapper;
+
+public final class LibvirtCheckOnHostCommandWrapper extends CommandWrapper<CheckOnHostCommand, Answer, LibvirtComputingResource> {
+
+    @Override
+    public Answer execute(final CheckOnHostCommand command, final LibvirtComputingResource libvirtComputingResource) {
+        final ExecutorService executors = Executors.newSingleThreadExecutor();
+        final KVMHAMonitor monitor = libvirtComputingResource.getMonitor();
+
+        final List<NfsStoragePool> pools = monitor.getStoragePools();
+        HostTO host = command.getHost();
+        NetworkTO privateNetwork = host.getPrivateNetwork();
+        final KVMHAChecker ha = new KVMHAChecker(pools, privateNetwork.getIp());
+
+        final Future<Boolean> future = executors.submit(ha);
+        try {
+            final Boolean result = future.get();
+            if (result) {
+                return new Answer(command, false, "Heart is still beating...");
+            } else {
+                return new Answer(command);
+            }
+        } catch (final InterruptedException e) {
+            return new Answer(command, false, "can't get status of host:");
+        } catch (final ExecutionException e) {
+            return new Answer(command, false, "can't get status of host:");
+        }
+    }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/3c8b2172/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtOvsCreateTunnelCommandWrapper.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtOvsCreateTunnelCommandWrapper.java b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtOvsCreateTunnelCommandWrapper.java
new file mode 100644
index 0000000..3a62057
--- /dev/null
+++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtOvsCreateTunnelCommandWrapper.java
@@ -0,0 +1,68 @@
+//
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you 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 com.cloud.hypervisor.kvm.resource.wrapper;
+
+import org.apache.log4j.Logger;
+
+import com.cloud.agent.api.Answer;
+import com.cloud.agent.api.OvsCreateTunnelAnswer;
+import com.cloud.agent.api.OvsCreateTunnelCommand;
+import com.cloud.hypervisor.kvm.resource.LibvirtComputingResource;
+import com.cloud.resource.CommandWrapper;
+import com.cloud.utils.script.Script;
+
+public final class LibvirtOvsCreateTunnelCommandWrapper extends CommandWrapper<OvsCreateTunnelCommand, Answer, LibvirtComputingResource> {
+
+    private static final Logger s_logger = Logger.getLogger(LibvirtOvsCreateTunnelCommandWrapper.class);
+
+    @Override
+    public Answer execute(final OvsCreateTunnelCommand command, final LibvirtComputingResource libvirtComputingResource) {
+        final String bridge = command.getNetworkName();
+        try {
+            if (!libvirtComputingResource.findOrCreateTunnelNetwork(bridge)) {
+                s_logger.debug("Error during bridge setup");
+                return new OvsCreateTunnelAnswer(command, false,
+                        "Cannot create network", bridge);
+            }
+
+            libvirtComputingResource.configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                    command.getNetworkName());
+
+            final Script scriptCommand = new Script(libvirtComputingResource.getOvsTunnelPath(), libvirtComputingResource.getTimeout(), s_logger);
+            scriptCommand.add("create_tunnel");
+            scriptCommand.add("--bridge", bridge);
+            scriptCommand.add("--remote_ip", command.getRemoteIp());
+            scriptCommand.add("--key", command.getKey().toString());
+            scriptCommand.add("--src_host", command.getFrom().toString());
+            scriptCommand.add("--dst_host", command.getTo().toString());
+
+            final String result = scriptCommand.execute();
+            if (result != null) {
+                return new OvsCreateTunnelAnswer(command, true, result, null,
+                        bridge);
+            } else {
+                return new OvsCreateTunnelAnswer(command, false, result, bridge);
+            }
+        } catch (final Exception e) {
+            s_logger.warn("Caught execption when creating ovs tunnel", e);
+            return new OvsCreateTunnelAnswer(command, false, e.getMessage(), bridge);
+        }
+    }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/3c8b2172/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtRequestWrapper.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtRequestWrapper.java b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtRequestWrapper.java
index ca7a7d2..af2f544 100644
--- a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtRequestWrapper.java
+++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtRequestWrapper.java
@@ -25,6 +25,7 @@ import com.cloud.agent.api.AttachIsoCommand;
 import com.cloud.agent.api.AttachVolumeCommand;
 import com.cloud.agent.api.CheckHealthCommand;
 import com.cloud.agent.api.CheckNetworkCommand;
+import com.cloud.agent.api.CheckOnHostCommand;
 import com.cloud.agent.api.CheckVirtualMachineCommand;
 import com.cloud.agent.api.CleanupNetworkRulesCmd;
 import com.cloud.agent.api.Command;
@@ -41,6 +42,7 @@ import com.cloud.agent.api.ModifySshKeysCommand;
 import com.cloud.agent.api.ModifyStoragePoolCommand;
 import com.cloud.agent.api.NetworkRulesSystemVmCommand;
 import com.cloud.agent.api.NetworkRulesVmSecondaryIpCommand;
+import com.cloud.agent.api.OvsCreateTunnelCommand;
 import com.cloud.agent.api.OvsDestroyBridgeCommand;
 import com.cloud.agent.api.OvsDestroyTunnelCommand;
 import com.cloud.agent.api.OvsFetchInterfaceCommand;
@@ -120,6 +122,8 @@ public class LibvirtRequestWrapper extends RequestWrapper {
         linbvirtCommands.put(CheckSshCommand.class, new LibvirtCheckSshCommandWrapper());
         linbvirtCommands.put(CheckNetworkCommand.class, new LibvirtCheckNetworkCommandWrapper());
         linbvirtCommands.put(OvsDestroyTunnelCommand.class, new LibvirtOvsDestroyTunnelCommandWrapper());
+        linbvirtCommands.put(CheckOnHostCommand.class, new LibvirtCheckOnHostCommandWrapper());
+        linbvirtCommands.put(OvsCreateTunnelCommand.class, new LibvirtOvsCreateTunnelCommandWrapper());
 
         resources.put(LibvirtComputingResource.class, linbvirtCommands);
     }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/3c8b2172/plugins/hypervisors/kvm/test/com/cloud/hypervisor/kvm/resource/LibvirtComputingResourceTest.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/kvm/test/com/cloud/hypervisor/kvm/resource/LibvirtComputingResourceTest.java b/plugins/hypervisors/kvm/test/com/cloud/hypervisor/kvm/resource/LibvirtComputingResourceTest.java
index 1551f98..f01ad7a 100644
--- a/plugins/hypervisors/kvm/test/com/cloud/hypervisor/kvm/resource/LibvirtComputingResourceTest.java
+++ b/plugins/hypervisors/kvm/test/com/cloud/hypervisor/kvm/resource/LibvirtComputingResourceTest.java
@@ -68,6 +68,7 @@ import com.cloud.agent.api.AttachIsoCommand;
 import com.cloud.agent.api.AttachVolumeCommand;
 import com.cloud.agent.api.CheckHealthCommand;
 import com.cloud.agent.api.CheckNetworkCommand;
+import com.cloud.agent.api.CheckOnHostCommand;
 import com.cloud.agent.api.CheckVirtualMachineCommand;
 import com.cloud.agent.api.CleanupNetworkRulesCmd;
 import com.cloud.agent.api.CreateStoragePoolCommand;
@@ -83,6 +84,7 @@ import com.cloud.agent.api.ModifySshKeysCommand;
 import com.cloud.agent.api.ModifyStoragePoolCommand;
 import com.cloud.agent.api.NetworkRulesSystemVmCommand;
 import com.cloud.agent.api.NetworkRulesVmSecondaryIpCommand;
+import com.cloud.agent.api.OvsCreateTunnelCommand;
 import com.cloud.agent.api.OvsDestroyBridgeCommand;
 import com.cloud.agent.api.OvsDestroyTunnelCommand;
 import com.cloud.agent.api.OvsFetchInterfaceCommand;
@@ -2542,4 +2544,114 @@ public class LibvirtComputingResourceTest {
 
         verify(libvirtComputingResource, times(1)).findOrCreateTunnelNetwork(command.getBridgeName());
     }
+
+    @Test
+    public void testCheckOnHostCommand() {
+        final com.cloud.host.Host host = Mockito.mock(com.cloud.host.Host.class);;
+
+        final CheckOnHostCommand command = new CheckOnHostCommand(host);
+
+        final KVMHAMonitor monitor = Mockito.mock(KVMHAMonitor.class);
+
+        when(libvirtComputingResource.getMonitor()).thenReturn(monitor);
+
+        final LibvirtRequestWrapper wrapper = LibvirtRequestWrapper.getInstance();
+        assertNotNull(wrapper);
+
+        final Answer answer = wrapper.execute(command, libvirtComputingResource);
+        assertTrue(answer.getResult());
+
+        verify(libvirtComputingResource, times(1)).getMonitor();
+    }
+
+    @Test
+    public void testOvsCreateTunnelCommand() {
+        final String remoteIp = "172.16.16.16";
+        final Integer key = 1;
+        final Long from = 1l;
+        final Long to = 2l;
+        final long networkId = 1l;
+        final String fromIp = "172.15.15.15";
+        final String networkName = "eth";
+        final String networkUuid = "8edb1156-a851-4914-afc6-468ee52ac861";
+
+        final OvsCreateTunnelCommand command = new OvsCreateTunnelCommand(remoteIp, key, from, to, networkId, fromIp, networkName, networkUuid);
+
+        final String bridge = command.getNetworkName();
+
+        when(libvirtComputingResource.findOrCreateTunnelNetwork(bridge)).thenReturn(true);
+        when(libvirtComputingResource.configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                command.getNetworkName())).thenReturn(true);
+
+        final LibvirtRequestWrapper wrapper = LibvirtRequestWrapper.getInstance();
+        assertNotNull(wrapper);
+
+        final Answer answer = wrapper.execute(command, libvirtComputingResource);
+        assertTrue(answer.getResult());
+
+        verify(libvirtComputingResource, times(1)).findOrCreateTunnelNetwork(bridge);
+        verify(libvirtComputingResource, times(1)).configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                command.getNetworkName());
+    }
+
+    @Test
+    public void testOvsCreateTunnelCommandFailure1() {
+        final String remoteIp = "172.16.16.16";
+        final Integer key = 1;
+        final Long from = 1l;
+        final Long to = 2l;
+        final long networkId = 1l;
+        final String fromIp = "172.15.15.15";
+        final String networkName = "eth";
+        final String networkUuid = "8edb1156-a851-4914-afc6-468ee52ac861";
+
+        final OvsCreateTunnelCommand command = new OvsCreateTunnelCommand(remoteIp, key, from, to, networkId, fromIp, networkName, networkUuid);
+
+        final String bridge = command.getNetworkName();
+
+        when(libvirtComputingResource.findOrCreateTunnelNetwork(bridge)).thenReturn(false);
+        when(libvirtComputingResource.configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                command.getNetworkName())).thenReturn(true);
+
+        final LibvirtRequestWrapper wrapper = LibvirtRequestWrapper.getInstance();
+        assertNotNull(wrapper);
+
+        final Answer answer = wrapper.execute(command, libvirtComputingResource);
+        assertFalse(answer.getResult());
+
+        verify(libvirtComputingResource, times(1)).findOrCreateTunnelNetwork(bridge);
+        verify(libvirtComputingResource, times(0)).configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                command.getNetworkName());
+    }
+
+    @SuppressWarnings("unchecked")
+    @Test
+    public void testOvsCreateTunnelCommandFailure2() {
+        final String remoteIp = "172.16.16.16";
+        final Integer key = 1;
+        final Long from = 1l;
+        final Long to = 2l;
+        final long networkId = 1l;
+        final String fromIp = "172.15.15.15";
+        final String networkName = "eth";
+        final String networkUuid = "8edb1156-a851-4914-afc6-468ee52ac861";
+
+        final OvsCreateTunnelCommand command = new OvsCreateTunnelCommand(remoteIp, key, from, to, networkId, fromIp, networkName, networkUuid);
+
+        final String bridge = command.getNetworkName();
+
+        when(libvirtComputingResource.findOrCreateTunnelNetwork(bridge)).thenReturn(true);
+        when(libvirtComputingResource.configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                command.getNetworkName())).thenThrow(Exception.class);
+
+        final LibvirtRequestWrapper wrapper = LibvirtRequestWrapper.getInstance();
+        assertNotNull(wrapper);
+
+        final Answer answer = wrapper.execute(command, libvirtComputingResource);
+        assertFalse(answer.getResult());
+
+        verify(libvirtComputingResource, times(1)).findOrCreateTunnelNetwork(bridge);
+        verify(libvirtComputingResource, times(1)).configureTunnelNetwork(command.getNetworkId(), command.getFrom(),
+                command.getNetworkName());
+    }
 }
\ No newline at end of file