// Copyright 2014 The Bazel Authors. All rights reserved.
//
// 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 com.google.devtools.build.lib.rules.java;

import static com.google.devtools.build.lib.packages.Attribute.attr;
import static com.google.devtools.build.lib.packages.BuildType.LABEL;
import static com.google.devtools.build.lib.packages.BuildType.LABEL_LIST;
import static com.google.devtools.build.lib.packages.BuildType.LICENSE;
import static com.google.devtools.build.lib.packages.Type.BOOLEAN;
import static com.google.devtools.build.lib.packages.Type.STRING;
import static com.google.devtools.build.lib.packages.Type.STRING_LIST;
import static com.google.devtools.build.lib.packages.Type.STRING_LIST_DICT;

import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.devtools.build.lib.analysis.BaseRuleClasses;
import com.google.devtools.build.lib.analysis.RuleDefinition;
import com.google.devtools.build.lib.analysis.RuleDefinitionEnvironment;
import com.google.devtools.build.lib.analysis.config.HostTransition;
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.util.FileTypeSet;
import java.util.List;

/** Rule definition for {@code java_toolchain} */
public final class JavaToolchainRule<C extends JavaToolchain> implements RuleDefinition {

  private final Class<C> ruleClass;

  public static <C extends JavaToolchain> JavaToolchainRule<C> create(Class<C> ruleClass) {
    return new JavaToolchainRule<C>(ruleClass);
  }

  private JavaToolchainRule(Class<C> ruleClass) {
    this.ruleClass = ruleClass;
  }

