You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by mc...@apache.org on 2013/04/20 02:10:49 UTC

[1/5] git commit: updated refs/heads/object_store to 09ba551

Updated Branches:
  refs/heads/object_store ef30ee52e -> 09ba55103


Populate hypervisor_type column in registering ISO by referring it from
guest os id to make listIsos and listTemplates implementation more
consistent.


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/7ba1a8fa
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/7ba1a8fa
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/7ba1a8fa

Branch: refs/heads/object_store
Commit: 7ba1a8fa2154ab0db543f4df42310208d1aae881
Parents: ef30ee5
Author: Min Chen <mi...@citrix.com>
Authored: Thu Apr 18 13:52:15 2013 -0700
Committer: Min Chen <mi...@citrix.com>
Committed: Thu Apr 18 13:52:35 2013 -0700

----------------------------------------------------------------------
 api/src/com/cloud/storage/GuestOSHypervisor.java   |   28 ++++++
 client/tomcatconf/applicationContext.xml.in        |    2 +
 .../src/com/cloud/storage/GuestOSHypervisorVO.java |   73 +++++++++++++++
 .../cloud/storage/dao/GuestOSHypervisorDao.java    |   27 ++++++
 .../storage/dao/GuestOSHypervisorDaoImpl.java      |   49 ++++++++++
 .../com/cloud/template/TemplateAdapterBase.java    |    9 ++-
 6 files changed, 187 insertions(+), 1 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7ba1a8fa/api/src/com/cloud/storage/GuestOSHypervisor.java
