mirror of
				https://github.com/apache/cloudstack.git
				synced 2025-10-26 08:42:29 +01:00 
			
		
		
		
	CLOUDSTACK-6941: Can't choose storage for the volume, when attaching uploaded data volume to VM
Changes: - Only way to choose a certain storage pool is by using disk_offering_tags - Added a parameter to take in a disk offering Id. - Admin will have to create a custom sized disk offering and tag it as necessary for the user - This custom offering Id should be passed during uploadVolume to associate the volume with this disk offering
This commit is contained in:
		
							parent
							
								
									569e94908b
								
							
						
					
					
						commit
						05c01a7dc9
					
				| @ -25,6 +25,7 @@ import org.apache.cloudstack.api.BaseAsyncCmd; | ||||
| import org.apache.cloudstack.api.Parameter; | ||||
| import org.apache.cloudstack.api.ResponseObject.ResponseView; | ||||
| import org.apache.cloudstack.api.ServerApiException; | ||||
| import org.apache.cloudstack.api.response.DiskOfferingResponse; | ||||
| import org.apache.cloudstack.api.response.DomainResponse; | ||||
| import org.apache.cloudstack.api.response.ProjectResponse; | ||||
| import org.apache.cloudstack.api.response.VolumeResponse; | ||||
| @ -89,6 +90,9 @@ public class UploadVolumeCmd extends BaseAsyncCmd { | ||||
|     @Parameter(name = ApiConstants.PROJECT_ID, type = CommandType.UUID, entityType = ProjectResponse.class, description = "Upload volume for the project") | ||||
|     private Long projectId; | ||||
| 
 | ||||
|     @Parameter(name = ApiConstants.DISK_OFFERING_ID, required = false, type = CommandType.UUID, entityType = DiskOfferingResponse.class, description = "the ID of the disk offering. This must be a custom sized offering since during uploadVolume volume size is unknown.") | ||||
|     private Long diskOfferingId; | ||||
| 
 | ||||
|     ///////////////////////////////////////////////////// | ||||
|     /////////////////// Accessors /////////////////////// | ||||
|     ///////////////////////////////////////////////////// | ||||
| @ -125,6 +129,10 @@ public class UploadVolumeCmd extends BaseAsyncCmd { | ||||
|         return imageStoreUuid; | ||||
|     } | ||||
| 
 | ||||
|     public Long getDiskOfferingId() { | ||||
|         return diskOfferingId; | ||||
|     } | ||||
| 
 | ||||
|     ///////////////////////////////////////////////////// | ||||
|     /////////////// API Implementation/////////////////// | ||||
|     ///////////////////////////////////////////////////// | ||||
|  | ||||
| @ -247,12 +247,13 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic | ||||
|         String volumeName = cmd.getVolumeName(); | ||||
|         String url = cmd.getUrl(); | ||||
|         String format = cmd.getFormat(); | ||||
|         Long diskOfferingId = cmd.getDiskOfferingId(); | ||||
|         String imageStoreUuid = cmd.getImageStoreUuid(); | ||||
|         DataStore store = _tmpltMgr.getImageStore(imageStoreUuid, zoneId); | ||||
| 
 | ||||
|         validateVolume(caller, ownerId, zoneId, volumeName, url, format); | ||||
|         validateVolume(caller, ownerId, zoneId, volumeName, url, format, diskOfferingId); | ||||
| 
 | ||||
|         VolumeVO volume = persistVolume(owner, zoneId, volumeName, url, cmd.getFormat()); | ||||
|         VolumeVO volume = persistVolume(owner, zoneId, volumeName, url, cmd.getFormat(), diskOfferingId); | ||||
| 
 | ||||
|         VolumeInfo vol = volFactory.getVolume(volume.getId()); | ||||
| 
 | ||||
| @ -263,13 +264,15 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic | ||||
|         return volume; | ||||
|     } | ||||
| 
 | ||||