  @Override
  public RuleClass build(RuleClass.Builder builder, RuleDefinitionEnvironment env) {
    return builder
        .requiresConfigurationFragments(JavaConfiguration.class)
        /* <!-- #BLAZE_RULE(java_plugin).ATTRIBUTE(output_licenses) -->
        See <a href="${link common-definitions#binary.output_licenses}"><code>common attributes
        </code></a>
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("output_licenses", LICENSE))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(source_version) -->
        The Java source version (e.g., '6' or '7'). It specifies which set of code structures
        are allowed in the Java source code.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("source_version", STRING)) // javac -source flag value.
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(target_version) -->
        The Java target version (e.g., '6' or '7'). It specifies for which Java runtime the class
        should be build.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("target_version", STRING)) // javac -target flag value.
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(bootclasspath) -->
        The Java target bootclasspath entries. Corresponds to javac's -bootclasspath flag.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("bootclasspath", LABEL_LIST)
                .value(ImmutableList.of())
                .allowedFileTypes(FileTypeSet.ANY_FILE))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(extclasspath) -->
        The Java target extdir entries. Corresponds to javac's -extdir flag.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("extclasspath", LABEL_LIST)
                .value(ImmutableList.of())
                .allowedFileTypes(FileTypeSet.ANY_FILE))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(xlint) -->
        The list of warning to add or removes from default list. Precedes it with a dash to
        removes it. Please see the Javac documentation on the -Xlint options for more information.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("xlint", STRING_LIST).value(ImmutableList.<String>of()))
        .add(
            attr("misc", STRING_LIST)
                .undocumented("use javacopts instead")
                .value(ImmutableList.<String>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(javacopts) -->
        The list of extra arguments for the Java compiler. Please refer to the Java compiler
        documentation for the extensive list of possible Java compiler flags.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("javacopts", STRING_LIST).value(ImmutableList.<String>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(jvm_opts) -->
        The list of arguments for the JVM when invoking the Java compiler. Please refer to the Java
        virtual machine documentation for the extensive list of possible flags for this option.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("jvm_opts", STRING_LIST).value(ImmutableList.<String>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(javabuilder_jvm_opts) -->
        The list of arguments for the JVM when invoking JavaBuilder.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("javabuilder_jvm_opts", STRING_LIST).value(ImmutableList.<String>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(turbine_jvm_opts) -->
        The list of arguments for the JVM when invoking turbine.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("turbine_jvm_opts", STRING_LIST).value(ImmutableList.<String>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(javac_supports_workers) -->
        True if JavaBuilder supports running as a persistent worker, false if it doesn't.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("javac_supports_workers", BOOLEAN).value(true))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(javac) -->
        Label of the javac jar.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("javac", LABEL_LIST)
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(tools) -->
        Labels of tools available for label-expansion in jvm_opts.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("tools", LABEL_LIST)
                .cfg(HostTransition.createFactory())
                .allowedFileTypes(FileTypeSet.ANY_FILE))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(javabuilder) -->
        Label of the JavaBuilder deploy jar.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("javabuilder", LABEL_LIST)
                .mandatory()
                .cfg(HostTransition.createFactory())
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(singlejar) -->
        Label of the SingleJar deploy jar.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("singlejar", LABEL_LIST)
                .mandatory()
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(genclass) -->
        Label of the GenClass deploy jar.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("genclass", LABEL_LIST)
                .mandatory()
                .singleArtifact()
                .cfg(HostTransition.createFactory())
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(resourcejar) -->
        Label of the resource jar builder executable.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("resourcejar", LABEL_LIST)
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(timezone_data) -->
        Label of a resource jar containing timezone data. If set, the timezone data is added as an
        implicitly runtime dependency of all java_binary rules.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("timezone_data", LABEL)
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(ijar) -->
        Label of the ijar executable.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("ijar", LABEL_LIST)
                .mandatory()
                .cfg(HostTransition.createFactory())
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(header_compiler) -->
        Label of the header compiler. Required if --java_header_compilation is enabled.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("header_compiler", LABEL_LIST)
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(header_compiler_direct) -->
        Optional label of the header compiler to use for direct classpath actions that do not
        include any API-generating annotation processors.

        <p>This tool does not support annotation processing.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("header_compiler_direct", LABEL_LIST)
                .cfg(HostTransition.createFactory())
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        .add(
            attr("header_compiler_builtin_processors", STRING_LIST)
                .undocumented("internal")
                .value(ImmutableList.<String>of()))
        .add(
            attr("reduced_classpath_incompatible_processors", STRING_LIST)
                .undocumented("internal")
                .value(ImmutableList.<String>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(oneversion) -->
        Label of the one-version enforcement binary.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("oneversion", LABEL)
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(oneversion_whitelist) -->
        Label of the one-version whitelist.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("oneversion_whitelist", LABEL)
                .cfg(HostTransition.createFactory())
                .singleArtifact()
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(forcibly_disable_header_compilation) -->
        Overrides --java_header_compilation to disable header compilation on platforms that do not
        support it, e.g. JDK 7 Bazel.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(attr("forcibly_disable_header_compilation", BOOLEAN).value(false))
        .add(
            attr("compatible_javacopts", STRING_LIST_DICT)
                .undocumented("internal")
                .value(ImmutableMap.<String, List<String>>of()))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(package_configuration) -->
        Configuration that should be applied to the specified package groups.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("package_configuration", LABEL_LIST)
                .cfg(HostTransition.createFactory())
                .allowedFileTypes()
                .mandatoryNativeProviders(ImmutableList.of(JavaPackageConfigurationProvider.class)))
        /* <!-- #BLAZE_RULE(java_toolchain).ATTRIBUTE(jacocorunner) -->
        Label of the JacocoCoverageRunner deploy jar.
        <!-- #END_BLAZE_RULE.ATTRIBUTE --> */
        .add(
            attr("jacocorunner", LABEL)
                .cfg(HostTransition.createFactory())
                .allowedFileTypes(FileTypeSet.ANY_FILE)
                .exec())
        .build();
  }

  @Override
  public Metadata getMetadata() {
    return RuleDefinition.Metadata.builder()
        .name("java_toolchain")
        .ancestors(BaseRuleClasses.BaseRule.class)
        .factoryClass(ruleClass)
        .build();
  }
}
/*<!-- #BLAZE_RULE (NAME = java_toolchain, TYPE = OTHER, FAMILY = Java) -->

<p>
Specifies the configuration for the Java compiler. Which toolchain to be used can be changed through
the --java_toolchain argument. Normally you should not write those kind of rules unless you want to
tune your Java compiler.
</p>

<h4 id="java_binary_examples">Examples</h4>

<p>A simple example would be:
</p>

<pre class="code">
java_toolchain(
    name = "toolchain",
    source_version = "7",
    target_version = "7",
    bootclasspath = ["//tools/jdk:bootclasspath"],
    xlint = [ "classfile", "divzero", "empty", "options", "path" ],
    javacopts = [ "-g" ],
    javabuilder = ":JavaBuilder_deploy.jar",
)
</pre>

<!-- #END_BLAZE_RULE -->*/
