// Copyright 2023 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.analysis;

import static com.google.common.collect.ImmutableList.toImmutableList;
import static com.google.common.truth.Truth.assertThat;
import static com.google.devtools.build.lib.rules.cpp.CppRuleClasses.CPP_LINK_EXEC_GROUP;

import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.ObjectArrays;
import com.google.devtools.build.lib.actions.Action;
import com.google.devtools.build.lib.actions.ActionAnalysisMetadata;
import com.google.devtools.build.lib.analysis.actions.LazyWritePathsFileAction;
import com.google.devtools.build.lib.analysis.config.ToolchainTypeRequirement;
import com.google.devtools.build.lib.analysis.configuredtargets.RuleConfiguredTarget;
import com.google.devtools.build.lib.analysis.platform.ToolchainInfo;
import com.google.devtools.build.lib.analysis.platform.ToolchainTypeInfo;
import com.google.devtools.build.lib.analysis.util.AnalysisMock;
import com.google.devtools.build.lib.analysis.util.BuildViewTestCase;
import com.google.devtools.build.lib.cmdline.Label;
import com.google.devtools.build.lib.packages.ExecGroup;
import com.google.devtools.build.lib.packages.util.Crosstool.CcToolchainConfig;
import com.google.devtools.build.lib.packages.util.MockCcSupport;
import com.google.devtools.build.lib.rules.cpp.CppCompileAction;
import com.google.devtools.build.lib.rules.cpp.CppRuleClasses;
import com.google.devtools.build.lib.rules.java.JavaGenJarsProvider;
import com.google.devtools.build.lib.rules.java.JavaInfo;
import com.google.devtools.build.lib.testutil.TestConstants;
import com.google.testing.junit.testparameterinjector.TestParameterInjector;
import com.google.testing.junit.testparameterinjector.TestParameters;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;

/** Test for automatic exec groups. */
@RunWith(TestParameterInjector.class)
public class AutoExecGroupsTest extends BuildViewTestCase {
  /**
   * Sets up two toolchains types, each with a single toolchain implementation and a single
   * exec_compatible_with platform.
   *
   * <p>toolchain_type_1 -> foo_toolchain -> exec_compatible_with platform_1; toolchain_type_1 ->
   * baz_toolchain -> exec_compatible_with platform_2; toolchain_type_2 -> bar_toolchain ->
   * exec_compatible_with platform_2
   */
  public void createToolchainsAndPlatforms() throws Exception {
    scratch.overwriteFile(
        "rule/test_toolchain.bzl",
        """
        def _impl(ctx):
            return [platform_common.ToolchainInfo(
                tool = ctx.executable._tool,
                files_to_run = ctx.attr._tool[DefaultInfo].files_to_run,
            )]

        test_toolchain = rule(
            implementation = _impl,
            attrs = {
                "_tool": attr.label(
                    default = "//toolchain:b_tool",
                    executable = True,
                    cfg = "exec",
                ),
            },
        )
        """);
    scratch.overwriteFile(
        "rule/BUILD",
        """
        exports_files(["test_toolchain/bzl"])

        toolchain_type(name = "toolchain_type_1")

        toolchain_type(name = "toolchain_type_2")

        java_runtime(
            name = "jvm-k8",
            srcs = [
                "k8/a",
                "k8/b",
            ],
            java_home = "k8",
        )
        """);
    scratch.overwriteFile(
        "toolchain/BUILD",
        """
        load("//rule:test_toolchain.bzl", "test_toolchain")

        genrule(
            name = "a_tool",
            outs = ["atool"],
            cmd = "",
            executable = True,
        )

        genrule(
            name = "b_tool",
            outs = ["btool"],
            cmd = "",
            executable = True,
        )

        test_toolchain(
            name = "foo",
        )

        toolchain(
            name = "foo_toolchain",
            exec_compatible_with = ["//platforms:constraint_1"],
            target_compatible_with = ["//platforms:constraint_1"],
            toolchain = ":foo",
            toolchain_type = "//rule:toolchain_type_1",
        )

        toolchain(
            name = "baz_toolchain",
            exec_compatible_with = ["//platforms:constraint_2"],
            target_compatible_with = ["//platforms:constraint_1"],
            toolchain = ":foo",
            toolchain_type = "//rule:toolchain_type_1",
        )

        test_toolchain(
            name = "bar",
        )

        toolchain(
            name = "bar_toolchain",
            exec_compatible_with = ["//platforms:constraint_2"],
            target_compatible_with = ["//platforms:constraint_1"],
            toolchain = ":bar",
            toolchain_type = "//rule:toolchain_type_2",
        )
        """);

    scratch.overwriteFile(
        "platforms/BUILD",
        """
        constraint_setting(name = "setting")

        constraint_value(
            name = "constraint_1",
            constraint_setting = ":setting",
        )

        constraint_value(
            name = "constraint_2",
            constraint_setting = ":setting",
        )

        platform(
            name = "platform_1",
            constraint_values = [":constraint_1"],
        )

        platform(
            name = "platform_2",
            constraint_values = [":constraint_2"],
            exec_properties = {
                "watermelon.ripeness": "unripe",
                "watermelon.color": "red",
            },
        )
        """);

    getAnalysisMock()
        .ccSupport()
        .setupCcToolchainConfig(
            mockToolsConfig,
            CcToolchainConfig.builder()
                .withToolchainTargetConstraints()
                .withToolchainExecConstraints()
                .withCpu("fake"));
  }

  @Before
  public void setup() throws Exception {
    useConfiguration();
  }

