// Copyright 2016 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;

import static com.google.common.truth.Truth.assertThat;

import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Iterables;
import com.google.devtools.build.lib.actions.Artifact;
import com.google.devtools.build.lib.actions.util.ActionsTestUtil;
import com.google.devtools.build.lib.analysis.AnalysisResult;
import com.google.devtools.build.lib.analysis.ConfiguredAspect;
import com.google.devtools.build.lib.analysis.ConfiguredTarget;
import com.google.devtools.build.lib.analysis.FileProvider;
import com.google.devtools.build.lib.analysis.LicensesProvider;
import com.google.devtools.build.lib.analysis.LicensesProvider.TargetLicense;
import com.google.devtools.build.lib.analysis.RunfilesProvider;
import com.google.devtools.build.lib.analysis.config.BuildConfiguration;
import com.google.devtools.build.lib.analysis.util.BuildViewTestCase;
import com.google.devtools.build.lib.cmdline.Label;
import com.google.devtools.build.lib.collect.nestedset.NestedSet;
import com.google.devtools.build.lib.packages.License.LicenseType;
import com.google.devtools.build.lib.packages.Provider;
import com.google.devtools.build.lib.packages.StarlarkProvider;
import com.google.devtools.build.lib.packages.StructImpl;
import com.google.devtools.build.lib.rules.cpp.CcInfo;
import com.google.devtools.build.lib.skyframe.AspectKeyCreator.AspectKey;
import java.util.Set;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;

/** Unit tests for the <code>alias</code> rule. */
@RunWith(JUnit4.class)
public class AliasTest extends BuildViewTestCase {
  @Test
  public void smoke() throws Exception {
    scratch.file("a/BUILD",
        "cc_library(name='a', srcs=['a.cc'])",
        "alias(name='b', actual='a')");

    ConfiguredTarget b = getConfiguredTarget("//a:b");
    assertThat(b.get(CcInfo.PROVIDER).getCcCompilationContext()).isNotNull();
  }

  @Test
  public void aliasToInputFile() throws Exception {
    scratch.file("a/BUILD",
        "exports_files(['a'])",
        "alias(name='b', actual='a')");

    ConfiguredTarget b = getConfiguredTarget("//a:b");
    assertThat(ActionsTestUtil.baseArtifactNames(getFilesToBuild(b))).containsExactly("a");
  }

  @Test
  public void visibilityIsOverriddenAndIsOkay() throws Exception {
    scratch.file("a/BUILD",
        "filegroup(name='a', visibility=['//b:__pkg__'])");
    scratch.file("b/BUILD",
        "alias(name='b', actual='//a:a', visibility=['//visibility:public'])");
    scratch.file("c/BUILD",
        "filegroup(name='c', srcs=['//b:b'])");

    getConfiguredTarget("//c:c");
  }

  @Test
  public void visibilityIsOverriddenAndIsError() throws Exception {
    scratch.file("a/BUILD",
        "filegroup(name='a', visibility=['//visibility:public'])");
    scratch.file("b/BUILD",
        "alias(name='b', actual='//a:a', visibility=['//visibility:private'])");
    scratch.file("c/BUILD",
        "filegroup(name='c', srcs=['//b:b'])");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//c:c");
    assertContainsEvent(
        "alias '//b:b' referring to target '//a:a' is not visible from target '//c:c'");
  }

  @Test
  public void visibilityIsOverriddenAndIsErrorAfterMultipleAliases() throws Exception {
    scratch.file("a/BUILD",
        "filegroup(name='a', visibility=['//visibility:public'])");
    scratch.file("b/BUILD",
        "alias(name='b', actual='//a:a', visibility=['//visibility:public'])");
    scratch.file("c/BUILD",
        "alias(name='c', actual='//b:b', visibility=['//visibility:private'])");
    scratch.file("d/BUILD",
        "filegroup(name='d', srcs=['//c:c'])");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//d:d");
    assertContainsEvent("alias '//c:c' referring to target '//a:a' through '//b:b' "
        + "is not visible from target '//d:d'");
  }

  @Test
  public void testAliasWithPrivateVisibilityAccessibleFromSamePackage() throws Exception {
    scratch.file("a/BUILD", "exports_files(['af'])");
    scratch.file("b/BUILD",
        "package(default_visibility=['//visibility:private'])",
        "alias(name='al', actual='//a:af')",
        "filegroup(name='ta', srcs=[':al'])");

    getConfiguredTarget("//b:ta");
  }

