Skip to content

Commit

Permalink
JENKINS-12092 Block category by other categories
Browse files Browse the repository at this point in the history
  • Loading branch information
fluffy88 committed May 6, 2015
1 parent 9502034 commit 97fd80b
Show file tree
Hide file tree
Showing 5 changed files with 75 additions and 4 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -17,19 +17,22 @@
import hudson.matrix.MatrixProject;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.WeakHashMap;
import java.util.concurrent.CopyOnWriteArrayList;

import javax.annotation.CheckForNull;
import javax.annotation.Nonnull;
import jenkins.model.Jenkins;

import jenkins.model.Jenkins;
import net.sf.json.JSONObject;

import org.apache.commons.lang.StringUtils;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.QueryParameter;
import org.kohsuke.stapler.StaplerRequest;
Expand Down Expand Up @@ -322,9 +325,10 @@ public static final class ThrottleCategory extends AbstractDescribableImpl<Throt
private Integer maxConcurrentPerNode;
private Integer maxConcurrentTotal;
private String categoryName;
private String blockingCategories;
private List<String> blockingCategoriesList = new ArrayList<String>();
private List<NodeLabeledPair> nodeLabeledPairs;

@DataBoundConstructor
public ThrottleCategory(String categoryName,
Integer maxConcurrentPerNode,
Integer maxConcurrentTotal,
Expand All @@ -335,7 +339,26 @@ public ThrottleCategory(String categoryName,
this.nodeLabeledPairs =
nodeLabeledPairs == null ? new ArrayList<NodeLabeledPair>() : nodeLabeledPairs;
}

@DataBoundConstructor
public ThrottleCategory(String categoryName,
Integer maxConcurrentPerNode,
Integer maxConcurrentTotal,
String blockingCategories,
List<NodeLabeledPair> nodeLabeledPairs) {
this(categoryName, maxConcurrentPerNode, maxConcurrentTotal, nodeLabeledPairs);
this.blockingCategories = blockingCategories;
convertCategoriesToList(blockingCategories);
}

private void convertCategoriesToList(String categoriesString) {
String[] catArray = StringUtils.split(categoriesString, ',');
catArray = StringUtils.stripAll(catArray);
if (catArray != null) {
Collections.addAll(blockingCategoriesList, catArray);
}
}

public Integer getMaxConcurrentPerNode() {
if (maxConcurrentPerNode == null)
maxConcurrentPerNode = 0;
Expand All @@ -354,6 +377,14 @@ public String getCategoryName() {
return categoryName;
}

public String getBlockingCategories() {
return blockingCategories;
}

public List<String> getBlockingCategoriesList() {
return blockingCategoriesList;
}

public List<NodeLabeledPair> getNodeLabeledPairs() {
if (nodeLabeledPairs == null)
nodeLabeledPairs = new ArrayList<NodeLabeledPair>();
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package hudson.plugins.throttleconcurrents;


import hudson.Extension;
import hudson.matrix.MatrixConfiguration;
import hudson.matrix.MatrixProject;
Expand All @@ -13,14 +14,18 @@
import hudson.model.labels.LabelAtom;
import hudson.model.queue.CauseOfBlockage;
import hudson.model.queue.QueueTaskDispatcher;
import hudson.plugins.throttleconcurrents.ThrottleJobProperty.ThrottleCategory;

import java.util.List;
import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.annotation.CheckForNull;
import javax.annotation.Nonnull;

import org.apache.commons.lang.StringUtils;

@Extension
public class ThrottleQueueTaskDispatcher extends QueueTaskDispatcher {

Expand Down Expand Up @@ -153,6 +158,11 @@ else if (tjp.getThrottleOption().equals("category")) {

// Double check category itself isn't null
if (category != null) {
// Check if this job is blocked by category
if (isBlockedByCategories(category.getBlockingCategoriesList())) {
return CauseOfBlockage.fromMessage(Messages._ThrottleQueueTaskDispatcher_BlockedByCategory());
}

if (category.getMaxConcurrentTotal().intValue() > 0) {
int maxConcurrentTotal = category.getMaxConcurrentTotal().intValue();
int totalRunCount = 0;
Expand All @@ -178,6 +188,32 @@ else if (tjp.getThrottleOption().equals("category")) {
return null;
}

private boolean isBlockedByCategories(List<String> categoryNames) {
for (String catName : categoryNames) {
if (areProjectsInCategoryBuilding(catName)) {
return true;
}
}
return false;
}

private boolean areProjectsInCategoryBuilding(String categoryName) {
List<AbstractProject<?, ?>> projectsInCategory = ThrottleJobProperty.getCategoryProjects(categoryName);
for (AbstractProject<?, ?> project : projectsInCategory) {
if (isProjectBuilding(project)) {
return true;
}
}
return false;
}

private boolean isProjectBuilding(AbstractProject<?, ?> project) {
if (project.isBuilding() || project.isInQueue()) {
return true;
}
return false;
}

@CheckForNull
private ThrottleJobProperty getThrottleJobProperty(Task task) {
if (task instanceof AbstractProject) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
ThrottleQueueTaskDispatcher.MaxCapacityOnNode=Already running {0} builds on node
ThrottleQueueTaskDispatcher.MaxCapacityTotal=Already running {0} builds across all nodes
ThrottleQueueTaskDispatcher.BuildPending=A build is pending launch
ThrottleQueueTaskDispatcher.BlockedByCategory=Build is blocked by jobs in another category

ThrottleMatrixProjectOptions.DisplayName=Additional options for Matrix projects
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@
<f:entry title="${%Maximum Concurrent Builds Per Node}" field="maxConcurrentPerNode">
<f:textbox />
</f:entry>
<f:entry title="${%Blocking Categories}" field="blockingCategories">
<f:textbox />
</f:entry>
</table>
<f:repeatable field="nodeLabeledPairs" add="${%Add Maximum Per Labeled Node}" minimum="0" header="${%Maximum Per Labeled Node}">
<table width="100%">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ public class ThrottleCategoryTest
public void shouldGetEmptyNodeLabeledPairsListUponInitialNull()
{
ThrottleJobProperty.ThrottleCategory category =
new ThrottleJobProperty.ThrottleCategory(testCategoryName, 0, 0, null);
new ThrottleJobProperty.ThrottleCategory(testCategoryName, 0, 0, null, null);
assertTrue("nodeLabeledPairs shall be empty", category.getNodeLabeledPairs().isEmpty());
}

Expand All @@ -47,7 +47,7 @@ public void shouldGetNonEmptyNodeLabeledPairsListThatWasSet()
Integer expectedMax = new Integer(1);

ThrottleJobProperty.ThrottleCategory category =
new ThrottleJobProperty.ThrottleCategory(testCategoryName, 0, 0, null);
new ThrottleJobProperty.ThrottleCategory(testCategoryName, 0, 0, "", null);
List<ThrottleJobProperty.NodeLabeledPair> nodeLabeledPairs = category.getNodeLabeledPairs();
nodeLabeledPairs.add(new ThrottleJobProperty.NodeLabeledPair(expectedLabel, expectedMax));

Expand Down

0 comments on commit 97fd80b

Please sign in to comment.