All Downloads are FREE. Search and download functionalities are using the official Maven repository.

hudson.cli.InstallToolCommand Maven / Gradle / Ivy

The newest version!
/*******************************************************************************
 *
 * Copyright (c) 2004-2010, Oracle Corporation.
 *
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *
 *
 *
 *
 *******************************************************************************/ 

package hudson.cli;

import hudson.Extension;
import hudson.AbortException;
import hudson.EnvVars;
import hudson.model.Hudson;
import hudson.model.AbstractProject;
import hudson.model.Run;
import hudson.model.Executor;
import hudson.model.Node;
import hudson.model.EnvironmentSpecific;
import hudson.model.Item;
import hudson.remoting.Callable;
import hudson.slaves.NodeSpecific;
import hudson.util.EditDistance;
import hudson.util.StreamTaskListener;
import hudson.tools.ToolDescriptor;
import hudson.tools.ToolInstallation;

import java.util.List;
import java.util.ArrayList;
import java.io.IOException;

import org.kohsuke.args4j.Argument;

/**
 * Performs automatic tool installation on demand.
 *
 * @author Kohsuke Kawaguchi
 */
@Extension
public class InstallToolCommand extends CLICommand {

    @Argument(index = 0, metaVar = "KIND", usage = "The type of the tool to install, such as 'Ant'")
    public String toolType;
    @Argument(index = 1, metaVar = "NAME", usage = "The name of the tool to install, as you've entered in the Hudson system configuration")
    public String toolName;

    public String getShortDescription() {
        return "Performs automatic tool installation, and print its location to stdout. Can be only called from inside a build";
    }

    protected int run() throws Exception {
        Hudson h = Hudson.getInstance();
        h.checkPermission(Hudson.READ);

        // where is this build running?
        BuildIDs id = channel.call(new BuildIDs());

        if (!id.isComplete()) {
            throw new AbortException("This command can be only invoked from a build executing inside Hudson");
        }

        AbstractProject p = Hudson.getInstance().getItemByFullName(id.job, AbstractProject.class);
        if (p == null) {
            throw new AbortException("No such job found: " + id.job);
        }
        p.checkPermission(Item.CONFIGURE);

        List toolTypes = new ArrayList();
        for (ToolDescriptor d : ToolInstallation.all()) {
            toolTypes.add(d.getDisplayName());
            if (d.getDisplayName().equals(toolType)) {
                List toolNames = new ArrayList();
                for (ToolInstallation t : d.getInstallations()) {
                    toolNames.add(t.getName());
                    if (t.getName().equals(toolName)) {
                        return install(t, id, p);
                    }
                }

                // didn't find the right tool name
                error(toolNames, toolName, "name");
            }
        }

        // didn't find the tool type
        error(toolTypes, toolType, "type");

        // will never be here
        throw new AssertionError();
    }

    private int error(List candidates, String given, String noun) throws AbortException {
        if (given == null) {
            throw new AbortException("No tool " + noun + " was specified. Valid values are " + candidates.toString());
        } else {
            throw new AbortException("Unrecognized tool " + noun + ". Perhaps you meant '" + EditDistance.findNearest(given, candidates) + "'?");
        }
    }

    /**
     * Performs an installation.
     */
    private int install(ToolInstallation t, BuildIDs id, AbstractProject p) throws IOException, InterruptedException {

        Run b = p.getBuildByNumber(Integer.parseInt(id.number));
        if (b == null) {
            throw new AbortException("No such build: " + id.number);
        }

        Executor exec = b.getExecutor();
        if (exec == null) {
            throw new AbortException(b.getFullDisplayName() + " is not building");
        }

        Node node = exec.getOwner().getNode();

        if (t instanceof NodeSpecific) {
            NodeSpecific n = (NodeSpecific) t;
            t = (ToolInstallation) n.forNode(node, new StreamTaskListener(stderr));
        }
        if (t instanceof EnvironmentSpecific) {
            EnvironmentSpecific e = (EnvironmentSpecific) t;
            t = (ToolInstallation) e.forEnvironment(EnvVars.getRemote(channel));
        }
        stdout.println(t.getHome());
        return 0;
    }

    private static final class BuildIDs implements Callable {

        String job, number, id;

        public BuildIDs call() throws IOException {
            job = System.getenv("JOB_NAME");
            number = System.getenv("BUILD_NUMBER");
            id = System.getenv("BUILD_ID");
            return this;
        }

        boolean isComplete() {
            return job != null && number != null && id != null;
        }
        private static final long serialVersionUID = 1L;
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy