package io.cattle.platform.allocator.constraint; import io.cattle.platform.allocator.dao.AllocatorDao; import io.cattle.platform.allocator.service.AllocationAttempt; import io.cattle.platform.allocator.service.AllocationLog; import io.cattle.platform.core.constants.InstanceConstants; import io.cattle.platform.core.constants.VolumeConstants; import io.cattle.platform.core.dao.GenericMapDao; import io.cattle.platform.core.dao.StoragePoolDao; import io.cattle.platform.core.model.Host; import io.cattle.platform.core.model.Instance; import io.cattle.platform.core.model.StoragePool; import io.cattle.platform.core.model.Volume; import io.cattle.platform.object.ObjectManager; import io.cattle.platform.object.util.DataAccessor; import io.cattle.platform.util.type.Priority; import java.util.Collection; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; import javax.inject.Inject; import org.apache.commons.lang3.StringUtils; public class BaseConstraintsProvider implements AllocationConstraintsProvider, Priority { @Inject AllocatorDao allocatorDao; @Inject ObjectManager objectManager; @Inject GenericMapDao mapDao; @Inject StoragePoolDao storagePoolDao; @Override public void appendConstraints(AllocationAttempt attempt, AllocationLog log, List<Constraint> constraints) { populateConstraints(attempt, log); } protected void populateConstraints(AllocationAttempt attempt, AllocationLog log) { List<Constraint> constraints = attempt.getConstraints(); addLogConstraints(attempt, log); addComputeConstraints(attempt, constraints); addStorageConstraints(attempt, constraints); } protected void addLogConstraints(AllocationAttempt attempt, AllocationLog log) { } protected void addComputeConstraints(AllocationAttempt attempt, List<Constraint> constraints) { ValidHostsConstraint hostSet = new ValidHostsConstraint(); if (attempt.getHostId() != null) { hostSet.addHost(attempt.getHostId()); } if (attempt.getRequestedHostId() != null) { hostSet.addHost(attempt.getRequestedHostId()); } if (hostSet.getHosts().size() > 0) { constraints.add(hostSet); } } protected void addStorageConstraints(AllocationAttempt attempt, List<Constraint> constraints) { for (Map.Entry<Volume, Set<StoragePool>> entry : attempt.getPools().entrySet()) { Volume volume = entry.getKey(); boolean alreadyMappedToPool = entry.getValue().size() > 0; Set<Long> storagePoolIds = new HashSet<>(); for (StoragePool pool : entry.getValue()) { storagePoolIds.add(pool.getId()); storagePoolToHostConstraint(constraints, pool); } boolean restrictToUnmanagedPool = false; if (!alreadyMappedToPool) { String driver = DataAccessor.fieldString(volume, VolumeConstants.FIELD_VOLUME_DRIVER); restrictToUnmanagedPool = true; if (StringUtils.isNotEmpty(driver) && !VolumeConstants.LOCAL_DRIVER.equals(driver)) { List<? extends StoragePool> pools = storagePoolDao.findStoragePoolByDriverName(volume.getAccountId(), driver); if (pools.size() > 0) { Set<Long> poolIds = new HashSet<>(); for (StoragePool pool : pools) { poolIds.add(pool.getId()); } constraints.add(new VolumeValidStoragePoolConstraint(volume, false, poolIds)); storagePoolToHostConstraint(constraints, pools); restrictToUnmanagedPool = false; } } Instance instance = objectManager.loadResource(Instance.class, volume.getInstanceId()); if (instance != null) { Host host = allocatorDao.getHost(instance); if (host != null) { for (StoragePool pool : allocatorDao.getAssociatedUnmanagedPools(host)) { storagePoolIds.add(pool.getId()); } } } } if (storagePoolIds.size() > 0) { constraints.add(new VolumeValidStoragePoolConstraint(volume, alreadyMappedToPool, storagePoolIds)); } if (restrictToUnmanagedPool || volume.getImageId() != null) { constraints.add(new UnmanagedStoragePoolKindConstraint(volume)); } } for (Instance instance : attempt.getInstances()) { String driver = DataAccessor.fieldString(instance, InstanceConstants.FIELD_VOLUME_DRIVER); if (StringUtils.isNotEmpty(driver) && !VolumeConstants.LOCAL_DRIVER.equals(driver)) { List<? extends StoragePool> pools = storagePoolDao.findStoragePoolByDriverName(instance.getAccountId(), driver); if (pools.size() > 0) { storagePoolToHostConstraint(constraints, pools.get(0)); } } } } void storagePoolToHostConstraint(List<Constraint> constraints, Collection<? extends StoragePool> pools) { ValidHostsConstraint hostSet = new ValidHostsConstraint(); for (Host host : allocatorDao.getHosts(pools)) { hostSet.addHost(host.getId()); } constraints.add(hostSet); } void storagePoolToHostConstraint(List<Constraint> constraints, StoragePool pool) { Set<StoragePool> p = new HashSet<>(); p.add(pool); storagePoolToHostConstraint(constraints, p); } @Override public int getPriority() { return Priority.PRE; } @Override public boolean isCritical() { return true; } }