Skip to content

Commit abfa929

Browse files
committed
merge conflicts 4.19 -> main
2 parents 1303a4f + a93f715 commit abfa929

File tree

10 files changed

+87
-47
lines changed

10 files changed

+87
-47
lines changed

plugins/hypervisors/kvm/src/main/java/com/cloud/hypervisor/kvm/storage/KVMPhysicalDisk.java

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,15 +18,18 @@
1818

1919
import org.apache.cloudstack.utils.qemu.QemuImg.PhysicalDiskFormat;
2020
import org.apache.cloudstack.utils.qemu.QemuObject;
21+
import org.apache.cloudstack.utils.reflectiontostringbuilderutils.ReflectionToStringBuilderUtils;
2122
import org.apache.commons.lang3.StringUtils;
2223

2324
import java.util.ArrayList;
2425
import java.util.List;
2526

2627
public class KVMPhysicalDisk {
2728
private String path;
28-
private String name;
29-
private KVMStoragePool pool;
29+
private final String name;
30+
private final KVMStoragePool pool;
31+
private String dispName;
32+
private String vmName;
3033
private boolean useAsTemplate;
3134

3235
public static String RBDStringBuilder(String monHost, int monPort, String authUserName, String authSecret, String image) {
@@ -81,7 +84,9 @@ public KVMPhysicalDisk(String path, String name, KVMStoragePool pool) {
8184

8285
@Override
8386
public String toString() {
84-
return "KVMPhysicalDisk [path=" + path + ", name=" + name + ", pool=" + pool + ", format=" + format + ", size=" + size + ", virtualSize=" + virtualSize + "]";
87+
return String.format("KVMPhysicalDisk %s",
88+
ReflectionToStringBuilderUtils.reflectOnlySelectedFields(
89+
this, "path", "name", "pool", "format", "size", "virtualSize", "dispName", "vmName"));
8590
}
8691

8792
public void setFormat(PhysicalDiskFormat format) {
@@ -135,4 +140,20 @@ public void setQemuEncryptFormat(QemuObject.EncryptFormat format) {
135140
public void setUseAsTemplate() { this.useAsTemplate = true; }
136141

137142
public boolean useAsTemplate() { return this.useAsTemplate; }
143+
144+
public String getDispName() {
145+
return dispName;
146+
}
147+
148+
public void setDispName(String dispName) {
149+
this.dispName = dispName;
150+
}
151+
152+
public String getVmName() {
153+
return vmName;
154+
}
155+
156+
public void setVmName(String vmName) {
157+
this.vmName = vmName;
158+
}
138159
}

plugins/hypervisors/kvm/src/main/java/com/cloud/hypervisor/kvm/storage/KVMStorageProcessor.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -435,6 +435,7 @@ public Answer cloneVolumeFromBaseTemplate(final CopyCommand cmd) {
435435
if (!storagePoolMgr.connectPhysicalDisk(primaryStore.getPoolType(), primaryStore.getUuid(), path, details)) {
436436
logger.warn("Failed to connect new volume at path: " + path + ", in storage pool id: " + primaryStore.getUuid());
437437
}
438+
BaseVol.setDispName(template.getName());
438439

439440
vol = storagePoolMgr.copyPhysicalDisk(BaseVol, path != null ? path : volume.getUuid(), primaryPool, cmd.getWaitInMillSeconds(), null, volume.getPassphrase(), volume.getProvisioningType());
440441

@@ -527,6 +528,8 @@ public Answer copyVolumeFromImageCacheToPrimary(final CopyCommand cmd) {
527528
final KVMPhysicalDisk volume = secondaryStoragePool.getPhysicalDisk(srcVolumeName);
528529

529530
volume.setFormat(PhysicalDiskFormat.valueOf(srcFormat.toString()));
531+
volume.setDispName(srcVol.getName());
532+
volume.setVmName(srcVol.getVmName());
530533

531534
final KVMPhysicalDisk newDisk = storagePoolMgr.copyPhysicalDisk(volume, path != null ? path : volumeName, primaryPool, cmd.getWaitInMillSeconds());
532535

@@ -2492,6 +2495,8 @@ public Answer copyVolumeFromPrimaryToPrimary(CopyCommand cmd) {
24922495
}
24932496

24942497
volume.setFormat(PhysicalDiskFormat.valueOf(srcFormat.toString()));
2498+
volume.setDispName(srcVol.getName());
2499+
volume.setVmName(srcVol.getVmName());
24952500

24962501
String destVolumeName = null;
24972502
if (destPrimaryStore.isManaged()) {

plugins/hypervisors/kvm/src/main/java/com/cloud/hypervisor/kvm/storage/LibvirtStorageAdaptor.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1409,7 +1409,10 @@ public KVMPhysicalDisk copyPhysicalDisk(KVMPhysicalDisk disk, String name, KVMSt
14091409
*/
14101410

14111411
KVMStoragePool srcPool = disk.getPool();
1412-
PhysicalDiskFormat sourceFormat = disk.getFormat();
1412+
/* Linstor images are always stored as RAW, but Linstor uses qcow2 in DB,
1413+
to support snapshots(backuped) as qcow2 files. */
1414+
PhysicalDiskFormat sourceFormat = srcPool.getType() != StoragePoolType.Linstor ?
1415+
disk.getFormat() : PhysicalDiskFormat.RAW;
14131416
String sourcePath = disk.getPath();
14141417

14151418
KVMPhysicalDisk newDisk;

plugins/storage/volume/linstor/src/main/java/com/cloud/hypervisor/kvm/storage/LinstorStorageAdaptor.java

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -521,6 +521,15 @@ public KVMPhysicalDisk copyPhysicalDisk(KVMPhysicalDisk disk, String name, KVMSt
521521
final KVMPhysicalDisk dstDisk = destPools.createPhysicalDisk(
522522
name, QemuImg.PhysicalDiskFormat.RAW, provisioningType, disk.getVirtualSize(), null);
523523

524+
final DevelopersApi api = getLinstorAPI(destPools);
525+
final String rscName = LinstorUtil.RSC_PREFIX + name;
526+
try {
527+
LinstorUtil.applyAuxProps(api, rscName, disk.getDispName(), disk.getVmName());
528+
} catch (ApiException apiExc) {
529+
s_logger.error(String.format("Error setting aux properties for %s", rscName));
530+
logLinstorAnswers(apiExc.getApiCallRcList());
531+
}
532+
524533
logger.debug(String.format("Linstor.copyPhysicalDisk: dstPath: %s", dstDisk.getPath()));
525534
final QemuImgFile destFile = new QemuImgFile(dstDisk.getPath());
526535
destFile.setFormat(dstDisk.getFormat());

plugins/storage/volume/linstor/src/main/java/org/apache/cloudstack/storage/datastore/driver/LinstorPrimaryDataStoreDriverImpl.java

Lines changed: 9 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,6 @@
2626
import com.linbit.linstor.api.model.ResourceDefinitionCloneRequest;
2727
import com.linbit.linstor.api.model.ResourceDefinitionCloneStarted;
2828
import com.linbit.linstor.api.model.ResourceDefinitionCreate;
29-
import com.linbit.linstor.api.model.ResourceDefinitionModify;
3029
import com.linbit.linstor.api.model.ResourceGroupSpawn;
3130
import com.linbit.linstor.api.model.ResourceMakeAvailable;
3231
import com.linbit.linstor.api.model.Snapshot;
@@ -62,8 +61,8 @@
6261
import com.cloud.storage.DataStoreRole;
6362
import com.cloud.storage.ResizeVolumePayload;
6463
import com.cloud.storage.SnapshotVO;
65-
import com.cloud.storage.Storage.StoragePoolType;
6664
import com.cloud.storage.Storage;
65+
import com.cloud.storage.Storage.StoragePoolType;
6766
import com.cloud.storage.StorageManager;
6867
import com.cloud.storage.StoragePool;
6968
import com.cloud.storage.VMTemplateStoragePoolVO;
@@ -390,27 +389,6 @@ private void applyQoSSettings(StoragePoolVO storagePool, DevelopersApi api, Stri
390389
}
391390
}
392391

393-
private void applyAuxProps(DevelopersApi api, String rscName, String dispName, String vmName)
394-
throws ApiException
395-
{
396-
ResourceDefinitionModify rdm = new ResourceDefinitionModify();
397-
Properties props = new Properties();
398-
if (dispName != null)
399-
{
400-
props.put("Aux/cs-name", dispName);
401-
}
402-
if (vmName != null)
403-
{
404-
props.put("Aux/cs-vm-name", vmName);
405-
}
406-
if (!props.isEmpty())
407-
{
408-
rdm.setOverrideProps(props);
409-
ApiCallRcList answers = api.resourceDefinitionModify(rscName, rdm);
410-
checkLinstorAnswersThrow(answers);
411-
}
412-
}
413-
414392
private String getRscGrp(StoragePoolVO storagePoolVO) {
415393
return storagePoolVO.getUserInfo() != null && !storagePoolVO.getUserInfo().isEmpty() ?
416394
storagePoolVO.getUserInfo() : "DfltRscGrp";
@@ -428,7 +406,8 @@ private String createResourceBase(
428406
ApiCallRcList answers = api.resourceGroupSpawn(rscGrp, rscGrpSpawn);
429407
checkLinstorAnswersThrow(answers);
430408

431-
applyAuxProps(api, rscName, volName, vmName);
409+
answers = LinstorUtil.applyAuxProps(api, rscName, volName, vmName);
410+
checkLinstorAnswersThrow(answers);
432411

433412
return LinstorUtil.getDevicePath(api, rscName);
434413
} catch (ApiException apiEx)
@@ -499,7 +478,8 @@ private String cloneResource(long csCloneId, VolumeInfo volumeInfo, StoragePoolV
499478
if (volumeInfo.getSize() != null && volumeInfo.getSize() > 0) {
500479
resizeResource(linstorApi, rscName, volumeInfo.getSize());
501480
}
502-
applyAuxProps(linstorApi, rscName, volumeInfo.getName(), volumeInfo.getAttachedVmName());
481+
482+
LinstorUtil.applyAuxProps(linstorApi, rscName, volumeInfo.getName(), volumeInfo.getAttachedVmName());
503483
applyQoSSettings(storagePoolVO, linstorApi, rscName, volumeInfo.getMaxIops());
504484

505485
return LinstorUtil.getDevicePath(linstorApi, rscName);
@@ -551,7 +531,7 @@ private String createResourceFromSnapshot(long csSnapshotId, String rscName, Sto
551531
answers = linstorApi.resourceSnapshotRestore(cloneRes, snapName, snapshotRestore);
552532
checkLinstorAnswersThrow(answers);
553533

554-
applyAuxProps(linstorApi, rscName, volumeVO.getName(), null);
534+
LinstorUtil.applyAuxProps(linstorApi, rscName, volumeVO.getName(), null);
555535
applyQoSSettings(storagePoolVO, linstorApi, rscName, volumeVO.getMaxIops());
556536

557537
return LinstorUtil.getDevicePath(linstorApi, rscName);
@@ -833,7 +813,7 @@ public void copyAsync(DataObject srcData, DataObject dstData, AsyncCompletionCal
833813
VolumeInfo volume = sinfo.getBaseVolume();
834814
deleteSnapshot(
835815
srcData.getDataStore(),
836-
LinstorUtil.RSC_PREFIX + volume.getUuid(),
816+
LinstorUtil.RSC_PREFIX + volume.getPath(),
837817
LinstorUtil.RSC_PREFIX + sinfo.getUuid());
838818
}
839819
res = new CopyCommandResult(null, answer);
@@ -969,7 +949,7 @@ private Answer copyVolume(DataObject srcData, DataObject dstData) {
969949
VolumeInfo srcVolInfo = (VolumeInfo) srcData;
970950
final StoragePoolVO pool = _storagePoolDao.findById(srcVolInfo.getDataStore().getId());
971951
final DevelopersApi api = LinstorUtil.getLinstorAPI(pool.getHostAddress());
972-
final String rscName = LinstorUtil.RSC_PREFIX + srcVolInfo.getUuid();
952+
final String rscName = LinstorUtil.RSC_PREFIX + srcVolInfo.getPath();
973953

974954
VolumeObjectTO to = (VolumeObjectTO) srcVolInfo.getTO();
975955
// patch source format
@@ -1082,7 +1062,7 @@ protected Answer copySnapshot(DataObject srcData, DataObject destData) {
10821062
options.put("volumeSize", snapshotObject.getBaseVolume().getSize() + "");
10831063

10841064
try {
1085-
final String rscName = LinstorUtil.RSC_PREFIX + snapshotObject.getBaseVolume().getUuid();
1065+
final String rscName = LinstorUtil.RSC_PREFIX + snapshotObject.getBaseVolume().getPath();
10861066
String snapshotName = setCorrectSnapshotPath(api, rscName, snapshotObject);
10871067

10881068
CopyCommand cmd = new LinstorBackupSnapshotCommand(

plugins/storage/volume/linstor/src/main/java/org/apache/cloudstack/storage/datastore/util/LinstorUtil.java

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,10 @@
2222
import com.linbit.linstor.api.model.ApiCallRc;
2323
import com.linbit.linstor.api.model.ApiCallRcList;
2424
import com.linbit.linstor.api.model.Node;
25+
import com.linbit.linstor.api.model.Properties;
2526
import com.linbit.linstor.api.model.ProviderKind;
2627
import com.linbit.linstor.api.model.Resource;
28+
import com.linbit.linstor.api.model.ResourceDefinitionModify;
2729
import com.linbit.linstor.api.model.ResourceGroup;
2830
import com.linbit.linstor.api.model.ResourceWithVolumes;
2931
import com.linbit.linstor.api.model.StoragePool;
@@ -240,4 +242,26 @@ public static String getDevicePath(DevelopersApi api, String rscName) throws Api
240242
LOGGER.error(errMsg);
241243
throw new CloudRuntimeException("Linstor: " + errMsg);
242244
}
245+
246+
public static ApiCallRcList applyAuxProps(DevelopersApi api, String rscName, String dispName, String vmName)
247+
throws ApiException
248+
{
249+
ResourceDefinitionModify rdm = new ResourceDefinitionModify();
250+
Properties props = new Properties();
251+
if (dispName != null)
252+
{
253+
props.put("Aux/cs-name", dispName);
254+
}
255+
if (vmName != null)
256+
{
257+
props.put("Aux/cs-vm-name", vmName);
258+
}
259+
ApiCallRcList answers = new ApiCallRcList();
260+
if (!props.isEmpty())
261+
{
262+
rdm.setOverrideProps(props);
263+
answers = api.resourceDefinitionModify(rscName, rdm);
264+
}
265+
return answers;
266+
}
243267
}

plugins/storage/volume/linstor/src/main/java/org/apache/cloudstack/storage/snapshot/LinstorVMSnapshotStrategy.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -240,7 +240,7 @@ public boolean deleteVMSnapshot(VMSnapshot vmSnapshot) {
240240
final String snapshotName = vmSnapshotVO.getName();
241241
final List<String> failedToDelete = new ArrayList<>();
242242
for (VolumeObjectTO volumeObjectTO : volumeTOs) {
243-
final String rscName = LinstorUtil.RSC_PREFIX + volumeObjectTO.getUuid();
243+
final String rscName = LinstorUtil.RSC_PREFIX + volumeObjectTO.getPath();
244244
String err = linstorDeleteSnapshot(api, rscName, snapshotName);
245245

246246
if (err != null)
@@ -293,7 +293,7 @@ private boolean revertVMSnapshotOperation(VMSnapshot vmSnapshot, long userVmId)
293293
final String snapshotName = vmSnapshotVO.getName();
294294

295295
for (VolumeObjectTO volumeObjectTO : volumeTOs) {
296-
final String rscName = LinstorUtil.RSC_PREFIX + volumeObjectTO.getUuid();
296+
final String rscName = LinstorUtil.RSC_PREFIX + volumeObjectTO.getPath();
297297
String err = linstorRevertSnapshot(api, rscName, snapshotName);
298298
if (err != null) {
299299
throw new CloudRuntimeException(String.format(

server/src/main/java/com/cloud/storage/VolumeApiServiceImpl.java

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -126,8 +126,6 @@
126126
import com.cloud.agent.api.to.DataTO;
127127
import com.cloud.agent.api.to.DiskTO;
128128
import com.cloud.api.ApiDBUtils;
129-
import com.cloud.api.query.dao.ServiceOfferingJoinDao;
130-
import com.cloud.api.query.vo.ServiceOfferingJoinVO;
131129
import com.cloud.configuration.Config;
132130
import com.cloud.configuration.ConfigurationManager;
133131
import com.cloud.configuration.Resource.ResourceType;
@@ -274,8 +272,6 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic
274272
@Inject
275273
private ServiceOfferingDetailsDao _serviceOfferingDetailsDao;
276274
@Inject
277-
private ServiceOfferingJoinDao serviceOfferingJoinDao;
278-
@Inject
279275
private UserVmDao _userVmDao;
280276
@Inject
281277
private UserVmDetailsDao userVmDetailsDao;
@@ -1362,8 +1358,7 @@ protected boolean isNotPossibleToResize(VolumeVO volume, DiskOfferingVO diskOffe
13621358
boolean isNotIso = format != null && format != ImageFormat.ISO;
13631359
boolean isRoot = Volume.Type.ROOT.equals(volume.getVolumeType());
13641360

1365-
ServiceOfferingJoinVO serviceOfferingView = serviceOfferingJoinDao.findById(diskOffering.getId());
1366-
boolean isOfferingEnforcingRootDiskSize = serviceOfferingView != null && serviceOfferingView.getRootDiskSize() > 0;
1361+
boolean isOfferingEnforcingRootDiskSize = diskOffering.isComputeOnly() && diskOffering.getDiskSize() > 0;
13671362

13681363
return isOfferingEnforcingRootDiskSize && isRoot && isNotIso;
13691364
}

server/src/test/java/com/cloud/storage/VolumeApiServiceImplTest.java

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,6 @@
8585
import org.springframework.test.util.ReflectionTestUtils;
8686

8787
import com.cloud.api.query.dao.ServiceOfferingJoinDao;
88-
import com.cloud.api.query.vo.ServiceOfferingJoinVO;
8988
import com.cloud.configuration.Resource;
9089
import com.cloud.configuration.Resource.ResourceType;
9190
import com.cloud.dc.DataCenterVO;
@@ -1366,10 +1365,8 @@ private void prepareAndRunTestOfIsNotPossibleToResize(Type volumeType, Long root
13661365

13671366
when(volume.getTemplateId()).thenReturn(1l);
13681367
DiskOfferingVO diskOffering = Mockito.mock(DiskOfferingVO.class);
1369-
1370-
ServiceOfferingJoinVO serviceOfferingJoinVO = Mockito.mock(ServiceOfferingJoinVO.class);
1371-
when(serviceOfferingJoinVO.getRootDiskSize()).thenReturn(rootDisk);
1372-
when(serviceOfferingJoinDao.findById(anyLong())).thenReturn(serviceOfferingJoinVO);
1368+
when(diskOffering.isComputeOnly()).thenReturn(true);
1369+
when(diskOffering.getDiskSize()).thenReturn(rootDisk);
13731370

13741371
VMTemplateVO template = Mockito.mock(VMTemplateVO.class);
13751372
when(template.getFormat()).thenReturn(imageFormat);

ui/src/config/section/compute.js

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -122,7 +122,13 @@ export default {
122122
groupAction: true,
123123
popup: true,
124124
groupMap: (selection, values) => { return selection.map(x => { return { id: x, considerlasthost: values.considerlasthost } }) },
125-
args: ['considerlasthost'],
125+
args: (record, store) => {
126+
if (['Admin'].includes(store.userInfo.roletype)) {
127+
return ['considerlasthost']
128+
}
129+
130+
return []
131+
},
126132
show: (record) => { return ['Stopped'].includes(record.state) },
127133
component: shallowRef(defineAsyncComponent(() => import('@/views/compute/StartVirtualMachine.vue')))
128134
},

0 commit comments

Comments
 (0)