| // 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.deploy; |
| |
| import java.util.ArrayList; |
| import java.util.List; |
| import java.util.Map; |
| |
| |
| |
| import com.cloud.utils.Pair; |
| import com.cloud.vm.VirtualMachineProfile; |
| |
| public class UserConcentratedPodPlanner extends FirstFitPlanner implements DeploymentClusterPlanner { |
| |
| |
| /** |
| * This method should reorder the given list of Cluster Ids by applying any necessary heuristic |
| * for this planner |
| * For UserConcentratedPodPlanner we need to order the clusters in a zone across pods, by considering those pods first which have more number of VMs for this account |
| * This reordering is not done incase the clusters within single pod are passed when the allocation is applied at pod-level. |
| * @return List<Long> ordered list of Cluster Ids |
| */ |
| @Override |
| protected List<Long> reorderClusters(long id, boolean isZone, Pair<List<Long>, Map<Long, Double>> clusterCapacityInfo, VirtualMachineProfile vmProfile, |
| DeploymentPlan plan) { |
| List<Long> clusterIdsByCapacity = clusterCapacityInfo.first(); |
| if (vmProfile.getOwner() == null || !isZone) { |
| return clusterIdsByCapacity; |
| } |
| return applyUserConcentrationPodHeuristicToClusters(id, clusterIdsByCapacity, vmProfile.getOwner().getAccountId()); |
| } |
| |
| private List<Long> applyUserConcentrationPodHeuristicToClusters(long zoneId, List<Long> prioritizedClusterIds, long accountId) { |
| //user has VMs in certain pods. - prioritize those pods first |
| //UserConcentratedPod strategy |
| List<Long> clusterList = new ArrayList<Long>(); |
| List<Long> podIds = listPodsByUserConcentration(zoneId, accountId); |
| if (!podIds.isEmpty()) { |
| clusterList = reorderClustersByPods(prioritizedClusterIds, podIds); |
| } else { |
| clusterList = prioritizedClusterIds; |
| } |
| return clusterList; |
| } |
| |
| private List<Long> reorderClustersByPods(List<Long> clusterIds, List<Long> podIds) { |
| |
| if (logger.isDebugEnabled()) { |
| logger.debug("Reordering cluster list as per pods ordered by user concentration"); |
| } |
| |
| Map<Long, List<Long>> podClusterMap = clusterDao.getPodClusterIdMap(clusterIds); |
| |
| if (logger.isTraceEnabled()) { |
| logger.trace("Pod To cluster Map is: " + podClusterMap); |
| } |
| |
| List<Long> reorderedClusters = new ArrayList<Long>(); |
| for (Long pod : podIds) { |
| if (podClusterMap.containsKey(pod)) { |
| List<Long> clustersOfThisPod = podClusterMap.get(pod); |
| if (clustersOfThisPod != null) { |
| for (Long clusterId : clusterIds) { |
| if (clustersOfThisPod.contains(clusterId)) { |
| reorderedClusters.add(clusterId); |
| } |
| } |
| clusterIds.removeAll(clustersOfThisPod); |
| } |
| } |
| } |
| reorderedClusters.addAll(clusterIds); |
| |
| if (logger.isTraceEnabled()) { |
| logger.trace("Reordered cluster list: " + reorderedClusters); |
| } |
| return reorderedClusters; |
| } |
| |
| protected List<Long> listPodsByUserConcentration(long zoneId, long accountId) { |
| |
| if (logger.isDebugEnabled()) { |
| logger.debug("Applying UserConcentratedPod heuristic for account: " + accountId); |
| } |
| |
| List<Long> prioritizedPods = vmDao.listPodIdsHavingVmsforAccount(zoneId, accountId); |
| |
| if (logger.isTraceEnabled()) { |
| logger.trace("List of pods to be considered, after applying UserConcentratedPod heuristic: " + prioritizedPods); |
| } |
| |
| return prioritizedPods; |
| } |
| |
| /** |
| * This method should reorder the given list of Pod Ids by applying any necessary heuristic |
| * for this planner |
| * For UserConcentratedPodPlanner we need to order the pods by considering those pods first which have more number of VMs for this account |
| * @return List<Long> ordered list of Pod Ids |
| */ |
| @Override |
| protected List<Long> reorderPods(Pair<List<Long>, Map<Long, Double>> podCapacityInfo, VirtualMachineProfile vmProfile, DeploymentPlan plan) { |
| List<Long> podIdsByCapacity = podCapacityInfo.first(); |
| if (vmProfile.getOwner() == null) { |
| return podIdsByCapacity; |
| } |
| long accountId = vmProfile.getOwner().getAccountId(); |
| |
| //user has VMs in certain pods. - prioritize those pods first |
| //UserConcentratedPod strategy |
| List<Long> podIds = listPodsByUserConcentration(plan.getDataCenterId(), accountId); |
| if (!podIds.isEmpty()) { |
| //remove pods that don't have capacity for this vm |
| podIds.retainAll(podIdsByCapacity); |
| podIdsByCapacity.removeAll(podIds); |
| podIds.addAll(podIdsByCapacity); |
| return podIds; |
| } else { |
| return podIdsByCapacity; |
| } |
| |
| } |
| |
| } |