  @Override
  public void useConfiguration(String... args) throws Exception {
    // These need to be defined before the configuration is parsed.
    createToolchainsAndPlatforms();
    String[] flags = {
      "--extra_toolchains=//toolchain:foo_toolchain,//toolchain:bar_toolchain,//toolchain:baz_toolchain",
      "--platforms=//platforms:platform_1",
      "--extra_execution_platforms=//platforms:platform_1,//platforms:platform_2",
      "--incompatible_enable_cc_toolchain_resolution"
    };

    super.useConfiguration(ObjectArrays.concat(flags, args, String.class));
  }

  /**
   * Creates custom rule which produces action with `actionParameters`, adds `extraAttributes`,
   * defines `toolchains`, and adds custom exec groups from `execGroups`. Depending on
   * `actionRunCommand` parameter, `actions.run` or `actions.run_shell` is created.
   */
  private void createCustomRule(
      String action,
      String actionParameters,
      String extraAttributes,
      String toolchains,
      String execGroups,
      String execCompatibleWith)
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file(ctx.label.name + '_dummy_output.jar')",
        "  " + action + "(",
        actionParameters,
        "    outputs = [output_jar],",
        action.equals("ctx.actions.run")
            ? (actionParameters.contains("executable =") // avoid adding executable parameter twice
                ? ""
                : "executable = ctx.toolchains['//rule:toolchain_type_1'].tool,")
            : "    command = 'echo',",
        "  )",
        "  return [DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    '_tool': attr.label(default = '//toolchain:a_tool', cfg = 'exec', executable = True),",
        "    '_nonexecutable_tool': attr.label(default = '//toolchain:b_tool', cfg = 'exec'),",
        extraAttributes,
        "  },",
        "  exec_groups = {",
        execGroups,
        "  },",
        "  toolchains = " + toolchains + ",",
        execCompatibleWith,
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void automaticExecutionGroups_disabledAndAttributeFalse_disabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "'_use_auto_exec_groups': attr.bool(default = False),",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();

    assertThat(execGroups).isEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void automaticExecutionGroups_disabledAndAttributeTrue_enabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "'_use_auto_exec_groups': attr.bool(default = True),",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();

    assertThat(execGroups).isNotEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void automaticExecutionGroups_disabledAndAttributeNotSet_disabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups=False");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();

    assertThat(execGroups).isEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void automaticExecutionGroups_enabledAndAttributeFalse_disabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "'_use_auto_exec_groups': attr.bool(default = False),",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();

    assertThat(execGroups).isEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void automaticExecutionGroups_enabledAndAttributeTrue_enabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "'_use_auto_exec_groups': attr.bool(default = True)",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();

    assertThat(execGroups).isNotEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void automaticExecutionGroups_enabledAndAttributeNotSet_enabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();

    assertThat(execGroups).isNotEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void getToolchainInfoAndContext_automaticExecGroupsEnabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    RuleContext ruleContext = getRuleContext(target);
    ImmutableMap<ToolchainTypeInfo, ToolchainInfo> defaultExecGroupToolchains =
        ruleContext.getToolchainContext().toolchains();
    ToolchainInfo toolchainInfo =
        ruleContext.getToolchainInfo(Label.parseCanonical("//rule:toolchain_type_1"));

    assertThat(defaultExecGroupToolchains).isEmpty();
    assertThat(toolchainInfo).isNotNull();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void getToolchainInfoAndContext_automaticExecGroupsDisabled(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups=False");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    RuleContext ruleContext = getRuleContext(target);
    ImmutableMap<ToolchainTypeInfo, ToolchainInfo> defaultExecGroupToolchains =
        ruleContext.getToolchainContext().toolchains();
    ToolchainInfo toolchainInfo =
        ruleContext.getToolchainInfo(Label.parseCanonical("//rule:toolchain_type_1"));

    assertThat(defaultExecGroupToolchains).isNotEmpty();
    assertThat(toolchainInfo).isNotNull();
  }