----------------------------------------------------------------------
diff --git a/api/src/com/cloud/storage/GuestOSHypervisor.java b/api/src/com/cloud/storage/GuestOSHypervisor.java
new file mode 100644
index 0000000..f022722
--- /dev/null
+++ b/api/src/com/cloud/storage/GuestOSHypervisor.java
@@ -0,0 +1,28 @@
+// 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 com.cloud.storage;
+
+import org.apache.cloudstack.api.InternalIdentity;
+
+public interface GuestOSHypervisor extends InternalIdentity {
+
+    String getHypervisorType();
+
+    String getGuestOsName();
+
+    long getGuestOsId();
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7ba1a8fa/client/tomcatconf/applicationContext.xml.in
----------------------------------------------------------------------
diff --git a/client/tomcatconf/applicationContext.xml.in b/client/tomcatconf/applicationContext.xml.in
index 7ad3bb5..7bbcf09 100644
--- a/client/tomcatconf/applicationContext.xml.in
+++ b/client/tomcatconf/applicationContext.xml.in
@@ -212,6 +212,8 @@
   <bean id="globalLoadBalancerLbRuleMapDaoImpl" class="org.apache.cloudstack.region.gslb.GlobalLoadBalancerLbRuleMapDaoImpl" />
   <bean id="guestOSCategoryDaoImpl" class="com.cloud.storage.dao.GuestOSCategoryDaoImpl" />
   <bean id="guestOSDaoImpl" class="com.cloud.storage.dao.GuestOSDaoImpl" />
+  <bean id="guestOSHypervisorDaoImpl" class="com.cloud.storage.dao.GuestOSHypervisorDaoImpl" />
+  <bean id="guestOSDaoImpl" class="com.cloud.storage.dao.GuestOSDaoImpl" />  
   <bean id="highAvailabilityDaoImpl" class="com.cloud.ha.dao.HighAvailabilityDaoImpl" />
   <bean id="hostDaoImpl" class="com.cloud.host.dao.HostDaoImpl" />
   <bean id="engineHostDetailsDaoImpl" class="org.apache.cloudstack.engine.datacenter.entity.api.db.dao.HostDetailsDaoImpl" />

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7ba1a8fa/core/src/com/cloud/storage/GuestOSHypervisorVO.java
----------------------------------------------------------------------
diff --git a/core/src/com/cloud/storage/GuestOSHypervisorVO.java b/core/src/com/cloud/storage/GuestOSHypervisorVO.java
new file mode 100644
index 0000000..5ab3480
--- /dev/null
+++ b/core/src/com/cloud/storage/GuestOSHypervisorVO.java
@@ -0,0 +1,73 @@
+// 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 com.cloud.storage;
+
+import java.util.UUID;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+import org.apache.cloudstack.api.Identity;
+import org.apache.cloudstack.api.InternalIdentity;
+
+@Entity
+@Table(name="guest_os_hypervisor")
+public class GuestOSHypervisorVO implements GuestOSHypervisor {
+    @Id
+    @GeneratedValue(strategy=GenerationType.IDENTITY)
+    @Column(name="id")
+    long id;
+
+    @Column(name="guest_os_id")
+    private long guestOsId;
+
+    @Column(name="guest_os_name")
+    String guestOsName;
+
+    @Column(name="hypervisor_type")
+    String hypervisorType;
+
+
+    @Override
+    public long getId() {
+    	return id;
+    }
+
+
+    @Override
+    public String getHypervisorType() {
+        return hypervisorType;
+    }
+
+
+    @Override
+    public String getGuestOsName() {
+        return guestOsName;
+    }
+
+
+    @Override
+    public long getGuestOsId() {
+        return guestOsId;
+    }
+
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7ba1a8fa/server/src/com/cloud/storage/dao/GuestOSHypervisorDao.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/storage/dao/GuestOSHypervisorDao.java b/server/src/com/cloud/storage/dao/GuestOSHypervisorDao.java
new file mode 100644
index 0000000..945a542
--- /dev/null
+++ b/server/src/com/cloud/storage/dao/GuestOSHypervisorDao.java
@@ -0,0 +1,27 @@
+// 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 com.cloud.storage.dao;
+
+import com.cloud.hypervisor.Hypervisor.HypervisorType;
+import com.cloud.storage.GuestOSHypervisorVO;
+import com.cloud.utils.db.GenericDao;
+
+public interface GuestOSHypervisorDao extends GenericDao<GuestOSHypervisorVO, Long> {
+
+     HypervisorType findHypervisorTypeByGuestOsId(long guestOsId);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7ba1a8fa/server/src/com/cloud/storage/dao/GuestOSHypervisorDaoImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/storage/dao/GuestOSHypervisorDaoImpl.java b/server/src/com/cloud/storage/dao/GuestOSHypervisorDaoImpl.java
new file mode 100644
index 0000000..48de6e9
--- /dev/null
+++ b/server/src/com/cloud/storage/dao/GuestOSHypervisorDaoImpl.java
@@ -0,0 +1,49 @@
+// 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 com.cloud.storage.dao;
+
+import javax.ejb.Local;
+
+import org.springframework.stereotype.Component;
+
+import com.cloud.hypervisor.Hypervisor.HypervisorType;
+import com.cloud.storage.GuestOSHypervisorVO;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Component
+@Local(value = { GuestOSHypervisorDao.class })
+public class GuestOSHypervisorDaoImpl extends GenericDaoBase<GuestOSHypervisorVO, Long> implements GuestOSHypervisorDao {
+
+    protected final SearchBuilder<GuestOSHypervisorVO> guestOsSearch;
+
+    protected GuestOSHypervisorDaoImpl() {
+        guestOsSearch = createSearchBuilder();
+        guestOsSearch.and("guest_os_id", guestOsSearch.entity().getGuestOsId(), SearchCriteria.Op.EQ);
+        guestOsSearch.done();
+    }
+
+    @Override
+    public HypervisorType findHypervisorTypeByGuestOsId(long guestOsId) {
+        SearchCriteria<GuestOSHypervisorVO> sc = guestOsSearch.create();
+        sc.setParameters("guest_os_id", guestOsId);
+        GuestOSHypervisorVO goh = findOneBy(sc);
+        return HypervisorType.getType(goh.getHypervisorType());
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7ba1a8fa/server/src/com/cloud/template/TemplateAdapterBase.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/template/TemplateAdapterBase.java b/server/src/com/cloud/template/TemplateAdapterBase.java
index 987e6ed..9826298 100755
--- a/server/src/com/cloud/template/TemplateAdapterBase.java
+++ b/server/src/com/cloud/template/TemplateAdapterBase.java
@@ -50,6 +50,7 @@ import com.cloud.storage.Storage.TemplateType;
 import com.cloud.storage.DataStoreRole;
 import com.cloud.storage.TemplateProfile;
 import com.cloud.storage.VMTemplateVO;
+import com.cloud.storage.dao.GuestOSHypervisorDao;
 import com.cloud.storage.dao.VMTemplateDao;
 import com.cloud.storage.dao.VMTemplateHostDao;
 import com.cloud.storage.dao.VMTemplateZoneDao;
@@ -81,6 +82,7 @@ public abstract class TemplateAdapterBase extends AdapterBase implements Templat
 	protected @Inject UsageEventDao _usageEventDao;
 	protected @Inject HostDao _hostDao;
 	protected @Inject UserVmDao _userVmDao;
+	protected @Inject GuestOSHypervisorDao _osHyperDao;
 	protected @Inject ResourceLimitService _resourceLimitMgr;
 	protected @Inject DataStoreManager storeMgr;
 	@Inject TemplateManager templateMgr;
@@ -232,9 +234,14 @@ public abstract class TemplateAdapterBase extends AdapterBase implements Templat
 	    Account owner = _accountMgr.getAccount(cmd.getEntityOwnerId());
 	    _accountMgr.checkAccess(caller, null, true, owner);
 
+	    HypervisorType hyperType = HypervisorType.None;
+	    if ( cmd.getOsTypeId() != null ){
+	        hyperType = _osHyperDao.findHypervisorTypeByGuestOsId(cmd.getOsTypeId());
+	    }
+
 		return prepare(true, UserContext.current().getCallerUserId(), cmd.getIsoName(), cmd.getDisplayText(), 64, false,
 					true, cmd.getUrl(), cmd.isPublic(), cmd.isFeatured(), cmd.isExtractable(), ImageFormat.ISO.toString(), cmd.getOsTypeId(),
-					cmd.getZoneId(), HypervisorType.None, cmd.getChecksum(), cmd.isBootable(), null, owner, null, false);
+					cmd.getZoneId(), hyperType, cmd.getChecksum(), cmd.isBootable(), null, owner, null, false);
 	}
 
 	protected VMTemplateVO persistTemplate(TemplateProfile profile) {


[3/5] Refactor listTemplatesCmd and listIsoCmd to use db view.

Posted by mc...@apache.org.
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/ApiResponseHelper.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/ApiResponseHelper.java b/server/src/com/cloud/api/ApiResponseHelper.java
index e9255c4..a0c9d38 100755
--- a/server/src/com/cloud/api/ApiResponseHelper.java
+++ b/server/src/com/cloud/api/ApiResponseHelper.java
@@ -151,6 +151,7 @@ import com.cloud.api.query.vo.ResourceTagJoinVO;
 import com.cloud.api.query.vo.SecurityGroupJoinVO;
 import com.cloud.api.query.vo.ServiceOfferingJoinVO;
 import com.cloud.api.query.vo.StoragePoolJoinVO;
+import com.cloud.api.query.vo.TemplateJoinVO;
 import com.cloud.api.query.vo.UserAccountJoinVO;
 import com.cloud.api.query.vo.UserVmJoinVO;
 import com.cloud.api.query.vo.VolumeJoinVO;
@@ -281,8 +282,10 @@ public class ApiResponseHelper implements ResponseGenerator {
 
     public final Logger s_logger = Logger.getLogger(ApiResponseHelper.class);
     private static final DecimalFormat s_percentFormat = new DecimalFormat("##.##");
-    @Inject private EntityManager _entityMgr = null;
-    @Inject private UsageService _usageSvc = null;
+    @Inject
+    private EntityManager _entityMgr = null;
+    @Inject
+    private UsageService _usageSvc = null;
 
     @Override
     public UserResponse createUserResponse(User user) {
@@ -290,9 +293,8 @@ public class ApiResponseHelper implements ResponseGenerator {
         return ApiDBUtils.newUserResponse(vUser);
     }
 
-
-
-    // this method is used for response generation via createAccount (which creates an account + user)
+    // this method is used for response generation via createAccount (which
+    // creates an account + user)
     @Override
     public AccountResponse createUserAccountResponse(UserAccount user) {
         return ApiDBUtils.newAccountResponse(ApiDBUtils.findAccountViewById(user.getAccountId()));
@@ -304,7 +306,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return ApiDBUtils.newAccountResponse(vUser);
     }
 
-
     @Override
     public UserResponse createUserResponse(UserAccount user) {
         UserAccountJoinVO vUser = ApiDBUtils.newUserView(user);
@@ -352,8 +353,8 @@ public class ApiResponseHelper implements ResponseGenerator {
             populateDomain(resourceLimitResponse, accountTemp.getDomainId());
         }
         resourceLimitResponse.setResourceType(Integer.valueOf(limit.getType().getOrdinal()).toString());
-        if(limit.getType() == ResourceType.primary_storage || limit.getType() == ResourceType.secondary_storage) {
-            resourceLimitResponse.setMax((long) Math.ceil(limit.getMax()/ResourceType.bytesToGiB));
+        if (limit.getType() == ResourceType.primary_storage || limit.getType() == ResourceType.secondary_storage) {
+            resourceLimitResponse.setMax((long) Math.ceil(limit.getMax() / ResourceType.bytesToGiB));
         } else {
             resourceLimitResponse.setMax(limit.getMax());
         }
@@ -420,7 +421,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         snapshotResponse.setIntervalType(ApiDBUtils.getSnapshotIntervalTypes(snapshot.getId()));
         snapshotResponse.setState(snapshot.getState());
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.Snapshot, snapshot.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -443,9 +444,9 @@ public class ApiResponseHelper implements ResponseGenerator {
         vmSnapshotResponse.setDescription(vmSnapshot.getDescription());
         vmSnapshotResponse.setDisplayName(vmSnapshot.getDisplayName());
         UserVm vm = ApiDBUtils.findUserVmById(vmSnapshot.getVmId());
-        if(vm!=null)
+        if (vm != null)
             vmSnapshotResponse.setVirtualMachineid(vm.getUuid());
-        if(vmSnapshot.getParent() != null)
+        if (vmSnapshot.getParent() != null)
             vmSnapshotResponse.setParentName(ApiDBUtils.getVMSnapshotById(vmSnapshot.getParent()).getDisplayName());
         vmSnapshotResponse.setCurrent(vmSnapshot.getCurrent());
         vmSnapshotResponse.setType(vmSnapshot.getType().toString());
@@ -542,9 +543,9 @@ public class ApiResponseHelper implements ResponseGenerator {
         // get start ip and end ip of corresponding vlan
         String ipRange = vlan.getIpRange();
         if (ipRange != null) {
-        	String[] range = ipRange.split("-");
-        	vlanResponse.setStartIp(range[0]);
-        	vlanResponse.setEndIp(range[1]);
+            String[] range = ipRange.split("-");
+            vlanResponse.setStartIp(range[0]);
+            vlanResponse.setEndIp(range[1]);
         }
 
         vlanResponse.setIp6Gateway(vlan.getIp6Gateway());
@@ -552,9 +553,9 @@ public class ApiResponseHelper implements ResponseGenerator {
 
         String ip6Range = vlan.getIp6Range();
         if (ip6Range != null) {
-        	String[] range = ip6Range.split("-");
-        	vlanResponse.setStartIpv6(range[0]);
-        	vlanResponse.setEndIpv6(range[1]);
+            String[] range = ip6Range.split("-");
+            vlanResponse.setStartIpv6(range[0]);
+            vlanResponse.setEndIpv6(range[1]);
         }
 
         if (vlan.getNetworkId() != null) {
@@ -683,7 +684,7 @@ public class ApiResponseHelper implements ResponseGenerator {
             }
         }
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.PublicIpAddress, ipAddr.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -723,7 +724,7 @@ public class ApiResponseHelper implements ResponseGenerator {
             lbResponse.setZoneId(zone.getUuid());
         }
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.UserVm, loadBalancer.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -788,7 +789,8 @@ public class ApiResponseHelper implements ResponseGenerator {
                     capacityResponse.setCapacityTotal(capacity.getTotalCapacity());
                 }
                 if (capacityResponse.getCapacityTotal() != 0) {
-                    capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed() / (float) capacityResponse.getCapacityTotal() * 100f));
+                    capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed()
+                            / (float) capacityResponse.getCapacityTotal() * 100f));
                 } else {
                     capacityResponse.setPercentUsed(s_percentFormat.format(0L));
                 }
@@ -808,7 +810,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         return ApiDBUtils.newDataCenterResponse(vOffering, showCapacities);
     }
 
-    public static List<CapacityResponse> getDataCenterCapacityResponse(Long zoneId){
+    public static List<CapacityResponse> getDataCenterCapacityResponse(Long zoneId) {
         List<SummedCapacity> capacities = ApiDBUtils.getCapacityByClusterPodZone(zoneId, null, null);
         Set<CapacityResponse> capacityResponses = new HashSet<CapacityResponse>();
         float cpuOverprovisioningFactor = ApiDBUtils.getCpuOverprovisioningFactor();
@@ -827,7 +829,8 @@ public class ApiResponseHelper implements ResponseGenerator {
                 capacityResponse.setCapacityTotal(capacity.getTotalCapacity());
             }
             if (capacityResponse.getCapacityTotal() != 0) {
-                capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed() / (float) capacityResponse.getCapacityTotal() * 100f));
+                capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed()
+                        / (float) capacityResponse.getCapacityTotal() * 100f));
             } else {
                 capacityResponse.setPercentUsed(s_percentFormat.format(0L));
             }
@@ -853,7 +856,8 @@ public class ApiResponseHelper implements ResponseGenerator {
             capacityResponse.setCapacityUsed(capacity.getUsedCapacity());
             capacityResponse.setCapacityTotal(capacity.getTotalCapacity());
             if (capacityResponse.getCapacityTotal() != 0) {
-                capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed() / (float) capacityResponse.getCapacityTotal() * 100f));
+                capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed()
+                        / (float) capacityResponse.getCapacityTotal() * 100f));
             } else {
                 capacityResponse.setPercentUsed(s_percentFormat.format(0L));
             }
@@ -878,31 +882,26 @@ public class ApiResponseHelper implements ResponseGenerator {
 
     }
 
-
-
     @Override
     public StoragePoolResponse createStoragePoolResponse(StoragePool pool) {
         List<StoragePoolJoinVO> viewPools = ApiDBUtils.newStoragePoolView(pool);
-        List<StoragePoolResponse> listPools = ViewResponseHelper.createStoragePoolResponse(viewPools.toArray(new StoragePoolJoinVO[viewPools.size()]));
+        List<StoragePoolResponse> listPools = ViewResponseHelper
+                .createStoragePoolResponse(viewPools.toArray(new StoragePoolJoinVO[viewPools.size()]));
         assert listPools != null && listPools.size() == 1 : "There should be one storage pool returned";
         return listPools.get(0);
 
-
     }
 
-
     @Override
     public ImageStoreResponse createImageStoreResponse(ImageStore os) {
         List<ImageStoreJoinVO> viewStores = ApiDBUtils.newImageStoreView(os);
-        List<ImageStoreResponse> listStores = ViewResponseHelper.createImageStoreResponse(viewStores.toArray(new ImageStoreJoinVO[viewStores.size()]));
+        List<ImageStoreResponse> listStores = ViewResponseHelper
+                .createImageStoreResponse(viewStores.toArray(new ImageStoreJoinVO[viewStores.size()]));
         assert listStores != null && listStores.size() == 1 : "There should be one image data store returned";
         return listStores.get(0);
 
-
     }
 
-
-
     @Override
     public ClusterResponse createClusterResponse(Cluster cluster, Boolean showCapacities) {
         ClusterResponse clusterResponse = new ClusterResponse();
@@ -922,12 +921,11 @@ public class ApiResponseHelper implements ResponseGenerator {
         clusterResponse.setClusterType(cluster.getClusterType().toString());
         clusterResponse.setAllocationState(cluster.getAllocationState().toString());
         clusterResponse.setManagedState(cluster.getManagedState().toString());
-        String cpuOvercommitRatio=ApiDBUtils.findClusterDetails(cluster.getId(),"cpuOvercommitRatio").getValue();
-        String memoryOvercommitRatio=ApiDBUtils.findClusterDetails(cluster.getId(),"memoryOvercommitRatio").getValue();
+        String cpuOvercommitRatio = ApiDBUtils.findClusterDetails(cluster.getId(), "cpuOvercommitRatio").getValue();
+        String memoryOvercommitRatio = ApiDBUtils.findClusterDetails(cluster.getId(), "memoryOvercommitRatio").getValue();
         clusterResponse.setCpuovercommitratio(cpuOvercommitRatio);
         clusterResponse.setRamovercommitratio(memoryOvercommitRatio);
 
-
         if (showCapacities != null && showCapacities) {
             List<SummedCapacity> capacities = ApiDBUtils.getCapacityByClusterPodZone(null, null, cluster.getId());
             Set<CapacityResponse> capacityResponses = new HashSet<CapacityResponse>();
@@ -939,10 +937,9 @@ public class ApiResponseHelper implements ResponseGenerator {
 
                 if (capacity.getCapacityType() == Capacity.CAPACITY_TYPE_CPU) {
                     capacityResponse.setCapacityTotal(new Long((long) (capacity.getTotalCapacity() * Float.parseFloat(cpuOvercommitRatio))));
-                }else if (capacity.getCapacityType() == Capacity.CAPACITY_TYPE_MEMORY){
+                } else if (capacity.getCapacityType() == Capacity.CAPACITY_TYPE_MEMORY) {
                     capacityResponse.setCapacityTotal(new Long((long) (capacity.getTotalCapacity() * Float.parseFloat(memoryOvercommitRatio))));
-                }
-                else if (capacity.getCapacityType() == Capacity.CAPACITY_TYPE_STORAGE_ALLOCATED) {
+                } else if (capacity.getCapacityType() == Capacity.CAPACITY_TYPE_STORAGE_ALLOCATED) {
                     List<SummedCapacity> c = ApiDBUtils.findNonSharedStorageForClusterPodZone(null, null, cluster.getId());
                     capacityResponse.setCapacityTotal(capacity.getTotalCapacity() - c.get(0).getTotalCapacity());
                     capacityResponse.setCapacityUsed(capacity.getUsedCapacity() - c.get(0).getUsedCapacity());
@@ -950,7 +947,8 @@ public class ApiResponseHelper implements ResponseGenerator {
                     capacityResponse.setCapacityTotal(capacity.getTotalCapacity());
                 }
                 if (capacityResponse.getCapacityTotal() != 0) {
-                    capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed() / (float) capacityResponse.getCapacityTotal() * 100f));
+                    capacityResponse.setPercentUsed(s_percentFormat.format((float) capacityResponse.getCapacityUsed()
+                            / (float) capacityResponse.getCapacityTotal() * 100f));
                 } else {
                     capacityResponse.setPercentUsed(s_percentFormat.format(0L));
                 }
@@ -999,7 +997,7 @@ public class ApiResponseHelper implements ResponseGenerator {
             stateToSet = "Deleting";
         }
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.PortForwardingRule, fwRule.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -1062,8 +1060,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return ViewResponseHelper.createUserVmResponse(objectName, viewVms.toArray(new UserVmJoinVO[viewVms.size()]));
     }
 
-
-
     @Override
     public DomainRouterResponse createDomainRouterResponse(VirtualRouter router) {
         List<DomainRouterJoinVO> viewVrs = ApiDBUtils.newDomainRouterView(router);
@@ -1072,26 +1068,25 @@ public class ApiResponseHelper implements ResponseGenerator {
         return listVrs.get(0);
     }
 
-
     @Override
     public SystemVmResponse createSystemVmResponse(VirtualMachine vm) {
         SystemVmResponse vmResponse = new SystemVmResponse();
         if (vm.getType() == Type.SecondaryStorageVm || vm.getType() == Type.ConsoleProxy) {
             // SystemVm vm = (SystemVm) systemVM;
             vmResponse.setId(vm.getUuid());
-            //vmResponse.setObjectId(vm.getId());
+            // vmResponse.setObjectId(vm.getId());
             vmResponse.setSystemVmType(vm.getType().toString().toLowerCase());
 
             vmResponse.setName(vm.getHostName());
-            if ( vm.getPodIdToDeployIn() != null ){
+            if (vm.getPodIdToDeployIn() != null) {
                 HostPodVO pod = ApiDBUtils.findPodById(vm.getPodIdToDeployIn());
-                if ( pod != null ){
-            vmResponse.setPodId(pod.getUuid());
+                if (pod != null) {
+                    vmResponse.setPodId(pod.getUuid());
                 }
             }
             VMTemplateVO template = ApiDBUtils.findTemplateById(vm.getTemplateId());
-            if (template != null){
-            vmResponse.setTemplateId(template.getUuid());
+            if (template != null) {
+                vmResponse.setTemplateId(template.getUuid());
             }
             vmResponse.setCreated(vm.getCreated());
 
@@ -1215,267 +1210,45 @@ public class ApiResponseHelper implements ResponseGenerator {
     }
 
     @Override
-    public TemplateResponse createIsoResponse(VirtualMachineTemplate result) {
-        TemplateResponse response = new TemplateResponse();
-        response.setId(result.getUuid());
-        response.setName(result.getName());
-        response.setDisplayText(result.getDisplayText());
-        response.setPublic(result.isPublicTemplate());
-        response.setCreated(result.getCreated());
-        response.setFormat(result.getFormat());
-        GuestOS os = ApiDBUtils.findGuestOSById(result.getGuestOSId());
-        if (os != null) {
-            response.setOsTypeId(os.getUuid());
-            response.setOsTypeName(os.getDisplayName());
-        }
-        response.setDetails(result.getDetails());
-        Account caller = UserContext.current().getCaller();
-
-        if (result.getFormat() == ImageFormat.ISO) { // Templates are always bootable
-            response.setBootable(result.isBootable());
-        } else {
-            response.setHypervisor(result.getHypervisorType().toString());// hypervisors are associated with templates
-        }
-
-        // add account ID and name
-        Account owner = ApiDBUtils.findAccountById(result.getAccountId());
-        populateAccount(response, owner.getId());
-        populateDomain(response, owner.getDomainId());
-
-        //set tag information
-        List<? extends ResourceTag> tags = null;
-        if (result.getFormat() == ImageFormat.ISO) {
-            tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.ISO, result.getId());
-        } else {
-            tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.Template, result.getId());
-        }
-
-        List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
-        for (ResourceTag tag : tags) {
-            ResourceTagResponse tagResponse = createResourceTagResponse(tag, true);
-            tagResponses.add(tagResponse);
-        }
-        response.setTags(tagResponses);
-
-        response.setObjectName("iso");
-        return response;
+    public TemplateResponse createTemplateUpdateResponse(VirtualMachineTemplate result) {
+        List<TemplateJoinVO> tvo = ApiDBUtils.newTemplateView(result);
+        List<TemplateResponse> listVrs = ViewResponseHelper.createTemplateUpdateResponse(tvo.toArray(new TemplateJoinVO[tvo.size()]));
+        assert listVrs != null && listVrs.size() == 1 : "There should be one template returned";
+        return listVrs.get(0);
     }
 
     @Override
-    public List<TemplateResponse> createTemplateResponses(long templateId, Long zoneId, boolean readyOnly) {
+    public List<TemplateResponse> createTemplateResponses(VirtualMachineTemplate result, Long zoneId, boolean readyOnly) {
+        List<TemplateJoinVO> tvo = null;
         if (zoneId == null || zoneId == -1) {
-            List<TemplateResponse> responses = new ArrayList<TemplateResponse>();
-            List<DataCenterVO> dcs = new ArrayList<DataCenterVO>();
-            responses = createSwiftTemplateResponses(templateId);
-            if (!responses.isEmpty()) {
-                return responses;
-            }
-            dcs.addAll(ApiDBUtils.listZones());
-            for (DataCenterVO dc : dcs) {
-                responses.addAll(createTemplateResponses(templateId, dc.getId(), readyOnly));
-            }
-            return responses;
+            tvo = ApiDBUtils.newTemplateView(result);
         } else {
-            return createTemplateResponses(templateId, zoneId.longValue(), readyOnly);
-        }
-    }
+            tvo = ApiDBUtils.newTemplateView(result, zoneId, readyOnly);
 
-    private List<TemplateResponse> createSwiftTemplateResponses(long templateId) {
-        VirtualMachineTemplate template = findTemplateById(templateId);
-        List<TemplateResponse> responses = new ArrayList<TemplateResponse>();
-        VMTemplateSwiftVO templateSwiftRef = ApiDBUtils.findTemplateSwiftRef(templateId);
-        if (templateSwiftRef == null) {
-            return responses;
         }
-
-        TemplateResponse templateResponse = new TemplateResponse();
-        templateResponse.setId(template.getUuid());
-        templateResponse.setName(template.getName());
-        templateResponse.setDisplayText(template.getDisplayText());
-        templateResponse.setPublic(template.isPublicTemplate());
-        templateResponse.setCreated(templateSwiftRef.getCreated());
-
-        templateResponse.setReady(true);
-        templateResponse.setFeatured(template.isFeatured());
-        templateResponse.setExtractable(template.isExtractable() && !(template.getTemplateType() == TemplateType.SYSTEM));
-        templateResponse.setPasswordEnabled(template.getEnablePassword());
-        templateResponse.setSshKeyEnabled(template.getEnableSshKey());
-        templateResponse.setCrossZones(template.isCrossZones());
-        templateResponse.setFormat(template.getFormat());
-        templateResponse.setDetails(template.getDetails());
-        if (template.getTemplateType() != null) {
-            templateResponse.setTemplateType(template.getTemplateType().toString());
-        }
-
-        templateResponse.setHypervisor(template.getHypervisorType().toString());
-
-        GuestOS os = ApiDBUtils.findGuestOSById(template.getGuestOSId());
-        if (os != null) {
-            templateResponse.setOsTypeId(os.getUuid());
-            templateResponse.setOsTypeName(os.getDisplayName());
-        } else {
-            templateResponse.setOsTypeId("-1");
-            templateResponse.setOsTypeName("");
-        }
-
-        Account account = ApiDBUtils.findAccountByIdIncludingRemoved(template.getAccountId());
-        populateAccount(templateResponse, account.getId());
-        populateDomain(templateResponse, account.getDomainId());
-
-        Account caller = UserContext.current().getCaller();
-        boolean isAdmin = false;
-        if (BaseCmd.isAdmin(caller.getType())) {
-            isAdmin = true;
-        }
-
-        // If the user is an Admin, add the template download status
-        if (isAdmin || caller.getId() == template.getAccountId()) {
-            // add download status
-            templateResponse.setStatus("Successfully Installed");
-        }
-
-        Long templateSize = templateSwiftRef.getSize();
-        if (templateSize > 0) {
-            templateResponse.setSize(templateSize);
-        }
-
-        templateResponse.setChecksum(template.getChecksum());
-        if (template.getSourceTemplateId() != null) {
-            VirtualMachineTemplate tmpl = ApiDBUtils.findTemplateById(template.getSourceTemplateId());
-            if (tmpl != null) {
-                templateResponse.setSourceTemplateId(tmpl.getUuid());
-            }
-        }
-
-        templateResponse.setChecksum(template.getChecksum());
-
-        templateResponse.setTemplateTag(template.getTemplateTag());
-
-        templateResponse.setObjectName("template");
-        responses.add(templateResponse);
-        return responses;
+        return ViewResponseHelper.createTemplateResponse(tvo.toArray(new TemplateJoinVO[tvo.size()]));
     }
 
     @Override
-    public List<TemplateResponse> createTemplateResponses(long templateId, long zoneId, boolean readyOnly) {
+    public List<TemplateResponse> createTemplateResponses(long templateId, Long zoneId, boolean readyOnly) {
         VirtualMachineTemplate template = findTemplateById(templateId);
-        List<TemplateResponse> responses = new ArrayList<TemplateResponse>();
-        VMTemplateHostVO templateHostRef = ApiDBUtils.findTemplateHostRef(templateId, zoneId, readyOnly);
-        if (templateHostRef == null) {
-            return responses;
-        }
-
-        HostVO host = ApiDBUtils.findHostById(templateHostRef.getHostId());
-        if (host.getType() == Host.Type.LocalSecondaryStorage && host.getStatus() != com.cloud.host.Status.Up) {
-            return responses;
-        }
-
-        TemplateResponse templateResponse = new TemplateResponse();
-        templateResponse.setId(template.getUuid());
-        templateResponse.setName(template.getName());
-        templateResponse.setDisplayText(template.getDisplayText());
-        templateResponse.setPublic(template.isPublicTemplate());
-        templateResponse.setCreated(templateHostRef.getCreated());
-
-        templateResponse.setReady(templateHostRef.getDownloadState() == Status.DOWNLOADED);
-        templateResponse.setFeatured(template.isFeatured());
-        templateResponse.setExtractable(template.isExtractable() && !(template.getTemplateType() == TemplateType.SYSTEM));
-        templateResponse.setPasswordEnabled(template.getEnablePassword());
-        templateResponse.setSshKeyEnabled(template.getEnableSshKey());
-        templateResponse.setCrossZones(template.isCrossZones());
-        templateResponse.setFormat(template.getFormat());
-        if (template.getTemplateType() != null) {
-            templateResponse.setTemplateType(template.getTemplateType().toString());
-        }
+        return createTemplateResponses(template, zoneId, readyOnly);
+    }
 
-        templateResponse.setHypervisor(template.getHypervisorType().toString());
-        templateResponse.setDetails(template.getDetails());
 
-        GuestOS os = ApiDBUtils.findGuestOSById(template.getGuestOSId());
-        if (os != null) {
-            templateResponse.setOsTypeId(os.getUuid());
-            templateResponse.setOsTypeName(os.getDisplayName());
+    @Override
+    public List<TemplateResponse> createIsoResponses(VirtualMachineTemplate result, Long zoneId, boolean readyOnly) {
+        List<TemplateJoinVO> tvo = null;
+        if (zoneId == null || zoneId == -1) {
+            tvo = ApiDBUtils.newTemplateView(result);
         } else {
-            templateResponse.setOsTypeId("-1");
-            templateResponse.setOsTypeName("");
-        }
+            tvo = ApiDBUtils.newTemplateView(result, zoneId, readyOnly);
 
-        Account account = ApiDBUtils.findAccountByIdIncludingRemoved(template.getAccountId());
-        populateAccount(templateResponse, account.getId());
-        populateDomain(templateResponse, account.getDomainId());
-
-        DataCenter datacenter = ApiDBUtils.findZoneById(zoneId);
-
-        if (datacenter != null) {
-            // Add the zone ID
-            templateResponse.setZoneId(datacenter.getUuid());
-            templateResponse.setZoneName(datacenter.getName());
-        }
-
-        boolean isAdmin = false;
-        Account caller = UserContext.current().getCaller();
-        if ((caller == null) || BaseCmd.isAdmin(caller.getType())) {
-            isAdmin = true;
-        }
-
-        // If the user is an Admin, add the template download status
-        if (isAdmin || caller.getId() == template.getAccountId()) {
-            // add download status
-            if (templateHostRef.getDownloadState() != Status.DOWNLOADED) {
-                String templateStatus = "Processing";
-                if (templateHostRef.getDownloadState() == VMTemplateHostVO.Status.DOWNLOAD_IN_PROGRESS) {
-                    if (templateHostRef.getDownloadPercent() == 100) {
-                        templateStatus = "Installing Template";
-                    } else {
-                        templateStatus = templateHostRef.getDownloadPercent() + "% Downloaded";
-                    }
-                } else {
-                    templateStatus = templateHostRef.getErrorString();
-                }
-                templateResponse.setStatus(templateStatus);
-            } else if (templateHostRef.getDownloadState() == VMTemplateHostVO.Status.DOWNLOADED) {
-                templateResponse.setStatus("Download Complete");
-            } else {
-                templateResponse.setStatus("Successfully Installed");
-            }
-        }
-
-        Long templateSize = templateHostRef.getSize();
-        if (templateSize > 0) {
-            templateResponse.setSize(templateSize);
         }
-
-        templateResponse.setChecksum(template.getChecksum());
-        if (template.getSourceTemplateId() != null) {
-            VirtualMachineTemplate tmpl = ApiDBUtils.findTemplateById(template.getSourceTemplateId());
-            if (tmpl != null) {
-                templateResponse.setSourceTemplateId(tmpl.getUuid());
-            }
-        }
-
-        templateResponse.setChecksum(template.getChecksum());
-
-        templateResponse.setTemplateTag(template.getTemplateTag());
-
-        //set tag information
-        List<? extends ResourceTag> tags = null;
-        if (template.getFormat() == ImageFormat.ISO) {
-            tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.ISO, template.getId());
-        } else {
-            tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.Template, template.getId());
-        }
-        List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
-        for (ResourceTag tag : tags) {
-            ResourceTagResponse tagResponse = createResourceTagResponse(tag, true);
-            tagResponses.add(tagResponse);
-        }
-        templateResponse.setTags(tagResponses);
-
-        templateResponse.setObjectName("template");
-        responses.add(templateResponse);
-        return responses;
+        return ViewResponseHelper.createIsoResponse(tvo.toArray(new TemplateJoinVO[tvo.size()]));
     }
 
+    /*
     @Override
     public List<TemplateResponse> createIsoResponses(long isoId, Long zoneId, boolean readyOnly) {
 
@@ -1503,8 +1276,8 @@ public class ApiResponseHelper implements ResponseGenerator {
             populateAccount(isoResponse, owner.getId());
             populateDomain(isoResponse, owner.getDomainId());
 
-            //set tag information
-            List<? extends ResourceTag> tags =  ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.ISO, iso.getId());
+            // set tag information
+            List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.ISO, iso.getId());
             List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
             for (ResourceTag tag : tags) {
                 ResourceTagResponse tagResponse = createResourceTagResponse(tag, true);
@@ -1727,8 +1500,8 @@ public class ApiResponseHelper implements ResponseGenerator {
             isoResponse.setSize(isoSize);
         }
 
-        //set tag information
-        List<? extends ResourceTag> tags =  ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.ISO, iso.getId());
+        // set tag information
+        List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.ISO, iso.getId());
 
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -1741,8 +1514,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         isoResponses.add(isoResponse);
         return isoResponses;
     }
-
-
+*/
 
     @Override
     public SecurityGroupResponse createSecurityGroupResponse(SecurityGroup group) {
@@ -1806,8 +1578,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return createTemplateResponses(templateId, host.getDataCenterId(), true);
     }
 
-
-
     @Override
     public EventResponse createEventResponse(Event event) {
         EventJoinVO vEvent = ApiDBUtils.newEventView(event);
@@ -1824,14 +1594,17 @@ public class ApiResponseHelper implements ResponseGenerator {
         List<? extends StoragePoolVO> allStoragePools = ApiDBUtils.searchForStoragePools(c);
         for (StoragePoolVO pool : allStoragePools) {
             StoragePoolType poolType = pool.getPoolType();
-            if (!(poolType.isShared())) {// All the non shared storages shouldn't show up in the capacity calculation
+            if (!(poolType.isShared())) {// All the non shared storages
+                                         // shouldn't show up in the capacity
+                                         // calculation
                 poolIdsToIgnore.add(pool.getId());
             }
         }
 
         float cpuOverprovisioningFactor = ApiDBUtils.getCpuOverprovisioningFactor();
 
-        // collect all the capacity types, sum allocated/used and sum total...get one capacity number for each
+        // collect all the capacity types, sum allocated/used and sum
+        // total...get one capacity number for each
         for (Capacity capacity : hostCapacities) {
 
             // check if zone exist
@@ -1991,10 +1764,11 @@ public class ApiResponseHelper implements ResponseGenerator {
                 capacityResponse.setZoneId(zone.getUuid());
                 capacityResponse.setZoneName(zone.getName());
             }
-            if (summedCapacity.getUsedPercentage() != null){
+            if (summedCapacity.getUsedPercentage() != null) {
                 capacityResponse.setPercentUsed(format.format(summedCapacity.getUsedPercentage() * 100f));
             } else if (summedCapacity.getTotalCapacity() != 0) {
-                capacityResponse.setPercentUsed(format.format((float) summedCapacity.getUsedCapacity() / (float) summedCapacity.getTotalCapacity() * 100f));
+                capacityResponse.setPercentUsed(format.format((float) summedCapacity.getUsedCapacity() / (float) summedCapacity.getTotalCapacity()
+                        * 100f));
             } else {
                 capacityResponse.setPercentUsed(format.format(0L));
             }
@@ -2012,7 +1786,8 @@ public class ApiResponseHelper implements ResponseGenerator {
         VirtualMachineTemplate template = ApiDBUtils.findTemplateById(id);
         Account templateOwner = ApiDBUtils.findAccountById(template.getAccountId());
         if (isAdmin) {
-            // FIXME: we have just template id and need to get template owner from that
+            // FIXME: we have just template id and need to get template owner
+            // from that
             if (templateOwner != null) {
                 templateOwnerDomain = templateOwner.getDomainId();
             }
@@ -2193,10 +1968,10 @@ public class ApiResponseHelper implements ResponseGenerator {
                 eLb.setValue(offering.getElasticLb() ? "true" : "false");
                 lbCapResponse.add(eLb);
 
-		CapabilityResponse inline = new CapabilityResponse();
-		inline.setName(Capability.InlineMode.getName());
-		inline.setValue(offering.isInline() ? "true" : "false");
-		lbCapResponse.add(inline);
+                CapabilityResponse inline = new CapabilityResponse();
+                inline.setName(Capability.InlineMode.getName());
+                inline.setValue(offering.isInline() ? "true" : "false");
+                lbCapResponse.add(inline);
 
                 svcRsp.setCapabilities(lbCapResponse);
             } else if (Service.SourceNat == service) {
@@ -2234,7 +2009,8 @@ public class ApiResponseHelper implements ResponseGenerator {
 
     @Override
     public NetworkResponse createNetworkResponse(Network network) {
-        // need to get network profile in order to retrieve dns information from there
+        // need to get network profile in order to retrieve dns information from
+        // there
         NetworkProfile profile = ApiDBUtils.getNetworkProfile(network.getId());
         NetworkResponse response = new NetworkResponse();
         response.setId(network.getUuid());
@@ -2257,8 +2033,10 @@ public class ApiResponseHelper implements ResponseGenerator {
         // FIXME - either set netmask or cidr
         response.setCidr(network.getCidr());
         response.setNetworkCidr((network.getNetworkCidr()));
-        // If network has reservation its entire network cidr is defined by getNetworkCidr()
-        // if no reservation is present then getCidr() will define the entire network cidr
+        // If network has reservation its entire network cidr is defined by
+        // getNetworkCidr()
+        // if no reservation is present then getCidr() will define the entire
+        // network cidr
         if (network.getNetworkCidr() != null) {
             response.setNetmask(NetUtils.cidr2Netmask(network.getNetworkCidr()));
         }
@@ -2269,44 +2047,45 @@ public class ApiResponseHelper implements ResponseGenerator {
         response.setIp6Gateway(network.getIp6Gateway());
         response.setIp6Cidr(network.getIp6Cidr());
 
-        // create response for reserved IP ranges that can be used for non-cloudstack purposes
-        String  reservation = null;
+        // create response for reserved IP ranges that can be used for
+        // non-cloudstack purposes
+        String reservation = null;
         if ((network.getCidr() != null) && (NetUtils.isNetworkAWithinNetworkB(network.getCidr(), network.getNetworkCidr()))) {
-                String[] guestVmCidrPair = network.getCidr().split("\\/");
-                String[] guestCidrPair = network.getNetworkCidr().split("\\/");
+            String[] guestVmCidrPair = network.getCidr().split("\\/");
+            String[] guestCidrPair = network.getNetworkCidr().split("\\/");
 
-                Long guestVmCidrSize = Long.valueOf(guestVmCidrPair[1]);
-                Long guestCidrSize = Long.valueOf(guestCidrPair[1]);
+            Long guestVmCidrSize = Long.valueOf(guestVmCidrPair[1]);
+            Long guestCidrSize = Long.valueOf(guestCidrPair[1]);
 
-                String[] guestVmIpRange = NetUtils.getIpRangeFromCidr(guestVmCidrPair[0], guestVmCidrSize);
-                String[] guestIpRange = NetUtils.getIpRangeFromCidr(guestCidrPair[0], guestCidrSize);
-                long startGuestIp = NetUtils.ip2Long(guestIpRange[0]);
-                long endGuestIp = NetUtils.ip2Long(guestIpRange[1]);
-                long startVmIp = NetUtils.ip2Long(guestVmIpRange[0]);
-                long endVmIp = NetUtils.ip2Long(guestVmIpRange[1]);
+            String[] guestVmIpRange = NetUtils.getIpRangeFromCidr(guestVmCidrPair[0], guestVmCidrSize);
+            String[] guestIpRange = NetUtils.getIpRangeFromCidr(guestCidrPair[0], guestCidrSize);
+            long startGuestIp = NetUtils.ip2Long(guestIpRange[0]);
+            long endGuestIp = NetUtils.ip2Long(guestIpRange[1]);
+            long startVmIp = NetUtils.ip2Long(guestVmIpRange[0]);
+            long endVmIp = NetUtils.ip2Long(guestVmIpRange[1]);
 
-                if (startVmIp == startGuestIp && endVmIp < endGuestIp -1) {
-                    reservation = (NetUtils.long2Ip(endVmIp + 1) + "-" + NetUtils.long2Ip(endGuestIp));
-                }
-                if (endVmIp == endGuestIp && startVmIp > startGuestIp + 1) {
-                    reservation = (NetUtils.long2Ip(startGuestIp) + "-" + NetUtils.long2Ip(startVmIp-1));
-                }
-                if(startVmIp > startGuestIp + 1 && endVmIp < endGuestIp - 1) {
-                reservation = (NetUtils.long2Ip(startGuestIp) + "-" +  NetUtils.long2Ip(startVmIp-1) + " ,  " +
-                        NetUtils.long2Ip(endVmIp + 1) + "-"+  NetUtils.long2Ip(endGuestIp));
+            if (startVmIp == startGuestIp && endVmIp < endGuestIp - 1) {
+                reservation = (NetUtils.long2Ip(endVmIp + 1) + "-" + NetUtils.long2Ip(endGuestIp));
+            }
+            if (endVmIp == endGuestIp && startVmIp > startGuestIp + 1) {
+                reservation = (NetUtils.long2Ip(startGuestIp) + "-" + NetUtils.long2Ip(startVmIp - 1));
+            }
+            if (startVmIp > startGuestIp + 1 && endVmIp < endGuestIp - 1) {
+                reservation = (NetUtils.long2Ip(startGuestIp) + "-" + NetUtils.long2Ip(startVmIp - 1) + " ,  " + NetUtils.long2Ip(endVmIp + 1) + "-" + NetUtils
+                        .long2Ip(endGuestIp));
             }
         }
         response.setReservedIpRange(reservation);
 
-        //return vlan information only to Root admin
+        // return vlan information only to Root admin
         if (network.getBroadcastUri() != null && UserContext.current().getCaller().getType() == Account.ACCOUNT_TYPE_ADMIN) {
             String broadcastUri = network.getBroadcastUri().toString();
             response.setBroadcastUri(broadcastUri);
-            String vlan="N/A";
+            String vlan = "N/A";
             if (broadcastUri.startsWith("vlan")) {
                 vlan = broadcastUri.substring("vlan://".length(), broadcastUri.length());
             }
-            //return vlan information only to Root admin
+            // return vlan information only to Root admin
             response.setVlan(vlan);
 
         }
@@ -2410,7 +2189,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         }
         response.setCanUseForDeploy(ApiDBUtils.canUseForDeploy(network));
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.Network, network.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -2441,9 +2220,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return listPrjs.get(0);
     }
 
-
-
-
     @Override
     public FirewallResponse createFirewallResponse(FirewallRule fwRule) {
         FirewallResponse response = new FirewallResponse();
@@ -2479,7 +2255,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         response.setIcmpCode(fwRule.getIcmpCode());
         response.setIcmpType(fwRule.getIcmpType());
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.FirewallRule, fwRule.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -2523,7 +2299,7 @@ public class ApiResponseHelper implements ResponseGenerator {
 
         response.setState(stateToSet);
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.NetworkACL, networkACL.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -2547,7 +2323,8 @@ public class ApiResponseHelper implements ResponseGenerator {
         return hpvCapabilitiesResponse;
     }
 
-    // TODO: we may need to refactor once ControlledEntityResponse and ControlledEntity id to uuid conversion are all done.
+    // TODO: we may need to refactor once ControlledEntityResponse and
+    // ControlledEntity id to uuid conversion are all done.
     // currently code is scattered in
     private void populateOwner(ControlledEntityResponse response, ControlledEntity object) {
         Account account = ApiDBUtils.findAccountByIdIncludingRemoved(object.getAccountId());
@@ -2606,16 +2383,12 @@ public class ApiResponseHelper implements ResponseGenerator {
         return listProjs.get(0);
     }
 
-
-
-
     @Override
     public ProjectInvitationResponse createProjectInvitationResponse(ProjectInvitation invite) {
         ProjectInvitationJoinVO vInvite = ApiDBUtils.newProjectInvitationView(invite);
         return ApiDBUtils.newProjectInvitationResponse(vInvite);
     }
 
-
     @Override
     public SystemVmInstanceResponse createSystemVmInstanceResponse(VirtualMachine vm) {
         SystemVmInstanceResponse vmResponse = new SystemVmInstanceResponse();
@@ -2685,9 +2458,8 @@ public class ApiResponseHelper implements ResponseGenerator {
             CapabilityResponse capabilityResponse = new CapabilityResponse();
             capabilityResponse.setName(cap.getName());
             capabilityResponse.setObjectName("capability");
-            if (cap.getName().equals(Capability.SupportedLBIsolation.getName()) ||
-                    cap.getName().equals(Capability.SupportedSourceNatTypes.getName()) ||
-                    cap.getName().equals(Capability.RedundantRouter.getName())) {
+            if (cap.getName().equals(Capability.SupportedLBIsolation.getName()) || cap.getName().equals(Capability.SupportedSourceNatTypes.getName())
+                    || cap.getName().equals(Capability.RedundantRouter.getName())) {
                 capabilityResponse.setCanChoose(true);
             } else {
                 capabilityResponse.setCanChoose(false);
@@ -2700,7 +2472,8 @@ public class ApiResponseHelper implements ResponseGenerator {
         List<? extends Network.Provider> serviceProviders = ApiDBUtils.getProvidersForService(service);
         List<ProviderResponse> serviceProvidersResponses = new ArrayList<ProviderResponse>();
         for (Network.Provider serviceProvider : serviceProviders) {
-            // return only Virtual Router/JuniperSRX as a provider for the firewall
+            // return only Virtual Router/JuniperSRX as a provider for the
+            // firewall
             if (service == Service.Firewall && !(serviceProvider == Provider.VirtualRouter || serviceProvider == Provider.JuniperSRX)) {
                 continue;
             }
@@ -2784,8 +2557,7 @@ public class ApiResponseHelper implements ResponseGenerator {
     }
 
     @Override
-    public LBStickinessResponse createLBStickinessPolicyResponse(
-            StickinessPolicy stickinessPolicy, LoadBalancer lb) {
+    public LBStickinessResponse createLBStickinessPolicyResponse(StickinessPolicy stickinessPolicy, LoadBalancer lb) {
         LBStickinessResponse spResponse = new LBStickinessResponse();
 
         spResponse.setlbRuleId(lb.getUuid());
@@ -2800,8 +2572,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         }
 
         List<LBStickinessPolicyResponse> responses = new ArrayList<LBStickinessPolicyResponse>();
-        LBStickinessPolicyResponse ruleResponse = new LBStickinessPolicyResponse(
-                stickinessPolicy);
+        LBStickinessPolicyResponse ruleResponse = new LBStickinessPolicyResponse(stickinessPolicy);
         responses.add(ruleResponse);
 
         spResponse.setRules(responses);
@@ -2811,8 +2582,7 @@ public class ApiResponseHelper implements ResponseGenerator {
     }
 
     @Override
-    public LBStickinessResponse createLBStickinessPolicyResponse(
-            List<? extends StickinessPolicy> stickinessPolicies, LoadBalancer lb) {
+    public LBStickinessResponse createLBStickinessPolicyResponse(List<? extends StickinessPolicy> stickinessPolicies, LoadBalancer lb) {
         LBStickinessResponse spResponse = new LBStickinessResponse();
 
         if (lb == null)
@@ -2840,8 +2610,7 @@ public class ApiResponseHelper implements ResponseGenerator {
     }
 
     @Override
-    public LBHealthCheckResponse createLBHealthCheckPolicyResponse(
-            List<? extends HealthCheckPolicy> healthcheckPolicies, LoadBalancer lb) {
+    public LBHealthCheckResponse createLBHealthCheckPolicyResponse(List<? extends HealthCheckPolicy> healthcheckPolicies, LoadBalancer lb) {
         LBHealthCheckResponse hcResponse = new LBHealthCheckResponse();
 
         if (lb == null)
@@ -2892,9 +2661,8 @@ public class ApiResponseHelper implements ResponseGenerator {
     }
 
     @Override
-    public LDAPConfigResponse createLDAPConfigResponse(String hostname,
-            Integer port, Boolean useSSL, String queryFilter,
-            String searchBase, String bindDN) {
+    public LDAPConfigResponse createLDAPConfigResponse(String hostname, Integer port, Boolean useSSL, String queryFilter, String searchBase,
+            String bindDN) {
         LDAPConfigResponse lr = new LDAPConfigResponse();
         lr.setHostname(hostname);
         lr.setPort(port.toString());
@@ -2922,15 +2690,15 @@ public class ApiResponseHelper implements ResponseGenerator {
         return response;
     }
 
-	@Override
-	public RegionResponse createRegionResponse(Region region) {
-		RegionResponse response = new RegionResponse();
-		response.setId(region.getId());
-		response.setName(region.getName());
-		response.setEndPoint(region.getEndPoint());
-		response.setObjectName("region");
-		return response;
-	}
+    @Override
+    public RegionResponse createRegionResponse(Region region) {
+        RegionResponse response = new RegionResponse();
+        response.setId(region.getId());
+        response.setName(region.getName());
+        response.setEndPoint(region.getEndPoint());
+        response.setObjectName("region");
+        return response;
+    }
 
     @Override
     public ResourceTagResponse createResourceTagResponse(ResourceTag resourceTag, boolean keyValueOnly) {
@@ -2938,8 +2706,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return ApiDBUtils.newResourceTagResponse(rto, keyValueOnly);
     }
 
-
-
     @Override
     public VpcOfferingResponse createVpcOfferingResponse(VpcOffering offering) {
         VpcOfferingResponse response = new VpcOfferingResponse();
@@ -2975,7 +2741,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return response;
     }
 
-
     @Override
     public VpcResponse createVpcResponse(Vpc vpc) {
         VpcResponse response = new VpcResponse();
@@ -3030,7 +2795,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         response.setServices(serviceResponses);
         populateOwner(response, vpc);
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.Vpc, vpc.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -3071,7 +2836,6 @@ public class ApiResponseHelper implements ResponseGenerator {
 
         response.setObjectName("privategateway");
 
-
         return response;
     }
 
@@ -3216,7 +2980,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         populateAccount(response, result.getAccountId());
         populateDomain(response, result.getDomainId());
 
-        //set tag information
+        // set tag information
         List<? extends ResourceTag> tags = ApiDBUtils.listByResourceTypeAndId(TaggedResourceType.StaticRoute, result.getId());
         List<ResourceTagResponse> tagResponses = new ArrayList<ResourceTagResponse>();
         for (ResourceTag tag : tags) {
@@ -3275,7 +3039,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         response.setId(result.getUuid());
 
         Long vpnGatewayId = result.getVpnGatewayId();
-        if(vpnGatewayId != null) {
+        if (vpnGatewayId != null) {
             Site2SiteVpnGateway vpnGateway = ApiDBUtils.findVpnGatewayById(vpnGatewayId);
             if (vpnGateway != null) {
                 response.setVpnGatewayId(vpnGateway.getUuid());
@@ -3286,7 +3050,7 @@ public class ApiResponseHelper implements ResponseGenerator {
         }
 
         Long customerGatewayId = result.getCustomerGatewayId();
-        if(customerGatewayId != null) {
+        if (customerGatewayId != null) {
             Site2SiteCustomerGateway customerGateway = ApiDBUtils.findCustomerGatewayById(customerGatewayId);
             if (customerGateway != null) {
                 response.setCustomerGatewayId(customerGateway.getUuid());
@@ -3310,13 +3074,14 @@ public class ApiResponseHelper implements ResponseGenerator {
         response.setObjectName("vpnconnection");
         return response;
     }
+
     @Override
     public GuestOSResponse createGuestOSResponse(GuestOS guestOS) {
         GuestOSResponse response = new GuestOSResponse();
         response.setDescription(guestOS.getDisplayName());
         response.setId(guestOS.getUuid());
         GuestOSCategoryVO category = ApiDBUtils.findGuestOsCategoryById(guestOS.getCategoryId());
-        if ( category != null ){
+        if (category != null) {
             response.setOsCategoryId(category.getUuid());
         }
 
@@ -3324,8 +3089,6 @@ public class ApiResponseHelper implements ResponseGenerator {
         return response;
     }
 
-
-
     @Override
     public SnapshotScheduleResponse createSnapshotScheduleResponse(SnapshotSchedule snapshotSchedule) {
         SnapshotScheduleResponse response = new SnapshotScheduleResponse();
@@ -3348,172 +3111,171 @@ public class ApiResponseHelper implements ResponseGenerator {
         return response;
     }
 
+    @Override
+    public UsageRecordResponse createUsageResponse(Usage usageRecord) {
+        UsageRecordResponse usageRecResponse = new UsageRecordResponse();
 
-	@Override
-	public UsageRecordResponse createUsageResponse(Usage usageRecord) {
-		UsageRecordResponse usageRecResponse = new UsageRecordResponse();
-
-		Account account = ApiDBUtils.findAccountByIdIncludingRemoved(usageRecord.getAccountId());
-		if (account.getType() == Account.ACCOUNT_TYPE_PROJECT) {
-			//find the project
-			Project project = ApiDBUtils.findProjectByProjectAccountIdIncludingRemoved(account.getId());
-			usageRecResponse.setProjectId(project.getUuid());
-			usageRecResponse.setProjectName(project.getName());
-		} else {
-			usageRecResponse.setAccountId(account.getUuid());
-			usageRecResponse.setAccountName(account.getAccountName());
-		}
-
-		Domain domain = ApiDBUtils.findDomainById(usageRecord.getDomainId());
-		if (domain != null) {
-			usageRecResponse.setDomainId(domain.getUuid());
-		}
-
-		if (usageRecord.getZoneId() != null) {
-			DataCenter zone = ApiDBUtils.findZoneById(usageRecord.getZoneId());
-			if (zone != null) {
-				usageRecResponse.setZoneId(zone.getUuid());
-			}
-		}
-		usageRecResponse.setDescription(usageRecord.getDescription());
-		usageRecResponse.setUsage(usageRecord.getUsageDisplay());
-		usageRecResponse.setUsageType(usageRecord.getUsageType());
-		if (usageRecord.getVmInstanceId() != null) {
-			VMInstanceVO vm = _entityMgr.findByIdIncludingRemoved(VMInstanceVO.class, usageRecord.getVmInstanceId());
-			usageRecResponse.setVirtualMachineId(vm.getUuid());
-		}
-		usageRecResponse.setVmName(usageRecord.getVmName());
-		if (usageRecord.getTemplateId() != null) {
-			VMTemplateVO template = ApiDBUtils.findTemplateById(usageRecord.getTemplateId());
-			if (template != null) {
-				usageRecResponse.setTemplateId(template.getUuid());
-			}
-		}
-
-		if(usageRecord.getUsageType() == UsageTypes.RUNNING_VM || usageRecord.getUsageType() == UsageTypes.ALLOCATED_VM){
-			ServiceOfferingVO svcOffering = _entityMgr.findByIdIncludingRemoved(ServiceOfferingVO.class, usageRecord.getOfferingId().toString());
-			//Service Offering Id
-			usageRecResponse.setOfferingId(svcOffering.getUuid());
-			//VM Instance ID
-			VMInstanceVO vm = _entityMgr.findByIdIncludingRemoved(VMInstanceVO.class, usageRecord.getUsageId().toString());
-			usageRecResponse.setUsageId(vm.getUuid());
-			//Hypervisor Type
-			usageRecResponse.setType(usageRecord.getType());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.IP_ADDRESS){
-			//isSourceNAT
-			usageRecResponse.setSourceNat((usageRecord.getType().equals("SourceNat"))?true:false);
-			//isSystem
-			usageRecResponse.setSystem((usageRecord.getSize() == 1)?true:false);
-			//IP Address ID
-			IPAddressVO ip = _entityMgr.findByIdIncludingRemoved(IPAddressVO.class, usageRecord.getUsageId().toString());
-			usageRecResponse.setUsageId(ip.getUuid());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.NETWORK_BYTES_SENT || usageRecord.getUsageType() == UsageTypes.NETWORK_BYTES_RECEIVED){
-			//Device Type
-			usageRecResponse.setType(usageRecord.getType());
-			if(usageRecord.getType().equals("DomainRouter")){
-				//Domain Router Id
-				VMInstanceVO vm = _entityMgr.findByIdIncludingRemoved(VMInstanceVO.class, usageRecord.getUsageId().toString());
-				usageRecResponse.setUsageId(vm.getUuid());
-			} else {
-				//External Device Host Id
-				HostVO host = _entityMgr.findByIdIncludingRemoved(HostVO.class, usageRecord.getUsageId().toString());
-				usageRecResponse.setUsageId(host.getUuid());
-			}
-			//Network ID
-			NetworkVO network = _entityMgr.findByIdIncludingRemoved(NetworkVO.class, usageRecord.getNetworkId().toString());
-			usageRecResponse.setNetworkId(network.getUuid());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.VOLUME){
-			//Volume ID
-			VolumeVO volume = _entityMgr.findByIdIncludingRemoved(VolumeVO.class, usageRecord.getUsageId().toString());
-			usageRecResponse.setUsageId(volume.getUuid());
-			//Volume Size
-			usageRecResponse.setSize(usageRecord.getSize());
-			//Disk Offering Id
-			if(usageRecord.getOfferingId() != null){
-				DiskOfferingVO diskOff = _entityMgr.findByIdIncludingRemoved(DiskOfferingVO.class, usageRecord.getOfferingId().toString());
-				usageRecResponse.setOfferingId(diskOff.getUuid());
-			}
-
-		} else if(usageRecord.getUsageType() == UsageTypes.TEMPLATE || usageRecord.getUsageType() == UsageTypes.ISO){
-			//Template/ISO ID
-			VMTemplateVO tmpl = _entityMgr.findByIdIncludingRemoved(VMTemplateVO.class, usageRecord.getUsageId().toString());
-			usageRecResponse.setUsageId(tmpl.getUuid());
-			//Template/ISO Size
-			usageRecResponse.setSize(usageRecord.getSize());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.SNAPSHOT){
-			//Snapshot ID
-			SnapshotVO snap = _entityMgr.findByIdIncludingRemoved(SnapshotVO.class, usageRecord.getUsageId().toString());
-			usageRecResponse.setUsageId(snap.getUuid());
-			//Snapshot Size
-			usageRecResponse.setSize(usageRecord.getSize());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.LOAD_BALANCER_POLICY){
-			//Load Balancer Policy ID
-			usageRecResponse.setUsageId(usageRecord.getUsageId().toString());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.PORT_FORWARDING_RULE){
-			//Port Forwarding Rule ID
-			usageRecResponse.setUsageId(usageRecord.getUsageId().toString());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.NETWORK_OFFERING){
-			//Network Offering Id
-			NetworkOfferingVO netOff = _entityMgr.findByIdIncludingRemoved(NetworkOfferingVO.class, usageRecord.getOfferingId().toString());
-			usageRecResponse.setOfferingId(netOff.getUuid());
-			//is Default
-			usageRecResponse.setDefault((usageRecord.getUsageId() == 1)? true:false);
-
-		} else if(usageRecord.getUsageType() == UsageTypes.VPN_USERS){
-			//VPN User ID
-			usageRecResponse.setUsageId(usageRecord.getUsageId().toString());
-
-		} else if(usageRecord.getUsageType() == UsageTypes.SECURITY_GROUP){
-			//Security Group Id
-			SecurityGroupVO sg = _entityMgr.findByIdIncludingRemoved(SecurityGroupVO.class, usageRecord.getUsageId().toString());
-			usageRecResponse.setUsageId(sg.getUuid());
-		}
-
-		if (usageRecord.getRawUsage() != null) {
-			DecimalFormat decimalFormat = new DecimalFormat("###########.######");
-			usageRecResponse.setRawUsage(decimalFormat.format(usageRecord.getRawUsage()));
-		}
-
-		if (usageRecord.getStartDate() != null) {
-			usageRecResponse.setStartDate(getDateStringInternal(usageRecord.getStartDate()));
-		}
-		if (usageRecord.getEndDate() != null) {
-			usageRecResponse.setEndDate(getDateStringInternal(usageRecord.getEndDate()));
-		}
-
-		return usageRecResponse;
-	}
+        Account account = ApiDBUtils.findAccountByIdIncludingRemoved(usageRecord.getAccountId());
+        if (account.getType() == Account.ACCOUNT_TYPE_PROJECT) {
+            // find the project
+            Project project = ApiDBUtils.findProjectByProjectAccountIdIncludingRemoved(account.getId());
+            usageRecResponse.setProjectId(project.getUuid());
+            usageRecResponse.setProjectName(project.getName());
+        } else {
+            usageRecResponse.setAccountId(account.getUuid());
+            usageRecResponse.setAccountName(account.getAccountName());
+        }
 
+        Domain domain = ApiDBUtils.findDomainById(usageRecord.getDomainId());
+        if (domain != null) {
+            usageRecResponse.setDomainId(domain.getUuid());
+        }
+
+        if (usageRecord.getZoneId() != null) {
+            DataCenter zone = ApiDBUtils.findZoneById(usageRecord.getZoneId());
+            if (zone != null) {
+                usageRecResponse.setZoneId(zone.getUuid());
+            }
+        }
+        usageRecResponse.setDescription(usageRecord.getDescription());
+        usageRecResponse.setUsage(usageRecord.getUsageDisplay());
+        usageRecResponse.setUsageType(usageRecord.getUsageType());
+        if (usageRecord.getVmInstanceId() != null) {
+            VMInstanceVO vm = _entityMgr.findByIdIncludingRemoved(VMInstanceVO.class, usageRecord.getVmInstanceId());
+            usageRecResponse.setVirtualMachineId(vm.getUuid());
+        }
+        usageRecResponse.setVmName(usageRecord.getVmName());
+        if (usageRecord.getTemplateId() != null) {
+            VMTemplateVO template = ApiDBUtils.findTemplateById(usageRecord.getTemplateId());
+            if (template != null) {
+                usageRecResponse.setTemplateId(template.getUuid());
+            }
+        }
+
+        if (usageRecord.getUsageType() == UsageTypes.RUNNING_VM || usageRecord.getUsageType() == UsageTypes.ALLOCATED_VM) {
+            ServiceOfferingVO svcOffering = _entityMgr.findByIdIncludingRemoved(ServiceOfferingVO.class, usageRecord.getOfferingId().toString());
+            // Service Offering Id
+            usageRecResponse.setOfferingId(svcOffering.getUuid());
+            // VM Instance ID
+            VMInstanceVO vm = _entityMgr.findByIdIncludingRemoved(VMInstanceVO.class, usageRecord.getUsageId().toString());
+            usageRecResponse.setUsageId(vm.getUuid());
+            // Hypervisor Type
+            usageRecResponse.setType(usageRecord.getType());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.IP_ADDRESS) {
+            // isSourceNAT
+            usageRecResponse.setSourceNat((usageRecord.getType().equals("SourceNat")) ? true : false);
+            // isSystem
+            usageRecResponse.setSystem((usageRecord.getSize() == 1) ? true : false);
+            // IP Address ID
+            IPAddressVO ip = _entityMgr.findByIdIncludingRemoved(IPAddressVO.class, usageRecord.getUsageId().toString());
+            usageRecResponse.setUsageId(ip.getUuid());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.NETWORK_BYTES_SENT || usageRecord.getUsageType() == UsageTypes.NETWORK_BYTES_RECEIVED) {
+            // Device Type
+            usageRecResponse.setType(usageRecord.getType());
+            if (usageRecord.getType().equals("DomainRouter")) {
+                // Domain Router Id
+                VMInstanceVO vm = _entityMgr.findByIdIncludingRemoved(VMInstanceVO.class, usageRecord.getUsageId().toString());
+                usageRecResponse.setUsageId(vm.getUuid());
+            } else {
+                // External Device Host Id
+                HostVO host = _entityMgr.findByIdIncludingRemoved(HostVO.class, usageRecord.getUsageId().toString());
+                usageRecResponse.setUsageId(host.getUuid());
+            }
+            // Network ID
+            NetworkVO network = _entityMgr.findByIdIncludingRemoved(NetworkVO.class, usageRecord.getNetworkId().toString());
+            usageRecResponse.setNetworkId(network.getUuid());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.VOLUME) {
+            // Volume ID
+            VolumeVO volume = _entityMgr.findByIdIncludingRemoved(VolumeVO.class, usageRecord.getUsageId().toString());
+            usageRecResponse.setUsageId(volume.getUuid());
+            // Volume Size
+            usageRecResponse.setSize(usageRecord.getSize());
+            // Disk Offering Id
+            if (usageRecord.getOfferingId() != null) {
+                DiskOfferingVO diskOff = _entityMgr.findByIdIncludingRemoved(DiskOfferingVO.class, usageRecord.getOfferingId().toString());
+                usageRecResponse.setOfferingId(diskOff.getUuid());
+            }
+
+        } else if (usageRecord.getUsageType() == UsageTypes.TEMPLATE || usageRecord.getUsageType() == UsageTypes.ISO) {
+            // Template/ISO ID
+            VMTemplateVO tmpl = _entityMgr.findByIdIncludingRemoved(VMTemplateVO.class, usageRecord.getUsageId().toString());
+            usageRecResponse.setUsageId(tmpl.getUuid());
+            // Template/ISO Size
+            usageRecResponse.setSize(usageRecord.getSize());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.SNAPSHOT) {
+            // Snapshot ID
+            SnapshotVO snap = _entityMgr.findByIdIncludingRemoved(SnapshotVO.class, usageRecord.getUsageId().toString());
+            usageRecResponse.setUsageId(snap.getUuid());
+            // Snapshot Size
+            usageRecResponse.setSize(usageRecord.getSize());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.LOAD_BALANCER_POLICY) {
+            // Load Balancer Policy ID
+            usageRecResponse.setUsageId(usageRecord.getUsageId().toString());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.PORT_FORWARDING_RULE) {
+            // Port Forwarding Rule ID
+            usageRecResponse.setUsageId(usageRecord.getUsageId().toString());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.NETWORK_OFFERING) {
+            // Network Offering Id
+            NetworkOfferingVO netOff = _entityMgr.findByIdIncludingRemoved(NetworkOfferingVO.class, usageRecord.getOfferingId().toString());
+            usageRecResponse.setOfferingId(netOff.getUuid());
+            // is Default
+            usageRecResponse.setDefault((usageRecord.getUsageId() == 1) ? true : false);
+
+        } else if (usageRecord.getUsageType() == UsageTypes.VPN_USERS) {
+            // VPN User ID
+            usageRecResponse.setUsageId(usageRecord.getUsageId().toString());
+
+        } else if (usageRecord.getUsageType() == UsageTypes.SECURITY_GROUP) {
+            // Security Group Id
+            SecurityGroupVO sg = _entityMgr.findByIdIncludingRemoved(SecurityGroupVO.class, usageRecord.getUsageId().toString());
+            usageRecResponse.setUsageId(sg.getUuid());
+        }
+
+        if (usageRecord.getRawUsage() != null) {
+            DecimalFormat decimalFormat = new DecimalFormat("###########.######");
+            usageRecResponse.setRawUsage(decimalFormat.format(usageRecord.getRawUsage()));
+        }
+
+        if (usageRecord.getStartDate() != null) {
+            usageRecResponse.setStartDate(getDateStringInternal(usageRecord.getStartDate()));
+        }
+        if (usageRecord.getEndDate() != null) {
+            usageRecResponse.setEndDate(getDateStringInternal(usageRecord.getEndDate()));
+        }
+
+        return usageRecResponse;
+    }
 
     public String getDateStringInternal(Date inputDate) {
-        if (inputDate == null) return null;
+        if (inputDate == null)
+            return null;
 
         TimeZone tz = _usageSvc.getUsageTimezone();
         Calendar cal = Calendar.getInstance(tz);
         cal.setTime(inputDate);
 
         StringBuffer sb = new StringBuffer();
-        sb.append(cal.get(Calendar.YEAR)+"-");
+        sb.append(cal.get(Calendar.YEAR) + "-");
 
         int month = cal.get(Calendar.MONTH) + 1;
         if (month < 10) {
             sb.append("0" + month + "-");
         } else {
-            sb.append(month+"-");
+            sb.append(month + "-");
         }
 
         int day = cal.get(Calendar.DAY_OF_MONTH);
         if (day < 10) {
             sb.append("0" + day);
         } else {
-            sb.append(""+day);
+            sb.append("" + day);
         }
 
         sb.append("'T'");
@@ -3522,38 +3284,40 @@ public class ApiResponseHelper implements ResponseGenerator {
         if (hour < 10) {
             sb.append("0" + hour + ":");
         } else {
-            sb.append(hour+":");
+            sb.append(hour + ":");
         }
 
         int minute = cal.get(Calendar.MINUTE);
         if (minute < 10) {
             sb.append("0" + minute + ":");
         } else {
-            sb.append(minute+":");
+            sb.append(minute + ":");
         }
 
         int seconds = cal.get(Calendar.SECOND);
         if (seconds < 10) {
             sb.append("0" + seconds);
         } else {
-            sb.append(""+seconds);
+            sb.append("" + seconds);
         }
 
         double offset = cal.get(Calendar.ZONE_OFFSET);
         if (tz.inDaylightTime(inputDate)) {
-            offset += (1.0*tz.getDSTSavings()); // add the timezone's DST value (typically 1 hour expressed in milliseconds)
+            offset += (1.0 * tz.getDSTSavings()); // add the timezone's DST
+                                                  // value (typically 1 hour
+                                                  // expressed in milliseconds)
         }
 
-        offset = offset / (1000d*60d*60d);
-        int hourOffset = (int)offset;
+        offset = offset / (1000d * 60d * 60d);
+        int hourOffset = (int) offset;
         double decimalVal = Math.abs(offset) - Math.abs(hourOffset);
-        int minuteOffset = (int)(decimalVal * 60);
+        int minuteOffset = (int) (decimalVal * 60);
 
         if (hourOffset < 0) {
             if (hourOffset > -10) {
-                sb.append("-0"+Math.abs(hourOffset));
+                sb.append("-0" + Math.abs(hourOffset));
             } else {
-                sb.append("-"+Math.abs(hourOffset));
+                sb.append("-" + Math.abs(hourOffset));
             }
         } else {
             if (hourOffset < 10) {
@@ -3607,7 +3371,7 @@ public class ApiResponseHelper implements ResponseGenerator {
             List<NicSecondaryIpVO> secondaryIps = ApiDBUtils.findNicSecondaryIps(result.getId());
             if (secondaryIps != null) {
                 List<NicSecondaryIpResponse> ipList = new ArrayList<NicSecondaryIpResponse>();
-                for (NicSecondaryIpVO ip: secondaryIps) {
+                for (NicSecondaryIpVO ip : secondaryIps) {
                     NicSecondaryIpResponse ipRes = new NicSecondaryIpResponse();
                     ipRes.setId(ip.getUuid());
                     ipRes.setIpAddr(ip.getIp4Address());


[5/5] git commit: updated refs/heads/object_store to 09ba551

Posted by mc...@apache.org.
Fix vmware plugin compilation error due to eclipse refactoring.

Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/09ba5510
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/09ba5510
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/09ba5510

Branch: refs/heads/object_store
Commit: 09ba55103e58cad6479bf3f73b150800f1052538
Parents: 5398247
Author: Min Chen <mi...@citrix.com>
Authored: Fri Apr 19 17:09:31 2013 -0700
Committer: Min Chen <mi...@citrix.com>
Committed: Fri Apr 19 17:09:31 2013 -0700

----------------------------------------------------------------------
 .../hypervisor/vmware/VmwareServerDiscoverer.java  |   14 +++++++-------
 .../vmware/manager/VmwareManagerImpl.java          |    8 ++++----
 .../hypervisor/vmware/resource/VmwareResource.java |    8 ++++----
 .../VmwareSecondaryStorageResourceHandler.java     |    4 ++--
 4 files changed, 17 insertions(+), 17 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/09ba5510/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/VmwareServerDiscoverer.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/VmwareServerDiscoverer.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/VmwareServerDiscoverer.java
index c4b53c2..00647d9 100755
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/VmwareServerDiscoverer.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/VmwareServerDiscoverer.java
@@ -119,9 +119,9 @@ public class VmwareServerDiscoverer extends DiscovererBase implements
 	public VmwareServerDiscoverer() {
 		s_logger.info("VmwareServerDiscoverer is constructed");
 	}
-	
+
 	@Override
-    public Map<? extends ServerResource, Map<String, String>> find(long dcId, Long podId, Long clusterId, URI url, 
+    public Map<? extends ServerResource, Map<String, String>> find(long dcId, Long podId, Long clusterId, URI url,
     	String username, String password, List<String> hostTags) throws DiscoveryException {
 
     	if(s_logger.isInfoEnabled())
@@ -312,7 +312,7 @@ public class VmwareServerDiscoverer extends DiscovererBase implements
 						.decode(uriFromCluster.getPath()));
 
 				if (morCluster == null
-						|| !morCluster.getProtocol().equalsIgnoreCase(
+						|| !morCluster.getType().equalsIgnoreCase(
 								"ClusterComputeResource")) {
 					s_logger.warn("Cluster url does not point to a valid vSphere cluster, url: "
 							+ clusterDetails.get("url"));
@@ -345,7 +345,7 @@ public class VmwareServerDiscoverer extends DiscovererBase implements
 				details.put("url", hostMo.getHostName());
 				details.put("username", username);
 				details.put("password", password);
-				String guid = morHost.getProtocol() + ":" + morHost.getValue()
+				String guid = morHost.getType() + ":" + morHost.getValue()
 						+ "@" + url.getHost();
 				details.put("guid", guid);
 
@@ -402,7 +402,7 @@ public class VmwareServerDiscoverer extends DiscovererBase implements
 			for (ManagedObjectReference morHost : morHosts) {
 				ManagedObjectReference morParent = (ManagedObjectReference) context
 						.getVimClient().getDynamicProperty(morHost, "parent");
-				if (morParent.getProtocol().equalsIgnoreCase(
+				if (morParent.getType().equalsIgnoreCase(
 						"ClusterComputeResource"))
 					return false;
 			}
@@ -410,7 +410,7 @@ public class VmwareServerDiscoverer extends DiscovererBase implements
 			for (ManagedObjectReference morHost : morHosts) {
 				ManagedObjectReference morParent = (ManagedObjectReference) context
 						.getVimClient().getDynamicProperty(morHost, "parent");
-				if (!morParent.getProtocol().equalsIgnoreCase(
+				if (!morParent.getType().equalsIgnoreCase(
 						"ClusterComputeResource"))
 					return false;
 
@@ -637,7 +637,7 @@ public class VmwareServerDiscoverer extends DiscovererBase implements
             return VirtualSwitchType.NexusDistributedVirtualSwitch;
         else if(useDVS)
             return VirtualSwitchType.VMwareDistributedVirtualSwitch;
-        else 
+        else
             return VirtualSwitchType.StandardVirtualSwitch;
     }
 

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/09ba5510/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java
index adcf23b..b2e3768 100755
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java
@@ -336,7 +336,7 @@ public class VmwareManagerImpl extends ManagerBase implements VmwareManager, Vmw
         if(mor != null) {
             List<ManagedObjectReference> returnedHostList = new ArrayList<ManagedObjectReference>();
 
-            if(mor.getProtocol().equals("ComputeResource")) {
+            if(mor.getType().equals("ComputeResource")) {
                 List<ManagedObjectReference> hosts = (List<ManagedObjectReference>)serviceContext.getVimClient().getDynamicProperty(mor, "host");
                 assert(hosts != null && hosts.size() > 0);
 
@@ -346,7 +346,7 @@ public class VmwareManagerImpl extends ManagerBase implements VmwareManager, Vmw
                 prepareHost(hostMo, privateTrafficLabel);
                 returnedHostList.add(hosts.get(0));
                 return returnedHostList;
-            } else if(mor.getProtocol().equals("ClusterComputeResource")) {
+            } else if(mor.getType().equals("ClusterComputeResource")) {
                 List<ManagedObjectReference> hosts = (List<ManagedObjectReference>)serviceContext.getVimClient().getDynamicProperty(mor, "host");
                 assert(hosts != null);
 
@@ -368,14 +368,14 @@ public class VmwareManagerImpl extends ManagerBase implements VmwareManager, Vmw
                     returnedHostList.add(morHost);
                 }
                 return returnedHostList;
-            } else if(mor.getProtocol().equals("HostSystem")) {
+            } else if(mor.getType().equals("HostSystem")) {
                 // For ESX host, we need to enable host firewall to allow VNC access
                 HostMO hostMo = new HostMO(serviceContext, mor);
                 prepareHost(hostMo, privateTrafficLabel);
                 returnedHostList.add(mor);
                 return returnedHostList;
             } else {
-                s_logger.error("Unsupport host type " + mor.getProtocol() + ":" + mor.getValue() + " from inventory path: " + hostInventoryPath);
+                s_logger.error("Unsupport host type " + mor.getType() + ":" + mor.getValue() + " from inventory path: " + hostInventoryPath);
                 return null;
             }
         }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/09ba5510/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
index b7218ef..0f85f4e 100755
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
@@ -1755,11 +1755,11 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
         	args += " -6 " + cmd.getVmIp6Address();
         	args += " -u " + cmd.getDuid();
         }
-        
+
         if (!cmd.isDefault()) {
         	args += " -N";
         }
-        
+
         if (s_logger.isDebugEnabled()) {
             s_logger.debug("Run command on domR " + cmd.getAccessDetail(NetworkElementCommand.ROUTER_IP) + ", /root/edithosts.sh " + args);
         }
@@ -4470,7 +4470,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
 
             ManagedObjectReference morParent = vmOwnerHost.getParentMor();
             HashMap<String, Integer> portInfo;
-            if(morParent.getProtocol().equalsIgnoreCase("ClusterComputeResource")) {
+            if(morParent.getType().equalsIgnoreCase("ClusterComputeResource")) {
                 ClusterMO clusterMo = new ClusterMO(vmOwnerHost.getContext(), morParent);
                 portInfo = clusterMo.getVmVncPortsOnCluster();
             } else {
@@ -5067,7 +5067,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
 
     @Override
     public VmwareHypervisorHost getHyperHost(VmwareContext context, Command cmd) {
-        if (_morHyperHost.getProtocol().equalsIgnoreCase("HostSystem")) {
+        if (_morHyperHost.getType().equalsIgnoreCase("HostSystem")) {
             return new HostMO(context, _morHyperHost);
         }
         return new ClusterMO(context, _morHyperHost);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/09ba5510/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java b/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
index bb5abb9..566e750 100644
--- a/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
@@ -221,7 +221,7 @@ public class VmwareSecondaryStorageResourceHandler implements SecondaryStorageRe
         morHyperHost.setType(hostTokens[0]);
         morHyperHost.setValue(hostTokens[1]);
 
-        if(morHyperHost.getProtocol().equalsIgnoreCase("HostSystem")) {
+        if(morHyperHost.getType().equalsIgnoreCase("HostSystem")) {
             HostMO hostMo =  new HostMO(context, morHyperHost);
 
             try {
@@ -278,7 +278,7 @@ public class VmwareSecondaryStorageResourceHandler implements SecondaryStorageRe
         morHyperHost.setType(hostTokens[0]);
         morHyperHost.setValue(hostTokens[1]);
 
-        if(morHyperHost.getProtocol().equalsIgnoreCase("HostSystem")) {
+        if(morHyperHost.getType().equalsIgnoreCase("HostSystem")) {
             HostMO hostMo =  new HostMO(context, morHyperHost);
             try {
                 VmwareHypervisorHostNetworkSummary netSummary = hostMo.getHyperHostNetworkSummary(


[4/5] git commit: updated refs/heads/object_store to 09ba551

Posted by mc...@apache.org.
Refactor listTemplatesCmd and listIsoCmd to use db view.

Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/53982479
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/53982479
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/53982479

Branch: refs/heads/object_store
Commit: 539824797c01a992d3f7868f5ad18848e066dbca
Parents: 7ba1a8f
Author: Min Chen <mi...@citrix.com>
Authored: Fri Apr 19 16:10:09 2013 -0700
Committer: Min Chen <mi...@citrix.com>
Committed: Fri Apr 19 16:10:09 2013 -0700

----------------------------------------------------------------------
 api/src/com/cloud/server/ManagementService.java    |   22 -
 .../apache/cloudstack/api/ResponseGenerator.java   |   14 +-
 .../command/admin/template/PrepareTemplateCmd.java |    2 +-
 .../api/command/user/iso/ListIsosCmd.java          |   11 +-
 .../api/command/user/iso/RegisterIsoCmd.java       |    6 +-
 .../api/command/user/iso/UpdateIsoCmd.java         |    2 +-
 .../api/command/user/template/CopyTemplateCmd.java |    2 +-
 .../command/user/template/ListTemplatesCmd.java    |   16 +-
 .../command/user/template/RegisterTemplateCmd.java |    2 +-
 .../command/user/template/UpdateTemplateCmd.java   |    2 +-
 .../cloudstack/api/response/TemplateResponse.java  |   35 +-
 .../api/response/TemplateZoneResponse.java         |   90 ++
 .../org/apache/cloudstack/query/QueryService.java  |    7 +
 server/src/com/cloud/api/ApiDBUtils.java           |   36 +
 server/src/com/cloud/api/ApiResponseHelper.java    |  838 +++++--------
 .../src/com/cloud/api/query/QueryManagerImpl.java  |  321 +++++
 .../com/cloud/api/query/ViewResponseHelper.java    |   53 +
 .../com/cloud/api/query/dao/TemplateJoinDao.java   |   42 +
 .../cloud/api/query/dao/TemplateJoinDaoImpl.java   |  441 +++++++
 .../src/com/cloud/api/query/vo/TemplateJoinVO.java | 1006 +++++++++++++++
 .../src/com/cloud/server/ManagementServerImpl.java |   66 +-
 .../src/com/cloud/storage/dao/VMTemplateDao.java   |   17 +-
 .../com/cloud/storage/dao/VMTemplateDaoImpl.java   |   36 +-
 .../com/cloud/template/TemplateManagerImpl.java    |    1 +
 setup/db/db/schema-410to420.sql                    |   95 ++
 25 files changed, 2472 insertions(+), 691 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/com/cloud/server/ManagementService.java
----------------------------------------------------------------------
diff --git a/api/src/com/cloud/server/ManagementService.java b/api/src/com/cloud/server/ManagementService.java
index d58ea3e..674f67c 100755
--- a/api/src/com/cloud/server/ManagementService.java
+++ b/api/src/com/cloud/server/ManagementService.java
@@ -219,28 +219,6 @@ public interface ManagementService {
      */
     List<? extends Capacity> listCapacities(ListCapacityCmd cmd);
 
-    /**
-     * List ISOs that match the specified criteria.
-     *
-     * @param cmd
-     *            The command that wraps the (optional) templateId, name, keyword, templateFilter, bootable, account,
-     *            and zoneId
-     *            parameters.
-     * @return list of ISOs
-     */
-    Set<Pair<Long, Long>> listIsos(ListIsosCmd cmd);
-
-    /**
-     * List templates that match the specified criteria.
-     *
-     * @param cmd
-     *            The command that wraps the (optional) templateId, name, keyword, templateFilter, bootable, account,
-     *            and zoneId
-     *            parameters.
-     * @return list of ISOs
-     */
-    Set<Pair<Long, Long>> listTemplates(ListTemplatesCmd cmd);
-
 
     /**
      * List system VMs by the given search criteria

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/ResponseGenerator.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/ResponseGenerator.java b/api/src/org/apache/cloudstack/api/ResponseGenerator.java
index 3d381b0..77d3bea 100644
--- a/api/src/org/apache/cloudstack/api/ResponseGenerator.java
+++ b/api/src/org/apache/cloudstack/api/ResponseGenerator.java
@@ -241,7 +241,7 @@ public interface ResponseGenerator {
 
     Host findHostById(Long hostId);
 
-    List<TemplateResponse> createTemplateResponses(long templateId, long zoneId, boolean readyOnly);
+    //List<TemplateResponse> createTemplateResponses(long templateId, long zoneId, boolean readyOnly);
 
     VpnUsersResponse createVpnUserResponse(VpnUser user);
 
@@ -267,7 +267,9 @@ public interface ResponseGenerator {
 
     //List<EventResponse> createEventResponse(EventJoinVO... events);
 
-    TemplateResponse createIsoResponse(VirtualMachineTemplate result);
+    TemplateResponse createTemplateUpdateResponse(VirtualMachineTemplate result);
+
+    List<TemplateResponse> createTemplateResponses(VirtualMachineTemplate result, Long zoneId, boolean readyOnly);
 
     List<CapacityResponse> createCapacityResponse(List<? extends Capacity> result, DecimalFormat format);
 
@@ -287,12 +289,12 @@ public interface ResponseGenerator {
 
     Long getSecurityGroupId(String groupName, long accountId);
 
-    List<TemplateResponse> createIsoResponses(long isoId, Long zoneId, boolean readyOnly);
-
-    ProjectResponse createProjectResponse(Project project);
+    List<TemplateResponse> createIsoResponses(VirtualMachineTemplate iso, Long zoneId, boolean readyOnly);
 
+   // List<TemplateResponse> createIsoResponses(long isoId, Long zoneId, boolean readyOnly);
+    //List<TemplateResponse> createIsoResponses(VirtualMachineTemplate iso, long zoneId, boolean readyOnly);
 
-    List<TemplateResponse> createIsoResponses(VirtualMachineTemplate iso, long zoneId, boolean readyOnly);
+    ProjectResponse createProjectResponse(Project project);
 
     List<TemplateResponse> createTemplateResponses(long templateId, Long vmId);
 

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/admin/template/PrepareTemplateCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/admin/template/PrepareTemplateCmd.java b/api/src/org/apache/cloudstack/api/command/admin/template/PrepareTemplateCmd.java
index 7d41d10..aee35ad 100644
--- a/api/src/org/apache/cloudstack/api/command/admin/template/PrepareTemplateCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/admin/template/PrepareTemplateCmd.java
@@ -80,7 +80,7 @@ public class PrepareTemplateCmd extends BaseCmd {
         ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
 
         VirtualMachineTemplate vmTemplate = _templateService.prepareTemplate(templateId, zoneId);
-        List<TemplateResponse> templateResponses = _responseGenerator.createTemplateResponses(vmTemplate.getId(), zoneId, true);
+        List<TemplateResponse> templateResponses = _responseGenerator.createTemplateResponses(vmTemplate, zoneId, true);
         response.setResponses(templateResponses);
         response.setResponseName(getCommandName());
         this.setResponseObject(response);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/iso/ListIsosCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/iso/ListIsosCmd.java b/api/src/org/apache/cloudstack/api/command/user/iso/ListIsosCmd.java
index 3219601..b490ca9 100644
--- a/api/src/org/apache/cloudstack/api/command/user/iso/ListIsosCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/iso/ListIsosCmd.java
@@ -148,16 +148,7 @@ public class ListIsosCmd extends BaseListTaggedResourcesCmd {
 
     @Override
     public void execute(){
-        Set<Pair<Long, Long>> isoZonePairSet = _mgr.listIsos(this);
-        ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
-        List<TemplateResponse> templateResponses = new ArrayList<TemplateResponse>();
-
-        for (Pair<Long, Long> iso : isoZonePairSet) {
-            List<TemplateResponse> responses = new ArrayList<TemplateResponse>();
-            responses = _responseGenerator.createIsoResponses(iso.first(), iso.second(), listInReadyState());
-            templateResponses.addAll(responses);
-        }
-        response.setResponses(templateResponses);
+        ListResponse<TemplateResponse> response = _queryService.listIsos(this);
         response.setResponseName(getCommandName());
         this.setResponseObject(response);
     }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/iso/RegisterIsoCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/iso/RegisterIsoCmd.java b/api/src/org/apache/cloudstack/api/command/user/iso/RegisterIsoCmd.java
index 284d553..0fa47eb 100644
--- a/api/src/org/apache/cloudstack/api/command/user/iso/RegisterIsoCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/iso/RegisterIsoCmd.java
@@ -88,7 +88,7 @@ public class RegisterIsoCmd extends BaseCmd {
     @Parameter(name=ApiConstants.PROJECT_ID, type=CommandType.UUID, entityType = ProjectResponse.class,
             description="Register iso for the project")
     private Long projectId;
-    
+
     @Parameter(name=ApiConstants.IMAGE_STORE_UUID, type=CommandType.STRING,
             description="Image store uuid")
     private String imageStoreUuid;
@@ -144,7 +144,7 @@ public class RegisterIsoCmd extends BaseCmd {
     public String getChecksum() {
         return checksum;
     }
-    
+
     public String getImageStoreUuid() {
         return this.imageStoreUuid;
     }
@@ -173,7 +173,7 @@ public class RegisterIsoCmd extends BaseCmd {
         VirtualMachineTemplate template = _templateService.registerIso(this);
         if (template != null) {
             ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
-            List<TemplateResponse> templateResponses = _responseGenerator.createIsoResponses(template.getId(), zoneId, false);
+            List<TemplateResponse> templateResponses = _responseGenerator.createIsoResponses(template, zoneId, false);
             response.setResponses(templateResponses);
             response.setResponseName(getCommandName());
             this.setResponseObject(response);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/iso/UpdateIsoCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/iso/UpdateIsoCmd.java b/api/src/org/apache/cloudstack/api/command/user/iso/UpdateIsoCmd.java
index 1384fa8..1d84847 100644
--- a/api/src/org/apache/cloudstack/api/command/user/iso/UpdateIsoCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/iso/UpdateIsoCmd.java
@@ -68,7 +68,7 @@ public class UpdateIsoCmd extends BaseUpdateTemplateOrIsoCmd {
     public void execute(){
         VirtualMachineTemplate result = _templateService.updateTemplate(this);
         if (result != null) {
-            TemplateResponse response = _responseGenerator.createIsoResponse(result);
+            TemplateResponse response = _responseGenerator.createTemplateUpdateResponse(result);
             response.setResponseName(getCommandName());
             this.setResponseObject(response);
         } else {

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/template/CopyTemplateCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/template/CopyTemplateCmd.java b/api/src/org/apache/cloudstack/api/command/user/template/CopyTemplateCmd.java
index a4f0582..34ee4bd 100644
--- a/api/src/org/apache/cloudstack/api/command/user/template/CopyTemplateCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/template/CopyTemplateCmd.java
@@ -124,7 +124,7 @@ public class CopyTemplateCmd extends BaseAsyncCmd {
             VirtualMachineTemplate template = _templateService.copyTemplate(this);
 
             if (template != null){
-                List<TemplateResponse> listResponse = _responseGenerator.createTemplateResponses(template.getId(), getDestinationZoneId(), false);
+                List<TemplateResponse> listResponse = _responseGenerator.createTemplateResponses(template, getDestinationZoneId(), false);
                 TemplateResponse response = new TemplateResponse();
                 if (listResponse != null && !listResponse.isEmpty()) {
                     response = listResponse.get(0);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/template/ListTemplatesCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/template/ListTemplatesCmd.java b/api/src/org/apache/cloudstack/api/command/user/template/ListTemplatesCmd.java
index aeb76f5..0b937be 100644
--- a/api/src/org/apache/cloudstack/api/command/user/template/ListTemplatesCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/template/ListTemplatesCmd.java
@@ -26,6 +26,7 @@ import org.apache.cloudstack.api.BaseListTaggedResourcesCmd;
 import org.apache.cloudstack.api.Parameter;
 import org.apache.cloudstack.api.response.ListResponse;
 import org.apache.cloudstack.api.response.TemplateResponse;
+import org.apache.cloudstack.api.response.VolumeResponse;
 import org.apache.cloudstack.api.response.ZoneResponse;
 import org.apache.log4j.Logger;
 
@@ -55,7 +56,7 @@ public class ListTemplatesCmd extends BaseListTaggedResourcesCmd {
     @Parameter(name=ApiConstants.NAME, type=CommandType.STRING, description="the template name")
     private String templateName;
 
-    @Parameter(name=ApiConstants.TEMPLATE_FILTER, type=CommandType.STRING, required=true, description="possible values are \"featured\", \"self\", \"selfexecutable\",\"sharedexecutable\",\"executable\", and \"community\". " + 
+    @Parameter(name=ApiConstants.TEMPLATE_FILTER, type=CommandType.STRING, required=true, description="possible values are \"featured\", \"self\", \"selfexecutable\",\"sharedexecutable\",\"executable\", and \"community\". " +
                                                                                         "* featured : templates that have been marked as featured and public. " +
                                                                                         "* self : templates that have been registered or created by the calling user. " +
                                                                                         "* selfexecutable : same as self, but only returns templates that can be used to deploy a new VM. " +
@@ -119,18 +120,7 @@ public class ListTemplatesCmd extends BaseListTaggedResourcesCmd {
 
     @Override
     public void execute(){
-        Set<Pair<Long, Long>> templateZonePairSet = _mgr.listTemplates(this);
-
-        ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
-        List<TemplateResponse> templateResponses = new ArrayList<TemplateResponse>();
-
-        for (Pair<Long, Long> template : templateZonePairSet) {
-            List<TemplateResponse> responses = new ArrayList<TemplateResponse>();
-            responses = _responseGenerator.createTemplateResponses(template.first().longValue(), template.second(), listInReadyState());
-            templateResponses.addAll(responses);
-        }
-
-        response.setResponses(templateResponses);
+        ListResponse<TemplateResponse> response = _queryService.listTemplates(this);
         response.setResponseName(getCommandName());
         this.setResponseObject(response);
     }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/template/RegisterTemplateCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/template/RegisterTemplateCmd.java b/api/src/org/apache/cloudstack/api/command/user/template/RegisterTemplateCmd.java
index f93c9f4..974edb3 100644
--- a/api/src/org/apache/cloudstack/api/command/user/template/RegisterTemplateCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/template/RegisterTemplateCmd.java
@@ -230,7 +230,7 @@ public class RegisterTemplateCmd extends BaseCmd {
             VirtualMachineTemplate template = _templateService.registerTemplate(this);
             if (template != null){
                 ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
-                List<TemplateResponse> templateResponses = _responseGenerator.createTemplateResponses(template.getId(), zoneId, false);
+                List<TemplateResponse> templateResponses = _responseGenerator.createTemplateResponses(template, zoneId, false);
                 response.setResponses(templateResponses);
                 response.setResponseName(getCommandName());
                 this.setResponseObject(response);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/command/user/template/UpdateTemplateCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/template/UpdateTemplateCmd.java b/api/src/org/apache/cloudstack/api/command/user/template/UpdateTemplateCmd.java
index e342fb1..9f55f9d 100644
--- a/api/src/org/apache/cloudstack/api/command/user/template/UpdateTemplateCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/template/UpdateTemplateCmd.java
@@ -68,7 +68,7 @@ public class UpdateTemplateCmd extends BaseUpdateTemplateOrIsoCmd {
     public void execute(){
         VirtualMachineTemplate result = _templateService.updateTemplate(this);
         if (result != null) {
-            TemplateResponse response = _responseGenerator.createIsoResponse(result);
+            TemplateResponse response = _responseGenerator.createTemplateUpdateResponse(result);
             response.setObjectName("template");
             response.setResponseName(getCommandName());
             this.setResponseObject(response);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/response/TemplateResponse.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/response/TemplateResponse.java b/api/src/org/apache/cloudstack/api/response/TemplateResponse.java
index ed933ff..225edd5 100644
--- a/api/src/org/apache/cloudstack/api/response/TemplateResponse.java
+++ b/api/src/org/apache/cloudstack/api/response/TemplateResponse.java
@@ -17,8 +17,10 @@
 package org.apache.cloudstack.api.response;
 
 import java.util.Date;
+import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Map;
+import java.util.Set;
 
 import org.apache.cloudstack.api.ApiConstants;
 import org.apache.cloudstack.api.BaseResponse;
@@ -31,7 +33,7 @@ import com.google.gson.annotations.SerializedName;
 
 @EntityReference(value=VirtualMachineTemplate.class)
 @SuppressWarnings("unused")
-public class TemplateResponse extends BaseResponse implements ControlledEntityResponse {
+public class TemplateResponse extends BaseResponse implements ControlledViewEntityResponse {
     @SerializedName(ApiConstants.ID) @Param(description="the template ID")
     private String id;
 
@@ -82,6 +84,8 @@ public class TemplateResponse extends BaseResponse implements ControlledEntityRe
     @SerializedName(ApiConstants.ACCOUNT) @Param(description="the account name to which the template belongs")
     private String account;
 
+    //TODO: since a template can be associated to more than one zones, this model is not accurate. For backward-compatibility, keep these fields
+    // here, but add a zones field to capture multiple zones.
     @SerializedName(ApiConstants.ZONE_ID) @Param(description="the ID of the zone for this template")
     private String zoneId;
 
@@ -133,12 +137,20 @@ public class TemplateResponse extends BaseResponse implements ControlledEntityRe
     @SerializedName(ApiConstants.DETAILS) @Param(description="additional key/value details tied with template")
     private Map details;
 
+    @SerializedName("zones")  @Param(description="list of zones associated with tempate", responseObject = TemplateZoneResponse.class)
+    private Set<TemplateZoneResponse> zones;
+
     @SerializedName(ApiConstants.TAGS)  @Param(description="the list of resource tags associated with tempate", responseObject = ResourceTagResponse.class)
-    private List<ResourceTagResponse> tags;
+    private Set<ResourceTagResponse> tags;
 
     @SerializedName(ApiConstants.SSHKEY_ENABLED) @Param(description="true if template is sshkey enabled, false otherwise")
     private Boolean sshKeyEnabled;
 
+    public TemplateResponse(){
+        zones = new LinkedHashSet<TemplateZoneResponse>();
+        tags = new LinkedHashSet<ResourceTagResponse>();
+    }
+
     @Override
     public String getObjectId() {
         return this.getId();
@@ -288,12 +300,29 @@ public class TemplateResponse extends BaseResponse implements ControlledEntityRe
         this.details = details;
     }
 
-    public void setTags(List<ResourceTagResponse> tags) {
+    public void setTags(Set<ResourceTagResponse> tags) {
         this.tags = tags;
     }
 
+    public void addTag(ResourceTagResponse tag){
+        this.tags.add(tag);
+    }
+
+    public void setZones(Set<TemplateZoneResponse> zones){
+        this.zones = zones;
+    }
+
+    public void addZone(TemplateZoneResponse zone){
+        this.zones.add(zone);
+    }
+
     public void setSshKeyEnabled(boolean sshKeyEnabled) {
         this.sshKeyEnabled = sshKeyEnabled;
     }
 
+    public String getZoneId() {
+        return zoneId;
+    }
+
+
 }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/api/response/TemplateZoneResponse.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/response/TemplateZoneResponse.java b/api/src/org/apache/cloudstack/api/response/TemplateZoneResponse.java
new file mode 100644
index 0000000..9d26ad9
--- /dev/null
+++ b/api/src/org/apache/cloudstack/api/response/TemplateZoneResponse.java
@@ -0,0 +1,90 @@
+// 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.response;
+
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.BaseResponse;
+
+import com.cloud.serializer.Param;
+import com.google.gson.annotations.SerializedName;
+
+public class TemplateZoneResponse extends BaseResponse {
+    @SerializedName(ApiConstants.ZONE_ID) @Param(description="the ID of the zone for the template")
+    private String zoneId;
+
+    @SerializedName(ApiConstants.ZONE_NAME) @Param(description="the name of the zone for the template")
+    private String zoneName;
+
+
+    public TemplateZoneResponse(){
+        super();
+    }
+
+    public TemplateZoneResponse(String zoneId, String zoneName){
+        super();
+        this.zoneId = zoneId;
+        this.zoneName = zoneName;
+    }
+
+
+
+    public String getZoneId() {
+        return zoneId;
+    }
+
+    public void setZoneId(String zoneId) {
+        this.zoneId = zoneId;
+    }
+
+    public String getZoneName() {
+        return zoneName;
+    }
+
+    public void setZoneName(String zoneName) {
+        this.zoneName = zoneName;
+    }
+
+    @Override
+    public int hashCode() {
+        final int prime = 31;
+        int result = 1;
+        String oid = this.getZoneId();
+        result = prime * result + ((oid== null) ? 0 : oid.hashCode());
+        return result;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj)
+            return true;
+        if (obj == null)
+            return false;
+        if (getClass() != obj.getClass())
+            return false;
+        TemplateZoneResponse other = (TemplateZoneResponse) obj;
+        String oid = this.getZoneId();
+        if (oid == null) {
+            if (other.getZoneId() != null)
+                return false;
+        } else if (!oid.equals(other.getZoneId()))
+            return false;
+        else if ( this.getZoneName().equals(other.getZoneName()))
+            return false;
+        return true;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/api/src/org/apache/cloudstack/query/QueryService.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/query/QueryService.java b/api/src/org/apache/cloudstack/query/QueryService.java
index 66f6399..4efbd1c 100644
--- a/api/src/org/apache/cloudstack/query/QueryService.java
+++ b/api/src/org/apache/cloudstack/query/QueryService.java
@@ -24,6 +24,7 @@ import org.apache.cloudstack.api.command.admin.user.ListUsersCmd;
 import org.apache.cloudstack.api.command.user.account.ListAccountsCmd;
 import org.apache.cloudstack.api.command.user.account.ListProjectAccountsCmd;
 import org.apache.cloudstack.api.command.user.event.ListEventsCmd;
+import org.apache.cloudstack.api.command.user.iso.ListIsosCmd;
 import org.apache.cloudstack.api.command.user.job.ListAsyncJobsCmd;
 import org.apache.cloudstack.api.command.user.offering.ListDiskOfferingsCmd;
 import org.apache.cloudstack.api.command.user.offering.ListServiceOfferingsCmd;
@@ -31,6 +32,7 @@ import org.apache.cloudstack.api.command.user.project.ListProjectInvitationsCmd;
 import org.apache.cloudstack.api.command.user.project.ListProjectsCmd;
 import org.apache.cloudstack.api.command.user.securitygroup.ListSecurityGroupsCmd;
 import org.apache.cloudstack.api.command.user.tag.ListTagsCmd;
+import org.apache.cloudstack.api.command.user.template.ListTemplatesCmd;
 import org.apache.cloudstack.api.command.user.vm.ListVMsCmd;
 import org.apache.cloudstack.api.command.user.vmgroup.ListVMGroupsCmd;
 import org.apache.cloudstack.api.command.user.volume.ListVolumesCmd;
@@ -51,6 +53,7 @@ import org.apache.cloudstack.api.response.ResourceTagResponse;
 import org.apache.cloudstack.api.response.SecurityGroupResponse;
 import org.apache.cloudstack.api.response.ServiceOfferingResponse;
 import org.apache.cloudstack.api.response.StoragePoolResponse;
+import org.apache.cloudstack.api.response.TemplateResponse;
 import org.apache.cloudstack.api.response.UserResponse;
 import org.apache.cloudstack.api.response.UserVmResponse;
 import org.apache.cloudstack.api.response.VolumeResponse;
@@ -101,4 +104,8 @@ public interface QueryService {
     public ListResponse<ServiceOfferingResponse>  searchForServiceOfferings(ListServiceOfferingsCmd cmd);
 
     public ListResponse<ZoneResponse>  listDataCenters(ListZonesByCmd cmd);
+
+    public ListResponse<TemplateResponse> listTemplates(ListTemplatesCmd cmd);
+
+    public ListResponse<TemplateResponse> listIsos(ListIsosCmd cmd);
 }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/ApiDBUtils.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/ApiDBUtils.java b/server/src/com/cloud/api/ApiDBUtils.java
index 6b8607f..00358d7 100755
--- a/server/src/com/cloud/api/ApiDBUtils.java
+++ b/server/src/com/cloud/api/ApiDBUtils.java
@@ -42,6 +42,7 @@ import org.apache.cloudstack.api.response.ResourceTagResponse;
 import org.apache.cloudstack.api.response.SecurityGroupResponse;
 import org.apache.cloudstack.api.response.ServiceOfferingResponse;
 import org.apache.cloudstack.api.response.StoragePoolResponse;
+import org.apache.cloudstack.api.response.TemplateResponse;
 import org.apache.cloudstack.api.response.UserResponse;
 import org.apache.cloudstack.api.response.UserVmResponse;
 import org.apache.cloudstack.api.response.VolumeResponse;
@@ -65,6 +66,7 @@ import com.cloud.api.query.dao.ResourceTagJoinDao;
 import com.cloud.api.query.dao.SecurityGroupJoinDao;
 import com.cloud.api.query.dao.ServiceOfferingJoinDao;
 import com.cloud.api.query.dao.StoragePoolJoinDao;
+import com.cloud.api.query.dao.TemplateJoinDao;
 import com.cloud.api.query.dao.UserAccountJoinDao;
 import com.cloud.api.query.dao.UserVmJoinDao;
 import com.cloud.api.query.dao.VolumeJoinDao;
@@ -84,6 +86,7 @@ import com.cloud.api.query.vo.ResourceTagJoinVO;
 import com.cloud.api.query.vo.SecurityGroupJoinVO;
 import com.cloud.api.query.vo.ServiceOfferingJoinVO;
 import com.cloud.api.query.vo.StoragePoolJoinVO;
+import com.cloud.api.query.vo.TemplateJoinVO;
 import com.cloud.api.query.vo.UserAccountJoinVO;
 import com.cloud.api.query.vo.UserVmJoinVO;
 import com.cloud.api.query.vo.VolumeJoinVO;
@@ -240,6 +243,7 @@ import com.cloud.storage.dao.VolumeDao;
 import com.cloud.storage.dao.VolumeHostDao;
 import com.cloud.storage.snapshot.SnapshotPolicy;
 import com.cloud.template.TemplateManager;
+import com.cloud.template.VirtualMachineTemplate;
 import com.cloud.user.Account;
 import com.cloud.user.AccountDetailsDao;
 import com.cloud.user.AccountVO;
@@ -369,6 +373,7 @@ public class ApiDBUtils {
     static ImageStoreJoinDao _imageStoreJoinDao;
     static AccountJoinDao _accountJoinDao;
     static AsyncJobJoinDao _jobJoinDao;
+    static TemplateJoinDao _templateJoinDao;
 
     static PhysicalNetworkTrafficTypeDao _physicalNetworkTrafficTypeDao;
     static PhysicalNetworkServiceProviderDao _physicalNetworkServiceProviderDao;
@@ -474,6 +479,7 @@ public class ApiDBUtils {
     @Inject private ImageStoreJoinDao imageStoreJoinDao;
     @Inject private AccountJoinDao accountJoinDao;
     @Inject private AsyncJobJoinDao jobJoinDao;
+    @Inject private TemplateJoinDao templateJoinDao;
 
     @Inject private PhysicalNetworkTrafficTypeDao physicalNetworkTrafficTypeDao;
     @Inject private PhysicalNetworkServiceProviderDao physicalNetworkServiceProviderDao;
@@ -575,6 +581,7 @@ public class ApiDBUtils {
         _imageStoreJoinDao = imageStoreJoinDao;
         _accountJoinDao = accountJoinDao;
         _jobJoinDao = jobJoinDao;
+        _templateJoinDao = templateJoinDao;
 
         _physicalNetworkTrafficTypeDao = physicalNetworkTrafficTypeDao;
         _physicalNetworkServiceProviderDao = physicalNetworkServiceProviderDao;
@@ -1606,4 +1613,33 @@ public class ApiDBUtils {
    public static List<NicSecondaryIpVO> findNicSecondaryIps(long nicId) {
        return _nicSecondaryIpDao.listByNicId(nicId);
    }
+
+
+   public static TemplateResponse newTemplateUpdateResponse(TemplateJoinVO vr) {
+       return _templateJoinDao.newUpdateResponse(vr);
+   }
+
+
+   public static TemplateResponse newTemplateResponse(TemplateJoinVO vr) {
+       return _templateJoinDao.newTemplateResponse(vr);
+   }
+
+
+   public static TemplateResponse newIsoResponse(TemplateJoinVO vr) {
+       return _templateJoinDao.newIsoResponse(vr);
+  }
+
+   public static TemplateResponse fillTemplateDetails(TemplateResponse vrData, TemplateJoinVO vr){
+       return _templateJoinDao.setTemplateResponse(vrData, vr);
+   }
+
+   public static List<TemplateJoinVO> newTemplateView(VirtualMachineTemplate vr){
+       return _templateJoinDao.newTemplateView(vr);
+   }
+
+
+   public static List<TemplateJoinVO> newTemplateView(VirtualMachineTemplate vr, long zoneId, boolean readyOnly){
+       return _templateJoinDao.newTemplateView(vr, zoneId, readyOnly);
+   }
+
 }


[2/5] Refactor listTemplatesCmd and listIsoCmd to use db view.

Posted by mc...@apache.org.
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/query/QueryManagerImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/query/QueryManagerImpl.java b/server/src/com/cloud/api/query/QueryManagerImpl.java
index 4b4c86e..71a0f29 100644
--- a/server/src/com/cloud/api/query/QueryManagerImpl.java
+++ b/server/src/com/cloud/api/query/QueryManagerImpl.java
@@ -16,9 +16,13 @@
 // under the License.
 package com.cloud.api.query;
 
+import java.sql.PreparedStatement;
+import java.sql.ResultSet;
+import java.sql.SQLException;
 import java.util.ArrayList;
 import java.util.Date;
 import java.util.HashSet;
+import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
@@ -27,6 +31,7 @@ import javax.ejb.Local;
 import javax.inject.Inject;
 import javax.naming.ConfigurationException;
 
+import org.apache.cloudstack.api.BaseCmd;
 import org.apache.cloudstack.api.command.admin.host.ListHostsCmd;
 import org.apache.cloudstack.api.command.admin.router.ListRoutersCmd;
 import org.apache.cloudstack.api.command.admin.storage.ListImageStoresCmd;
@@ -35,6 +40,7 @@ import org.apache.cloudstack.api.command.admin.user.ListUsersCmd;
 import org.apache.cloudstack.api.command.user.account.ListAccountsCmd;
 import org.apache.cloudstack.api.command.user.account.ListProjectAccountsCmd;
 import org.apache.cloudstack.api.command.user.event.ListEventsCmd;
+import org.apache.cloudstack.api.command.user.iso.ListIsosCmd;
 import org.apache.cloudstack.api.command.user.job.ListAsyncJobsCmd;
 import org.apache.cloudstack.api.command.user.offering.ListDiskOfferingsCmd;
 import org.apache.cloudstack.api.command.user.offering.ListServiceOfferingsCmd;
@@ -42,6 +48,7 @@ import org.apache.cloudstack.api.command.user.project.ListProjectInvitationsCmd;
 import org.apache.cloudstack.api.command.user.project.ListProjectsCmd;
 import org.apache.cloudstack.api.command.user.securitygroup.ListSecurityGroupsCmd;
 import org.apache.cloudstack.api.command.user.tag.ListTagsCmd;
+import org.apache.cloudstack.api.command.user.template.ListTemplatesCmd;
 import org.apache.cloudstack.api.command.user.vm.ListVMsCmd;
 import org.apache.cloudstack.api.command.user.vmgroup.ListVMGroupsCmd;
 import org.apache.cloudstack.api.command.user.volume.ListVolumesCmd;
@@ -62,6 +69,7 @@ import org.apache.cloudstack.api.response.ResourceTagResponse;
 import org.apache.cloudstack.api.response.SecurityGroupResponse;
 import org.apache.cloudstack.api.response.ServiceOfferingResponse;
 import org.apache.cloudstack.api.response.StoragePoolResponse;
+import org.apache.cloudstack.api.response.TemplateResponse;
 import org.apache.cloudstack.api.response.UserResponse;
 import org.apache.cloudstack.api.response.UserVmResponse;
 import org.apache.cloudstack.api.response.VolumeResponse;
@@ -85,6 +93,7 @@ import com.cloud.api.query.dao.ResourceTagJoinDao;
 import com.cloud.api.query.dao.SecurityGroupJoinDao;
 import com.cloud.api.query.dao.ServiceOfferingJoinDao;
 import com.cloud.api.query.dao.StoragePoolJoinDao;
+import com.cloud.api.query.dao.TemplateJoinDao;
 import com.cloud.api.query.dao.UserAccountJoinDao;
 import com.cloud.api.query.dao.UserVmJoinDao;
 import com.cloud.api.query.dao.VolumeJoinDao;
@@ -104,6 +113,7 @@ import com.cloud.api.query.vo.ResourceTagJoinVO;
 import com.cloud.api.query.vo.SecurityGroupJoinVO;
 import com.cloud.api.query.vo.ServiceOfferingJoinVO;
 import com.cloud.api.query.vo.StoragePoolJoinVO;
+import com.cloud.api.query.vo.TemplateJoinVO;
 import com.cloud.api.query.vo.UserAccountJoinVO;
 import com.cloud.api.query.vo.UserVmJoinVO;
 import com.cloud.api.query.vo.VolumeJoinVO;
@@ -127,12 +137,20 @@ import com.cloud.projects.Project;
 import com.cloud.projects.ProjectManager;
 import com.cloud.projects.dao.ProjectAccountDao;
 import com.cloud.projects.dao.ProjectDao;
+import com.cloud.resource.ResourceManager;
 import com.cloud.server.Criteria;
+import com.cloud.server.ResourceTag.TaggedResourceType;
 import com.cloud.service.ServiceOfferingVO;
 import com.cloud.service.dao.ServiceOfferingDao;
 import com.cloud.storage.ImageStore;
 import com.cloud.storage.ScopeType;
+import com.cloud.storage.Storage;
+import com.cloud.storage.VMTemplateVO;
 import com.cloud.storage.Volume;
+import com.cloud.storage.Storage.ImageFormat;
+import com.cloud.storage.VMTemplateStorageResourceAssoc.Status;
+import com.cloud.storage.dao.VMTemplateDao;
+import com.cloud.template.VirtualMachineTemplate.TemplateFilter;
 import com.cloud.user.Account;
 import com.cloud.user.AccountManager;
 import com.cloud.user.AccountVO;
@@ -146,6 +164,7 @@ import com.cloud.utils.component.ManagerBase;
 import com.cloud.utils.db.Filter;
 import com.cloud.utils.db.SearchBuilder;
 import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.Transaction;
 import com.cloud.utils.db.SearchCriteria.Func;
 import com.cloud.utils.db.SearchCriteria.Op;
 import com.cloud.vm.DomainRouterVO;
@@ -255,6 +274,15 @@ public class QueryManagerImpl extends ManagerBase implements QueryService {
     @Inject
     private HighAvailabilityManager _haMgr;
 
+    @Inject
+    private VMTemplateDao _templateDao;
+
+    @Inject
+    private TemplateJoinDao _templateJoinDao;
+
+    @Inject
+    ResourceManager _resourceMgr;
+
     /* (non-Javadoc)
      * @see com.cloud.api.query.QueryService#searchForUsers(org.apache.cloudstack.api.command.admin.user.ListUsersCmd)
      */
@@ -2419,5 +2447,298 @@ public class QueryManagerImpl extends ManagerBase implements QueryService {
         return false;
     }
 
+    @Override
+    public ListResponse<TemplateResponse> listTemplates(ListTemplatesCmd cmd) {
+        Pair<List<TemplateJoinVO>, Integer> result = searchForTemplatesInternal(cmd);
+        ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
+
+        List<TemplateResponse> templateResponses = ViewResponseHelper.createTemplateResponse(result.first().toArray(new TemplateJoinVO[result.first().size()]));
+        response.setResponses(templateResponses, result.second());
+        return response;
+    }
+
+    private Pair<List<TemplateJoinVO>, Integer> searchForTemplatesInternal(ListTemplatesCmd cmd) {
+        TemplateFilter templateFilter = TemplateFilter.valueOf(cmd.getTemplateFilter());
+        Long id = cmd.getId();
+        Map<String, String> tags = cmd.getTags();
+        Account caller = UserContext.current().getCaller();
+
+        boolean listAll = false;
+        if (templateFilter != null && templateFilter == TemplateFilter.all) {
+            if (caller.getType() == Account.ACCOUNT_TYPE_NORMAL) {
+                throw new InvalidParameterValueException("Filter " + TemplateFilter.all + " can be specified by admin only");
+            }
+            listAll = true;
+        }
+
+        List<Long> permittedAccountIds = new ArrayList<Long>();
+        Ternary<Long, Boolean, ListProjectResourcesCriteria> domainIdRecursiveListProject = new Ternary<Long, Boolean, ListProjectResourcesCriteria>(
+                cmd.getDomainId(), cmd.isRecursive(), null);
+        _accountMgr.buildACLSearchParameters(caller, id, cmd.getAccountName(), cmd.getProjectId(), permittedAccountIds, domainIdRecursiveListProject,
+                listAll, false);
+        ListProjectResourcesCriteria listProjectResourcesCriteria = domainIdRecursiveListProject.third();
+        List<Account> permittedAccounts = new ArrayList<Account>();
+        for (Long accountId : permittedAccountIds) {
+            permittedAccounts.add(_accountMgr.getAccount(accountId));
+        }
+
+        boolean showDomr = ((templateFilter != TemplateFilter.selfexecutable) && (templateFilter != TemplateFilter.featured));
+        HypervisorType hypervisorType = HypervisorType.getType(cmd.getHypervisor());
+
+        return searchForTemplatesInternal(id, cmd.getTemplateName(), cmd.getKeyword(), templateFilter, false, null, cmd.getPageSizeVal(), cmd.getStartIndex(),
+                cmd.getZoneId(), hypervisorType, showDomr, cmd.listInReadyState(), permittedAccounts, caller, listProjectResourcesCriteria, tags);
+    }
+
+    private Pair<List<TemplateJoinVO>, Integer> searchForTemplatesInternal(Long templateId, String name, String keyword, TemplateFilter templateFilter, boolean isIso,
+            Boolean bootable, Long pageSize, Long startIndex, Long zoneId, HypervisorType hyperType, boolean showDomr, boolean onlyReady,
+            List<Account> permittedAccounts, Account caller, ListProjectResourcesCriteria listProjectResourcesCriteria, Map<String, String> tags) {
+        VMTemplateVO template = null;
+
+        // verify templateId parameter
+        if (templateId != null) {
+            template = _templateDao.findById(templateId);
+            if (template == null) {
+                throw new InvalidParameterValueException("Please specify a valid template ID.");
+            }// If ISO requested then it should be ISO.
+            if (isIso && template.getFormat() != ImageFormat.ISO) {
+                s_logger.error("Template Id " + templateId + " is not an ISO");
+                InvalidParameterValueException ex = new InvalidParameterValueException("Specified Template Id is not an ISO");
+                ex.addProxyObject(template, templateId, "templateId");
+                throw ex;
+            }// If ISO not requested then it shouldn't be an ISO.
+            if (!isIso && template.getFormat() == ImageFormat.ISO) {
+                s_logger.error("Incorrect format of the template id " + templateId);
+                InvalidParameterValueException ex = new InvalidParameterValueException("Incorrect format " + template.getFormat()
+                        + " of the specified template id");
+                ex.addProxyObject(template, templateId, "templateId");
+                throw ex;
+            }
+
+            // if template is not public, perform permission check here
+            if (!template.isPublicTemplate() && caller.getType() != Account.ACCOUNT_TYPE_ADMIN) {
+                Account owner = _accountMgr.getAccount(template.getAccountId());
+                _accountMgr.checkAccess(caller, null, true, owner);
+            }
+        }
+
+        DomainVO domain = null;
+        if (!permittedAccounts.isEmpty()) {
+            domain = _domainDao.findById(permittedAccounts.get(0).getDomainId());
+        } else {
+            domain = _domainDao.findById(DomainVO.ROOT_DOMAIN);
+        }
+
+        List<HypervisorType> hypers = null;
+        if (!isIso) {
+            hypers = _resourceMgr.listAvailHypervisorInZone(null, null);
+        }
+
+        Boolean isAscending = Boolean.parseBoolean(_configDao.getValue("sortkey.algorithm"));
+        isAscending = (isAscending == null ? true : isAscending);
+        Filter searchFilter = new Filter(TemplateJoinVO.class, "sort_key", isAscending, startIndex, pageSize);
+        SearchCriteria<TemplateJoinVO> sc = _templateJoinDao.createSearchCriteria();
+
+        // add criteria for project or not
+        if (listProjectResourcesCriteria == ListProjectResourcesCriteria.SkipProjectResources) {
+            sc.addAnd("accountType", SearchCriteria.Op.NEQ, Account.ACCOUNT_TYPE_PROJECT);
+        } else if (listProjectResourcesCriteria == ListProjectResourcesCriteria.ListProjectResourcesOnly){
+            sc.addAnd("accountType", SearchCriteria.Op.EQ, Account.ACCOUNT_TYPE_PROJECT);
+        }
+
+        // add criteria for domain path in case of domain admin
+         if ((templateFilter == TemplateFilter.self || templateFilter == TemplateFilter.selfexecutable) &&
+                 (caller.getType() == Account.ACCOUNT_TYPE_DOMAIN_ADMIN || caller.getType() == Account.ACCOUNT_TYPE_RESOURCE_DOMAIN_ADMIN)) {
+             sc.addAnd("domainPath", SearchCriteria.Op.LIKE, domain.getPath() + "%");
+         }
+
+         List<Long> relatedDomainIds = new ArrayList<Long>();
+         List<Long> permittedAccountIds = new ArrayList<Long>();
+            if (!permittedAccounts.isEmpty()) {
+                for (Account account : permittedAccounts) {
+                    permittedAccountIds.add(account.getId());
+                    DomainVO accountDomain = _domainDao.findById(account.getDomainId());
+
+                    // get all parent domain ID's all the way till root domain
+                    DomainVO domainTreeNode = accountDomain;
+                    relatedDomainIds.add(domainTreeNode.getId());
+                    while (domainTreeNode.getParent() != null ){
+                        domainTreeNode = _domainDao.findById(domainTreeNode.getParent());
+                        relatedDomainIds.add(domainTreeNode.getId());
+                    }
+
+                    // get all child domain ID's
+                    if (_accountMgr.isAdmin(account.getType()) ) {
+                        List<DomainVO> allChildDomains = _domainDao.findAllChildren(accountDomain.getPath(), accountDomain.getId());
+                        for (DomainVO childDomain : allChildDomains) {
+                            relatedDomainIds.add(childDomain.getId());
+                        }
+                    }
+                }
+            }
+
+            // add hypervisor criteria
+            if ( !hypers.isEmpty()){
+                String[] relatedHypers = new String[hypers.size()];
+                for (int i = 0; i < hypers.size(); i++){
+                    relatedHypers[i] = hypers.get(i).toString();
+                }
+                sc.addAnd("hypervisorType", SearchCriteria.Op.IN, relatedHypers);
+            }
+
+            // control different template filters
+            if (templateFilter == TemplateFilter.featured || templateFilter == TemplateFilter.community) {
+                sc.addAnd("publicTemplate", SearchCriteria.Op.EQ, true);
+                if ( templateFilter == TemplateFilter.featured){
+                sc.addAnd("featured", SearchCriteria.Op.EQ, true);
+                }
+                else{
+                    sc.addAnd("featured", SearchCriteria.Op.EQ, false);
+                }
+                if (!permittedAccounts.isEmpty()) {
+                    SearchCriteria<TemplateJoinVO> scc = _templateJoinDao.createSearchCriteria();
+                    scc.addOr("domainId", SearchCriteria.Op.IN, relatedDomainIds.toArray());
+                    scc.addOr("domainId", SearchCriteria.Op.NULL);
+                    sc.addAnd("domainId", SearchCriteria.Op.SC, scc);
+
+                    if (!_accountMgr.isAdmin(caller.getType())){
+                        // for non-root users, we should only show featured and community templates that they can see
+                        sc.addAnd("accountId", SearchCriteria.Op.IN, permittedAccountIds.toArray());
+                    }
+                }
+            } else if (templateFilter == TemplateFilter.self || templateFilter == TemplateFilter.selfexecutable ) {
+                if ( !permittedAccounts.isEmpty()){
+                    sc.addAnd("accountId", SearchCriteria.Op.IN, permittedAccountIds.toArray());
+                }
+            } else if (templateFilter == TemplateFilter.sharedexecutable || templateFilter == TemplateFilter.shared ) {
+                SearchCriteria<TemplateJoinVO> scc = _templateJoinDao.createSearchCriteria();
+                scc.addOr("accountId", SearchCriteria.Op.IN, permittedAccountIds.toArray());
+                scc.addOr("sharedAccountId", SearchCriteria.Op.IN, permittedAccountIds.toArray());
+                sc.addAnd("accountId", SearchCriteria.Op.SC, scc);
+            } else if (templateFilter == TemplateFilter.executable ) {
+                SearchCriteria<TemplateJoinVO> scc = _templateJoinDao.createSearchCriteria();
+                scc.addOr("publicTemplate", SearchCriteria.Op.EQ, true);
+                if ( !permittedAccounts.isEmpty()){
+                    scc.addOr("accountId", SearchCriteria.Op.IN, permittedAccountIds.toArray());
+                }
+                sc.addAnd("publicTemplate", SearchCriteria.Op.SC, scc);
+            }
+
+            // add tags criteria
+            if (tags != null && !tags.isEmpty()) {
+                SearchCriteria<TemplateJoinVO> scc = _templateJoinDao.createSearchCriteria();
+                int count = 0;
+                for (String key : tags.keySet()) {
+                    SearchCriteria<TemplateJoinVO> scTag = _templateJoinDao.createSearchCriteria();
+                    scTag.addAnd("tagKey", SearchCriteria.Op.EQ, key);
+                    scTag.addAnd("tagValue", SearchCriteria.Op.EQ, tags.get(key));
+                    if ( isIso){
+                        scTag.addAnd("tagResourceType", SearchCriteria.Op.EQ, TaggedResourceType.ISO);
+                    } else {
+                        scTag.addAnd("tagResourceType", SearchCriteria.Op.EQ, TaggedResourceType.Template);
+                    }
+                    scc.addOr("tagKey", SearchCriteria.Op.SC, scTag);
+                    count++;
+                }
+                sc.addAnd("tagKey", SearchCriteria.Op.SC, scc);
+            }
+
+            // other criteria
+            if (keyword != null) {
+                sc.addAnd("name", SearchCriteria.Op.LIKE, "%" + keyword + "%");
+            } else if (name != null) {
+                sc.addAnd("name", SearchCriteria.Op.EQ, name);
+            }
+
+            if (isIso) {
+                sc.addAnd("format", SearchCriteria.Op.EQ, "ISO");
+
+            } else {
+                sc.addAnd("format", SearchCriteria.Op.NEQ, "ISO");
+            }
+
+            if (!hyperType.equals(HypervisorType.None)) {
+                sc.addAnd("hypervisorType", SearchCriteria.Op.EQ, hyperType);
+            }
+
+            if (bootable != null) {
+                sc.addAnd("bootable", SearchCriteria.Op.EQ, bootable);
+            }
+
+            if (onlyReady){
+                sc.addAnd("downlaadState", SearchCriteria.Op.EQ, Status.DOWNLOADED);
+                sc.addAnd("destroyed",  SearchCriteria.Op.EQ, false);
+            }
+
+            if (zoneId != null){
+                sc.addAnd("dataCenterId", SearchCriteria.Op.EQ, zoneId);
+            }
+
+            if (!showDomr){
+                // excluding system template
+                sc.addAnd("type", SearchCriteria.Op.NEQ, Storage.TemplateType.SYSTEM);
+            }
+
+            // search unique templates and find details by Ids
+            Pair<List<TemplateJoinVO>, Integer> uniqueTmplPair = _templateJoinDao.searchAndCount(sc, searchFilter);
+            Integer count = uniqueTmplPair.second();
+            if (count.intValue() == 0) {
+                // empty result
+                return uniqueTmplPair;
+            }
+            List<TemplateJoinVO> uniqueTmpls = uniqueTmplPair.first();
+            Long[] vrIds = new Long[uniqueTmpls.size()];
+            int i = 0;
+            for (TemplateJoinVO v : uniqueTmpls) {
+                vrIds[i++] = v.getId();
+            }
+            List<TemplateJoinVO> vrs = _templateJoinDao.searchByIds(vrIds);
+            return new Pair<List<TemplateJoinVO>, Integer>(vrs, count);
+
+            //TODO: revisit the special logic for iso search in VMTemplateDaoImpl.searchForTemplates and understand why we need to
+            //specially handle ISO. The original logic is very twisted and no idea about what the code was doing.
+
+    }
+
+    @Override
+    public ListResponse<TemplateResponse> listIsos(ListIsosCmd cmd) {
+        Pair<List<TemplateJoinVO>, Integer> result = searchForIsosInternal(cmd);
+        ListResponse<TemplateResponse> response = new ListResponse<TemplateResponse>();
+
+        List<TemplateResponse> templateResponses = ViewResponseHelper.createIsoResponse(result.first().toArray(new TemplateJoinVO[result.first().size()]));
+        response.setResponses(templateResponses, result.second());
+        return response;
+    }
+
+    private Pair<List<TemplateJoinVO>, Integer> searchForIsosInternal(ListIsosCmd cmd) {
+        TemplateFilter isoFilter = TemplateFilter.valueOf(cmd.getIsoFilter());
+        Long id = cmd.getId();
+        Map<String, String> tags = cmd.getTags();
+        Account caller = UserContext.current().getCaller();
+
+        boolean listAll = false;
+        if (isoFilter != null && isoFilter == TemplateFilter.all) {
+            if (caller.getType() == Account.ACCOUNT_TYPE_NORMAL) {
+                throw new InvalidParameterValueException("Filter " + TemplateFilter.all + " can be specified by admin only");
+            }
+            listAll = true;
+        }
+
+        List<Long> permittedAccountIds = new ArrayList<Long>();
+        Ternary<Long, Boolean, ListProjectResourcesCriteria> domainIdRecursiveListProject = new Ternary<Long, Boolean, ListProjectResourcesCriteria>(
+                cmd.getDomainId(), cmd.isRecursive(), null);
+        _accountMgr.buildACLSearchParameters(caller, id, cmd.getAccountName(), cmd.getProjectId(), permittedAccountIds, domainIdRecursiveListProject,
+                listAll, false);
+        ListProjectResourcesCriteria listProjectResourcesCriteria = domainIdRecursiveListProject.third();
+        List<Account> permittedAccounts = new ArrayList<Account>();
+        for (Long accountId : permittedAccountIds) {
+            permittedAccounts.add(_accountMgr.getAccount(accountId));
+        }
+
+        HypervisorType hypervisorType = HypervisorType.getType(cmd.getHypervisor());
+
+        return searchForTemplatesInternal(cmd.getId(), cmd.getIsoName(), cmd.getKeyword(), isoFilter, true, cmd.isBootable(), cmd.getPageSizeVal(),
+                cmd.getStartIndex(), cmd.getZoneId(), hypervisorType, true, cmd.listInReadyState(), permittedAccounts, caller,
+                listProjectResourcesCriteria, tags);
+    }
 
 }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/query/ViewResponseHelper.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/query/ViewResponseHelper.java b/server/src/com/cloud/api/query/ViewResponseHelper.java
index 5b3c934..8ac99d2 100644
--- a/server/src/com/cloud/api/query/ViewResponseHelper.java
+++ b/server/src/com/cloud/api/query/ViewResponseHelper.java
@@ -38,6 +38,7 @@ import org.apache.cloudstack.api.response.ResourceTagResponse;
 import org.apache.cloudstack.api.response.SecurityGroupResponse;
 import org.apache.cloudstack.api.response.ServiceOfferingResponse;
 import org.apache.cloudstack.api.response.StoragePoolResponse;
+import org.apache.cloudstack.api.response.TemplateResponse;
 import org.apache.cloudstack.api.response.UserResponse;
 import org.apache.cloudstack.api.response.UserVmResponse;
 import org.apache.cloudstack.api.response.VolumeResponse;
@@ -61,6 +62,7 @@ import com.cloud.api.query.vo.ResourceTagJoinVO;
 import com.cloud.api.query.vo.SecurityGroupJoinVO;
 import com.cloud.api.query.vo.ServiceOfferingJoinVO;
 import com.cloud.api.query.vo.StoragePoolJoinVO;
+import com.cloud.api.query.vo.TemplateJoinVO;
 import com.cloud.api.query.vo.UserAccountJoinVO;
 import com.cloud.api.query.vo.UserVmJoinVO;
 import com.cloud.api.query.vo.VolumeJoinVO;
@@ -323,4 +325,55 @@ public class ViewResponseHelper {
         }
         return respList;
     }
+
+    public static List<TemplateResponse> createTemplateResponse(TemplateJoinVO... templates) {
+        Hashtable<Long, TemplateResponse> vrDataList = new Hashtable<Long, TemplateResponse>();
+        for (TemplateJoinVO vr : templates) {
+            TemplateResponse vrData = vrDataList.get(vr.getId());
+            if ( vrData == null ){
+                // first time encountering this volume
+                vrData = ApiDBUtils.newTemplateResponse(vr);
+            }
+            else{
+                // update tags
+                vrData = ApiDBUtils.fillTemplateDetails(vrData, vr);
+            }
+            vrDataList.put(vr.getId(), vrData);
+        }
+        return new ArrayList<TemplateResponse>(vrDataList.values());
+    }
+
+    public static List<TemplateResponse> createTemplateUpdateResponse(TemplateJoinVO... templates) {
+        Hashtable<Long, TemplateResponse> vrDataList = new Hashtable<Long, TemplateResponse>();
+        for (TemplateJoinVO vr : templates) {
+            TemplateResponse vrData = vrDataList.get(vr.getId());
+            if ( vrData == null ){
+                // first time encountering this volume
+                vrData = ApiDBUtils.newTemplateUpdateResponse(vr);
+            }
+            else{
+                // update tags
+                vrData = ApiDBUtils.fillTemplateDetails(vrData, vr);
+            }
+            vrDataList.put(vr.getId(), vrData);
+        }
+        return new ArrayList<TemplateResponse>(vrDataList.values());
+    }
+
+    public static List<TemplateResponse> createIsoResponse(TemplateJoinVO... templates) {
+        Hashtable<Long, TemplateResponse> vrDataList = new Hashtable<Long, TemplateResponse>();
+        for (TemplateJoinVO vr : templates) {
+            TemplateResponse vrData = vrDataList.get(vr.getId());
+            if ( vrData == null ){
+                // first time encountering this volume
+                vrData = ApiDBUtils.newIsoResponse(vr);
+            }
+            else{
+                // update tags
+                vrData = ApiDBUtils.fillTemplateDetails(vrData, vr);
+            }
+            vrDataList.put(vr.getId(), vrData);
+        }
+        return new ArrayList<TemplateResponse>(vrDataList.values());
+    }
 }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/query/dao/TemplateJoinDao.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/query/dao/TemplateJoinDao.java b/server/src/com/cloud/api/query/dao/TemplateJoinDao.java
new file mode 100644
index 0000000..3897db5
--- /dev/null
+++ b/server/src/com/cloud/api/query/dao/TemplateJoinDao.java
@@ -0,0 +1,42 @@
+// 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 com.cloud.api.query.dao;
+
+import java.util.List;
+
+import org.apache.cloudstack.api.response.TemplateResponse;
+import com.cloud.api.query.vo.TemplateJoinVO;
+import com.cloud.template.VirtualMachineTemplate;
+import com.cloud.utils.db.GenericDao;
+
+public interface TemplateJoinDao extends GenericDao<TemplateJoinVO, Long> {
+
+    TemplateResponse newTemplateResponse(TemplateJoinVO tmpl);
+
+    TemplateResponse newIsoResponse(TemplateJoinVO tmpl);
+
+    TemplateResponse newUpdateResponse(TemplateJoinVO tmpl);
+
+    TemplateResponse setTemplateResponse(TemplateResponse tmplData, TemplateJoinVO tmpl);
+
+    List<TemplateJoinVO> newTemplateView(VirtualMachineTemplate tmpl);
+
+    List<TemplateJoinVO> newTemplateView(VirtualMachineTemplate tmpl, long zoneId, boolean readyOnly);
+
+    List<TemplateJoinVO> searchByIds(Long... ids);
+
+ }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/query/dao/TemplateJoinDaoImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/query/dao/TemplateJoinDaoImpl.java b/server/src/com/cloud/api/query/dao/TemplateJoinDaoImpl.java
new file mode 100644
index 0000000..0e5001b
--- /dev/null
+++ b/server/src/com/cloud/api/query/dao/TemplateJoinDaoImpl.java
@@ -0,0 +1,441 @@
+// 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 com.cloud.api.query.dao;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.ejb.Local;
+import javax.inject.Inject;
+
+import org.apache.cloudstack.api.BaseCmd;
+import org.apache.cloudstack.api.response.ResourceTagResponse;
+import org.apache.cloudstack.api.response.TemplateResponse;
+import org.apache.cloudstack.api.response.TemplateZoneResponse;
+import org.apache.cloudstack.api.response.VolumeResponse;
+import org.apache.log4j.Logger;
+import org.springframework.stereotype.Component;
+
+import com.cloud.api.ApiDBUtils;
+import com.cloud.api.ApiResponseHelper;
+import com.cloud.api.query.vo.ResourceTagJoinVO;
+import com.cloud.api.query.vo.TemplateJoinVO;
+import com.cloud.api.query.vo.VolumeJoinVO;
+import com.cloud.configuration.dao.ConfigurationDao;
+import com.cloud.dc.DataCenter;
+import com.cloud.offering.ServiceOffering;
+import com.cloud.server.ResourceTag;
+import com.cloud.server.ResourceTag.TaggedResourceType;
+import com.cloud.storage.GuestOS;
+import com.cloud.storage.Storage;
+import com.cloud.storage.VMTemplateHostVO;
+import com.cloud.storage.Storage.ImageFormat;
+import com.cloud.storage.Storage.TemplateType;
+import com.cloud.storage.VMTemplateStorageResourceAssoc;
+import com.cloud.storage.VMTemplateStorageResourceAssoc.Status;
+import com.cloud.storage.Volume;
+import com.cloud.template.VirtualMachineTemplate;
+import com.cloud.user.Account;
+import com.cloud.user.UserContext;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+
+@Component
+@Local(value={TemplateJoinDao.class})
+public class TemplateJoinDaoImpl extends GenericDaoBase<TemplateJoinVO, Long> implements TemplateJoinDao {
+
+
+
+    public static final Logger s_logger = Logger.getLogger(TemplateJoinDaoImpl.class);
+
+    @Inject
+    private ConfigurationDao  _configDao;
+
+    private final SearchBuilder<TemplateJoinVO> tmpltSearch;
+
+    private final SearchBuilder<TemplateJoinVO> tmpltIdSearch;
+
+    private final SearchBuilder<TemplateJoinVO> tmpltZoneSearch;
+
+
+    protected TemplateJoinDaoImpl() {
+
+        tmpltSearch = createSearchBuilder();
+        tmpltSearch.and("idIN", tmpltSearch.entity().getId(), SearchCriteria.Op.IN);
+        tmpltSearch.done();
+
+        tmpltIdSearch = createSearchBuilder();
+        tmpltIdSearch.and("id", tmpltIdSearch.entity().getId(), SearchCriteria.Op.EQ);
+        tmpltIdSearch.done();
+
+        tmpltZoneSearch = createSearchBuilder();
+        tmpltZoneSearch.and("id", tmpltZoneSearch.entity().getId(), SearchCriteria.Op.EQ);
+        tmpltZoneSearch.and("dataCenterId", tmpltZoneSearch.entity().getDataCenterId(), SearchCriteria.Op.EQ);
+        tmpltZoneSearch.and("downloadState", tmpltZoneSearch.entity().getDownloadState(), SearchCriteria.Op.EQ);
+        tmpltZoneSearch.done();
+
+        // select distinct pair (template_id, zone_id)
+        this._count = "select count(distinct id) from template_view WHERE ";
+    }
+
+
+
+
+    @Override
+    public TemplateResponse newTemplateResponse(TemplateJoinVO template) {
+        TemplateResponse templateResponse = new TemplateResponse();
+        templateResponse.setId(template.getUuid());
+        templateResponse.setName(template.getName());
+        templateResponse.setDisplayText(template.getDisplayText());
+        templateResponse.setPublic(template.isPublicTemplate());
+        templateResponse.setCreated(template.getCreatedOnStore());
+        templateResponse.setReady(template.getDownloadState() == Status.DOWNLOADED);
+        templateResponse.setFeatured(template.isFeatured());
+        templateResponse.setExtractable(template.isExtractable() && !(template.getTemplateType() == TemplateType.SYSTEM));
+        templateResponse.setPasswordEnabled(template.isEnablePassword());
+        templateResponse.setSshKeyEnabled(template.isEnableSshKey());
+        templateResponse.setCrossZones(template.isCrossZones());
+        templateResponse.setFormat(template.getFormat());
+        if (template.getTemplateType() != null) {
+            templateResponse.setTemplateType(template.getTemplateType().toString());
+        }
+
+        templateResponse.setHypervisor(template.getHypervisorType().toString());
+
+
+        templateResponse.setOsTypeId(template.getGuestOSUuid());
+        templateResponse.setOsTypeName(template.getGuestOSName());
+
+        // populate owner.
+        ApiResponseHelper.populateOwner(templateResponse, template);
+
+        // populate domain
+        templateResponse.setDomainId(template.getDomainUuid());
+        templateResponse.setDomainName(template.getDomainName());
+
+
+
+        boolean isAdmin = false;
+        Account caller = UserContext.current().getCaller();
+        if ((caller == null) || BaseCmd.isAdmin(caller.getType())) {
+            isAdmin = true;
+        }
+
+        // If the user is an Admin, add the template download status
+        if (isAdmin || caller.getId() == template.getAccountId()) {
+            // add download status
+            if (template.getDownloadState() != Status.DOWNLOADED) {
+                String templateStatus = "Processing";
+                if (template.getDownloadState() == VMTemplateHostVO.Status.DOWNLOAD_IN_PROGRESS) {
+                    if (template.getDownloadPercent() == 100) {
+                        templateStatus = "Installing Template";
+                    } else {
+                        templateStatus = template.getDownloadPercent() + "% Downloaded";
+                    }
+                } else {
+                    templateStatus = template.getErrorString();
+                }
+                templateResponse.setStatus(templateStatus);
+            } else if (template.getDownloadState() == VMTemplateHostVO.Status.DOWNLOADED) {
+                templateResponse.setStatus("Download Complete");
+            } else {
+                templateResponse.setStatus("Successfully Installed");
+            }
+        }
+
+        Long templateSize = template.getSize();
+        if (templateSize > 0) {
+            templateResponse.setSize(templateSize);
+        }
+
+        templateResponse.setChecksum(template.getChecksum());
+        if (template.getSourceTemplateId() != null) {
+            templateResponse.setSourceTemplateId(template.getSourceTemplateUuid());
+        }
+        templateResponse.setTemplateTag(template.getTemplateTag());
+
+        // set template zone information
+        if (template.getDataCenterId() > 0 ){
+            TemplateZoneResponse tmplZoneResp = new TemplateZoneResponse(template.getDataCenterUuid(), template.getDataCenterName());
+            templateResponse.addZone(tmplZoneResp);
+            // set the first found associated zone directly in TemplateResponse
+            templateResponse.setZoneId(template.getDataCenterUuid());
+            templateResponse.setZoneName(template.getDataCenterName());
+        }
+
+        // set details map
+        if (template.getDetailName() != null){
+            Map<String, String> details = new HashMap<String, String>();
+            details.put(template.getDetailName(), template.getDetailValue());
+            templateResponse.setDetails(details);
+        }
+
+        // update tag information
+        long tag_id = template.getTagId();
+        if (tag_id > 0) {
+            ResourceTagJoinVO vtag = ApiDBUtils.findResourceTagViewById(tag_id);
+            if ( vtag != null ){
+                templateResponse.addTag(ApiDBUtils.newResourceTagResponse(vtag, false));
+            }
+        }
+
+
+        templateResponse.setObjectName("template");
+        return templateResponse;
+    }
+
+
+    //TODO: This is to keep compatibility with 4.1 API, where updateTemplateCmd and updateIsoCmd will return a simpler TemplateResponse
+    // compared to listTemplates and listIsos.
+    @Override
+    public TemplateResponse newUpdateResponse(TemplateJoinVO result) {
+        TemplateResponse response = new TemplateResponse();
+        response.setId(result.getUuid());
+        response.setName(result.getName());
+        response.setDisplayText(result.getDisplayText());
+        response.setPublic(result.isPublicTemplate());
+        response.setCreated(result.getCreated());
+        response.setFormat(result.getFormat());
+        response.setOsTypeId(result.getGuestOSUuid());
+        response.setOsTypeName(result.getGuestOSName());
+        response.setBootable(result.isBootable());
+        response.setHypervisor(result.getHypervisorType().toString());
+
+        // populate owner.
+        ApiResponseHelper.populateOwner(response, result);
+
+        // populate domain
+        response.setDomainId(result.getDomainUuid());
+        response.setDomainName(result.getDomainName());
+
+        // set details map
+        if (result.getDetailName() != null) {
+            Map<String, String> details = new HashMap<String, String>();
+            details.put(result.getDetailName(), result.getDetailValue());
+            response.setDetails(details);
+        }
+
+        // update tag information
+        long tag_id = result.getTagId();
+        if (tag_id > 0) {
+            ResourceTagJoinVO vtag = ApiDBUtils.findResourceTagViewById(tag_id);
+            if (vtag != null) {
+                response.addTag(ApiDBUtils.newResourceTagResponse(vtag, false));
+            }
+        }
+
+        response.setObjectName("iso");
+        return response;
+    }
+
+
+
+
+    @Override
+    public TemplateResponse setTemplateResponse(TemplateResponse templateResponse, TemplateJoinVO template) {
+
+        // update template zone information
+        if (template.getDataCenterId() > 0 ){
+            TemplateZoneResponse tmplZoneResp = new TemplateZoneResponse(template.getDataCenterUuid(), template.getDataCenterName());
+            templateResponse.addZone(tmplZoneResp);
+            if (templateResponse.getZoneId() == null) {
+                // set the first found associated zone directly in
+                // TemplateResponse
+                templateResponse.setZoneId(template.getDataCenterUuid());
+                templateResponse.setZoneName(template.getDataCenterName());
+            }
+        }
+
+        // update details map
+        if (template.getDetailName() != null){
+            Map<String, String> details = templateResponse.getDetails();
+            if ( details == null ){
+                details = new HashMap<String, String>();
+            }
+            details.put(template.getDetailName(), template.getDetailValue());
+            templateResponse.setDetails(details);
+        }
+
+        // update tag information
+        long tag_id = template.getTagId();
+        if (tag_id > 0) {
+            ResourceTagJoinVO vtag = ApiDBUtils.findResourceTagViewById(tag_id);
+            if ( vtag != null ){
+                templateResponse.addTag(ApiDBUtils.newResourceTagResponse(vtag, false));
+            }
+        }
+
+        return templateResponse;
+    }
+
+
+    @Override
+    public TemplateResponse newIsoResponse(TemplateJoinVO iso) {
+
+        TemplateResponse isoResponse = new TemplateResponse();
+        isoResponse.setId(iso.getUuid());
+        isoResponse.setName(iso.getName());
+        isoResponse.setDisplayText(iso.getDisplayText());
+        isoResponse.setPublic(iso.isPublicTemplate());
+        isoResponse.setExtractable(iso.isExtractable() && !(iso.getTemplateType() == TemplateType.PERHOST));
+        isoResponse.setCreated(iso.getCreatedOnStore());
+        isoResponse.setReady(iso.getDownloadState() == Status.DOWNLOADED);
+        isoResponse.setBootable(iso.isBootable());
+        isoResponse.setFeatured(iso.isFeatured());
+        isoResponse.setCrossZones(iso.isCrossZones());
+        isoResponse.setPublic(iso.isPublicTemplate());
+        isoResponse.setChecksum(iso.getChecksum());
+
+        isoResponse.setOsTypeId(iso.getGuestOSUuid());
+        isoResponse.setOsTypeName(iso.getGuestOSName());
+
+        // populate owner.
+        ApiResponseHelper.populateOwner(isoResponse, iso);
+
+        // populate domain
+        isoResponse.setDomainId(iso.getDomainUuid());
+        isoResponse.setDomainName(iso.getDomainName());
+
+        // set template zone information
+        if (iso.getDataCenterId() > 0 ){
+            TemplateZoneResponse tmplZoneResp = new TemplateZoneResponse(iso.getDataCenterUuid(), iso.getDataCenterName());
+            isoResponse.addZone(tmplZoneResp);
+            // set the first found associated zone directly in TemplateResponse
+            isoResponse.setZoneId(iso.getDataCenterUuid());
+            isoResponse.setZoneName(iso.getDataCenterName());
+        }
+
+
+        Account caller = UserContext.current().getCaller();
+        boolean isAdmin = false;
+        if ((caller == null) || BaseCmd.isAdmin(caller.getType())) {
+            isAdmin = true;
+        }
+
+
+        // If the user is an admin, add the template download status
+        if (isAdmin || caller.getId() == iso.getAccountId()) {
+            // add download status
+            if (iso.getDownloadState() != Status.DOWNLOADED) {
+                String isoStatus = "Processing";
+                if (iso.getDownloadState() == VMTemplateHostVO.Status.DOWNLOADED) {
+                    isoStatus = "Download Complete";
+                } else if (iso.getDownloadState() == VMTemplateHostVO.Status.DOWNLOAD_IN_PROGRESS) {
+                    if (iso.getDownloadPercent() == 100) {
+                        isoStatus = "Installing ISO";
+                    } else {
+                        isoStatus = iso.getDownloadPercent() + "% Downloaded";
+                    }
+                } else {
+                    isoStatus = iso.getErrorString();
+                }
+                isoResponse.setStatus(isoStatus);
+            } else {
+                isoResponse.setStatus("Successfully Installed");
+            }
+        }
+
+        Long isoSize = iso.getSize();
+        if (isoSize > 0) {
+            isoResponse.setSize(isoSize);
+        }
+
+        // update tag information
+        long tag_id = iso.getTagId();
+        if (tag_id > 0) {
+            ResourceTagJoinVO vtag = ApiDBUtils.findResourceTagViewById(tag_id);
+            if ( vtag != null ){
+                isoResponse.addTag(ApiDBUtils.newResourceTagResponse(vtag, false));
+            }
+        }
+
+        isoResponse.setObjectName("iso");
+        return isoResponse;
+
+    }
+
+    @Override
+    public List<TemplateJoinVO> newTemplateView(VirtualMachineTemplate template) {
+        SearchCriteria<TemplateJoinVO> sc = tmpltIdSearch.create();
+        sc.setParameters("id", template.getId());
+        return searchIncludingRemoved(sc, null, null, false);
+    }
+
+    @Override
+    public List<TemplateJoinVO> newTemplateView(VirtualMachineTemplate template, long zoneId, boolean readyOnly) {
+        SearchCriteria<TemplateJoinVO> sc = tmpltZoneSearch.create();
+        sc.setParameters("id", template.getId());
+        sc.setParameters("dataCenterId", zoneId);
+        if ( readyOnly ){
+            sc.setParameters("downloadState", VMTemplateStorageResourceAssoc.Status.DOWNLOADED);
+        }
+        return searchIncludingRemoved(sc, null, null, false);
+    }
+
+
+
+    @Override
+    public List<TemplateJoinVO> searchByIds(Long... tmplIds) {
+        // set detail batch query size
+        int DETAILS_BATCH_SIZE = 2000;
+        String batchCfg = _configDao.getValue("detail.batch.query.size");
+        if ( batchCfg != null ){
+            DETAILS_BATCH_SIZE = Integer.parseInt(batchCfg);
+        }
+        // query details by batches
+        List<TemplateJoinVO> uvList = new ArrayList<TemplateJoinVO>();
+        // query details by batches
+        int curr_index = 0;
+        if ( tmplIds.length > DETAILS_BATCH_SIZE ){
+            while ( (curr_index + DETAILS_BATCH_SIZE ) <= tmplIds.length ) {
+                Long[] ids = new Long[DETAILS_BATCH_SIZE];
+                for (int k = 0, j = curr_index; j < curr_index + DETAILS_BATCH_SIZE; j++, k++) {
+                    ids[k] = tmplIds[j];
+                }
+                SearchCriteria<TemplateJoinVO> sc = tmpltSearch.create();
+                sc.setParameters("idIN", ids);
+                List<TemplateJoinVO> vms = searchIncludingRemoved(sc, null, null, false);
+                if (vms != null) {
+                    uvList.addAll(vms);
+                }
+                curr_index += DETAILS_BATCH_SIZE;
+            }
+        }
+        if (curr_index < tmplIds.length) {
+            int batch_size = (tmplIds.length - curr_index);
+            // set the ids value
+            Long[] ids = new Long[batch_size];
+            for (int k = 0, j = curr_index; j < curr_index + batch_size; j++, k++) {
+                ids[k] = tmplIds[j];
+            }
+            SearchCriteria<TemplateJoinVO> sc = tmpltSearch.create();
+            sc.setParameters("idIN", ids);
+            List<TemplateJoinVO> vms = searchIncludingRemoved(sc, null, null, false);
+            if (vms != null) {
+                uvList.addAll(vms);
+            }
+        }
+        return uvList;
+    }
+
+
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/api/query/vo/TemplateJoinVO.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/query/vo/TemplateJoinVO.java b/server/src/com/cloud/api/query/vo/TemplateJoinVO.java
new file mode 100644
index 0000000..0a6b0f9
--- /dev/null
+++ b/server/src/com/cloud/api/query/vo/TemplateJoinVO.java
@@ -0,0 +1,1006 @@
+// 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 com.cloud.api.query.vo;
+
+import java.util.Date;
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.EnumType;
+import javax.persistence.Enumerated;
+import javax.persistence.Id;
+import javax.persistence.Table;
+import javax.persistence.Temporal;
+import javax.persistence.TemporalType;
+
+import org.apache.cloudstack.api.Identity;
+import org.apache.cloudstack.api.InternalIdentity;
+
+import com.cloud.hypervisor.Hypervisor.HypervisorType;
+import com.cloud.server.ResourceTag.TaggedResourceType;
+import com.cloud.storage.Storage;
+import com.cloud.storage.Volume;
+import com.cloud.storage.VMTemplateStorageResourceAssoc.Status;
+import com.cloud.utils.db.GenericDao;
+import com.cloud.vm.VirtualMachine;
+
+@Entity
+@Table(name="template_view")
+public class TemplateJoinVO extends BaseViewVO implements ControlledViewEntity {
+
+    @Id
+    @Column(name="id")
+    private long id;
+
+    @Column(name="uuid")
+    private String uuid;
+
+    @Column(name="unique_name")
+    private String uniqueName;
+
+    @Column(name="name")
+    private String name;
+
+    @Column(name="format")
+    private Storage.ImageFormat format;
+
+    @Column(name="public")
+    private boolean publicTemplate = true;
+
+    @Column(name="featured")
+    private boolean featured;
+
+    @Column(name="type")
+    private Storage.TemplateType templateType;
+
+    @Column(name="url")
+    private String url = null;
+
+    @Column(name="hvm")
+    private boolean requiresHvm;
+
+    @Column(name="bits")
+    private int bits;
+
+    @Temporal(value=TemporalType.TIMESTAMP)
+    @Column(name=GenericDao.CREATED_COLUMN)
+    private Date created = null;
+
+    @Temporal(value=TemporalType.TIMESTAMP)
+    @Column(name="created_on_store")
+    private Date createdOnStore = null;
+
+    @Column(name=GenericDao.REMOVED)
+    @Temporal(TemporalType.TIMESTAMP)
+    private Date removed;
+
+    @Column(name="checksum")
+    private String checksum;
+
+    @Column(name="display_text", length=4096)
+    private String displayText;
+
+    @Column(name="enable_password")
+    private boolean enablePassword;
+
+    @Column(name="guest_os_id")
+    private long guestOSId;
+
+    @Column(name="guest_os_uuid")
+    private String guestOSUuid;
+
+    @Column(name="guest_os_name")
+    private String guestOSName;
+
+    @Column(name="bootable")
+    private boolean bootable = true;
+
+    @Column(name="prepopulate")
+    private boolean prepopulate = false;
+
+    @Column(name="cross_zones")
+    private boolean crossZones = false;
+
+    @Column(name="hypervisor_type")
+    @Enumerated(value=EnumType.STRING)
+    private HypervisorType hypervisorType;
+
+    @Column(name="extractable")
+    private boolean extractable = true;
+
+    @Column(name="source_template_id")
+    private Long sourceTemplateId;
+
+    @Column(name="source_template_uuid")
+    private String sourceTemplateUuid;
+
+
+    @Column(name="template_tag")
+    private String templateTag;
+
+    @Column(name="sort_key")
+    private int sortKey;
+
+    @Column(name="enable_sshkey")
+    private boolean enableSshKey;
+
+    @Column(name="account_id")
+    private long accountId;
+
+    @Column(name="account_uuid")
+    private String accountUuid;
+
+    @Column(name="account_name")
+    private String accountName = null;
+
+    @Column(name="account_type")
+    private short accountType;
+
+    @Column(name="domain_id")
+    private long domainId;
+
+    @Column(name="domain_uuid")
+    private String domainUuid;
+
+    @Column(name="domain_name")
+    private String domainName = null;
+
+    @Column(name="domain_path")
+    private String domainPath = null;
+
+    @Column(name="project_id")
+    private long projectId;
+
+    @Column(name="project_uuid")
+    private String projectUuid;
+
+    @Column(name="project_name")
+    private String projectName;
+
+    @Column(name="data_center_id")
+    private long dataCenterId;
+
+    @Column(name="data_center_uuid")
+    private String dataCenterUuid;
+
+    @Column(name="data_center_name")
+    private String dataCenterName;
+
+    @Column (name="download_state")
+    @Enumerated(EnumType.STRING)
+    private Status downloadState;
+
+    @Column (name="download_pct")
+    private int downloadPercent;
+
+    @Column (name="error_str")
+    private String errorString;
+
+    @Column (name="size")
+    private long size;
+
+    @Column(name="destroyed")
+    boolean destroyed = false;
+
+    @Column(name="lp_account_id")
+    private Long sharedAccountId;
+
+    @Column(name="detail_name")
+    private String detailName;
+
+    @Column(name="detail_value")
+    private String detailValue;
+
+
+    @Column(name="tag_id")
+    private long tagId;
+
+    @Column(name="tag_uuid")
+    private String tagUuid;
+
+    @Column(name="tag_key")
+    private String tagKey;
+
+    @Column(name="tag_value")
+    private String tagValue;
+
+    @Column(name="tag_domain_id")
+    private long tagDomainId;
+
+    @Column(name="tag_account_id")
+    private long tagAccountId;
+
+    @Column(name="tag_resource_id")
+    private long tagResourceId;
+
+    @Column(name="tag_resource_uuid")
+    private String tagResourceUuid;
+
+    @Column(name="tag_resource_type")
+    @Enumerated(value=EnumType.STRING)
+    private TaggedResourceType tagResourceType;
+
+    @Column(name="tag_customer")
+    private String tagCustomer;
+
+
+
+    public TemplateJoinVO() {
+    }
+
+
+
+    @Override
+    public long getId() {
+        return id;
+    }
+
+
+
+    @Override
+    public void setId(long id) {
+        this.id = id;
+    }
+
+
+
+    @Override
+    public String getUuid() {
+        return uuid;
+    }
+
+
+
+    public void setUuid(String uuid) {
+        this.uuid = uuid;
+    }
+
+
+
+    public String getName() {
+        return name;
+    }
+
+
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+
+    public Date getCreated() {
+        return created;
+    }
+
+
+
+    public void setCreated(Date created) {
+        this.created = created;
+    }
+
+
+
+    public Date getRemoved() {
+        return removed;
+    }
+
+
+
+    public void setRemoved(Date removed) {
+        this.removed = removed;
+    }
+
+
+
+    @Override
+    public long getAccountId() {
+        return accountId;
+    }
+
+
+
+    public void setAccountId(long accountId) {
+        this.accountId = accountId;
+    }
+
+
+
+    @Override
+    public String getAccountUuid() {
+        return accountUuid;
+    }
+
+
+
+    public void setAccountUuid(String accountUuid) {
+        this.accountUuid = accountUuid;
+    }
+
+
+
+    @Override
+    public String getAccountName() {
+        return accountName;
+    }
+
+
+
+    public void setAccountName(String accountName) {
+        this.accountName = accountName;
+    }
+
+
+
+    @Override
+    public short getAccountType() {
+        return accountType;
+    }
+
+
+
+    public void setAccountType(short accountType) {
+        this.accountType = accountType;
+    }
+
+
+
+    @Override
+    public long getDomainId() {
+        return domainId;
+    }
+
+
+
+    public void setDomainId(long domainId) {
+        this.domainId = domainId;
+    }
+
+
+
+    @Override
+    public String getDomainUuid() {
+        return domainUuid;
+    }
+
+
+
+    public void setDomainUuid(String domainUuid) {
+        this.domainUuid = domainUuid;
+    }
+
+
+
+    @Override
+    public String getDomainName() {
+        return domainName;
+    }
+
+
+
+    public void setDomainName(String domainName) {
+        this.domainName = domainName;
+    }
+
+
+
+    @Override
+    public String getDomainPath() {
+        return domainPath;
+    }
+
+
+
+    public void setDomainPath(String domainPath) {
+        this.domainPath = domainPath;
+    }
+
+
+
+    public long getProjectId() {
+        return projectId;
+    }
+
+
+
+    public void setProjectId(long projectId) {
+        this.projectId = projectId;
+    }
+
+
+
+    @Override
+    public String getProjectUuid() {
+        return projectUuid;
+    }
+
+
+
+    public void setProjectUuid(String projectUuid) {
+        this.projectUuid = projectUuid;
+    }
+
+
+
+    @Override
+    public String getProjectName() {
+        return projectName;
+    }
+
+
+
+    public void setProjectName(String projectName) {
+        this.projectName = projectName;
+    }
+
+
+
+
+    public boolean isExtractable() {
+        return extractable;
+    }
+
+
+
+    public void setExtractable(boolean extractable) {
+        this.extractable = extractable;
+    }
+
+
+
+    public Storage.TemplateType getTemplateType() {
+        return templateType;
+    }
+
+
+
+    public void setTemplateType(Storage.TemplateType templateType) {
+        this.templateType = templateType;
+    }
+
+
+
+
+
+
+    public long getTagId() {
+        return tagId;
+    }
+
+
+
+    public void setTagId(long tagId) {
+        this.tagId = tagId;
+    }
+
+
+
+    public String getTagUuid() {
+        return tagUuid;
+    }
+
+
+
+    public void setTagUuid(String tagUuid) {
+        this.tagUuid = tagUuid;
+    }
+
+
+
+    public String getTagKey() {
+        return tagKey;
+    }
+
+
+
+    public void setTagKey(String tagKey) {
+        this.tagKey = tagKey;
+    }
+
+
+
+    public String getTagValue() {
+        return tagValue;
+    }
+
+
+
+    public void setTagValue(String tagValue) {
+        this.tagValue = tagValue;
+    }
+
+
+
+    public long getTagDomainId() {
+        return tagDomainId;
+    }
+
+
+
+    public void setTagDomainId(long tagDomainId) {
+        this.tagDomainId = tagDomainId;
+    }
+
+
+
+    public long getTagAccountId() {
+        return tagAccountId;
+    }
+
+
+
+    public void setTagAccountId(long tagAccountId) {
+        this.tagAccountId = tagAccountId;
+    }
+
+
+
+    public long getTagResourceId() {
+        return tagResourceId;
+    }
+
+
+
+    public void setTagResourceId(long tagResourceId) {
+        this.tagResourceId = tagResourceId;
+    }
+
+
+
+    public String getTagResourceUuid() {
+        return tagResourceUuid;
+    }
+
+
+
+    public void setTagResourceUuid(String tagResourceUuid) {
+        this.tagResourceUuid = tagResourceUuid;
+    }
+
+
+
+    public TaggedResourceType getTagResourceType() {
+        return tagResourceType;
+    }
+
+
+
+    public void setTagResourceType(TaggedResourceType tagResourceType) {
+        this.tagResourceType = tagResourceType;
+    }
+
+
+
+    public String getTagCustomer() {
+        return tagCustomer;
+    }
+
+
+
+    public void setTagCustomer(String tagCustomer) {
+        this.tagCustomer = tagCustomer;
+    }
+
+
+
+    public long getDataCenterId() {
+        return dataCenterId;
+    }
+
+
+
+    public void setDataCenterId(long dataCenterId) {
+        this.dataCenterId = dataCenterId;
+    }
+
+
+
+    public String getDataCenterUuid() {
+        return dataCenterUuid;
+    }
+
+
+
+    public void setDataCenterUuid(String dataCenterUuid) {
+        this.dataCenterUuid = dataCenterUuid;
+    }
+
+
+
+    public String getDataCenterName() {
+        return dataCenterName;
+    }
+
+
+
+    public void setDataCenterName(String dataCenterName) {
+        this.dataCenterName = dataCenterName;
+    }
+
+
+
+    public String getUniqueName() {
+        return uniqueName;
+    }
+
+
+
+    public void setUniqueName(String uniqueName) {
+        this.uniqueName = uniqueName;
+    }
+
+
+
+    public boolean isPublicTemplate() {
+        return publicTemplate;
+    }
+
+
+
+    public void setPublicTemplate(boolean publicTemplate) {
+        this.publicTemplate = publicTemplate;
+    }
+
+
+
+    public boolean isFeatured() {
+        return featured;
+    }
+
+
+
+    public void setFeatured(boolean featured) {
+        this.featured = featured;
+    }
+
+
+
+    public String getUrl() {
+        return url;
+    }
+
+
+
+    public void setUrl(String url) {
+        this.url = url;
+    }
+
+
+
+    public boolean isRequiresHvm() {
+        return requiresHvm;
+    }
+
+
+
+    public void setRequiresHvm(boolean requiresHvm) {
+        this.requiresHvm = requiresHvm;
+    }
+
+
+
+    public int getBits() {
+        return bits;
+    }
+
+
+
+    public void setBits(int bits) {
+        this.bits = bits;
+    }
+
+
+
+    public String getChecksum() {
+        return checksum;
+    }
+
+
+
+    public void setChecksum(String checksum) {
+        this.checksum = checksum;
+    }
+
+
+
+    public String getDisplayText() {
+        return displayText;
+    }
+
+
+
+    public void setDisplayText(String displayText) {
+        this.displayText = displayText;
+    }
+
+
+
+    public boolean isEnablePassword() {
+        return enablePassword;
+    }
+
+
+
+    public void setEnablePassword(boolean enablePassword) {
+        this.enablePassword = enablePassword;
+    }
+
+
+
+    public long getGuestOSId() {
+        return guestOSId;
+    }
+
+
+
+    public void setGuestOSId(long guestOSId) {
+        this.guestOSId = guestOSId;
+    }
+
+
+
+    public String getGuestOSUuid() {
+        return guestOSUuid;
+    }
+
+
+
+    public void setGuestOSUuid(String guestOSUuid) {
+        this.guestOSUuid = guestOSUuid;
+    }
+
+
+
+    public String getGuestOSName() {
+        return guestOSName;
+    }
+
+
+
+    public void setGuestOSName(String guestOSName) {
+        this.guestOSName = guestOSName;
+    }
+
+
+
+    public boolean isBootable() {
+        return bootable;
+    }
+
+
+
+    public void setBootable(boolean bootable) {
+        this.bootable = bootable;
+    }
+
+
+
+    public boolean isPrepopulate() {
+        return prepopulate;
+    }
+
+
+
+    public void setPrepopulate(boolean prepopulate) {
+        this.prepopulate = prepopulate;
+    }
+
+
+
+    public boolean isCrossZones() {
+        return crossZones;
+    }
+
+
+
+    public void setCrossZones(boolean crossZones) {
+        this.crossZones = crossZones;
+    }
+
+
+
+    public HypervisorType getHypervisorType() {
+        return hypervisorType;
+    }
+
+
+
+    public void setHypervisorType(HypervisorType hypervisorType) {
+        this.hypervisorType = hypervisorType;
+    }
+
+
+
+    public Long getSourceTemplateId() {
+        return sourceTemplateId;
+    }
+
+
+
+    public void setSourceTemplateId(Long sourceTemplateId) {
+        this.sourceTemplateId = sourceTemplateId;
+    }
+
+
+
+    public String getSourceTemplateUuid() {
+        return sourceTemplateUuid;
+    }
+
+
+
+    public void setSourceTemplateUuid(String sourceTemplateUuid) {
+        this.sourceTemplateUuid = sourceTemplateUuid;
+    }
+
+
+
+    public String getTemplateTag() {
+        return templateTag;
+    }
+
+
+
+    public void setTemplateTag(String templateTag) {
+        this.templateTag = templateTag;
+    }
+
+
+
+    public int getSortKey() {
+        return sortKey;
+    }
+
+
+
+    public void setSortKey(int sortKey) {
+        this.sortKey = sortKey;
+    }
+
+
+
+    public boolean isEnableSshKey() {
+        return enableSshKey;
+    }
+
+
+
+    public void setEnableSshKey(boolean enableSshKey) {
+        this.enableSshKey = enableSshKey;
+    }
+
+
+
+    public Status getDownloadState() {
+        return downloadState;
+    }
+
+
+
+    public void setDownloadState(Status downloadState) {
+        this.downloadState = downloadState;
+    }
+
+
+
+    public long getSize() {
+        return size;
+    }
+
+
+
+    public void setSize(long size) {
+        this.size = size;
+    }
+
+
+
+    public boolean isDestroyed() {
+        return destroyed;
+    }
+
+
+
+    public void setDestroyed(boolean destroyed) {
+        this.destroyed = destroyed;
+    }
+
+
+
+    public Long getSharedAccountId() {
+        return sharedAccountId;
+    }
+
+
+
+    public void setSharedAccountId(Long sharedAccountId) {
+        this.sharedAccountId = sharedAccountId;
+    }
+
+
+
+    public String getDetailName() {
+        return detailName;
+    }
+
+
+
+    public void setDetailName(String detailName) {
+        this.detailName = detailName;
+    }
+
+
+
+    public String getDetailValue() {
+        return detailValue;
+    }
+
+
+
+    public void setDetailValue(String detailValue) {
+        this.detailValue = detailValue;
+    }
+
+
+
+    public Date getCreatedOnStore() {
+        return createdOnStore;
+    }
+
+
+
+    public void setCreatedOnStore(Date createdOnStore) {
+        this.createdOnStore = createdOnStore;
+    }
+
+
+
+    public Storage.ImageFormat getFormat() {
+        return format;
+    }
+
+
+
+    public void setFormat(Storage.ImageFormat format) {
+        this.format = format;
+    }
+
+
+
+    public int getDownloadPercent() {
+        return downloadPercent;
+    }
+
+
+
+    public void setDownloadPercent(int downloadPercent) {
+        this.downloadPercent = downloadPercent;
+    }
+
+
+
+    public String getErrorString() {
+        return errorString;
+    }
+
+
+
+    public void setErrorString(String errorString) {
+        this.errorString = errorString;
+    }
+
+
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/server/ManagementServerImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java
index ff60ce5..c2871d9 100755
--- a/server/src/com/cloud/server/ManagementServerImpl.java
+++ b/server/src/com/cloud/server/ManagementServerImpl.java
@@ -1112,70 +1112,10 @@ public class ManagementServerImpl extends ManagerBase implements ManagementServe
         return new Pair<List<? extends Configuration>, Integer>(result.first(), result.second());
     }
 
-    @Override
-    public Set<Pair<Long, Long>> listIsos(ListIsosCmd cmd) throws IllegalArgumentException, InvalidParameterValueException {
-        TemplateFilter isoFilter = TemplateFilter.valueOf(cmd.getIsoFilter());
-        Account caller = UserContext.current().getCaller();
-        Map<String, String> tags = cmd.getTags();
 
-        boolean listAll = false;
-        if (isoFilter != null && isoFilter == TemplateFilter.all) {
-            if (caller.getType() == Account.ACCOUNT_TYPE_NORMAL) {
-                throw new InvalidParameterValueException("Filter " + TemplateFilter.all + " can be specified by admin only");
-            }
-            listAll = true;
-        }
-        List<Long> permittedAccountIds = new ArrayList<Long>();
-        Ternary<Long, Boolean, ListProjectResourcesCriteria> domainIdRecursiveListProject = new Ternary<Long, Boolean, ListProjectResourcesCriteria>(
-                cmd.getDomainId(), cmd.isRecursive(), null);
-        _accountMgr.buildACLSearchParameters(caller, cmd.getId(), cmd.getAccountName(), cmd.getProjectId(), permittedAccountIds,
-                domainIdRecursiveListProject, listAll, false);
-        ListProjectResourcesCriteria listProjectResourcesCriteria = domainIdRecursiveListProject.third();
-
-        List<Account> permittedAccounts = new ArrayList<Account>();
-        for (Long accountId : permittedAccountIds) {
-            permittedAccounts.add(_accountMgr.getAccount(accountId));
-        }
-
-        HypervisorType hypervisorType = HypervisorType.getType(cmd.getHypervisor());
-        return listTemplates(cmd.getId(), cmd.getIsoName(), cmd.getKeyword(), isoFilter, true, cmd.isBootable(), cmd.getPageSizeVal(),
-                cmd.getStartIndex(), cmd.getZoneId(), hypervisorType, true, cmd.listInReadyState(), permittedAccounts, caller,
-                listProjectResourcesCriteria, tags);
-    }
-
-    @Override
-    public Set<Pair<Long, Long>> listTemplates(ListTemplatesCmd cmd) throws IllegalArgumentException, InvalidParameterValueException {
-        TemplateFilter templateFilter = TemplateFilter.valueOf(cmd.getTemplateFilter());
-        Long id = cmd.getId();
-        Map<String, String> tags = cmd.getTags();
-        Account caller = UserContext.current().getCaller();
-
-        boolean listAll = false;
-        if (templateFilter != null && templateFilter == TemplateFilter.all) {
-            if (caller.getType() == Account.ACCOUNT_TYPE_NORMAL) {
-                throw new InvalidParameterValueException("Filter " + TemplateFilter.all + " can be specified by admin only");
-            }
-            listAll = true;
-        }
-
-        List<Long> permittedAccountIds = new ArrayList<Long>();
-        Ternary<Long, Boolean, ListProjectResourcesCriteria> domainIdRecursiveListProject = new Ternary<Long, Boolean, ListProjectResourcesCriteria>(
-                cmd.getDomainId(), cmd.isRecursive(), null);
-        _accountMgr.buildACLSearchParameters(caller, id, cmd.getAccountName(), cmd.getProjectId(), permittedAccountIds, domainIdRecursiveListProject,
-                listAll, false);
-        ListProjectResourcesCriteria listProjectResourcesCriteria = domainIdRecursiveListProject.third();
-        List<Account> permittedAccounts = new ArrayList<Account>();
-        for (Long accountId : permittedAccountIds) {
-            permittedAccounts.add(_accountMgr.getAccount(accountId));
-        }
-
-        boolean showDomr = ((templateFilter != TemplateFilter.selfexecutable) && (templateFilter != TemplateFilter.featured));
-        HypervisorType hypervisorType = HypervisorType.getType(cmd.getHypervisor());
-
-        return listTemplates(id, cmd.getTemplateName(), cmd.getKeyword(), templateFilter, false, null, cmd.getPageSizeVal(), cmd.getStartIndex(),
-                cmd.getZoneId(), hypervisorType, showDomr, cmd.listInReadyState(), permittedAccounts, caller, listProjectResourcesCriteria, tags);
-    }
 
+    /* TODO: this method should go away. Keep here just in case that our latest refactoring using template_store_ref missed anything
+     * in handling Swift or S3.
     private Set<Pair<Long, Long>> listTemplates(Long templateId, String name, String keyword, TemplateFilter templateFilter, boolean isIso,
             Boolean bootable, Long pageSize, Long startIndex, Long zoneId, HypervisorType hyperType, boolean showDomr, boolean onlyReady,
             List<Account> permittedAccounts, Account caller, ListProjectResourcesCriteria listProjectResourcesCriteria, Map<String, String> tags) {
@@ -1274,7 +1214,7 @@ public class ManagementServerImpl extends ManagerBase implements ManagementServe
 
         return templateZonePairSet;
     }
-
+*/
 
 
     @Override

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/storage/dao/VMTemplateDao.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/storage/dao/VMTemplateDao.java b/server/src/com/cloud/storage/dao/VMTemplateDao.java
index 7263371..8c2b941 100755
--- a/server/src/com/cloud/storage/dao/VMTemplateDao.java
+++ b/server/src/com/cloud/storage/dao/VMTemplateDao.java
@@ -37,11 +37,11 @@ import com.cloud.utils.fsm.StateDao;
  * Data Access Object for vm_templates table
  */
 public interface VMTemplateDao extends GenericDao<VMTemplateVO, Long>, StateDao<TemplateState, TemplateEvent, VMTemplateVO> {
-	
-	
+
+
 	public List<VMTemplateVO> listByPublic();
 	public VMTemplateVO findByName(String templateName);
-	public VMTemplateVO findByTemplateName(String templateName);	
+	public VMTemplateVO findByTemplateName(String templateName);
 
 	//public void update(VMTemplateVO template);
 
@@ -53,11 +53,13 @@ public interface VMTemplateDao extends GenericDao<VMTemplateVO, Long>, StateDao<
 	public List<VMTemplateVO> findIsosByIdAndPath(Long domainId, Long accountId, String path);
 	public List<VMTemplateVO> listReadyTemplates();
 	public List<VMTemplateVO> listByAccountId(long accountId);
+
+	/* TODO: these routines should go away, the logic has been consolidated and refactored in QueryService
 	public Set<Pair<Long, Long>> searchTemplates(String name, String keyword, TemplateFilter templateFilter, boolean isIso,
 	        List<HypervisorType> hypers, Boolean bootable, DomainVO domain, Long pageSize, Long startIndex, Long zoneId,
 	        HypervisorType hyperType, boolean onlyReady, boolean showDomr, List<Account> permittedAccounts, Account caller,
 	        ListProjectResourcesCriteria listProjectResourcesCriteria, Map<String, String> tags);
-	
+
     public Set<Pair<Long, Long>> searchSwiftTemplates(String name, String keyword, TemplateFilter templateFilter,
             boolean isIso, List<HypervisorType> hypers, Boolean bootable, DomainVO domain, Long pageSize, Long startIndex,
             Long zoneId, HypervisorType hyperType, boolean onlyReady, boolean showDomr, List<Account> permittedAccounts, Account caller, Map<String, String> tags);
@@ -65,10 +67,11 @@ public interface VMTemplateDao extends GenericDao<VMTemplateVO, Long>, StateDao<
     public Set<Pair<Long, Long>> searchS3Templates(String name, String keyword, TemplateFilter templateFilter,
             boolean isIso, List<HypervisorType> hypers, Boolean bootable, DomainVO domain, Long pageSize, Long startIndex,
             Long zoneId, HypervisorType hyperType, boolean onlyReady, boolean showDomr, List<Account> permittedAccounts, Account caller, Map<String, String> tags);
+    */
 
 	public long addTemplateToZone(VMTemplateVO tmplt, long zoneId);
-	public List<VMTemplateVO> listAllInZone(long dataCenterId);	
-	
+	public List<VMTemplateVO> listAllInZone(long dataCenterId);
+
     public List<VMTemplateVO> listByHypervisorType(List<HypervisorType> hyperTypes);
 	public List<VMTemplateVO> publicIsoSearch(Boolean bootable, boolean listRemoved, Map<String, String> tags);
 	public List<VMTemplateVO> userIsoSearch(boolean listRemoved);
@@ -78,7 +81,7 @@ public interface VMTemplateDao extends GenericDao<VMTemplateVO, Long>, StateDao<
     VMTemplateVO findRoutingTemplate(HypervisorType type);
     List<Long> listPrivateTemplatesByHost(Long hostId);
     public Long countTemplatesForAccount(long accountId);
-	
+
     List<VMTemplateVO> findTemplatesToSyncToS3();
 
 }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/storage/dao/VMTemplateDaoImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/storage/dao/VMTemplateDaoImpl.java b/server/src/com/cloud/storage/dao/VMTemplateDaoImpl.java
index d9a26d3..1bc77df 100755
--- a/server/src/com/cloud/storage/dao/VMTemplateDaoImpl.java
+++ b/server/src/com/cloud/storage/dao/VMTemplateDaoImpl.java
@@ -16,25 +16,17 @@
 // under the License.
 package com.cloud.storage.dao;
 
-import static com.cloud.utils.StringUtils.join;
-import static com.cloud.utils.db.DbUtil.closeResources;
-
 import java.sql.PreparedStatement;
 import java.sql.ResultSet;
 import java.sql.SQLException;
 import java.util.ArrayList;
 import java.util.Date;
-import java.util.HashSet;
-import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Map;
-import java.util.Set;
-
 import javax.ejb.Local;
 import javax.inject.Inject;
 import javax.naming.ConfigurationException;
 
-import org.apache.cloudstack.api.BaseCmd;
 import org.apache.cloudstack.engine.subsystem.api.storage.TemplateEvent;
 import org.apache.cloudstack.engine.subsystem.api.storage.TemplateState;
 import org.apache.log4j.Logger;
@@ -42,25 +34,19 @@ import org.springframework.stereotype.Component;
 
 import com.cloud.configuration.dao.ConfigurationDao;
 import com.cloud.dc.dao.DataCenterDao;
-import com.cloud.domain.DomainVO;
 import com.cloud.domain.dao.DomainDao;
 import com.cloud.host.Host;
 import com.cloud.host.HostVO;
 import com.cloud.host.dao.HostDao;
 import com.cloud.hypervisor.Hypervisor.HypervisorType;
-import com.cloud.projects.Project.ListProjectResourcesCriteria;
 import com.cloud.server.ResourceTag.TaggedResourceType;
 import com.cloud.storage.Storage;
 import com.cloud.storage.Storage.ImageFormat;
 import com.cloud.storage.Storage.TemplateType;
-import com.cloud.storage.VMTemplateStorageResourceAssoc.Status;
 import com.cloud.storage.VMTemplateVO;
 import com.cloud.storage.VMTemplateZoneVO;
 import com.cloud.tags.ResourceTagVO;
 import com.cloud.tags.dao.ResourceTagDao;
-import com.cloud.template.VirtualMachineTemplate.TemplateFilter;
-import com.cloud.user.Account;
-import com.cloud.utils.Pair;
 import com.cloud.utils.db.DB;
 import com.cloud.utils.db.Filter;
 import com.cloud.utils.db.GenericDaoBase;
@@ -92,6 +78,9 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
     DomainDao _domainDao;
     @Inject
     DataCenterDao _dcDao;
+
+    /* TODO: these direct sql should go away with recent QueryService refactoring to handle listTemplatesCmd. Keep here just for
+     * potential bug reference.
     private final String SELECT_TEMPLATE_HOST_REF = "SELECT t.id, h.data_center_id, t.unique_name, t.name, t.public, t.featured, t.type, t.hvm, t.bits, t.url, t.format, t.created, t.account_id, " +
     								"t.checksum, t.display_text, t.enable_password, t.guest_os_id, t.bootable, t.prepopulate, t.cross_zones, t.hypervisor_type FROM vm_template t";
 
@@ -103,6 +92,7 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
 
     private final String SELECT_TEMPLATE_S3_REF = "SELECT t.id, t.unique_name, t.name, t.public, t.featured, t.type, t.hvm, t.bits, t.url, t.format, t.created, t.account_id, "
             + "t.checksum, t.display_text, t.enable_password, t.guest_os_id, t.bootable, t.prepopulate, t.cross_zones, t.hypervisor_type FROM vm_template t";
+    */
 
     private static final String SELECT_S3_CANDIDATE_TEMPLATES = "SELECT t.id, t.unique_name, t.name, t.public, t.featured, " +
         "t.type, t.hvm, t.bits, t.url, t.format, t.created, t.account_id, t.checksum, t.display_text, " +
@@ -397,6 +387,7 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
 		return routerTmpltName;
 	}
 
+	/*
     @Override
     public Set<Pair<Long, Long>> searchSwiftTemplates(String name, String keyword, TemplateFilter templateFilter, boolean isIso, List<HypervisorType> hypers, Boolean bootable, DomainVO domain,
             Long pageSize, Long startIndex, Long zoneId, HypervisorType hyperType, boolean onlyReady, boolean showDomr, List<Account> permittedAccounts, Account caller, Map<String, String> tags) {
@@ -538,7 +529,7 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
 	    Transaction txn = Transaction.currentTxn();
         txn.start();
 
-        /* Use LinkedHashSet here to guarantee iteration order */
+        // Use LinkedHashSet here to guarantee iteration order
         Set<Pair<Long, Long>> templateZonePairList = new LinkedHashSet<Pair<Long, Long>>();
         PreparedStatement pstmt = null;
         ResultSet rs = null;
@@ -751,7 +742,9 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
 
         return templateZonePairList;
 	}
+    */
 
+	/*
 	private String getExtrasWhere(TemplateFilter templateFilter, String name, String keyword, boolean isIso, Boolean bootable, HypervisorType hyperType, Long zoneId, boolean onlyReady, boolean showDomr) {
 	    String sql = "";
         if (keyword != null) {
@@ -811,6 +804,7 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
         }
         return sql;
 	}
+    */
 
 	@Override
 	@DB
@@ -873,7 +867,8 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
 		}
 	}
 
-	public VMTemplateVO findSystemVMTemplate(long zoneId, HypervisorType hType) {
+	@Override
+    public VMTemplateVO findSystemVMTemplate(long zoneId, HypervisorType hType) {
 	    SearchCriteria<VMTemplateVO> sc = tmpltTypeHyperSearch.create();
 	    sc.setParameters("templateType", Storage.TemplateType.SYSTEM);
 	    sc.setJoinParameters("tmplHyper",  "type", Host.Type.Routing);
@@ -938,18 +933,14 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
         return result;
     }
 
-    private boolean isAdmin(short accountType) {
-	    return ((accountType == Account.ACCOUNT_TYPE_ADMIN) ||
-	    	    (accountType == Account.ACCOUNT_TYPE_RESOURCE_DOMAIN_ADMIN) ||
-	            (accountType == Account.ACCOUNT_TYPE_DOMAIN_ADMIN) ||
-	            (accountType == Account.ACCOUNT_TYPE_READ_ONLY_ADMIN));
-	}
+
 
     @Override
     public List<VMTemplateVO> findTemplatesToSyncToS3() {
         return executeList(SELECT_S3_CANDIDATE_TEMPLATES, new Object[] {});
     }
 
+    /*
     @Override
     public Set<Pair<Long, Long>> searchS3Templates(final String name,
             final String keyword, final TemplateFilter templateFilter,
@@ -1083,6 +1074,7 @@ public class VMTemplateDaoImpl extends GenericDaoBase<VMTemplateVO, Long> implem
 
         return templateZonePairList;
     }
+*/
 
     @Override
     public boolean updateState(TemplateState currentState, TemplateEvent event,

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/server/src/com/cloud/template/TemplateManagerImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/template/TemplateManagerImpl.java b/server/src/com/cloud/template/TemplateManagerImpl.java
index 9e52422..619cd7e 100755
--- a/server/src/com/cloud/template/TemplateManagerImpl.java
+++ b/server/src/com/cloud/template/TemplateManagerImpl.java
@@ -2118,6 +2118,7 @@ public class TemplateManagerImpl extends ManagerBase implements TemplateManager,
     @Override
     public VMTemplateHostVO getTemplateHostRef(long zoneId, long tmpltId,
             boolean readyOnly) {
+        // readyOnly flag is not used at all
         List<HostVO> hosts = _ssvmMgr
                 .listSecondaryStorageHostsInOneZone(zoneId);
         if (hosts == null || hosts.size() == 0) {

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/53982479/setup/db/db/schema-410to420.sql
----------------------------------------------------------------------
diff --git a/setup/db/db/schema-410to420.sql b/setup/db/db/schema-410to420.sql
index fd03088..6a7365f 100644
--- a/setup/db/db/schema-410to420.sql
+++ b/setup/db/db/schema-410to420.sql
@@ -519,3 +519,98 @@ INSERT INTO `cloud`.`vm_template` (id, unique_name, name, public, created, type,
      VALUES (10, 'routing-10', 'SystemVM Template (LXC)', 0, now(), 'SYSTEM', 0, 64, 1, 'http://download.cloud.com/templates/acton/acton-systemvm-02062012.qcow2.bz2', '2755de1f9ef2ce4d6f2bee2efbb4da92', 0, 'SystemVM Template (LXC)', 'QCOW2', 15, 0, 1, 'LXC');
 
 -- END: support for LXC
+
+DROP VIEW IF EXISTS `cloud`.`template_view`;
+CREATE VIEW `cloud`.`template_view` AS
+    select 
+        vm_template.id,
+        vm_template.uuid,
+        vm_template.unique_name,
+        vm_template.name,
+        vm_template.public,
+        vm_template.featured,
+        vm_template.type,
+        vm_template.hvm,
+        vm_template.bits,
+        vm_template.url,
+        vm_template.format,
+        vm_template.created,
+        vm_template.checksum,
+        vm_template.display_text,
+        vm_template.enable_password,
+        vm_template.guest_os_id,
+        guest_os.uuid guest_os_uuid,
+        guest_os.display_name guest_os_name,
+        vm_template.bootable,
+        vm_template.prepopulate,
+        vm_template.cross_zones,
+        vm_template.hypervisor_type,
+        vm_template.extractable,
+        vm_template.template_tag,
+        vm_template.sort_key,
+        source_template.id source_template_id,
+        source_template.uuid source_template_uuid,
+        account.id account_id,
+        account.uuid account_uuid,
+        account.account_name account_name,
+        account.type account_type,
+        domain.id domain_id,
+        domain.uuid domain_uuid,
+        domain.name domain_name,
+        domain.path domain_path,
+        projects.id project_id,
+        projects.uuid project_uuid,
+        projects.name project_name,        
+        data_center.id data_center_id,
+        data_center.uuid data_center_uuid,
+        data_center.name data_center_name,
+        launch_permission.account_id lp_account_id,
+        template_store_ref.download_state,
+        template_store_ref.download_pct,
+        template_store_ref.error_str,
+        template_store_ref.size,
+        template_store_ref.destroyed,
+        template_store_ref.created created_on_store,
+        vm_template_details.name detail_name,
+        vm_template_details.value detail_value,
+        resource_tags.id tag_id,
+        resource_tags.uuid tag_uuid,
+        resource_tags.key tag_key,
+        resource_tags.value tag_value,
+        resource_tags.domain_id tag_domain_id,
+        resource_tags.account_id tag_account_id,
+        resource_tags.resource_id tag_resource_id,
+        resource_tags.resource_uuid tag_resource_uuid,
+        resource_tags.resource_type tag_resource_type,
+        resource_tags.customer tag_customer
+    from
+        `cloud`.`vm_template`
+            inner join
+        `cloud`.`guest_os` ON guest_os.id = vm_template.guest_os_id        
+            inner join
+        `cloud`.`account` ON account.id = vm_template.account_id
+            inner join
+        `cloud`.`domain` ON domain.id = account.domain_id
+            left join
+        `cloud`.`projects` ON projects.project_account_id = account.id    
+            left join
+        `cloud`.`vm_template_details` ON vm_template_details.template_id = vm_template.id         
+            left join
+        `cloud`.`vm_template` source_template ON source_template.id = vm_template.source_template_id            
+            left join
+        `cloud`.`template_zone_ref` ON template_zone_ref.template_id = vm_template.id
+            AND template_zone_ref.removed is null
+            left join
+        `cloud`.`data_center` ON template_zone_ref.zone_id = data_center.id
+            left join
+        `cloud`.`image_store` ON image_store.data_center_id = data_center.id OR image_store.scope = 'REGION'
+            left join
+        `cloud`.`template_store_ref` ON template_store_ref.template_id = vm_template.id AND template_store_ref.store_id = image_store.id
+            left join
+        `cloud`.`launch_permission` ON launch_permission.template_id = vm_template.id
+            left join
+        `cloud`.`resource_tags` ON resource_tags.resource_id = vm_template.id
+            and (resource_tags.resource_type = 'Template' or resource_tags.resource_type='ISO');
+
+
+