Daniel Erez has uploaded a new change for review.

Change subject: core: SyncLunsInfoForIscsiStorageDomain
......................................................................

core: SyncLunsInfoForIscsiStorageDomain

Change-Id: I5867ad8d36f329e23c611079512be30a9c5f83a5
Signed-off-by: Daniel Erez <de...@redhat.com>
---
M 
backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/ISCSIStorageHelper.java
A 
backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommand.java
A 
backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommandTest.java
M 
backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/action/VdcActionType.java
4 files changed, 202 insertions(+), 0 deletions(-)


  git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/19/17919/1

diff --git 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/ISCSIStorageHelper.java
 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/ISCSIStorageHelper.java
index 8264dde..5e7101d 100644
--- 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/ISCSIStorageHelper.java
+++ 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/ISCSIStorageHelper.java
@@ -6,6 +6,8 @@
 
 import org.apache.commons.collections.CollectionUtils;
 import org.ovirt.engine.core.bll.Backend;
+import org.ovirt.engine.core.common.action.StorageDomainParametersBase;
+import org.ovirt.engine.core.common.action.VdcActionType;
 import 
org.ovirt.engine.core.common.businessentities.LUN_storage_server_connection_map;
 import org.ovirt.engine.core.common.businessentities.LUNs;
 import org.ovirt.engine.core.common.businessentities.StorageDomain;
@@ -60,6 +62,11 @@
             isSuccess = returnValue.getSucceeded();
             if (isSuccess && VDSCommandType.forValue(type) == 
VDSCommandType.ConnectStorageServer) {
                 isSuccess = isConnectSucceeded((Map<String, String>) 
returnValue.getReturnValue(), list);
+
+                // Synchronize LUN details comprising the storage domain with 
the DB
+                StorageDomainParametersBase parameters = new 
StorageDomainParametersBase(storageDomain.getId());
+                parameters.setVdsId(vdsId);
+                
Backend.getInstance().runInternalAction(VdcActionType.SyncLunsInfoForIscsiStorageDomain,
 parameters);
             }
         }
         return isSuccess;
diff --git 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommand.java
 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommand.java