|     private boolean validateVolume(Account caller, long ownerId, Long zoneId, String volumeName, String url, String format) throws ResourceAllocationException { | ||||
|     private boolean validateVolume(Account caller, long ownerId, Long zoneId, String volumeName, String url, | ||||
|             String format, Long diskOfferingId) throws ResourceAllocationException { | ||||
| 
 | ||||
|         // permission check | ||||
|         _accountMgr.checkAccess(caller, null, true, _accountMgr.getActiveAccountById(ownerId)); | ||||
|         Account volumeOwner = _accountMgr.getActiveAccountById(ownerId); | ||||
|         _accountMgr.checkAccess(caller, null, true, volumeOwner); | ||||
| 
 | ||||
|         // Check that the resource limit for volumes won't be exceeded | ||||
|         _resourceLimitMgr.checkResourceLimit(_accountMgr.getAccount(ownerId), ResourceType.volume); | ||||
|         _resourceLimitMgr.checkResourceLimit(volumeOwner, ResourceType.volume); | ||||
| 
 | ||||
|         // Verify that zone exists | ||||
|         DataCenterVO zone = _dcDao.findById(zoneId); | ||||
| @ -316,9 +319,28 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic | ||||
|         } | ||||
|         UriUtils.validateUrl(url); | ||||
| 
 | ||||
| 
 | ||||
|         // Check that the resource limit for secondary storage won't be exceeded | ||||
|         _resourceLimitMgr.checkResourceLimit(_accountMgr.getAccount(ownerId), ResourceType.secondary_storage, UriUtils.getRemoteSize(url)); | ||||
| 
 | ||||
|         // Check that the the disk offering specified is valid | ||||
|         if (diskOfferingId != null) { | ||||
|             DiskOfferingVO diskOffering = _diskOfferingDao.findById(diskOfferingId); | ||||
|             if ((diskOffering == null) || diskOffering.getRemoved() != null | ||||
|                     || !DiskOfferingVO.Type.Disk.equals(diskOffering.getType())) { | ||||
|                 throw new InvalidParameterValueException("Please specify a valid disk offering."); | ||||
|             } | ||||
|             if (!diskOffering.isCustomized()) { | ||||
|                 throw new InvalidParameterValueException("Please specify a custom sized disk offering."); | ||||
|             } | ||||
| 
 | ||||
|             if (diskOffering.getDomainId() == null) { | ||||
|                 // do nothing as offering is public | ||||
|             } else { | ||||
|                 _configMgr.checkDiskOfferingAccess(volumeOwner, diskOffering); | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         return false; | ||||
|     } | ||||
| 
 | ||||
| @ -327,7 +349,8 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic | ||||
|     } | ||||
| 
 | ||||
|     @DB | ||||
|     protected VolumeVO persistVolume(final Account owner, final Long zoneId, final String volumeName, final String url, final String format) { | ||||
|     protected VolumeVO persistVolume(final Account owner, final Long zoneId, final String volumeName, final String url, | ||||
|             final String format, final Long diskOfferingId) { | ||||
|         return Transaction.execute(new TransactionCallback<VolumeVO>() { | ||||
|             @Override | ||||
|             public VolumeVO doInTransaction(TransactionStatus status) { | ||||
| @ -339,8 +362,13 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic | ||||
|                 // TODO Decide if this is valid or whether  throwing a CloudRuntimeException is more appropriate | ||||
|                 volume.setAccountId((owner == null) ? Account.ACCOUNT_ID_SYSTEM : owner.getAccountId()); | ||||
|                 volume.setDomainId((owner == null) ? Domain.ROOT_DOMAIN : owner.getDomainId()); | ||||
|         long diskOfferingId = _diskOfferingDao.findByUniqueName("Cloud.com-Custom").getId(); | ||||
| 
 | ||||
|                 if (diskOfferingId == null) { | ||||
|                     long defaultDiskOfferingId = _diskOfferingDao.findByUniqueName("Cloud.com-Custom").getId(); | ||||
|                     volume.setDiskOfferingId(defaultDiskOfferingId); | ||||
|                 } else { | ||||
|                     volume.setDiskOfferingId(diskOfferingId); | ||||
|                 } | ||||
|         // volume.setSize(size); | ||||
|         volume.setInstanceId(null); | ||||
|         volume.setUpdated(new Date()); | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user