  @Test
  public void toolInExecutableIdentified_noToolchainParameter_noError() throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "executable = ctx.executable._tool, ",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  public void toolWithFilesToRunExecutable_noToolchainParameter_reportsError() throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "executable ="
            + " ctx.attr._nonexecutable_tool[DefaultInfo].files_to_run.executable,",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "Couldn't identify if tools are from implicit dependencies or a toolchain. Please set"
            + " the toolchain parameter. If you're not using a toolchain, set it to 'None'.");
  }

  @Test
  public void toolWithFilesToRunExecutable_toolchainParameterSetToNone_noError() throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "toolchain = None,"
            + " executable = ctx.attr._nonexecutable_tool[DefaultInfo].files_to_run.executable,",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  public void toolWithFilesToRunExecutable_noToolchains_noError() throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ " executable ="
            + " ctx.attr._nonexecutable_tool[DefaultInfo].files_to_run.executable,",
        /* extraAttributes= */ "",
        /* toolchains= */ "[]",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  public void toolInExecutableUnidentified_noToolchainParameter_reportsError() throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "executable = ctx.toolchains['//rule:toolchain_type_1'].tool, ",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "Couldn't identify if tools are from implicit dependencies or a toolchain. Please set"
            + " the toolchain parameter. If you're not using a toolchain, set it to 'None'.");
  }

  @Test
  public void toolWithFilesToRunInExecutableUnidentified_noToolchainParameter_reportsError()
      throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "executable ="
            + " ctx.toolchains['//rule:toolchain_type_1'].files_to_run, ",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "Couldn't identify if tools are from implicit dependencies or a toolchain. Please set"
            + " the toolchain parameter. If you're not using a toolchain, set it to 'None'.");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void toolInToolsUnidentified_noToolchainParameter_reportsError(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "tools = [ctx.toolchains['//rule:toolchain_type_1'].tool],",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "Couldn't identify if tools are from implicit dependencies or a toolchain. Please set"
            + " the toolchain parameter. If you're not using a toolchain, set it to 'None'.");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void toolWithFilesToRunInToolsUnidentified_noToolchainParameter_reportsError(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "tools = [ctx.toolchains['//rule:toolchain_type_1'].files_to_run],",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "Couldn't identify if tools are from implicit dependencies or a toolchain. Please set"
            + " the toolchain parameter. If you're not using a toolchain, set it to 'None'.");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void depsetInTools_noToolchainParameter_reportsError(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "tools = [depset([ctx.executable._tool])], ",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "Couldn't identify if tools are from implicit dependencies or a toolchain. Please set"
            + " the toolchain parameter. If you're not using a toolchain, set it to 'None'.");
  }

  @Test
  public void toolInExecutableUnidentified_toolchainParameter_noError() throws Exception {
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "executable = ctx.toolchains['//rule:toolchain_type_1'].tool, "
            + "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  public void toolInExecutableUnidentified_toolchainParameterNone_noError() throws Exception {
    // Setting toolchain parameter that doesn't match what is used in the executable is technically
    // an error. However, we cannot detect this error at analysis time.
    // It's possible to construct a correct case where executable is from a provider from a
    // dependency that is not a toolchain (like proto_lang_toolchain). In this case the user should
    // set `toolchain = None` (because we wouldn't/couldn't detect where executable is coming from)
    createCustomRule(
        /* action= */ "ctx.actions.run",
        /* actionParameters= */ "executable = ctx.toolchains['//rule:toolchain_type_1'].tool, "
            + "toolchain = None,",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  public void execGroupSetOnAction_noToolchainParameter_noError() throws Exception {
    scratch.file(
        "test/defs.bzl",
        """
        def _impl(ctx):
            output_jar = ctx.actions.declare_file("test_" + ctx.label.name + ".jar")
            ctx.actions.run(
                outputs = [output_jar],
                executable = ctx.toolchains["//rule:toolchain_type_2"].tool,
                exec_group = "custom_exec_group",
            )
            return []

        custom_rule = rule(
            implementation = _impl,
            exec_groups = {
                "custom_exec_group": exec_group(toolchains = ["//rule:toolchain_type_2"]),
            },
            toolchains = ["//rule:toolchain_type_2"],
        )
        """);
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void twoToolchains_createTwoExecutionGroups(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ExecGroupCollection execGroups = getRuleContext(target).getExecGroups();

    assertThat(execGroups.execGroups().keySet())
        .containsExactly("//rule:toolchain_type_1", "//rule:toolchain_type_2");
    ExecGroup execGroupTT1 = execGroups.getExecGroup("//rule:toolchain_type_1");
    assertThat(execGroupTT1.toolchainTypes())
        .containsExactly(
            ToolchainTypeRequirement.create(Label.parseCanonical("//rule:toolchain_type_1")));
    assertThat(execGroupTT1.execCompatibleWith()).isEmpty();
    ExecGroup execGroupTT2 = execGroups.getExecGroup("//rule:toolchain_type_2");
    assertThat(execGroupTT2.toolchainTypes())
        .containsExactly(
            ToolchainTypeRequirement.create(Label.parseCanonical("//rule:toolchain_type_2")));
    assertThat(execGroupTT2.execCompatibleWith()).isEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void twoToolchains_threeToolchainContexts(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableSet<String> toolchainContextsKeys =
        getRuleContext(target).getToolchainContexts().getContextMap().keySet();

    assertThat(toolchainContextsKeys)
        .containsExactly(
            ExecGroup.DEFAULT_EXEC_GROUP_NAME,
            "//rule:toolchain_type_1",
            "//rule:toolchain_type_2");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void defaultExecGroupHasNoToolchains(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ResolvedToolchainContext defaultExecGroupContext =
        getRuleContext(target).getToolchainContexts().getDefaultToolchainContext();

    assertThat(defaultExecGroupContext).isNotNull();
    assertThat(defaultExecGroupContext.toolchainTypes()).isEmpty();
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void defaultExecGroupHasBasicExecutionPlatform(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ResolvedToolchainContext defaultExecGroupContext =
        getRuleContext(target).getToolchainContexts().getDefaultToolchainContext();

    assertThat(defaultExecGroupContext).isNotNull();
    assertThat(defaultExecGroupContext.executionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void toolchainParameterAsLabel_correctParsingOfToolchain(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = Label('@//rule:toolchain_type_1'),",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action generatedAction = getGeneratingAction(target, "test/custom_rule_name_dummy_output.jar");

    assertThat(generatedAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void toolchainParameterAsString_correctParsingOfToolchain(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '@//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action generatedAction = getGeneratingAction(target, "test/custom_rule_name_dummy_output.jar");

    assertThat(generatedAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void toolchainParameterAsString_syntaxErrorInParsingOfToolchain(String action)
      throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = 'rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "invalid label 'rule:toolchain_type_1': absolute label must begin with '@'" + " or '//'");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void independentExecPlatformForAction_toolchainType1(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action generatedAction = getGeneratingAction(target, "test/custom_rule_name_dummy_output.jar");

    assertThat(generatedAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void independentExecPlatformForAction_toolchainType2(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_2',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1', '//rule:toolchain_type_2']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action generatedAction = getGeneratingAction(target, "test/custom_rule_name_dummy_output.jar");

    assertThat(generatedAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  public void ctxToolchains_automaticExecGroupsEnabled() throws Exception {
    scratch.file(
        "test/defs.bzl",
        """
        def _impl(ctx):
            toolchain_info = ctx.toolchains["//rule:toolchain_type_1"]
            if toolchain_info == None:
                fail("Toolchain info is None.")
            return []

        custom_rule = rule(
            implementation = _impl,
            attrs = {
                "dep": attr.label(cfg = "exec"),
            },
            toolchains = ["//rule:toolchain_type_1"],
        )
        """);
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertNoEvents();
  }

  @Test
  public void ctxToolchains_automaticExecGroupsEnabled_wrongToolchainError() throws Exception {
    scratch.file(
        "test/defs.bzl",
        """
        def _impl(ctx):
            toolchain_info = ctx.toolchains["//rule:wrong_toolchain_type"]
            if toolchain_info == None:
                fail("Toolchain info is None.")
            return []

        custom_rule = rule(
            implementation = _impl,
            attrs = {
                "dep": attr.label(cfg = "exec"),
            },
            toolchains = ["//rule:toolchain_type_1"],
        )
        """);
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "In custom_rule rule //test:custom_rule_name, toolchain type //rule:wrong_toolchain_type"
            + " was requested but only types [//rule:toolchain_type_1] are configured");
  }

  @Test
  public void ctxToolchainsPrint_automaticExecGroupsEnabled() throws Exception {
    scratch.file(
        "test/defs.bzl",
        """
        def _impl(ctx):
            print(ctx.toolchains)
            return []

        custom_rule = rule(
            implementation = _impl,
            attrs = {
                "dep": attr.label(cfg = "exec"),
            },
            toolchains = ["//rule:toolchain_type_1"],
        )
        """);
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent("<toolchain_context.resolved_labels: //rule:toolchain_type_1>");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void toolchainNotDefinedButUsedInAction(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ (action.equals("ctx.actions.run")
                ? "executable = ctx.executable._tool, "
                : "")
            + "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "[]",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent("Action declared for non-existent toolchain '//rule:toolchain_type_1'");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void customExecGroupsAndToolchain(String action) throws Exception {
    String customExecGroups =
        "    'custom_exec_group': exec_group(\n"
            + "      exec_compatible_with = ['//platforms:constraint_1'],\n"
            + "      toolchains = ['//rule:toolchain_type_1'],\n"
            + "    ),\n";
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1', "
            + "exec_group = 'custom_exec_group',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ customExecGroups,
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();
    Action generatedAction = getGeneratingAction(target, "test/custom_rule_name_dummy_output.jar");

    assertThat(execGroups.keySet()).containsExactly("//rule:toolchain_type_1", "custom_exec_group");
    assertThat(generatedAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void customExecGroups_execCompatibleWith(String action) throws Exception {
    String customExecGroups =
        "    'custom_exec_group': exec_group(\n"
            + "      exec_compatible_with = ['//platforms:constraint_1'],\n"
            + "      toolchains = ['//rule:toolchain_type_1'],\n"
            + "    ),\n";
    String executable =
        action.equals("ctx.actions.run") ? "executable = ctx.executable._tool," : "";
    String execCompatibleWith = "  exec_compatible_with = ['//platforms:constraint_1'],";
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "exec_group = 'custom_exec_group'," + executable,
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ customExecGroups,
        /* execCompatibleWith= */ execCompatibleWith);
    scratch.overwriteFile(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            exec_properties = {"custom_exec_group.mem": "64"},
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    ImmutableMap<String, ExecGroup> execGroups =
        getRuleContext(target).getExecGroups().execGroups();
    Action ruleAction = (Action) ((RuleConfiguredTarget) target).getActions().get(0);

    assertThat(execGroups.keySet()).containsExactly("custom_exec_group", "//rule:toolchain_type_1");
    assertThat(execGroups.get("custom_exec_group").toolchainTypes())
        .containsExactly(
            ToolchainTypeRequirement.create(Label.parseCanonical("//rule:toolchain_type_1")));
    assertThat(execGroups.get("custom_exec_group").execCompatibleWith())
        .isEqualTo(ImmutableSet.of(Label.parseCanonical("//platforms:constraint_1")));
    assertThat(ruleAction.getOwner().getExecProperties()).containsExactly("mem", "64");
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void customRule_execCompatibleWith(String action) throws Exception {
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_1',",
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_1']",
        /* execGroups= */ "",
        /* execCompatibleWith= */ "");
    scratch.overwriteFile(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            exec_compatible_with = ["//platforms:constraint_2"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action ruleAction = (Action) ((RuleConfiguredTarget) target).getActions().get(0);

    assertThat(ruleAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  @TestParameters({
    "{action: ctx.actions.run}",
    "{action: ctx.actions.run_shell}",
  })
  public void customExecGroupsAndToolchain_notCompatibleError(String action) throws Exception {
    String customExecGroups =
        "    'custom_exec_group': exec_group(\n"
            + "      exec_compatible_with = ['//platforms:constraint_1'],\n"
            + "      toolchains = ['//rule:toolchain_type_1'],\n"
            + "    ),\n";
    createCustomRule(
        /* action= */ action,
        /* actionParameters= */ "toolchain = '//rule:toolchain_type_2', "
            + "exec_group = 'custom_exec_group',"
            + (action.equals("ctx.actions.run")
                ? "executable = ctx.toolchains['//rule:toolchain_type_2'].tool, "
                : ""),
        /* extraAttributes= */ "",
        /* toolchains= */ "['//rule:toolchain_type_2']",
        /* execGroups= */ customExecGroups,
        /* execCompatibleWith= */ "");
    useConfiguration("--incompatible_auto_exec_groups");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//test:custom_rule_name");

    assertContainsEvent(
        "`toolchain` and `exec_group` parameters inside actions.{run, run_shell} are not"
            + " compatible; use one of them or define `toolchain` which is compatible with the"
            + " exec_group (already exists inside the `exec_group`)");
  }

  @Test
  public void
      javaCommonCompile_automaticExecGroupsEnabled_optimizationJarActionExecutesOnFirstPlatform()
          throws Exception {
    scratch.file("java/com/google/optimizationtest/config.txt");
    scratch.file(
        "java/com/google/optimizationtest/BUILD",
        """
        java_binary(
            name = "optimizer",
            srcs = ["Foo.java"],
        )

        exports_files(["config.txt"])
        """);
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return [DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    '_use_auto_exec_groups': attr.bool(default = True),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration(
        "--experimental_local_java_optimizations",
        "--experimental_bytecode_optimizers=Optimizer=//java/com/google/optimizationtest:optimizer",
        "--experimental_local_java_optimization_configuration=//java/com/google/optimizationtest:config.txt");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action action = getGeneratingAction(target, "test/lib_custom_rule_name.jar");

    assertThat(action.getMnemonic()).isEqualTo("Optimizer");
    assertThat(action.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void
      javaCommonCompile_automaticExecGroupsDisabled_optimizationJarActionExecutesOnSecondPlatform()
          throws Exception {
    scratch.file("java/com/google/optimizationtest/config.txt");
    scratch.file(
        "java/com/google/optimizationtest/BUILD",
        """
        java_binary(
            name = "optimizer",
            srcs = ["Foo.java"],
        )

        exports_files(["config.txt"])
        """);
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return [java_info, DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration(
        "--experimental_local_java_optimizations",
        "--experimental_bytecode_optimizers=Optimizer=//java/com/google/optimizationtest:optimizer",
        "--experimental_local_java_optimization_configuration=//java/com/google/optimizationtest:config.txt",
        "--incompatible_auto_exec_groups=False");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action action = getGeneratingAction(target, "test/lib_custom_rule_name.jar");

    assertThat(action.getMnemonic()).isEqualTo("Optimizer");
    assertThat(action.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  public void javaCommonCompile_automaticExecGroupsEnabled_outputActionExecutesOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return [DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action action = getGeneratingAction(target, "test/lib_custom_rule_name.jar");

    assertThat(action.getMnemonic()).isEqualTo("Javac");
    assertThat(action.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void javaCommonCompile_automaticExecGroupsDisabled_outputActionExecutesOnSecondPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return [DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups=False");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    Action action = getGeneratingAction(target, "test/lib_custom_rule_name.jar");

    assertThat(action.getMnemonic()).isEqualTo("Javac");
    assertThat(action.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  public void javaCommonCompile_automaticExecGroupsEnabled_javaInfoActionsExecuteOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "    plugins = [ctx.attr._plugins[JavaPluginInfo]],",
        "  )",
        "  return [java_info]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    '_plugins': attr.label(",
        "      default = Label('//test:test_plugin'),",
        "    ),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        java_plugin(
            name = "test_plugin",
            processor_class = "GeneratedProcessor",
        )

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    JavaInfo javaInfo = target.get(JavaInfo.PROVIDER);
    Action genSrcOutputAction =
        getGeneratingAction(javaInfo.getOutputJars().getAllSrcOutputJars().get(0));
    JavaGenJarsProvider javaGenJarsProvider = javaInfo.getGenJarsProvider();
    Action genClassAction = getGeneratingAction(javaGenJarsProvider.getGenClassJar());
    Action genSourceAction = getGeneratingAction(javaGenJarsProvider.getGenSourceJar());

    assertThat(genSrcOutputAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
    assertThat(genClassAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
    assertThat(genSourceAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void javaCommonCompile_automaticExecGroupsDisabled_javaInfoActionsExecuteOnSecondPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "    plugins = [ctx.attr._plugins[JavaPluginInfo]],",
        "  )",
        "  return [java_info]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    '_plugins': attr.label(",
        "      default = Label('//test:test_plugin'),",
        "    ),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        java_plugin(
            name = "test_plugin",
            processor_class = "GeneratedProcessor",
        )

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups=False");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    JavaInfo javaInfo = target.get(JavaInfo.PROVIDER);
    Action genSrcOutputAction =
        getGeneratingAction(javaInfo.getOutputJars().getAllSrcOutputJars().get(0));
    JavaGenJarsProvider javaGenJarsProvider = javaInfo.getGenJarsProvider();
    Action genClassAction = getGeneratingAction(javaGenJarsProvider.getGenClassJar());
    Action genSourceAction = getGeneratingAction(javaGenJarsProvider.getGenSourceJar());

    assertThat(genSrcOutputAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
    assertThat(genClassAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
    assertThat(genSourceAction.getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  public void javaCommonCompile_automaticExecGroupsEnabled_lazyActionExecutesOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "    source_files = ctx.files.srcs,",
        "  )",
        "  return [java_info, DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files=['.java']),",
        "  },",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["Main.java"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups", "--collect_code_coverage");

    ImmutableList<Action> actions =
        getActions("//test:custom_rule_name", LazyWritePathsFileAction.class);

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void javaCommonCompile_automaticExecGroupsDisabled_lazyActionExecutesOnSecondPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "    source_files = ctx.files.srcs,",
        "  )",
        "  return [java_info, DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files=['.java']),",
        "  },",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["Main.java"],
        )
        """);
    useConfiguration("--collect_code_coverage", "--incompatible_auto_exec_groups=False");

    ImmutableList<Action> actions =
        getActions("//test:custom_rule_name", LazyWritePathsFileAction.class);

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  public void
      javaCommonCompile_automaticExecGroupsEnabled_javaResourceActionsExecuteOnFirstPlatform()
          throws Exception {
    scratch.file(
        "bazel_internal/test_rules/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "    resources = ctx.files.resources,",
        "  )",
        "  return [java_info, DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  attrs = {",
        "    'resources': attr.label_list(allow_files = True),",
        "  },",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/BUILD",
        """
        load("//bazel_internal/test_rules:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            resources = ["Resources.java"],
        )
        """);
    useConfiguration(
        "--incompatible_auto_exec_groups", "--experimental_turbine_annotation_processing");

    ImmutableList<Action> actions = getActions("//bazel_internal/test_rules:custom_rule_name");
    ImmutableList<Action> javaResourceActions =
        actions.stream()
            .filter(action -> action.getMnemonic().equals("JavaResourceJar"))
            .collect(toImmutableList());

    assertThat(javaResourceActions).hasSize(1);
    assertThat(javaResourceActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void
      javaCommonCompile_automaticExecGroupsDisabled_javaResourceActionsExecuteOnSecondPlatform()
          throws Exception {
    scratch.file(
        "bazel_internal/test_rules/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  java_info = java_common.compile(",
        "    ctx,",
        "    output = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "    resources = ctx.files.resources,",
        "  )",
        "  return [java_info, DefaultInfo(files = depset([output_jar]))]",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  attrs = {",
        "    'resources': attr.label_list(allow_files = True),",
        "  },",
        "  provides = [JavaInfo],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/BUILD",
        """
        load("//bazel_internal/test_rules:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            resources = ["Resources.java"],
        )
        """);
    useConfiguration(
        "--experimental_turbine_annotation_processing", "--incompatible_auto_exec_groups=False");

    ImmutableList<Action> actions = getActions("//bazel_internal/test_rules:custom_rule_name");
    ImmutableList<Action> javaResourceActions =
        actions.stream()
            .filter(action -> action.getMnemonic().equals("JavaResourceJar"))
            .collect(toImmutableList());

    assertThat(javaResourceActions).hasSize(1);
    assertThat(javaResourceActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_2"));
  }

  @Test
  public void javaCommonBuildIjar_automaticExecGroupsEnabled_ijarActionsExecuteOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  ctx.actions.run(",
        "    outputs = [output_jar],",
        "    executable = ctx.toolchains['//rule:toolchain_type_2'].tool,",
        "    toolchain = '//rule:toolchain_type_2',",
        "  )",
        "  compile_jar = java_common.run_ijar(",
        "    actions = ctx.actions,",
        "    jar = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> actions =
        getActions("//test:custom_rule_name").stream()
            .filter(action -> action.getMnemonic().equals("JavaIjar"))
            .collect(toImmutableList());

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void javaCommonPackSources_automaticExecGroupsEnabled_sourceActionExecutesOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  source_jar = java_common.pack_sources(",
        "    ctx.actions,",
        "    output_source_jar = output_jar,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> actions =
        getActions("//test:custom_rule_name").stream()
            .filter(action -> action.getMnemonic().equals("JavaSourceJar"))
            .collect(toImmutableList());

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void javaCommonStampJar_automaticExecGroupsEnabled_actionExecutesOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _impl(ctx):",
        "  output_jar = ctx.actions.declare_file('lib_' + ctx.label.name + '.jar')",
        "  ctx.actions.run(",
        "    outputs = [output_jar],",
        "    executable = ctx.toolchains['//rule:toolchain_type_2'].tool,",
        "    toolchain = '//rule:toolchain_type_2',",
        "  )",
        "  source_jar = java_common.stamp_jar(",
        "    ctx.actions,",
        "    jar = output_jar,",
        "    target_label = ctx.label,",
        "    java_toolchain = ctx.toolchains['" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'].java,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  toolchains = ['//rule:toolchain_type_2', '" + TestConstants.JAVA_TOOLCHAIN_TYPE + "'],",
        "  fragments = ['java']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> actions =
        getActions("//test:custom_rule_name").stream()
            .filter(action -> action.getMnemonic().equals("JavaIjar"))
            .collect(toImmutableList());
    ;

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getProgressMessage())
        .matches("Stamping target label into jar .*/lib_custom_rule_name.jar");
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonLink_cppLinkExecGroupNotDefined_cppLinkActionExecutesOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "     unsupported_features = ctx.disabled_features,",
        "  )",
        "  linking_outputs = cc_common.link(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  exec_groups = { ",
        "    '" + CPP_LINK_EXEC_GROUP + "': exec_group(toolchains = _use_cpp_toolchain()),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> actions = getActions("//test:custom_rule_name", "CppLink");

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonLink_cppLinkExecGroupDefined_cppLinkActionExecutesOnFirstPlatform()
      throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "     unsupported_features = ctx.disabled_features,",
        "  )",
        "  linking_outputs = cc_common.link(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  exec_groups = { ",
        "    '" + CPP_LINK_EXEC_GROUP + "': exec_group(toolchains = _use_cpp_toolchain()),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        custom_rule(name = "custom_rule_name")
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> actions = getActions("//test:custom_rule_name", "CppLink");

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonLink_cppLTOActionExecutesOnFirstPlatform() throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  linking_outputs = cc_common.link(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    linking_contexts = [dep[CcInfo].linking_context for dep in ctx.attr.deps if"
            + " CcInfo in dep]",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'deps': attr.label_list(),",
        "    'srcs': attr.label_list(allow_files = ['.cc']),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        cc_library(
            name = "dep",
            srcs = ["dep.cc"],
        )

        custom_rule(
            name = "custom_rule_name",
            srcs = ["custom.cc"],
            deps = ["dep"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups", "--features=thin_lto");
    AnalysisMock.get()
        .ccSupport()
        .setupCcToolchainConfig(
            mockToolsConfig,
            CcToolchainConfig.builder()
                .withFeatures(CppRuleClasses.THIN_LTO, CppRuleClasses.SUPPORTS_START_END_LIB)
                .withToolchainTargetConstraints("@@//platforms:constraint_1")
                .withToolchainExecConstraints("@@//platforms:constraint_1"));

    ImmutableList<Action> cppLtoActions = getActions("//test:custom_rule_name", "CppLTOIndexing");

    assertThat(cppLtoActions).hasSize(1);
    assertThat(cppLtoActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonLink_linkstampCompileActionExecutesOnFirstPlatform() throws Exception {
    scratch.file(
        "bazel_internal/test_rules/cc/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  linking_outputs = cc_common.link(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    linking_contexts = [dep[CcInfo].linking_context for dep in ctx.attr.deps if"
            + " CcInfo in dep]",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'deps': attr.label_list(),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/cc/BUILD",
        """
        load("//bazel_internal/test_rules/cc:defs.bzl", "custom_rule")

        cc_library(
            name = "dep",
            linkstamp = "stamp.cc",
        )

        custom_rule(
            name = "custom_rule_name",
            deps = ["dep"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> cppCompileActions =
        getActions("//bazel_internal/test_rules/cc:custom_rule_name", "CppLinkstampCompile");

    assertThat(cppCompileActions).hasSize(1);
    assertThat(cppCompileActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonCompile_cppCompileActionExecutesOnFirstPlatform() throws Exception {
    scratch.file(
        "bazel_internal/test_rules/cc/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  (compilation_context, compilation_outputs) = cc_common.compile(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    srcs = ctx.files.srcs,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files = ['.cc']),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/cc/BUILD",
        """
        load("//bazel_internal/test_rules/cc:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["custom.cc"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<Action> cppCompileActions =
        getActions("//bazel_internal/test_rules/cc:custom_rule_name", CppCompileAction.class);

    assertThat(cppCompileActions).hasSize(1);
    assertThat(cppCompileActions.get(0).getProgressMessage())
        .isEqualTo("Compiling bazel_internal/test_rules/cc/custom.cc");
    assertThat(cppCompileActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonCompile_moduleActionsExecuteOnFirstPlatform() throws Exception {
    scratch.file(
        "bazel_internal/test_rules/cc/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  (compilation_context, compilation_outputs) = cc_common.compile(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    srcs = ctx.files.srcs,",
        "    public_hdrs = ctx.files.hdrs,",
        "    separate_module_headers = ctx.files.hdrs,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files = ['.cc']),",
        "    'hdrs': attr.label_list(allow_files = ['.h']),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/cc/BUILD",
        """
        load("//bazel_internal/test_rules/cc:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["custom.cc"],
            hdrs = ["custom.h"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups", "--features=header_modules");
    AnalysisMock.get()
        .ccSupport()
        .setupCcToolchainConfig(
            mockToolsConfig,
            CcToolchainConfig.builder()
                .withFeatures(MockCcSupport.HEADER_MODULES_FEATURES)
                .withToolchainTargetConstraints("@@//platforms:constraint_1")
                .withToolchainExecConstraints("@@//platforms:constraint_1"));

    ImmutableList<Action> cppCompileActions =
        getActions("//bazel_internal/test_rules/cc:custom_rule_name", CppCompileAction.class);
    ImmutableList<Action> moduleActions =
        cppCompileActions.stream()
            .filter(action -> action.getProgressMessage().contains("custom_rule_name.cppmap"))
            .collect(toImmutableList());

    assertThat(moduleActions).hasSize(2);
    assertThat(moduleActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
    assertThat(moduleActions.get(1).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonCompile_codeGenModuleActionExecutesOnFirstPlatform() throws Exception {
    scratch.file(
        "bazel_internal/test_rules/cc/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  (compilation_context, compilation_outputs) = cc_common.compile(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    srcs = ctx.files.srcs,",
        "    public_hdrs = ctx.files.hdrs,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files = ['.cc']),",
        "    'hdrs': attr.label_list(allow_files = ['.h']),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/cc/BUILD",
        """
        load("//bazel_internal/test_rules/cc:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["custom.cc"],
            hdrs = ["custom.h"],
        )
        """);
    useConfiguration(
        "--incompatible_auto_exec_groups",
        "--features=header_modules",
        "--features=header_module_codegen");
    AnalysisMock.get()
        .ccSupport()
        .setupCcToolchainConfig(
            mockToolsConfig,
            CcToolchainConfig.builder()
                .withFeatures(MockCcSupport.HEADER_MODULES_FEATURES)
                .withToolchainTargetConstraints("@@//platforms:constraint_1")
                .withToolchainExecConstraints("@@//platforms:constraint_1"));

    ImmutableList<Action> cppCompileActions =
        getActions("//bazel_internal/test_rules/cc:custom_rule_name", CppCompileAction.class);
    ImmutableList<Action> codeGenCompileActions =
        cppCompileActions.stream()
            .filter(action -> action.getProgressMessage().contains("custom_rule_name.pcm"))
            .collect(toImmutableList());

    assertThat(codeGenCompileActions).hasSize(1);
    assertThat(codeGenCompileActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonCompile_compileHeaderActionExecutesOnFirstPlatform() throws Exception {
    scratch.file(
        "bazel_internal/test_rules/cc/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  (compilation_context, compilation_outputs) = cc_common.compile(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    srcs = ctx.files.srcs,",
        "    private_hdrs = ctx.files.hdrs,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files = ['.cc']),",
        "    'hdrs': attr.label_list(allow_files = ['.h']),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "bazel_internal/test_rules/cc/BUILD",
        """
        load("//bazel_internal/test_rules/cc:defs.bzl", "custom_rule")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["custom.cc"],
            hdrs = ["custom.h"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups", "--features=parse_headers");
    AnalysisMock.get()
        .ccSupport()
        .setupCcToolchainConfig(
            mockToolsConfig,
            CcToolchainConfig.builder()
                .withFeatures(CppRuleClasses.PARSE_HEADERS)
                .withToolchainTargetConstraints("@@//platforms:constraint_1")
                .withToolchainExecConstraints("@@//platforms:constraint_1"));

    ImmutableList<Action> cppCompileActions =
        getActions("//bazel_internal/test_rules/cc:custom_rule_name", CppCompileAction.class);
    ImmutableList<Action> compileHeaderActions =
        cppCompileActions.stream()
            .filter(
                action ->
                    action
                        .getProgressMessage()
                        .equals("Compiling bazel_internal/test_rules/cc/custom.h"))
            .collect(toImmutableList());

    assertThat(compileHeaderActions).hasSize(1);
    assertThat(compileHeaderActions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void ccCommonCompile_treeArtifactActionExecutesOnFirstPlatform() throws Exception {
    scratch.file(
        "test/defs.bzl",
        "def _use_cpp_toolchain():",
        "   return [",
        "      config_common.toolchain_type('"
            + TestConstants.CPP_TOOLCHAIN_TYPE
            + "', mandatory = False),",
        "   ]",
        "def _ta_impl(ctx):",
        "    tree = ctx.actions.declare_directory('dir')",
        "    ctx.actions.run_shell(",
        "        outputs = [tree],",
        "        inputs = [],",
        "        arguments = [tree.path],",
        "        command = 'mkdir $1',",
        "    )",
        "    return [DefaultInfo(files = depset([tree]))]",
        "create_tree_artifact = rule(implementation = _ta_impl)",
        "def _impl(ctx):",
        "  cc_toolchain = ctx.toolchains['" + TestConstants.CPP_TOOLCHAIN_TYPE + "'].cc",
        "  feature_configuration = cc_common.configure_features(",
        "      ctx = ctx,",
        "      cc_toolchain = cc_toolchain,",
        "      requested_features = ctx.features,",
        "      unsupported_features = ctx.disabled_features,",
        "  )",
        "  (compilation_context, compilation_outputs) = cc_common.compile(",
        "    name = ctx.label.name,",
        "    actions = ctx.actions,",
        "    feature_configuration = feature_configuration,",
        "    cc_toolchain = cc_toolchain,",
        "    srcs = ctx.files.srcs,",
        "  )",
        "  return []",
        "custom_rule = rule(",
        "  implementation = _impl,",
        "  attrs = {",
        "    'srcs': attr.label_list(allow_files = ['.cc']),",
        "  },",
        "  toolchains = ['//rule:toolchain_type_2'] + _use_cpp_toolchain(),",
        "  fragments = ['cpp']",
        ")");
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "create_tree_artifact", "custom_rule")

        package(default_visibility = ["//visibility:public"])

        create_tree_artifact(name = "tree_artifact")

        custom_rule(
            name = "custom_rule_name",
            srcs = ["tree_artifact"],
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ImmutableList<ActionAnalysisMetadata> actions =
        ((RuleConfiguredTarget) getConfiguredTarget("//test:custom_rule_name")).getActions();

    assertThat(actions).hasSize(1);
    assertThat(actions.get(0).getOwner().getExecutionPlatform().label())
        .isEqualTo(Label.parseCanonical("//platforms:platform_1"));
  }

  @Test
  public void testToolchainAsAlias() throws Exception {
    scratch.file(
        "test/alias/BUILD",
        """
        alias(
            name = "alias_toolchain_type_1",
            actual = "//rule:toolchain_type_1",
        )
        alias(
            name = "alias_toolchain_type_2",
            actual = "//rule:toolchain_type_2",
        )
        """);
    scratch.file(
        "test/defs.bzl",
        """
        def _impl(ctx):
            return []

        custom_rule = rule(
            implementation = _impl,
            toolchains = ["//test/alias:alias_toolchain_type_1",
             "//test/alias:alias_toolchain_type_2"],
            exec_groups = {
                "custom_exec_group": exec_group(
                    toolchains = ["//rule:toolchain_type_1"],
                ),
            },
        )
        """);
    scratch.file(
        "test/BUILD",
        """
        load("//test:defs.bzl", "custom_rule")

        package(default_visibility = ["//visibility:public"])

        custom_rule(
            name = "custom_rule_name",
        )
        """);
    useConfiguration("--incompatible_auto_exec_groups");

    ConfiguredTarget target = getConfiguredTarget("//test:custom_rule_name");
    RuleContext ruleContext = getRuleContext(target);
    ToolchainInfo realToolchainInfo1 =
        ruleContext.getToolchainInfo(Label.parseCanonical("//rule:toolchain_type_1"));
    ToolchainInfo aliasToolchainInfo1 =
        ruleContext.getToolchainInfo(Label.parseCanonical("//test/alias:alias_toolchain_type_1"));

    assertThat(realToolchainInfo1).isEqualTo(aliasToolchainInfo1);

    ToolchainInfo realToolchainInfo2 =
        ruleContext.getToolchainInfo(Label.parseCanonical("//rule:toolchain_type_2"));
    ToolchainInfo aliasToolchainInfo2 =
        ruleContext.getToolchainInfo(Label.parseCanonical("//test/alias:alias_toolchain_type_2"));

    assertThat(realToolchainInfo2).isEqualTo(aliasToolchainInfo2);
  }
}
