# HG changeset patch # Parent 590423437216c0b86eef4340cba2a41d6413f548 #214300: Permit Show Failures to be enabled on multiple-node selections diff --git a/hudson/src/org/netbeans/modules/hudson/api/UI.java b/hudson/src/org/netbeans/modules/hudson/api/UI.java --- a/hudson/src/org/netbeans/modules/hudson/api/UI.java +++ b/hudson/src/org/netbeans/modules/hudson/api/UI.java @@ -56,6 +56,7 @@ import org.openide.nodes.Node; import org.openide.nodes.NodeNotFoundException; import org.openide.nodes.NodeOp; +import org.openide.util.ContextAwareAction; import org.openide.util.ImageUtilities; import org.openide.util.Mutex; import org.openide.util.RequestProcessor; @@ -146,15 +147,8 @@ /** * Action to show test failures of a build. */ - public static Action showFailuresAction(HudsonJobBuild build) { - return new ShowFailures(build); - } - - /** - * Action to show test failures of a Maven module build. - */ - public static Action showFailuresAction(HudsonMavenModuleBuild build) { - return new ShowFailures(build); + public static ContextAwareAction showFailuresAction() { + return ShowFailures.getInstance(); } /** diff --git a/hudson/src/org/netbeans/modules/hudson/ui/actions/ShowFailures.java b/hudson/src/org/netbeans/modules/hudson/ui/actions/ShowFailures.java --- a/hudson/src/org/netbeans/modules/hudson/ui/actions/ShowFailures.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/actions/ShowFailures.java @@ -42,67 +42,163 @@ package org.netbeans.modules.hudson.ui.actions; import java.awt.event.ActionEvent; -import java.util.logging.Logger; +import java.util.LinkedList; +import java.util.List; import javax.swing.AbstractAction; +import javax.swing.Action; import org.netbeans.modules.hudson.api.HudsonInstance; import org.netbeans.modules.hudson.api.HudsonJobBuild; import org.netbeans.modules.hudson.api.HudsonMavenModuleBuild; import org.netbeans.modules.hudson.impl.HudsonInstanceImpl; import org.netbeans.modules.hudson.spi.BuilderConnector; -import static org.netbeans.modules.hudson.ui.actions.Bundle.*; +import org.openide.util.ContextAwareAction; +import org.openide.util.Lookup; import org.openide.util.NbBundle.Messages; -import org.openide.util.RequestProcessor; +import org.openide.util.Utilities; /** * Action to display test failures. */ -public class ShowFailures extends AbstractAction { +public class ShowFailures extends AbstractAction implements ContextAwareAction { - private static final Logger LOG = Logger.getLogger(ShowFailures.class.getName()); - private static final RequestProcessor RP = new RequestProcessor(ShowFailures.class); - private final HudsonJobBuild build; - private final HudsonMavenModuleBuild moduleBuild; + private static ShowFailures INSTANCE = null; + private final Lookup context; - public ShowFailures(HudsonJobBuild build) { - this(build, null); + /** + * Get the shared instance from system filesystem. + */ + public static ShowFailures getInstance() { + if (INSTANCE == null) { + INSTANCE = new ShowFailures(); + } + return INSTANCE; } - public ShowFailures(HudsonMavenModuleBuild module) { - this(module.getBuild(), module); + public ShowFailures() { + this(Utilities.actionsGlobalContext()); } @Messages("ShowFailures.label=Show Test Failures") - private ShowFailures(HudsonJobBuild build, - HudsonMavenModuleBuild moduleBuild) { - - this.build = build; - this.moduleBuild = moduleBuild; - putValue(NAME, ShowFailures_label()); + private ShowFailures(Lookup context) { + putValue(NAME, Bundle.ShowFailures_label()); + this.context = context; } - @Override - public void actionPerformed(ActionEvent e) { - HudsonInstance hudsonInstance = build.getJob().getInstance(); - if (hudsonInstance instanceof HudsonInstanceImpl) { - HudsonInstanceImpl hudsonInstanceImpl = - (HudsonInstanceImpl) hudsonInstance; - BuilderConnector builderClient = hudsonInstanceImpl.getBuilderConnector(); - if (moduleBuild != null) { - builderClient.getFailureDisplayer().showFailures(moduleBuild); - } else { - builderClient.getFailureDisplayer().showFailures(build); - } - } - } - - @Override - public boolean isEnabled() { + /** + * Check if failures for job build or maven module build can be shown. The + * build has to be unstable, and a failure displayer has to be available. + */ + private boolean canShowFailures(HudsonJobBuild build, + HudsonMavenModuleBuild module) { HudsonInstance instance = build.getJob().getInstance(); if (instance instanceof HudsonInstanceImpl) { + if (module == null && !HudsonJobBuild.Result.UNSTABLE.equals( + build.getResult())) { + return false; + } else if (module != null) { + boolean failed = false; + switch (module.getColor()) { + case yellow: + case yellow_anime: + failed = true; + } + if (!failed) { + return false; + } + } BuilderConnector builderClient = ((HudsonInstanceImpl) instance).getBuilderConnector(); return builderClient.getFailureDisplayer() != null; } return false; } + + /** + * Find maven module builds that are part of a job build but are not already + * included in the context. + */ + private List getExtraModuleBuilds( + HudsonJobBuild build) { + List result = new LinkedList(); + for (HudsonMavenModuleBuild m : build.getMavenModules()) { + if (null == context.lookup(new Lookup.Template( + HudsonMavenModuleBuild.class, null, m))) { + result.add(m); + } + } + return result; + } + + /** + * If there is at least one unstable build in the context, this action will + * be enabled. + */ + @Override + public boolean isEnabled() { + for (HudsonJobBuild job : context.lookupAll(HudsonJobBuild.class)) { + if (canShowFailures(job, null)) { + return true; + } + } + for (HudsonMavenModuleBuild module + : context.lookupAll(HudsonMavenModuleBuild.class)) { + if (canShowFailures(module.getBuild(), module)) { + return true; + } + } + return false; + } + + @Override + public void actionPerformed(ActionEvent e) { + + for (HudsonJobBuild job : context.lookupAll(HudsonJobBuild.class)) { + showFailures(job, null); + } + for (HudsonMavenModuleBuild module + : context.lookupAll(HudsonMavenModuleBuild.class)) { + showFailures(module.getBuild(), module); + } + } + + /** + * Show failures in a job build or maven module build. If a maven module + * build is not specified, but the job build contains some module build, + * failures from all its module builds will be shown. + */ + private void showFailures(HudsonJobBuild build, + HudsonMavenModuleBuild moduleBuild) { + + if (!canShowFailures(build, moduleBuild)) { + return; + } + HudsonInstance hudsonInstance = build.getJob().getInstance(); + if (hudsonInstance instanceof HudsonInstanceImpl) { + HudsonInstanceImpl hudsonInstanceImpl = + (HudsonInstanceImpl) hudsonInstance; + BuilderConnector builderClient = + hudsonInstanceImpl.getBuilderConnector(); + BuilderConnector.FailureDisplayer failureDisplayer = + builderClient.getFailureDisplayer(); + if (failureDisplayer != null) { + if (moduleBuild != null) { + failureDisplayer.showFailures(moduleBuild); + } else { + if (build.getMavenModules().isEmpty()) { + failureDisplayer.showFailures(build); + } else { + for (HudsonMavenModuleBuild extraModule + : getExtraModuleBuilds(build)) { + failureDisplayer.showFailures(extraModule); + } + } + } + } + } + } + + @Override + public Action createContextAwareInstance(Lookup actionContext) { + return new ShowFailures(actionContext); + } } diff --git a/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonJobBuildNode.java b/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonJobBuildNode.java --- a/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonJobBuildNode.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonJobBuildNode.java @@ -94,9 +94,7 @@ List actions = new ArrayList(); actions.add(UI.showChangesAction(build)); actions.add(UI.showConsoleAction(build)); - if (build.getResult() == HudsonJobBuild.Result.UNSTABLE && build.getMavenModules().isEmpty()) { - actions.add(UI.showFailuresAction(build)); - } + actions.add(UI.showFailuresAction()); actions.add(null); if (build instanceof OpenableInBrowser) { actions.add(OpenUrlAction.forOpenable((OpenableInBrowser) build)); diff --git a/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonMavenModuleBuildNode.java b/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonMavenModuleBuildNode.java --- a/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonMavenModuleBuildNode.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/nodes/HudsonMavenModuleBuildNode.java @@ -85,11 +85,7 @@ public @Override Action[] getActions(boolean context) { List actions = new ArrayList(); actions.add(UI.showConsoleAction(module)); - switch (module.getColor()) { - case yellow: - case yellow_anime: - actions.add(UI.showFailuresAction(module)); - } + actions.add(UI.showFailuresAction()); actions.add(null); if (module instanceof OpenableInBrowser) { actions.add(OpenUrlAction.forOpenable((OpenableInBrowser) module)); diff --git a/hudson/src/org/netbeans/modules/hudson/ui/notification/ProblemNotification.java b/hudson/src/org/netbeans/modules/hudson/ui/notification/ProblemNotification.java --- a/hudson/src/org/netbeans/modules/hudson/ui/notification/ProblemNotification.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/notification/ProblemNotification.java @@ -59,6 +59,7 @@ import org.openide.util.NbBundle.Messages; import org.openide.util.RequestProcessor; import static org.netbeans.modules.hudson.ui.notification.Bundle.*; +import org.openide.util.lookup.Lookups; /** * Build failed or was unstable. @@ -109,13 +110,16 @@ if (failed) { UI.showConsoleAction(b).actionPerformed(null); } else if (b.getMavenModules().isEmpty()) { - UI.showFailuresAction(b).actionPerformed(null); + UI.showFailuresAction().createContextAwareInstance( + Lookups.singleton(b)).actionPerformed(null); } else { for (HudsonMavenModuleBuild module : b.getMavenModules()) { switch (module.getColor()) { case yellow: case yellow_anime: - UI.showFailuresAction(module).actionPerformed(null); + UI.showFailuresAction() + .createContextAwareInstance(Lookups.singleton(module)) + .actionPerformed(null); } } }