diff --git a/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/capacity/CapacityScheduler.java b/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/capacity/CapacityScheduler.java index 956d840eb3e..9fd691b0858 100644 --- a/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/capacity/CapacityScheduler.java +++ b/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/capacity/CapacityScheduler.java @@ -2520,7 +2520,7 @@ public boolean attemptAllocationOnNode(SchedulerApplicationAttempt appAttempt, try { if (!PlacementConstraintsUtil.canSatisfyConstraints( appAttempt.getApplicationId(), - schedulingRequest.getAllocationTags(), + schedulingRequest, schedulerNode, rmContext.getPlacementConstraintManager(), rmContext.getAllocationTagsManager())) { diff --git a/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/PlacementConstraintsUtil.java b/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/PlacementConstraintsUtil.java index 956a3c95051..dca48ec44b5 100644 --- a/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/PlacementConstraintsUtil.java +++ b/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/PlacementConstraintsUtil.java @@ -23,6 +23,7 @@ import org.apache.hadoop.classification.InterfaceAudience.Public; import org.apache.hadoop.classification.InterfaceStability.Unstable; import org.apache.hadoop.yarn.api.records.ApplicationId; +import org.apache.hadoop.yarn.api.records.SchedulingRequest; import org.apache.hadoop.yarn.api.resource.PlacementConstraint; import org.apache.hadoop.yarn.api.resource.PlacementConstraint.TargetExpression; import org.apache.hadoop.yarn.api.resource.PlacementConstraint.TargetExpression.TargetType; @@ -47,7 +48,7 @@ private PlacementConstraintsUtil() { } /** - * Returns true if **single** application constraint with associated + * Returns true if single application constraint with associated * allocationTags and scope is satisfied by a specific scheduler Node. * * @param appId the application id @@ -84,28 +85,23 @@ private static boolean canSatisfySingleConstraintExpression( } /** - * Returns true if all application constraints with associated allocationTags - * are **currently** satisfied by a specific scheduler Node. - * To do so the method retrieves and goes through all application constraint + * Returns true if the certain placement constraint of an application + * is currently satisfied by a specific scheduler node. + * To do so the method retrieves and goes through all constraint * expressions and checks if the specific allocation is between the allowed * min-max cardinality values under the constraint scope (Node/Rack/etc). * * @param appId the application id - * @param allocationTags the allocation tags set + * @param constraint placement constraint * @param node the scheduler node - * @param pcm the placement constraints store * @param tagsManager the allocation tags store - * @return true if all application constraints are satisfied by node + * @return true if all constraints are satisfied by node * @throws InvalidAllocationTagsQueryException */ - public static boolean canSatisfyConstraints(ApplicationId appId, - Set allocationTags, SchedulerNode node, - PlacementConstraintManager pcm, AllocationTagsManager tagsManager) + private static boolean canSatisfyConstraints(ApplicationId appId, + PlacementConstraint constraint, SchedulerNode node, + AllocationTagsManager tagsManager) throws InvalidAllocationTagsQueryException { - PlacementConstraint constraint = pcm.getConstraint(appId, allocationTags); - if (constraint == null) { - return true; - } // Transform to SimpleConstraint SingleConstraintTransformer singleTransformer = new SingleConstraintTransformer(constraint); @@ -129,4 +125,67 @@ public static boolean canSatisfyConstraints(ApplicationId appId, return true; } + /** + * Returns true if all application constraints with associated allocationTags + * are currently satisfied by a specific scheduler Node. + * + * @param appId the application id + * @param allocationTags the allocation tags set + * @param node the scheduler node + * @param pcm the placement constraints store + * @param tagsManager the allocation tags store + * @return true if all application constraints are satisfied by node + * @throws InvalidAllocationTagsQueryException + */ + public static boolean canSatisfyConstraints(ApplicationId appId, + Set allocationTags, SchedulerNode node, + PlacementConstraintManager pcm, AllocationTagsManager tagsManager) + throws InvalidAllocationTagsQueryException { + PlacementConstraint constraint = pcm.getConstraint(appId, allocationTags); + if (constraint == null) { + return true; + } + return canSatisfyConstraints(appId, constraint, node, tagsManager); + } + + /** + * Returns true if the placement constraint for a given scheduling request + * is currently satisfied by a specific scheduler node. This method + * first validates the constraint specified in the request; if not specified, + * then it validates application level constraint if exists; otherwise, it + * validates the global constraint if it is set by admin. + *

+ * This method only checks whether a scheduling request can be placed + * on a node with respect to the certain placement constraint. It gives no + * guarantee that asked allocations can be eventually allocated because + * it doesn't check resource, that needs a further decision from a scheduler. + * + * @param applicationId application id + * @param request scheduling request + * @param schedulerNode node + * @param pcm placement constraint manager + * @param atm allocation tags manager + * @return true if the given node satisfies the constraint of the request + * @throws InvalidAllocationTagsQueryException + */ + public static boolean canSatisfyConstraints(ApplicationId applicationId, + SchedulingRequest request, SchedulerNode schedulerNode, + PlacementConstraintManager pcm, AllocationTagsManager atm) + throws InvalidAllocationTagsQueryException { + // Request level constraint + PlacementConstraint constraint = request.getPlacementConstraint(); + if (constraint == null) { + // Application level constraint + constraint = pcm.getConstraint(applicationId, + request.getAllocationTags()); + if (constraint == null) { + // Global level constraint + constraint = pcm.getGlobalConstraint(request.getAllocationTags()); + if (constraint == null) { + return true; + } + } + } + return canSatisfyConstraints(applicationId, constraint, schedulerNode, atm); + } } diff --git a/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/algorithm/DefaultPlacementAlgorithm.java b/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/algorithm/DefaultPlacementAlgorithm.java index 9ed9ab13b91..1fbc9008ef7 100644 --- a/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/algorithm/DefaultPlacementAlgorithm.java +++ b/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/scheduler/constraint/algorithm/DefaultPlacementAlgorithm.java @@ -68,7 +68,7 @@ public boolean attemptPlacementOnNode(ApplicationId appId, int numAllocs = schedulingRequest.getResourceSizing().getNumAllocations(); if (numAllocs > 0) { if (PlacementConstraintsUtil.canSatisfyConstraints(appId, - schedulingRequest.getAllocationTags(), schedulerNode, + schedulingRequest, schedulerNode, constraintManager, tagsManager)) { return true; }