  @Test
  public void testAliasCycle() throws Exception {
    scratch.file("a/BUILD",
        "alias(name='a', actual=':b')",
        "alias(name='b', actual=':c')",
        "alias(name='c', actual=':a')",
        "filegroup(name='d', srcs=[':c'])");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//a:d");
    assertContainsEvent("cycle in dependency graph");
  }

  @Test
  public void testAliasedInvalidDependency() throws Exception {
    scratch.file("a/BUILD",
        "cc_library(name='a', deps=[':b'])",
        "alias(name='b', actual=':c')",
        "filegroup(name='c')");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//a:a");
    assertContainsEvent("alias '//a:b' referring to filegroup rule '//a:c' is misplaced here");
  }

  @Test
  public void testAspectPropagation() throws Exception {
    writeConfigTransitionTestFiles();
    scratch.file(
        "test/aspect.bzl",
        "load('//myinfo:myinfo.bzl', 'MyInfo')",
        "def _impl(target, ctx):",
        "    if not target[MyInfo]:",
        "        fail('missing MyInfo')",
        "    if target[MyInfo].config != ctx.configuration:",
        "        fail('mismatched configs')",
        "    return MyInfo(",
        "        origin = 'aspect',",
        "        config = target[MyInfo].config)",
        "MyAspect = aspect(implementation=_impl)");
    scratch.file(
        "test/BUILD",
        "alias(name = 'simple_alias', actual = '//test/starlark:test')",
        "alias(name = 'selecting_alias',",
        "  actual = select({':arm': ':simple_alias'}))",
        "config_setting(name = 'arm', values = {'cpu': 'armeabi-v7a'})");

    // Set --cpu so we can test alias :selecting_alias that selects on this flag
    useConfiguration("--cpu=armeabi-v7a");

    // 1. Query "actual" target to establish reference values to compare to below. Make some basic
    // assertions that tie aspect's config to underlying target.
    AnalysisResult analysisResult =
        update(
            ImmutableList.of("//test/starlark:test"),
            ImmutableList.of("//test:aspect.bzl%MyAspect"),
            true,
            1,
            true,
            eventBus);
    assertThat(analysisResult.getTargetsToBuild()).hasSize(1);
    assertThat(analysisResult.getAspectsMap()).hasSize(1);

    ConfiguredTarget actualTarget = Iterables.getOnlyElement(analysisResult.getTargetsToBuild());
    ConfiguredAspect aspect = Iterables.getOnlyElement(analysisResult.getAspectsMap().values());
    AspectKey actualKey = Iterables.getOnlyElement(analysisResult.getAspectsMap().keySet());
    assertThat(actualKey.getBaseConfiguredTargetKey().getConfigurationKey())
        .isEqualTo(actualTarget.getConfigurationKey());
    assertThat(getMyInfoFromTarget(aspect).getValue("origin")).isEqualTo("aspect");
    BuildConfiguration actualConfig =
        (BuildConfiguration) getMyInfoFromTarget(aspect).getValue("config");
    assertThat(actualKey.getBaseConfiguredTargetKey().getConfigurationKey().getOptions().checksum())
        .isEqualTo(actualConfig.checksum());

    // 2. Query :simple_alias and assert that its aspect value is the same as above.
    analysisResult =
        update(
            ImmutableList.of("//test:simple_alias"),
            ImmutableList.of("//test:aspect.bzl%MyAspect"),
            true,
            1,
            true,
            eventBus);
    assertThat(analysisResult.getTargetsToBuild()).hasSize(1);
    assertThat(analysisResult.getAspectsMap()).hasSize(1);

    ConfiguredTarget alias = Iterables.getOnlyElement(analysisResult.getTargetsToBuild());
    assertThat(alias.getActual()).isEqualTo(actualTarget);
    // Alias and actual must have different configs for this test to be meaningful
    assertThat(alias.getConfigurationKey()).isNotEqualTo(alias.getActual().getConfigurationKey());
    AspectKey aspectKey = Iterables.getOnlyElement(analysisResult.getAspectsMap().keySet());
    assertThat(aspectKey.getBaseConfiguredTargetKey().getConfigurationKey())
        .isEqualTo(alias.getConfigurationKey());

    aspect = Iterables.getOnlyElement(analysisResult.getAspectsMap().values());
    assertThat(getMyInfoFromTarget(aspect).getValue("origin")).isEqualTo("aspect");
    // We should be seeing actual's config here
    assertThat(getMyInfoFromTarget(aspect).getValue("config")).isEqualTo(actualConfig);

    // 3. Do the same with :selecting_alias, which is an indirect alias through :simple_alias.
    // This alias also uses a (non-trivial) select to resolve its actual.
    analysisResult =
        update(
            ImmutableList.of("//test:selecting_alias"),
            ImmutableList.of("//test:aspect.bzl%MyAspect"),
            true,
            1,
            true,
            eventBus);
    assertThat(analysisResult.getTargetsToBuild()).hasSize(1);
    assertThat(analysisResult.getAspectsMap()).hasSize(1);

    ConfiguredTarget indirectAlias = Iterables.getOnlyElement(analysisResult.getTargetsToBuild());
    assertThat(indirectAlias.getActual()).isEqualTo(actualTarget);
    assertThat(indirectAlias.getConfigurationKey()).isEqualTo(alias.getConfigurationKey());

    aspect = Iterables.getOnlyElement(analysisResult.getAspectsMap().values());
    assertThat(getMyInfoFromTarget(aspect).getValue("origin")).isEqualTo("aspect");
    assertThat(getMyInfoFromTarget(aspect).getValue("config")).isEqualTo(actualConfig);
  }

