Generalise linked clone formats which are different for each datastore type

This commit is contained in:
Harikrishna Patnala 2020-07-23 04:18:21 +05:30
parent fef3926469
commit ed7efdf4d2
2 changed files with 111 additions and 75 deletions

View File

@ -16,8 +16,11 @@
// under the License.
package com.cloud.storage.resource;
import java.util.Arrays;
import java.util.List;
import org.apache.cloudstack.framework.config.ConfigKey;
import org.apache.cloudstack.framework.config.Configurable;
import org.apache.log4j.Logger;
import com.cloud.hypervisor.vmware.mo.DatacenterMO;
@ -32,32 +35,49 @@ import com.cloud.utils.Pair;
* To provide helper methods to handle storage layout in one place
*
*/
public class VmwareStorageLayoutHelper {
public class VmwareStorageLayoutHelper implements Configurable {
private static final Logger s_logger = Logger.getLogger(VmwareStorageLayoutHelper.class);
static final ConfigKey<String> VsphereLinkedCloneExtensions = new ConfigKey<String>("Hidden", String.class,
"vsphere.linked.clone.extensions", "delta.vmdk,sesparse.vmdk",
"Comma separated list of linked clone disk formats allowed to handle storage in VMware", true);
public static String[] getVmdkFilePairDatastorePath(DatastoreMO dsMo, String vmName, String vmdkName, VmwareStorageLayoutType layoutType, boolean linkedVmdk)
throws Exception {
String[] filePair = new String[2];
int i = 0;
String[] vSphereLinkedCloneExtensions = VsphereLinkedCloneExtensions.value().trim().split("\\s*,\\s*");
String[] fileNames;
if (linkedVmdk)
fileNames = new String[vSphereLinkedCloneExtensions.length + 1];
else
fileNames = new String[2];
switch (layoutType) {
case VMWARE:
assert (vmName != null && !vmName.isEmpty());
filePair[0] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + ".vmdk");
fileNames[i] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + ".vmdk");
if (linkedVmdk)
filePair[1] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + "-delta.vmdk");
if (linkedVmdk) {
for (int j=0 ; j < vSphereLinkedCloneExtensions.length; j++) {
fileNames[++i] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, String.format("%s-%s",vmdkName, vSphereLinkedCloneExtensions[j]));
}
}
else
filePair[1] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + "-flat.vmdk");
return filePair;
fileNames[i+1] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + "-flat.vmdk");
return fileNames;
case CLOUDSTACK_LEGACY:
filePair[0] = getDatastorePathBaseFolderFromVmdkFileName(dsMo, vmdkName + ".vmdk");
fileNames[i] = getDatastorePathBaseFolderFromVmdkFileName(dsMo, vmdkName + ".vmdk");
if (linkedVmdk)
filePair[1] = getDatastorePathBaseFolderFromVmdkFileName(dsMo, vmdkName + "-delta.vmdk");
else
filePair[1] = getDatastorePathBaseFolderFromVmdkFileName(dsMo, vmdkName + "-flat.vmdk");
return filePair;
if (linkedVmdk) {
for (int j=0 ; j < vSphereLinkedCloneExtensions.length; j++) {
fileNames[++i] = getDatastorePathBaseFolderFromVmdkFileName(dsMo, String.format("%s-%s",vmdkName, vSphereLinkedCloneExtensions[j]));
}
} else
fileNames[i+1] = getDatastorePathBaseFolderFromVmdkFileName(dsMo, vmdkName + "-flat.vmdk");
return fileNames;
default:
assert (false);
@ -71,26 +91,37 @@ public class VmwareStorageLayoutHelper {
public static String[] getVmdkFilePairManagedDatastorePath(DatastoreMO dsMo, String vmName, String vmdkName, VmwareStorageLayoutType layoutType, boolean linkedVmdk)
throws Exception {
String[] filePair = new String[2];
int i = 0;
String[] vSphereLinkedCloneExtensions = VsphereLinkedCloneExtensions.value().trim().split("\\s*,\\s*");
String[] fileNames;
if (linkedVmdk)
fileNames = new String[vSphereLinkedCloneExtensions.length + 1];
else
fileNames = new String[2];
switch (layoutType) {
case VMWARE:
assert (vmName != null && !vmName.isEmpty());
filePair[0] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + ".vmdk");
fileNames[i] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + ".vmdk");
if (linkedVmdk)
filePair[1] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + "-delta.vmdk");
else
filePair[1] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + "-flat.vmdk");
return filePair;
if (linkedVmdk) {
for (int j=0 ; j < vSphereLinkedCloneExtensions.length; j++) {
fileNames[++i] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, String.format("%s-%s",vmdkName, vSphereLinkedCloneExtensions[j]));
}
} else
fileNames[i+1] = getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, vmdkName + "-flat.vmdk");
return fileNames;
case CLOUDSTACK_LEGACY:
filePair[0] = getDeprecatedLegacyDatastorePathFromVmdkFileName(dsMo, vmdkName + ".vmdk");
fileNames[i] = getDeprecatedLegacyDatastorePathFromVmdkFileName(dsMo, vmdkName + ".vmdk");
if (linkedVmdk)
filePair[1] = getDeprecatedLegacyDatastorePathFromVmdkFileName(dsMo, vmdkName + "-delta.vmdk");
else
filePair[1] = getDeprecatedLegacyDatastorePathFromVmdkFileName(dsMo, vmdkName + "-flat.vmdk");
return filePair;
if (linkedVmdk) {
for (int j=0 ; j < vSphereLinkedCloneExtensions.length; j++) {
fileNames[++i] = getDeprecatedLegacyDatastorePathFromVmdkFileName(dsMo, String.format("%s-%s",vmdkName, vSphereLinkedCloneExtensions[j]));
}
} else
fileNames[i+1] = getDeprecatedLegacyDatastorePathFromVmdkFileName(dsMo, vmdkName + "-flat.vmdk");
return fileNames;
default:
assert (false);
@ -156,16 +187,20 @@ public class VmwareStorageLayoutHelper {
syncVolumeToRootFolder(dcMo, ds, vmdkName, vmName, excludeFolders);
}
if (ds.fileExists(vmdkFullCloneModeLegacyPair[1])) {
s_logger.info("sync " + vmdkFullCloneModeLegacyPair[1] + "->" + vmdkFullCloneModePair[1]);
for (int i=1; i<vmdkFullCloneModeLegacyPair.length; i++) {
if (ds.fileExists(vmdkFullCloneModeLegacyPair[i])) {
s_logger.info("sync " + vmdkFullCloneModeLegacyPair[i] + "->" + vmdkFullCloneModePair[i]);
ds.moveDatastoreFile(vmdkFullCloneModeLegacyPair[1], dcMo.getMor(), ds.getMor(), vmdkFullCloneModePair[1], dcMo.getMor(), true);
ds.moveDatastoreFile(vmdkFullCloneModeLegacyPair[i], dcMo.getMor(), ds.getMor(), vmdkFullCloneModePair[i], dcMo.getMor(), true);
}
}
if (ds.fileExists(vmdkLinkedCloneModeLegacyPair[1])) {
s_logger.info("sync " + vmdkLinkedCloneModeLegacyPair[1] + "->" + vmdkLinkedCloneModePair[1]);
for (int i=1; i<vmdkLinkedCloneModeLegacyPair.length; i++) {
if (ds.fileExists(vmdkLinkedCloneModeLegacyPair[i])) {
s_logger.info("sync " + vmdkLinkedCloneModeLegacyPair[i] + "->" + vmdkLinkedCloneModePair[i]);
ds.moveDatastoreFile(vmdkLinkedCloneModeLegacyPair[1], dcMo.getMor(), ds.getMor(), vmdkLinkedCloneModePair[1], dcMo.getMor(), true);
ds.moveDatastoreFile(vmdkLinkedCloneModeLegacyPair[i], dcMo.getMor(), ds.getMor(), vmdkLinkedCloneModePair[i], dcMo.getMor(), true);
}
}
if (ds.fileExists(vmdkLinkedCloneModeLegacyPair[0])) {
@ -192,20 +227,18 @@ public class VmwareStorageLayoutHelper {
}
DatastoreFile srcDsFile = new DatastoreFile(fileDsFullPath);
String companionFilePath = srcDsFile.getCompanionPath(vmdkName + "-flat.vmdk");
if (ds.fileExists(companionFilePath)) {
String targetPath = getDatastorePathBaseFolderFromVmdkFileName(ds, vmdkName + "-flat.vmdk");
s_logger.info("Fixup folder-synchronization. move " + companionFilePath + " -> " + targetPath);
ds.moveDatastoreFile(companionFilePath, dcMo.getMor(), ds.getMor(), targetPath, dcMo.getMor(), true);
}
List<String> vSphereFileExtensions = Arrays.asList(VsphereLinkedCloneExtensions.value().trim().split("\\s*,\\s*"));
// add flat file format to the above list
vSphereFileExtensions.add("flat.vmdk");
for (String linkedCloneExtension : vSphereFileExtensions) {
String companionFilePath = srcDsFile.getCompanionPath(String.format("%s-%s",vmdkName, linkedCloneExtension));
if (ds.fileExists(companionFilePath)) {
String targetPath = getDatastorePathBaseFolderFromVmdkFileName(ds, String.format("%s-%s",vmdkName, linkedCloneExtension));
companionFilePath = srcDsFile.getCompanionPath(vmdkName + "-delta.vmdk");
if (ds.fileExists(companionFilePath)) {
String targetPath = getDatastorePathBaseFolderFromVmdkFileName(ds, vmdkName + "-delta.vmdk");
s_logger.info("Fixup folder-synchronization. move " + companionFilePath + " -> " + targetPath);
ds.moveDatastoreFile(companionFilePath, dcMo.getMor(), ds.getMor(), targetPath, dcMo.getMor(), true);
s_logger.info("Fixup folder-synchronization. move " + companionFilePath + " -> " + targetPath);
ds.moveDatastoreFile(companionFilePath, dcMo.getMor(), ds.getMor(), targetPath, dcMo.getMor(), true);
}
}
// move the identity VMDK file the last
@ -234,18 +267,16 @@ public class VmwareStorageLayoutHelper {
s_logger.info("Move " + file.getPath() + " -> " + targetFile.getPath());
dsMo.moveDatastoreFile(file.getPath(), dcMo.getMor(), dsMo.getMor(), targetFile.getPath(), dcMo.getMor(), true);
String pairSrcFilePath = file.getCompanionPath(file.getFileBaseName() + "-flat.vmdk");
String pairTargetFilePath = targetFile.getCompanionPath(file.getFileBaseName() + "-flat.vmdk");
if (dsMo.fileExists(pairSrcFilePath)) {
s_logger.info("Move " + pairSrcFilePath + " -> " + pairTargetFilePath);
dsMo.moveDatastoreFile(pairSrcFilePath, dcMo.getMor(), dsMo.getMor(), pairTargetFilePath, dcMo.getMor(), true);
}
pairSrcFilePath = file.getCompanionPath(file.getFileBaseName() + "-delta.vmdk");
pairTargetFilePath = targetFile.getCompanionPath(file.getFileBaseName() + "-delta.vmdk");
if (dsMo.fileExists(pairSrcFilePath)) {
s_logger.info("Move " + pairSrcFilePath + " -> " + pairTargetFilePath);
dsMo.moveDatastoreFile(pairSrcFilePath, dcMo.getMor(), dsMo.getMor(), pairTargetFilePath, dcMo.getMor(), true);
List<String> vSphereFileExtensions = Arrays.asList(VsphereLinkedCloneExtensions.value().trim().split("\\s*,\\s*"));
// add flat file format to the above list
vSphereFileExtensions.add("flat.vmdk");
for (String linkedCloneExtension : vSphereFileExtensions) {
String pairSrcFilePath = file.getCompanionPath(String.format("%s-%s", file.getFileBaseName(), linkedCloneExtension));
String pairTargetFilePath = targetFile.getCompanionPath(String.format("%s-%s", file.getFileBaseName(), linkedCloneExtension));
if (dsMo.fileExists(pairSrcFilePath)) {
s_logger.info("Move " + pairSrcFilePath + " -> " + pairTargetFilePath);
dsMo.moveDatastoreFile(pairSrcFilePath, dcMo.getMor(), dsMo.getMor(), pairTargetFilePath, dcMo.getMor(), true);
}
}
}
} else {
@ -322,24 +353,17 @@ public class VmwareStorageLayoutHelper {
s_logger.warn("Unable to locate VMDK file: " + fileName);
}
fileName = volumeName + "-flat.vmdk";
fileFullPath = getLegacyDatastorePathFromVmdkFileName(dsMo, fileName);
if (!dsMo.fileExists(fileFullPath))
fileFullPath = dsMo.searchFileInSubFolders(fileName, false, excludeFolders);
if (fileFullPath != null) {
dsMo.deleteFile(fileFullPath, dcMo.getMor(), true, excludeFolders);
} else {
s_logger.warn("Unable to locate VMDK file: " + fileName);
}
fileName = volumeName + "-delta.vmdk";
fileFullPath = getLegacyDatastorePathFromVmdkFileName(dsMo, fileName);
if (!dsMo.fileExists(fileFullPath))
fileFullPath = dsMo.searchFileInSubFolders(fileName, false, excludeFolders);
if (fileFullPath != null) {
dsMo.deleteFile(fileFullPath, dcMo.getMor(), true, excludeFolders);
} else {
s_logger.warn("Unable to locate VMDK file: " + fileName);
List<String> vSphereFileExtensions = Arrays.asList(VsphereLinkedCloneExtensions.value().trim().split("\\s*,\\s*"));
vSphereFileExtensions.add("flat.vmdk");
for (String linkedCloneExtension : vSphereFileExtensions) {
fileFullPath = getLegacyDatastorePathFromVmdkFileName(dsMo, String.format("%s-%s", volumeName, linkedCloneExtension));
if (!dsMo.fileExists(fileFullPath))
fileFullPath = dsMo.searchFileInSubFolders(String.format("%s-%s", volumeName, linkedCloneExtension), false, excludeFolders);
if (fileFullPath != null) {
dsMo.deleteFile(fileFullPath, dcMo.getMor(), true, excludeFolders);
} else {
s_logger.warn("Unable to locate VMDK file: " + String.format("%s-%s", volumeName, linkedCloneExtension));
}
}
}
@ -364,4 +388,14 @@ public class VmwareStorageLayoutHelper {
public static String getVmwareDatastorePathFromVmdkFileName(DatastoreMO dsMo, String vmName, String vmdkFileName) throws Exception {
return String.format("[%s] %s/%s", dsMo.getName(), vmName, vmdkFileName);
}
@Override
public String getConfigComponentName() {
return VmwareStorageLayoutHelper.class.getSimpleName();
}
@Override
public ConfigKey<?>[] getConfigKeys() {
return new ConfigKey<?>[] {VsphereLinkedCloneExtensions};
}
}

View File

@ -671,7 +671,9 @@ public class VmwareStorageProcessor implements StorageProcessor {
managedStoragePoolRootVolumeName, VmwareStorageLayoutType.CLOUDSTACK_LEGACY, false);
dsMo.moveDatastoreFile(vmwareLayoutFilePair[0], dcMo.getMor(), dsMo.getMor(), legacyCloudStackLayoutFilePair[0], dcMo.getMor(), true);
dsMo.moveDatastoreFile(vmwareLayoutFilePair[1], dcMo.getMor(), dsMo.getMor(), legacyCloudStackLayoutFilePair[1], dcMo.getMor(), true);
for (int i=1; i<vmwareLayoutFilePair.length; i++) {
dsMo.moveDatastoreFile(vmwareLayoutFilePair[i], dcMo.getMor(), dsMo.getMor(), legacyCloudStackLayoutFilePair[i], dcMo.getMor(), true);
}
String folderToDelete = dsMo.getDatastorePath(managedStoragePoolRootVolumeName, true);
dsMo.deleteFolder(folderToDelete, dcMo.getMor());