package hudson.model.queue;

import hudson.model.Queue.Task;
import hudson.model.Node;
import hudson.model.Messages;
import hudson.model.Label;
import org.jvnet.localizer.Localizable;

/**
 * If a {@link Task} execution is blocked in the queue, this object represents why.
 *
 * <h2>View</h2>
 * <tt>summary.jelly</tt> should do one-line HTML rendering to be used while rendering
 * "build history" widget, next to the blocking build. By default it simply renders
 * {@link #getShortDescription()} text.
 *
 * @since 1.330
 */
public abstract class CauseOfBlockage {
    /**
     * Human readable description of why the build is blocked.
     */
    public abstract String getShortDescription();

    /**
     * Obtains a simple implementation backed by {@link Localizable}.
     */
    public static CauseOfBlockage fromMessage(final Localizable l) {
        return new CauseOfBlockage() {
            public String getShortDescription() {
                return l.toString();
            }
        };
    }

    /**
     * Build is blocked because a node is offline.
     */
    public static final class BecauseNodeIsOffline extends CauseOfBlockage {
        public final Node node;

        public BecauseNodeIsOffline(Node node) {
            this.node = node;
        }

        public String getShortDescription() {
            return Messages.Queue_NodeOffline(node.getDisplayName());
        }
    }

    /**
     * Build is blocked because all the nodes that match a given label is offline.
     */
    public static final class BecauseLabelIsOffline extends CauseOfBlockage {
        public final Label label;

        public BecauseLabelIsOffline(Label l) {
            this.label = l;
        }

        public String getShortDescription() {
            return Messages.Queue_AllNodesOffline(label.getName());
        }
    }

    /**
     * Build is blocked because a node is fully busy
     */
    public static final class BecauseNodeIsBusy extends CauseOfBlockage {
        public final Node node;

        public BecauseNodeIsBusy(Node node) {
            this.node = node;
        }

        public String getShortDescription() {
            return Messages.Queue_WaitingForNextAvailableExecutorOn(node.getNodeName());
        }
    }

    /**
     * Build is blocked because everyone that matches the specified label is fully busy
     */
    public static final class BecauseLabelIsBusy extends CauseOfBlockage {
        public final Label label;

        public BecauseLabelIsBusy(Label label) {
            this.label = label;
        }

        public String getShortDescription() {
            return Messages.Queue_WaitingForNextAvailableExecutorOn(label.getName());
        }
    }
}

@@ -137,16 +137,44 @@
 .Label;%0A
+import hudson.slaves.Cloud;%0A
 import o
@@ -1023,32 +1023,822 @@
       %7D;%0A    %7D%0A%0A
+    /**%0A     * Marker interface to indicates that we can reasonably expect%0A     * that adding a suitable executor/node will resolve this blockage.%0A     *%0A     * Primarily this is used by %7B@link Cloud%7D to see if it should%0A     * consider provisioning new node.%0A     *%0A     * @since 1.427%0A     */%0A    interface NeedsMoreExecutor %7B%7D%0A%0A    public static CauseOfBlockage createNeedsMoreExecutor(Localizable l) %7B%0A        return new NeedsMoreExecutorImpl(l);%0A    %7D%0A%0A    private static final class NeedsMoreExecutorImpl extends CauseOfBlockage implements NeedsMoreExecutor %7B%0A        private final Localizable l;%0A%0A        private NeedsMoreExecutorImpl(Localizable l) %7B%0A            this.l = l;%0A        %7D%0A%0A        public String getShortDescription() %7B%0A            return l.toString();%0A        %7D%0A    %7D%0A%0A
     /**%0A     * B
@@ -1955,32 +1955,61 @@
 CauseOfBlockage 
+implements NeedsMoreExecutor 
 %7B%0A        public
@@ -2417,32 +2417,61 @@
 CauseOfBlockage 
+implements NeedsMoreExecutor 
 %7B%0A        public
@@ -2842,32 +2842,61 @@
 CauseOfBlockage 
+implements NeedsMoreExecutor 
 %7B%0A        public
@@ -3326,24 +3326,53 @@
 eOfBlockage 
+implements NeedsMoreExecutor 
 %7B%0A        pu

allow classification by the type of blockage