  private void writeAllowlistFile() throws Exception {
    scratch.overwriteFile(
        "tools/allowlists/function_transition_allowlist/BUILD",
        "package_group(",
        "    name = 'function_transition_allowlist',",
        "    packages = [",
        "        '//test/...',",
        "    ],",
        ")");
  }

  private static StructImpl getMyInfoFromTarget(ConfiguredAspect configuredAspect)
      throws Exception {
    Provider.Key key =
        new StarlarkProvider.Key(
            Label.parseAbsolute("//myinfo:myinfo.bzl", ImmutableMap.of()), "MyInfo");
    return (StructImpl) configuredAspect.get(key);
  }

  public void setupMyInfo() throws Exception {
    scratch.file("myinfo/myinfo.bzl", "MyInfo = provider()");
    scratch.file("myinfo/BUILD");
  }

  private void writeConfigTransitionTestFiles() throws Exception {
    writeAllowlistFile();
    setupMyInfo();
    getAnalysisMock().ccSupport().setupCcToolchainConfigForCpu(mockToolsConfig, "armeabi-v7a");
    scratch.file(
        "test/starlark/my_rule.bzl",
        "load('//myinfo:myinfo.bzl', 'MyInfo')",
        "def transition_func(settings, attr):",
        "  return [",
        "    {'//command_line_option:cpu': 'k8'},",
        "    {'//command_line_option:cpu': 'armeabi-v7a'}",
        "  ]",
        "my_transition = transition(implementation = transition_func, inputs = [],",
        "  outputs = ['//command_line_option:cpu'])",
        "def impl(ctx): ",
        "  print(ctx.label, ctx.configuration)",
        "  return MyInfo(",
        "    config = ctx.configuration,",
        "    attr_deps = ctx.split_attr.deps,",
        "    attr_dep = ctx.split_attr.dep)",
        "my_rule = rule(",
        "  implementation = impl,",
        "  attrs = {",
        "    'deps': attr.label_list(cfg = my_transition),",
        "    'dep':  attr.label(cfg = my_transition),",
        "    '_allowlist_function_transition': attr.label(",
        "        default = '//tools/allowlists/function_transition_allowlist',",
        "    ),",
        "  })");

    scratch.file(
        "test/starlark/BUILD",
        "load('//test/starlark:my_rule.bzl', 'my_rule')",
        "my_rule(name = 'test', deps = [':main1', ':main2'], dep = ':main1')",
        "cc_binary(name = 'main1', srcs = ['main1.c'])",
        "cc_binary(name = 'main2', srcs = ['main2.c'])");
  }

