diff --git a/api/src/com/cloud/storage/StorageService.java b/api/src/com/cloud/storage/StorageService.java
index ee1a9565be4..665abcbfc94 100644
--- a/api/src/com/cloud/storage/StorageService.java
+++ b/api/src/com/cloud/storage/StorageService.java
@@ -23,6 +23,7 @@ import org.apache.cloudstack.api.command.admin.storage.CancelPrimaryStorageMaint
import org.apache.cloudstack.api.command.admin.storage.CreateStoragePoolCmd;
import org.apache.cloudstack.api.command.admin.storage.DeleteImageStoreCmd;
import org.apache.cloudstack.api.command.admin.storage.DeletePoolCmd;
+import org.apache.cloudstack.api.command.admin.storage.EnableImageStoreCmd;
import org.apache.cloudstack.api.command.admin.storage.UpdateStoragePoolCmd;
import com.cloud.exception.DiscoveryException;
@@ -91,4 +92,5 @@ public interface StorageService{
ImageStore discoverImageStore(AddImageStoreCmd cmd) throws IllegalArgumentException, DiscoveryException, InvalidParameterValueException;
+ ImageStore enableImageStore(EnableImageStoreCmd cmd);
}
diff --git a/api/src/org/apache/cloudstack/api/command/admin/storage/EnableImageStoreCmd.java b/api/src/org/apache/cloudstack/api/command/admin/storage/EnableImageStoreCmd.java
new file mode 100644
index 00000000000..7586fa9be18
--- /dev/null
+++ b/api/src/org/apache/cloudstack/api/command/admin/storage/EnableImageStoreCmd.java
@@ -0,0 +1,89 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package org.apache.cloudstack.api.command.admin.storage;
+
+import javax.inject.Inject;
+
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AccountResponse;
+import org.apache.cloudstack.api.response.DomainResponse;
+import org.apache.cloudstack.api.response.ImageStoreResponse;
+import org.apache.cloudstack.region.RegionService;
+import org.apache.log4j.Logger;
+
+import com.cloud.storage.ImageStore;
+import com.cloud.user.Account;
+
+@APICommand(name = "enableImageStore", description="Enable an image store", responseObject=ImageStoreResponse.class)
+public class EnableImageStoreCmd extends BaseCmd {
+ public static final Logger s_logger = Logger.getLogger(EnableImageStoreCmd.class.getName());
+ private static final String s_name = "enableimagestoreresponse";
+
+ /////////////////////////////////////////////////////
+ //////////////// API parameters /////////////////////
+ /////////////////////////////////////////////////////
+ @Parameter(name=ApiConstants.ID, type=CommandType.UUID, entityType=ImageStoreResponse.class,
+ description="Image Store id")
+ private Long id;
+
+ @Parameter(name=ApiConstants.NAME, type=CommandType.STRING, description="Enables specified image store.")
+ private String storeName;
+
+
+ /////////////////////////////////////////////////////
+ /////////////////// Accessors ///////////////////////
+ /////////////////////////////////////////////////////
+
+ public Long getId() {
+ return id;
+ }
+
+ public String getStoreName() {
+ return storeName;
+ }
+
+ /////////////////////////////////////////////////////
+ /////////////// API Implementation///////////////////
+ /////////////////////////////////////////////////////
+
+ @Override
+ public String getCommandName() {
+ return s_name;
+ }
+
+ @Override
+ public long getEntityOwnerId() {
+ return Account.ACCOUNT_ID_SYSTEM;
+ }
+
+ @Override
+ public void execute(){
+ ImageStore result = _storageService.enableImageStore(this);
+ if (result != null){
+ ImageStoreResponse response = _responseGenerator.createImageStoreResponse(result);
+ response.setResponseName(getCommandName());
+ this.setResponseObject(response);
+ } else {
+ throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to enable image store");
+ }
+ }
+}
diff --git a/client/pom.xml b/client/pom.xml
index 9323d0fb20f..39f1cb0d1a6 100644
--- a/client/pom.xml
+++ b/client/pom.xml
@@ -224,6 +224,21 @@
cloud-plugin-storage-volume-default
${project.version}
+
+ org.apache.cloudstack
+ cloud-plugin-storage-image-default
+ ${project.version}
+
+
+ org.apache.cloudstack
+ cloud-plugin-storage-image-s3
+ ${project.version}
+
+
+ org.apache.cloudstack
+ cloud-plugin-storage-image-swift
+ ${project.version}
+
org.apache.cloudstack
cloud-plugin-syslog-alerts
diff --git a/client/tomcatconf/applicationContext.xml.in b/client/tomcatconf/applicationContext.xml.in
index 7bf45a24715..d8bb30abbc0 100644
--- a/client/tomcatconf/applicationContext.xml.in
+++ b/client/tomcatconf/applicationContext.xml.in
@@ -190,7 +190,7 @@
-
+
@@ -223,8 +223,12 @@
-
-
+
+
+
+
+
+
@@ -270,7 +274,7 @@
-
+
@@ -713,7 +717,6 @@
-
@@ -732,6 +735,7 @@
+
@@ -739,8 +743,7 @@
-
-
+
diff --git a/engine/api/src/org/apache/cloudstack/storage/datastore/db/ImageStoreDao.java b/engine/api/src/org/apache/cloudstack/storage/datastore/db/ImageStoreDao.java
index a81fa9c0bc1..1c307664a75 100644
--- a/engine/api/src/org/apache/cloudstack/storage/datastore/db/ImageStoreDao.java
+++ b/engine/api/src/org/apache/cloudstack/storage/datastore/db/ImageStoreDao.java
@@ -22,4 +22,6 @@ import com.cloud.utils.db.GenericDao;
public interface ImageStoreDao extends GenericDao {
public ImageStoreVO findByName(String name);
+
+ public ImageStoreVO findEnabledStore();
}
diff --git a/engine/storage/src/org/apache/cloudstack/storage/image/db/ImageStoreDaoImpl.java b/engine/storage/src/org/apache/cloudstack/storage/image/db/ImageStoreDaoImpl.java
index 2becada51a1..8aa5079e46b 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/image/db/ImageStoreDaoImpl.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/image/db/ImageStoreDaoImpl.java
@@ -18,11 +18,22 @@
*/
package org.apache.cloudstack.storage.image.db;
+import java.util.Map;
+
+import javax.naming.ConfigurationException;
+
import org.apache.cloudstack.storage.datastore.db.ImageStoreDao;
import org.apache.cloudstack.storage.datastore.db.ImageStoreVO;
+import org.apache.cloudstack.storage.datastore.db.SnapshotDataStoreVO;
+import org.apache.log4j.Logger;
import org.springframework.stereotype.Component;
+import com.cloud.storage.ImageStore;
+import com.cloud.user.AccountVO;
+import com.cloud.utils.db.DB;
import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
import com.cloud.utils.db.SearchCriteria2;
import com.cloud.utils.db.SearchCriteriaService;
import com.cloud.utils.db.SearchCriteria.Op;
@@ -30,11 +41,41 @@ import com.cloud.utils.db.SearchCriteria.Op;
@Component
public class ImageStoreDaoImpl extends GenericDaoBase implements ImageStoreDao {
+ private static final Logger s_logger = Logger.getLogger(ImageStoreDaoImpl.class);
+ private SearchBuilder nameSearch;
+ private SearchBuilder enableSearch;
+
+
@Override
- public ImageStoreVO findByName(String name) {
- SearchCriteriaService sc = SearchCriteria2.create(ImageStoreVO.class);
- sc.addAnd(sc.getEntity().getName(), Op.EQ, name);
- return sc.find();
+ public boolean configure(String name, Map params) throws ConfigurationException {
+ super.configure(name, params);
+
+ nameSearch = createSearchBuilder();
+ nameSearch.and("name", nameSearch.entity().getName(), SearchCriteria.Op.EQ);
+ nameSearch.done();
+
+
+ enableSearch = createSearchBuilder();
+ enableSearch.and("state", enableSearch.entity().getState(), SearchCriteria.Op.EQ);
+ enableSearch.done();
+
+ return true;
}
+ @Override
+ public ImageStoreVO findByName(String name) {
+ SearchCriteria sc = nameSearch.create();
+ sc.setParameters("name", name);
+ return findOneBy(sc);
+ }
+
+ @Override
+ public ImageStoreVO findEnabledStore() {
+ SearchCriteria sc = nameSearch.create();
+ sc.setParameters("state", ImageStore.State.Enabled); // only one image store is enabled at one time.
+ return findOneBy(sc);
+ }
+
+
+
}
diff --git a/engine/storage/src/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java b/engine/storage/src/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
index 1fed7919a58..a1c4871caa3 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
@@ -52,8 +52,8 @@ public class SnapshotDataStoreDaoImpl extends GenericDaoBase listLiveByStoreId(long id) {
- SearchCriteria sc = storeSearch.create();
+ SearchCriteria sc = liveStoreSearch.create();
sc.setParameters("store_id", id);
sc.setParameters("destroyed", false);
return listIncludingRemovedBy(sc);
diff --git a/engine/storage/src/org/apache/cloudstack/storage/image/db/TemplateDataStoreDaoImpl.java b/engine/storage/src/org/apache/cloudstack/storage/image/db/TemplateDataStoreDaoImpl.java
index 2066c5d7c6f..d7019d29924 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/image/db/TemplateDataStoreDaoImpl.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/image/db/TemplateDataStoreDaoImpl.java
@@ -53,8 +53,8 @@ public class TemplateDataStoreDaoImpl extends GenericDaoBase listLiveByStoreId(long id) {
- SearchCriteria sc = storeSearch.create();
+ SearchCriteria sc = liveStoreSearch.create();
sc.setParameters("store_id", id);
sc.setParameters("destroyed", false);
return listIncludingRemovedBy(sc);
diff --git a/engine/storage/src/org/apache/cloudstack/storage/image/db/VolumeDataStoreDaoImpl.java b/engine/storage/src/org/apache/cloudstack/storage/image/db/VolumeDataStoreDaoImpl.java
index 34de3f249b4..b8127ee3361 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/image/db/VolumeDataStoreDaoImpl.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/image/db/VolumeDataStoreDaoImpl.java
@@ -49,6 +49,15 @@ public class VolumeDataStoreDaoImpl extends GenericDaoBase params) throws ConfigurationException {
super.configure(name, params);
+ storeSearch = createSearchBuilder();
+ storeSearch.and("store_id", storeSearch.entity().getDataStoreId(), SearchCriteria.Op.EQ);
+ storeSearch.done();
+
+ liveStoreSearch = createSearchBuilder();
+ liveStoreSearch.and("store_id", liveStoreSearch.entity().getDataStoreId(), SearchCriteria.Op.EQ);
+ liveStoreSearch.and("destroyed", liveStoreSearch.entity().getDestroyed(), SearchCriteria.Op.EQ);
+ liveStoreSearch.done();
+
updateStateSearch = this.createSearchBuilder();
updateStateSearch.and("id", updateStateSearch.entity().getId(), Op.EQ);
updateStateSearch.and("state", updateStateSearch.entity().getState(), Op.EQ);
@@ -100,7 +109,7 @@ public class VolumeDataStoreDaoImpl extends GenericDaoBase listLiveByStoreId(long id) {
- SearchCriteria sc = storeSearch.create();
+ SearchCriteria sc = liveStoreSearch.create();
sc.setParameters("store_id", id);
sc.setParameters("destroyed", false);
return listIncludingRemovedBy(sc);
diff --git a/server/src/com/cloud/storage/StorageManagerImpl.java b/server/src/com/cloud/storage/StorageManagerImpl.java
index c9f97be2a81..162df1a1cd3 100755
--- a/server/src/com/cloud/storage/StorageManagerImpl.java
+++ b/server/src/com/cloud/storage/StorageManagerImpl.java
@@ -45,6 +45,7 @@ import org.apache.cloudstack.api.command.admin.storage.CancelPrimaryStorageMaint
import org.apache.cloudstack.api.command.admin.storage.CreateStoragePoolCmd;
import org.apache.cloudstack.api.command.admin.storage.DeleteImageStoreCmd;
import org.apache.cloudstack.api.command.admin.storage.DeletePoolCmd;
+import org.apache.cloudstack.api.command.admin.storage.EnableImageStoreCmd;
import org.apache.cloudstack.api.command.admin.storage.UpdateStoragePoolCmd;
import org.apache.cloudstack.engine.subsystem.api.storage.ClusterScope;
import org.apache.cloudstack.engine.subsystem.api.storage.DataStore;
@@ -165,6 +166,7 @@ import com.cloud.tags.dao.ResourceTagDao;
import com.cloud.template.TemplateManager;
import com.cloud.user.Account;
import com.cloud.user.AccountManager;
+import com.cloud.user.AccountVO;
import com.cloud.user.ResourceLimitService;
import com.cloud.user.User;
import com.cloud.user.UserContext;
@@ -2011,5 +2013,40 @@ public class StorageManagerImpl extends ManagerBase implements StorageManager, C
return true;
}
+ @Override
+ public ImageStore enableImageStore(EnableImageStoreCmd cmd) {
+ Long storeId = cmd.getId();
+ String storeName = cmd.getStoreName();
+
+ ImageStore store = null;
+ if ( storeId != null ){
+ store = _imageStoreDao.findById(storeId);
+ } else if ( storeName != null ){
+ store = _imageStoreDao.findByName(storeName);
+ } else {
+ throw new InvalidParameterValueException("Either image store id or name has to be specified!");
+ }
+
+ if (store == null) {
+ throw new InvalidParameterValueException("Unable to find image store by id: " + storeId + " OR by name: " + storeName);
+ }
+ // disable currently active store
+ ImageStoreVO activeStore = _imageStoreDao.findEnabledStore();
+ ImageStoreVO activeStoreForUpdate = _imageStoreDao.createForUpdate();
+ activeStoreForUpdate.setState(ImageStore.State.Disabled);
+ if ( !_imageStoreDao.update(activeStore.getId(), activeStoreForUpdate)){
+ throw new CloudRuntimeException("Failed to disable current active image store " + activeStore.getName());
+ }
+
+ ImageStoreVO storeForUpdate = _imageStoreDao.createForUpdate();
+ storeForUpdate.setState(ImageStore.State.Enabled);
+ if (_imageStoreDao.update(store.getId(), storeForUpdate)){
+ return _imageStoreDao.findById(store.getId());
+ }
+ else{
+ throw new CloudRuntimeException("Failed to enable image store by id: " + storeId + " OR by name: " + storeName);
+ }
+ }
+
}