// Copyright 2019 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.python;

import static com.google.common.truth.Truth.assertThat;
import static com.google.devtools.build.lib.syntax.Runtime.NONE;

import com.google.devtools.build.lib.analysis.platform.ToolchainInfo;
import com.google.devtools.build.lib.analysis.util.BuildViewTestCase;
import com.google.devtools.build.lib.testutil.TestConstants;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;

/**
 * Tests for the standard Python toolchain definitions.
 *
 * <p>This covers invariants of the toolchain definitions, and the interaction with a user-defined
 * consuming rule, but not the behavior of {@code py_binary} and {@code py_test}. Those tests are
 * under {@link PyExecutableConfiguredTargetTestBase} instead.
 */
@RunWith(JUnit4.class)
public class PythonToolchainTest extends BuildViewTestCase {

  private static final String TOOLCHAIN_BZL =
      TestConstants.TOOLS_REPOSITORY + "//tools/python:toolchain.bzl";

  private static final String TOOLCHAIN_TYPE =
      TestConstants.TOOLS_REPOSITORY + "//tools/python:toolchain_type";

  private static final String PY2_PATH_CONSTRAINT =
      TestConstants.TOOLS_REPOSITORY + "//tools/python:py2_interpreter_path";

  private static final String PY3_PATH_CONSTRAINT =
      TestConstants.TOOLS_REPOSITORY + "//tools/python:py3_interpreter_path";

  @Test
  public void userDefinedConsumerUsingToolchainResolution() throws Exception {
    // A simple platform with unique constraint values.
    scratch.file(
        "platforms/BUILD",
        "constraint_value(",
        "    name = 'my_py2_path',",
        "    constraint_setting = '" + PY2_PATH_CONSTRAINT + "',",
        ")",
        "constraint_value(",
        "    name = 'my_py3_path',",
        "    constraint_setting = '" + PY3_PATH_CONSTRAINT + "',",
        ")",
        "platform(",
        "    name = 'my_platform',",
        "    constraint_values = [':my_py2_path', ':my_py3_path'],",
        ")");
    // A user rule that requires the Python toolchain type and spits out the resulting info.
    scratch.file(
        "pkg/rules.bzl",
        "def _myrule_impl(ctx):",
        "    info = ctx.toolchains['" + TOOLCHAIN_TYPE + "']",
        "    print('PY2 path: ' + info.py2_runtime.interpreter_path)",
        "    print('PY3 path: ' + info.py3_runtime.interpreter_path)",
        "myrule = rule(",
        "    implementation = _myrule_impl,",
        "    toolchains = ['" + TOOLCHAIN_TYPE + "'],",
        ")");
    // A toolchain implementation and an instance of the rule that will use it.
    scratch.file(
        "pkg/BUILD",
        "load('" + TOOLCHAIN_BZL + "', 'py_runtime_pair')",
        "load(':rules.bzl', 'myrule')",
        "py_runtime(",
        "    name = 'my_py2_runtime',",
        "    interpreter_path = '/system/python2',",
        "    python_version = 'PY2',",
        ")",
        "py_runtime(",
        "    name = 'my_py3_runtime',",
        "    interpreter_path = '/system/python3',",
        "    python_version = 'PY3',",
        ")",
        "py_runtime_pair(",
        "    name = 'my_py_runtime_pair',",
        "    py2_runtime = ':my_py2_runtime',",
        "    py3_runtime = ':my_py3_runtime',",
        ")",
        "toolchain(",
        "    name = 'my_toolchain',",
        "    target_compatible_with = ['//platforms:my_py2_path', '//platforms:my_py3_path'],",
        "    toolchain = ':my_py_runtime_pair',",
        "    toolchain_type = '" + TOOLCHAIN_TYPE + "',",
        ")",
        "myrule(",
        "    name = 'mytarget',",
        ")");
    // Register the toolchain and ask for the platform.
    useConfiguration(
        "--platforms=//platforms:my_platform", "--extra_toolchains=//pkg:my_toolchain");

    getConfiguredTarget("//pkg:mytarget");
    assertContainsEvent("PY2 path: /system/python2");
    assertContainsEvent("PY3 path: /system/python3");
  }

  @Test
  public void okToOmitRuntimes() throws Exception {
    scratch.file(
        "pkg/BUILD",
        "load('" + TOOLCHAIN_BZL + "', 'py_runtime_pair')",
        "py_runtime_pair(",
        "    name = 'my_py_runtime_pair',",
        ")");
    ToolchainInfo info =
        getConfiguredTarget("//pkg:my_py_runtime_pair").get(ToolchainInfo.PROVIDER);
    assertThat(info.getValue("py2_runtime")).isEqualTo(NONE);
    assertThat(info.getValue("py3_runtime")).isEqualTo(NONE);
  }

  @Test
  public void wrongVersionInToolchainAttribute() throws Exception {
    reporter.removeHandler(failFastHandler);
    scratch.file(
        "pkg/BUILD",
        "load('" + TOOLCHAIN_BZL + "', 'py_runtime_pair')",
        "py_runtime(",
        "    name = 'bad_py2_runtime',",
        "    interpreter_path = '/system/python2',",
        "    python_version = 'PY3',",
        ")",
        "py_runtime(",
        "    name = 'bad_py3_runtime',",
        "    interpreter_path = '/system/python3',",
        "    python_version = 'PY2',",
        ")",
        "py_runtime_pair(",
        "    name = 'with_bad_py2_runtime',",
        "    py2_runtime = ':bad_py2_runtime',",
        ")",
        "py_runtime_pair(",
        "    name = 'with_bad_py3_runtime',",
        "    py3_runtime = ':bad_py3_runtime',",
        ")");
    getConfiguredTarget("//pkg:with_bad_py2_runtime");
    getConfiguredTarget("//pkg:with_bad_py3_runtime");
    assertContainsEvent(
        "The Python runtime in the 'py2_runtime' attribute did not have version 'PY2'");
    assertContainsEvent(
        "The Python runtime in the 'py3_runtime' attribute did not have version 'PY3'");
  }

  @Test
  public void missingProviderInToolchainAttribute() throws Exception {
    reporter.removeHandler(failFastHandler);
    scratch.file(
        "pkg/BUILD",
        "load('" + TOOLCHAIN_BZL + "', 'py_runtime_pair')",
        "sh_binary(",
        "    name = 'not_a_runtime',",
        "    srcs = ['not_a_runtime.sh'],",
        ")",
        "py_runtime_pair(",
        "    name = 'bad_py_runtime_pair',",
        "    py2_runtime = ':not_a_runtime',",
        ")");
    getConfiguredTarget("//pkg:bad_py_runtime_pair");
    assertContainsEvent("'//pkg:not_a_runtime' does not have mandatory providers: 'PyRuntimeInfo'");
  }
}