  @Test
  public void licensesAreCollected() throws Exception {
    scratch.file("a/BUILD",
        "filegroup(name='a', licenses=['restricted'], output_licenses=['unencumbered'])",
        "alias(name='b', actual=':a')",
        "filegroup(name='c', srcs=[':b'])",
        "genrule(name='d', outs=['do'], tools=[':b'], cmd='cmd')",
        "genrule(name='e', outs=['eo'], srcs=[':b'], cmd='cmd')");
    useConfiguration("--check_licenses");
    assertThat(getLicenses("//a:d", "//a:a")).containsExactly(LicenseType.UNENCUMBERED);
    assertThat(getLicenses("//a:e", "//a:a")).containsExactly(LicenseType.RESTRICTED);
    assertThat(getLicenses("//a:b", "//a:a")).containsExactly(LicenseType.RESTRICTED);
    assertThat(
            getConfiguredTarget("//a:b")
                .getProvider(LicensesProvider.class)
                .getTransitiveLicenses()
                .toList())
        .hasSize(1);
  }

  @Test
  public void assertNoLicensesAttribute() throws Exception {
    scratch.file("a/BUILD",
        "filegroup(name='a')",
        "alias(name='b', actual=':a', licenses=['unencumbered'])");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//a:b");
    assertContainsEvent("no such attribute 'licenses' in 'alias' rule");
  }

  private Set<LicenseType> getLicenses(String topLevelTarget, String licenseTarget)
      throws Exception {
    LicensesProvider licenses =
        getConfiguredTarget(topLevelTarget).getProvider(LicensesProvider.class);
    for (TargetLicense license : licenses.getTransitiveLicenses().toList()) {
      if (license.getLabel().toString().equals(licenseTarget)) {
        return license.getLicense().getLicenseTypes();
      }
    }

    throw new IllegalStateException("License for '" + licenseTarget
        + "' not found in the transitive closure of '" + topLevelTarget + "'");
  }

  @Test
  public void passesTargetTypeCheck() throws Exception {
    scratch.file("a/BUILD",
        "cc_library(name='a', srcs=['a.cc'], deps=[':b'])",
        "alias(name='b', actual=':c')",
        "cc_library(name='c', srcs=['c.cc'])");

    getConfiguredTarget("//a:a");
  }

  @Test
  public void packageGroupInAlias() throws Exception {
    scratch.file("a/BUILD",
        "package_group(name='a', packages=['//a'])",
        "alias(name='b', actual=':a')",
        "filegroup(name='c', srcs=[':b'])");

    reporter.removeHandler(failFastHandler);
    getConfiguredTarget("//a:c");
    assertContainsEvent(
        "in actual attribute of alias rule //a:b: package group '//a:a' is misplaced here");
  }

  @Test
  public void aliasedFile() throws Exception {
    scratch.file("a/BUILD",
        "exports_files(['a'])",
        "alias(name='b', actual='a')",
        "filegroup(name='c', srcs=[':b'])");

    ConfiguredTarget c = getConfiguredTarget("//a:c");
    assertThat(ActionsTestUtil.baseArtifactNames(
        c.getProvider(FileProvider.class).getFilesToBuild()))
        .containsExactly("a");
  }

  @Test
  public void aliasedConfigSetting() throws Exception {
    scratch.file("a/BUILD",
        "filegroup(name='a', srcs=select({':b': ['f1'], '//conditions:default': ['f2']}))",
        "alias(name='b', actual=':c')",
        "config_setting(name='c', values={'define': 'foo=bar'})");

    useConfiguration("--define=foo=bar");
    getConfiguredTarget("//a");
  }

  @Test
  public void aliasedTestSuiteDep() throws Exception {
    scratch.file("a/BUILD",
        "sh_test(name='a', srcs=['a.sh'])");
    scratch.file("b/BUILD",
        "alias(name='b', actual='//a:a', testonly=1)",
        "test_suite(name='c', tests=[':b'])");

    ConfiguredTarget c = getConfiguredTarget("//b:c");
    NestedSet<Artifact> runfiles =
        c.getProvider(RunfilesProvider.class).getDataRunfiles().getAllArtifacts();
    assertThat(ActionsTestUtil.baseArtifactNames(runfiles)).contains("a.sh");
  }

  @Test
  public void testRedirectChasing() throws Exception {
    String toolsRepository = ruleClassProvider.getToolsRepository();
    scratch.file("a/BUILD",
        "alias(name='cc', actual='" + toolsRepository + "//tools/cpp:toolchain')",
        "cc_library(name='a', srcs=['a.cc'])");

    useConfiguration("--crosstool_top=//a:cc");
    getConfiguredTarget("//a:a");
  }

  @Test
  public void testNoActual() throws Exception {
    checkError("a", "a", "missing value for mandatory attribute 'actual'", "alias(name='a')");
  }
}
