private List<HostSpec> allocateHostGroup(ClusterSpec clusterGroup, String flavor, int nodesInGroup, int startIndex, boolean canFail) {
List<HostSpec> allocation = allocations.getOrDefault(clusterGroup, new ArrayList<>());
allocations.put(clusterGroup, allocation);
int nextIndex = nextIndexInCluster.getOrDefault(new Pair<>(clusterGroup.type(), clusterGroup.id()), startIndex);
while (allocation.size() < nodesInGroup) {
if (freeNodes.get(flavor).isEmpty()) {
if (canFail)
throw new IllegalArgumentException("Insufficient capacity of flavor '" + flavor + "'");
else
break;
}
Host newHost = freeNodes.removeValue(flavor, 0);
ClusterMembership membership = ClusterMembership.from(clusterGroup, nextIndex++);
allocation.add(new HostSpec(newHost.hostname(), newHost.aliases(), newHost.flavor(), Optional.of(membership), newHost.version()));
}
nextIndexInCluster.put(new Pair<>(clusterGroup.type(), clusterGroup.id()), nextIndex);
while (allocation.size() > nodesInGroup)
allocation.remove(0);
return allocation;
}