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

org.gradle.api.internal.tasks.AntGroovydoc Maven / Gradle / Ivy

There is a newer version: 8.11.1
Show newest version
/*
 * Copyright 2016 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.gradle.api.internal.tasks;

import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Maps;
import com.google.common.io.Files;
import groovy.lang.Closure;
import groovy.lang.GroovyObjectSupport;
import org.gradle.api.Action;
import org.gradle.api.GradleException;
import org.gradle.api.Project;
import org.gradle.api.file.CopySpec;
import org.gradle.api.file.FileCollection;
import org.gradle.api.internal.ClassPathRegistry;
import org.gradle.api.internal.file.FileOperations;
import org.gradle.api.internal.project.IsolatedAntBuilder;
import org.gradle.api.internal.project.ProjectInternal;
import org.gradle.api.tasks.javadoc.Groovydoc;
import org.gradle.util.VersionNumber;

import java.io.File;
import java.io.IOException;
import java.nio.charset.Charset;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * Generates groovy doc using Ant.
 */
public class AntGroovydoc {

    private final IsolatedAntBuilder ant;

    public AntGroovydoc(IsolatedAntBuilder ant, @SuppressWarnings("UnusedParameters") ClassPathRegistry ignored) {
        this.ant = ant;
    }

    public void execute(final FileCollection source, File destDir, boolean use, boolean noTimestamp, boolean noVersionStamp,
            String windowTitle, String docTitle, String header, String footer, String overview, boolean includePrivate,
            final Set links, final Iterable groovyClasspath, Iterable classpath, Project project) {

        final File tmpDir = new File(project.getBuildDir(), "tmp/groovydoc");
        FileOperations fileOperations = ((ProjectInternal) project).getFileOperations();
        fileOperations.delete(tmpDir);
        fileOperations.copy(new Action() {
            public void execute(CopySpec copySpec) {
                copySpec.from(source).into(tmpDir);
            }
        });

        List combinedClasspath = ImmutableList.builder()
            .addAll(classpath)
            .addAll(groovyClasspath)
            .build();

        VersionNumber version = VersionNumber.parse(getGroovyVersion(combinedClasspath));

        final Map args = Maps.newLinkedHashMap();
        args.put("sourcepath", tmpDir.toString());
        args.put("destdir", destDir);
        args.put("use", use);
        if (isAtLeast(version, "2.4.6")) {
            args.put("noTimestamp", noTimestamp);
            args.put("noVersionStamp", noVersionStamp);
        }
        args.put("private", includePrivate);
        putIfNotNull(args, "windowtitle", windowTitle);
        putIfNotNull(args, "doctitle", docTitle);
        putIfNotNull(args, "header", header);
        putIfNotNull(args, "footer", footer);

        if (overview != null) {
            args.put("overview", overview);
        }

        invokeGroovydoc(links, combinedClasspath, args);
    }

    private boolean isAtLeast(VersionNumber version, String versionString) {
        return version.compareTo(VersionNumber.parse(versionString)) >= 0;
    }

    private String getGroovyVersion(List combinedClasspath) {
        File temp;
        final String tempPath;
        try {
            temp = File.createTempFile("temp", "");
            String p = temp.getCanonicalPath();
            tempPath = File.separatorChar == '/' ? p : p.replace(File.separatorChar, '/');
            temp.deleteOnExit();
        } catch (IOException e) {
            throw new GradleException("Unable to create temp file needed for Groovydoc", e);
        }

        ant.withClasspath(combinedClasspath).execute(new Closure(this, this) {
            @SuppressWarnings("UnusedDeclaration")
            public Object doCall(Object it) {
                final GroovyObjectSupport antBuilder = (GroovyObjectSupport) it;

                antBuilder.invokeMethod("taskdef", ImmutableMap.of(
                    "name", "groovy",
                    "classname", "org.codehaus.groovy.ant.Groovy"
                ));

                antBuilder.invokeMethod("groovy", new Object[]{"new File('"+ tempPath + "').text = GroovySystem.version"});

                return null;
            }
        });
        try {
            return Files.toString(temp, Charset.defaultCharset()).trim();
        } catch (IOException e) {
            throw new GradleException("Unable to find Groovy version needed for Groovydoc", e);
        }
    }

    private void invokeGroovydoc(final Set links, List combinedClasspath, final Map args) {
        ant.withClasspath(combinedClasspath).execute(new Closure(this, this) {
            @SuppressWarnings("UnusedDeclaration")
            public Object doCall(Object it) {
                final GroovyObjectSupport antBuilder = (GroovyObjectSupport) it;

                antBuilder.invokeMethod("taskdef", ImmutableMap.of(
                        "name", "groovydoc",
                        "classname", "org.codehaus.groovy.ant.Groovydoc"
                ));

                antBuilder.invokeMethod("groovydoc", new Object[]{args, new Closure(this, this) {
                    public Object doCall(Object ignore) {
                        for (Groovydoc.Link link : links) {
                            antBuilder.invokeMethod("link", new Object[]{
                                    ImmutableMap.of(
                                            "packages", Joiner.on(",").join(link.getPackages()),
                                            "href", link.getUrl()
                                    )
                            });
                        }

                        return null;
                    }
                }});

                return null;
            }
        });
    }

    private static void putIfNotNull(Map map, String key, Object value) {
        if (value != null) {
            map.put(key, value);
        }
    }

}