new file mode 100644
index 0000000..8e3ba23
--- /dev/null
+++ 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommand.java
@@ -0,0 +1,121 @@
+package org.ovirt.engine.core.bll.storage;
+
+import java.util.List;
+
+import org.ovirt.engine.core.bll.InternalCommandAttribute;
+import org.ovirt.engine.core.bll.NonTransactiveCommandAttribute;
+import org.ovirt.engine.core.common.action.StorageDomainParametersBase;
+import 
org.ovirt.engine.core.common.businessentities.BusinessEntitiesDefinitions;
+import 
org.ovirt.engine.core.common.businessentities.LUN_storage_server_connection_map;
+import org.ovirt.engine.core.common.businessentities.LUNs;
+import org.ovirt.engine.core.common.businessentities.StorageServerConnections;
+import org.ovirt.engine.core.common.vdscommands.GetVGInfoVDSCommandParameters;
+import org.ovirt.engine.core.common.vdscommands.VDSCommandType;
+import org.ovirt.engine.core.dao.StorageServerConnectionLunMapDAO;
+import org.ovirt.engine.core.utils.transaction.TransactionMethod;
+import org.ovirt.engine.core.utils.transaction.TransactionSupport;
+
+/**
+ * Synchronize LUN details comprising the storage domain with the DB
+ */
+@InternalCommandAttribute
+@NonTransactiveCommandAttribute(forceCompensation = true)
+public class SyncLunsInfoForIscsiStorageDomainCommand<T extends 
StorageDomainParametersBase> extends StorageDomainCommandBase<T> {
+
+    public SyncLunsInfoForIscsiStorageDomainCommand(T parameters) {
+        super(parameters);
+        setVdsId(parameters.getVdsId());
+    }
+
+    @Override
+    protected void executeCommand() {
+        final List<LUNs> lunsFromVgInfo = (List<LUNs>) 
runVdsCommand(VDSCommandType.GetVGInfo,
+                new GetVGInfoVDSCommandParameters(getVds().getId(), 
getStorageDomain().getStorage())).getReturnValue();
+        final List<LUNs> lunsFromDb = 
getLunDao().getAllForVolumeGroup(getStorageDomain().getStorage());
+
+        if (isLunsInfoMismatch(lunsFromVgInfo, lunsFromDb)) {
+            TransactionSupport.executeInNewTransaction(new 
TransactionMethod<Void>() {
+                @Override
+                public Void runInTransaction() {
+                    log.infoFormat("LUN details mismatch has been detected - 
refresh data from the underlying storage");
+                    refreshLunsInfo(lunsFromVgInfo, lunsFromDb);
+                    return null;
+                }
+            });
+        }
+
+        setSucceeded(true);
+    }
+
+    protected void refreshLunsInfo(List<LUNs> lunsFromVgInfo, List<LUNs> 
lunsFromDb) {
+        for (LUNs lunFromVgInfo : lunsFromVgInfo) {
+            // Update LUN
+            if (getLunDao().get(lunFromVgInfo.getLUN_id()) == null) {
+                getLunDao().save(lunFromVgInfo);
+                log.infoFormat("Recovered LUN ID: {0}", 
lunFromVgInfo.getLUN_id());
+            }
+
+            // Update lun connections map
+            for (StorageServerConnections connection : 
lunFromVgInfo.getLunConnections()) {
+                StorageServerConnections connectionFromDb =
+                        
getStorageServerConnectionDAO().getForIqn(connection.getiqn());
+                if (connectionFromDb == null) {
+                    // Shouldn't happen
+                    continue;
+                }
+
+                LUN_storage_server_connection_map lunConnection = new 
LUN_storage_server_connection_map(
+                        lunFromVgInfo.getLUN_id(), connectionFromDb.getid());
+                if 
(getStorageServerConnectionLunMapDao().get(lunConnection.getId()) == null) {
+                    getStorageServerConnectionLunMapDao().save(lunConnection);
+                }
+            }
+        }
+
+        // Cleanup LUNs from DB
+        for (LUNs lunFromDb : lunsFromDb) {
+            if (!isDummyLun(lunFromDb) && !containsLun(lunsFromVgInfo, 
lunFromDb)) {
+                getLunDao().remove(lunFromDb.getLUN_id());
+                log.infoFormat("Removed LUN ID: {0}", lunFromDb.getLUN_id());
+            }
+        }
+    }
+
+    protected boolean isLunsInfoMismatch(List<LUNs> lunsFromVgInfo, List<LUNs> 
lunsFromDb) {
+        if (lunsFromDb.size() != lunsFromVgInfo.size()) {
+            return true;
+        }
+
+        for (LUNs lunFromVgInfo : lunsFromVgInfo) {
+            for (LUNs lunFromDb : lunsFromDb) {
+                if (lunFromDb.getphysical_volume_id() == null ||
+                        
!lunFromDb.getphysical_volume_id().equals(lunFromVgInfo.getphysical_volume_id()))
 {
+                    continue;
+                }
+
+                if (!lunFromDb.getLUN_id().equals(lunFromVgInfo.getLUN_id())) {
+                    return true;
+                }
+            }
+        }
+
+        return false;
+    }
+
+    private boolean isDummyLun(LUNs lun) {
+        return 
lun.getLUN_id().startsWith(BusinessEntitiesDefinitions.DUMMY_LUN_ID_PREFIX);
+    }
+
+    private boolean containsLun(List<LUNs> luns, LUNs lunToFind) {
+        for (LUNs lun : luns) {
+            if (lun.getLUN_id().equals(lunToFind.getLUN_id())) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    protected StorageServerConnectionLunMapDAO 
getStorageServerConnectionLunMapDao() {
+        return getDbFacade().getStorageServerConnectionLunMapDao();
+    }
+}
diff --git 
a/backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommandTest.java
 
b/backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommandTest.java
new file mode 100644
index 0000000..3a026b5
--- /dev/null
+++ 
b/backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/storage/SyncLunsInfoForIscsiStorageDomainCommandTest.java
@@ -0,0 +1,73 @@
+package org.ovirt.engine.core.bll.storage;
+
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.spy;
+
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.runners.MockitoJUnitRunner;
+import org.ovirt.engine.core.common.action.StorageDomainParametersBase;
+import org.ovirt.engine.core.common.businessentities.LUNs;
+import org.ovirt.engine.core.compat.Guid;
+
+@RunWith(MockitoJUnitRunner.class)
+public class SyncLunsInfoForIscsiStorageDomainCommandTest {
+
+    private 
SyncLunsInfoForIscsiStorageDomainCommand<StorageDomainParametersBase> command;
+    private StorageDomainParametersBase parameters;
+
+    @Before
+    public void setup() {
+        parameters = new StorageDomainParametersBase(Guid.newGuid());
+        parameters.setVdsId(Guid.newGuid());
+
+        command = spy(new 
SyncLunsInfoForIscsiStorageDomainCommand<StorageDomainParametersBase>(parameters));
+    }
+
+    @Test
+    public void lunsMismatchListSize() {
+        List<LUNs> lunsFromVgInfo = Collections.singletonList(new LUNs());
+        List<LUNs> lunsFromDb = Collections.emptyList();
+
+        boolean isMismatch = command.isLunsInfoMismatch(lunsFromVgInfo, 
lunsFromDb);
+        assertTrue(isMismatch);
+    }
+
+    @Test
+    public void lunsMismatchWrongId() {
+        Guid pvID = Guid.newGuid();
+
+        LUNs lunFromVG = new LUNs();
+        lunFromVG.setLUN_id(Guid.newGuid().toString());
+        lunFromVG.setphysical_volume_id(pvID.toString());
+
+        LUNs lunFromDB = new LUNs();
+        lunFromDB.setLUN_id(Guid.newGuid().toString());
+        lunFromDB.setphysical_volume_id(pvID.toString());
+
+        List<LUNs> lunsFromVgInfo = Collections.singletonList(lunFromVG);
+        List<LUNs> lunsFromDb = Collections.singletonList(lunFromDB);
+
+        boolean isMismatch = command.isLunsInfoMismatch(lunsFromVgInfo, 
lunsFromDb);
+        assertTrue(isMismatch);
+    }
+
+    @Test
+    public void lunsMatch() {
+        LUNs lun = new LUNs();
+        lun.setLUN_id(Guid.newGuid().toString());
+        lun.setphysical_volume_id(Guid.newGuid().toString());
+
+        List<LUNs> lunsFromVgInfo = Arrays.asList(lun, lun);
+        List<LUNs> lunsFromDb = Arrays.asList(lun, lun);
+
+        boolean isMismatch = command.isLunsInfoMismatch(lunsFromVgInfo, 
lunsFromDb);
+        assertFalse(isMismatch);
+    }
+}
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 08e686d..679e0bc 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
@@ -230,6 +230,7 @@
     ExportRepoImage(1015, QuotaDependency.NONE),
     AttachStorageConnectionToStorageDomain(1016, 
ActionGroup.MANIPULATE_STORAGE_DOMAIN, QuotaDependency.NONE),
     DetachStorageConnectionFromStorageDomain(1017, 
ActionGroup.MANIPULATE_STORAGE_DOMAIN, QuotaDependency.NONE),
+    SyncLunsInfoForIscsiStorageDomain(1018, false, QuotaDependency.NONE),
 
     // Event Notification
     AddEventSubscription(1100, false, QuotaDependency.NONE),


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

Gerrit-MessageType: newchange
Gerrit-Change-Id: I5867ad8d36f329e23c611079512be30a9c5f83a5
Gerrit-PatchSet: 1
Gerrit-Project: ovirt-engine
Gerrit-Branch: master
Gerrit-Owner: Daniel Erez <de...@redhat.com>
_______________________________________________
Engine-patches mailing list
Engine-patches@ovirt.org
http://lists.ovirt.org/mailman/listinfo/engine-patches

Reply via email to