volume-upload: added account level secondary storage resource limit checks
Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/75ae90b0 Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/75ae90b0 Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/75ae90b0 Branch: refs/heads/master Commit: 75ae90b0730b632127cba01f9a4fdeb3ad16e86a Parents: 0525e47 Author: Rajani Karuturi <rajanikarut...@gmail.com> Authored: Thu Apr 23 17:18:31 2015 +0530 Committer: Rajani Karuturi <rajanikarut...@gmail.com> Committed: Fri Apr 24 15:48:44 2015 +0530 ---------------------------------------------------------------------- .../TemplateOrVolumePostUploadCommand.java | 20 ++++++++ .../com/cloud/storage/VolumeApiServiceImpl.java | 2 + .../template/HypervisorTemplateAdapter.java | 2 + .../resource/NfsSecondaryStorageResource.java | 48 ++++++++++++++++++++ 4 files changed, 72 insertions(+) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cloudstack/blob/75ae90b0/core/src/org/apache/cloudstack/storage/command/TemplateOrVolumePostUploadCommand.java ---------------------------------------------------------------------- diff --git a/core/src/org/apache/cloudstack/storage/command/TemplateOrVolumePostUploadCommand.java b/core/src/org/apache/cloudstack/storage/command/TemplateOrVolumePostUploadCommand.java index 0a5f1d6..5d1e56b 100644 --- a/core/src/org/apache/cloudstack/storage/command/TemplateOrVolumePostUploadCommand.java +++ b/core/src/org/apache/cloudstack/storage/command/TemplateOrVolumePostUploadCommand.java @@ -49,6 +49,10 @@ public class TemplateOrVolumePostUploadCommand { String description; + private String defaultMaxAccountSecondaryStorage; + + private long accountId; + public TemplateOrVolumePostUploadCommand(long entityId, String entityUUID, String absolutePath, String checksum, String type, String name, String imageFormat, String dataTo, String dataToRole) { this.entityId = entityId; @@ -176,4 +180,20 @@ public class TemplateOrVolumePostUploadCommand { public void setDescription(String description) { this.description = description; } + + public void setDefaultMaxAccountSecondaryStorage(String defaultMaxAccountSecondaryStorage) { + this.defaultMaxAccountSecondaryStorage = defaultMaxAccountSecondaryStorage; + } + + public String getDefaultMaxAccountSecondaryStorage() { + return defaultMaxAccountSecondaryStorage; + } + + public void setAccountId(long accountId) { + this.accountId = accountId; + } + + public long getAccountId() { + return accountId; + } } http://git-wip-us.apache.org/repos/asf/cloudstack/blob/75ae90b0/server/src/com/cloud/storage/VolumeApiServiceImpl.java ---------------------------------------------------------------------- diff --git a/server/src/com/cloud/storage/VolumeApiServiceImpl.java b/server/src/com/cloud/storage/VolumeApiServiceImpl.java index d7000f7..7e12284 100644 --- a/server/src/com/cloud/storage/VolumeApiServiceImpl.java +++ b/server/src/com/cloud/storage/VolumeApiServiceImpl.java @@ -339,6 +339,8 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic command.setLocalPath(volumeStore.getLocalDownloadPath()); //using the existing max upload size configuration command.setMaxUploadSize(_configDao.getValue(Config.MaxUploadVolumeSize.key())); + command.setDefaultMaxAccountSecondaryStorage(_configDao.getValue(Config.DefaultMaxAccountSecondaryStorage.key())); + command.setAccountId(vol.getAccountId()); Gson gson = new GsonBuilder().create(); String metadata = EncryptionUtil.encodeData(gson.toJson(command), key); response.setMetadata(metadata); http://git-wip-us.apache.org/repos/asf/cloudstack/blob/75ae90b0/server/src/com/cloud/template/HypervisorTemplateAdapter.java ---------------------------------------------------------------------- diff --git a/server/src/com/cloud/template/HypervisorTemplateAdapter.java b/server/src/com/cloud/template/HypervisorTemplateAdapter.java index 265bc12..38a145b 100755 --- a/server/src/com/cloud/template/HypervisorTemplateAdapter.java +++ b/server/src/com/cloud/template/HypervisorTemplateAdapter.java @@ -270,6 +270,8 @@ public class HypervisorTemplateAdapter extends TemplateAdapterBase { templateOnStore.getDataStore().getRole().toString()); //using the existing max template size configuration payload.setMaxUploadSize(_configDao.getValue(Config.MaxTemplateAndIsoSize.key())); + payload.setDefaultMaxAccountSecondaryStorage(_configDao.getValue(Config.DefaultMaxAccountSecondaryStorage.key())); + payload.setAccountId(template.getAccountId()); payload.setRemoteEndPoint(ep.getPublicAddr()); payload.setRequiresHvm(template.requiresHvm()); payload.setDescription(template.getDisplayText()); http://git-wip-us.apache.org/repos/asf/cloudstack/blob/75ae90b0/services/secondary-storage/server/src/org/apache/cloudstack/storage/resource/NfsSecondaryStorageResource.java ---------------------------------------------------------------------- diff --git a/services/secondary-storage/server/src/org/apache/cloudstack/storage/resource/NfsSecondaryStorageResource.java b/services/secondary-storage/server/src/org/apache/cloudstack/storage/resource/NfsSecondaryStorageResource.java index 1cd69fc..bedd5c1 100755 --- a/services/secondary-storage/server/src/org/apache/cloudstack/storage/resource/NfsSecondaryStorageResource.java +++ b/services/secondary-storage/server/src/org/apache/cloudstack/storage/resource/NfsSecondaryStorageResource.java @@ -48,6 +48,7 @@ import javax.naming.ConfigurationException; import com.cloud.exception.InvalidParameterValueException; import com.cloud.storage.Storage; +import com.cloud.storage.template.TemplateConstants; import com.cloud.utils.EncryptionUtil; import com.google.gson.Gson; import com.google.gson.GsonBuilder; @@ -2633,6 +2634,7 @@ public class NfsSecondaryStorageResource extends ServerResourceBase implements S updateStateMapWithError(uuid, errorMessage); throw new InvalidParameterValueException(errorMessage); } + checkSecondaryStorageResourceLimit(cmd, contentLengthInGB); try { String absolutePath = cmd.getAbsolutePath(); uploadEntity = new UploadEntity(uuid, cmd.getEntityId(), UploadEntity.Status.IN_PROGRESS, cmd.getName(), absolutePath); @@ -2663,6 +2665,52 @@ public class NfsSecondaryStorageResource extends ServerResourceBase implements S return uploadEntity; } + private synchronized void checkSecondaryStorageResourceLimit(TemplateOrVolumePostUploadCommand cmd, int contentLengthInGB) { + String rootDir = this.getRootDir(cmd.getDataTo()) + File.separator; + long accountId = cmd.getAccountId(); + + long accountTemplateDirSize = 0; + File accountTemplateDir = new File(rootDir + getTemplatePathForAccount(accountId)); + if(accountTemplateDir.exists()) { + FileUtils.sizeOfDirectory(accountTemplateDir); + } + long accountVolumeDirSize = 0; + File accountVolumeDir = new File(rootDir + getVolumePathForAccount(accountId)); + if(accountVolumeDir.exists()) { + accountVolumeDirSize = FileUtils.sizeOfDirectory(accountVolumeDir); + } + long accountSnapshotDirSize = 0; + File accountSnapshotDir = new File(rootDir + getSnapshotPathForAccount(accountId)); + if(accountSnapshotDir.exists()) { + accountSnapshotDirSize = FileUtils.sizeOfDirectory(accountSnapshotDir); + } + s_logger.debug("accountTemplateDirSize: " + accountTemplateDirSize + " accountSnapshotDirSize: " +accountSnapshotDirSize + " accountVolumeDirSize: " + + accountVolumeDirSize); + + int accountDirSizeInGB = getSizeInGB(accountTemplateDirSize + accountSnapshotDirSize + accountVolumeDirSize); + int defaultMaxAccountSecondaryStorageInGB = Integer.parseInt(cmd.getDefaultMaxAccountSecondaryStorage()); + + if ((accountDirSizeInGB + contentLengthInGB) > defaultMaxAccountSecondaryStorageInGB) { + s_logger.error("accountDirSizeInGb: " + accountDirSizeInGB + " defaultMaxAccountSecondaryStorageInGB: " + defaultMaxAccountSecondaryStorageInGB + " contentLengthInGB:" + + contentLengthInGB); + String errorMessage = "Maximum number of resources of type secondary_storage for account has exceeded"; + updateStateMapWithError(cmd.getEntityUUID(), errorMessage); + throw new InvalidParameterValueException(errorMessage); + } + } + + private String getVolumePathForAccount(long accountId) { + return TemplateConstants.DEFAULT_VOLUME_ROOT_DIR + "/" + accountId; + } + + private String getTemplatePathForAccount(long accountId) { + return TemplateConstants.DEFAULT_TMPLT_ROOT_DIR + "/" + TemplateConstants.DEFAULT_TMPLT_FIRST_LEVEL_DIR + accountId; + } + + private String getSnapshotPathForAccount(long accountId) { + return TemplateConstants.DEFAULT_SNAPSHOT_ROOT_DIR + "/" + accountId; + } + private boolean isOneTimePostUrlUsed(TemplateOrVolumePostUploadCommand cmd) { String uuid = cmd.getEntityUUID(); String uploadPath = this.getRootDir(cmd.getDataTo()) + File.separator + cmd.getAbsolutePath();