// Copyright 2014 The Bazel Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//    http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.devtools.build.lib.syntax;

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

import com.google.devtools.build.lib.syntax.util.EvaluationTestCase;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;

/**
 * A test class for functions and scoping.
 */
@RunWith(JUnit4.class)
public class FunctionTest extends EvaluationTestCase {

  @Test
  public void testFunctionDef() throws Exception {
    eval("def func(a,b,c):",
        "  a = 1",
        "  b = a\n");
    UserDefinedFunction stmt = (UserDefinedFunction) lookup("func");
    assertThat(stmt).isNotNull();
    assertThat(stmt.getName()).isEqualTo("func");
    assertThat(stmt.getSignature().getSignature().getShape().getMandatoryPositionals())
        .isEqualTo(3);
    assertThat(stmt.getStatements()).hasSize(2);
  }

  @Test
  public void testFunctionDefDuplicateArguments() throws Exception {
    setFailFast(false);
    parseFile("def func(a,b,a):",
        "  a = 1\n");
    assertContainsError("duplicate parameter name in function definition");
  }

  @Test
  public void testFunctionDefCallOuterFunc() throws Exception {
    List<Object> params = new ArrayList<>();
    createOuterFunction(params);
    eval("def func(a):",
        "  outer_func(a)",
        "func(1)",
        "func(2)");
    assertThat(params).containsExactly(1, 2).inOrder();
  }

  private void createOuterFunction(final List<Object> params) throws Exception {
    BaseFunction outerFunc = new BaseFunction("outer_func") {
      @Override
      public Object call(List<Object> args, Map<String, Object> kwargs, FuncallExpression ast,
          Environment env) throws EvalException, InterruptedException {
        params.addAll(args);
        return Runtime.NONE;
      }
    };
    update("outer_func", outerFunc);
  }

  @Test
  public void testFunctionDefNoEffectOutsideScope() throws Exception {
    update("a", 1);
    eval("def func():",
        "  a = 2",
        "func()\n");
    assertThat(lookup("a")).isEqualTo(1);
  }

  @Test
  public void testFunctionDefGlobalVaribleReadInFunction() throws Exception {
    eval("a = 1",
        "def func():",
        "  b = a",
        "  return b",
        "c = func()\n");
    assertThat(lookup("c")).isEqualTo(1);
  }

  @Test
  public void testFunctionDefLocalGlobalScope() throws Exception {
    eval("a = 1",
        "def func():",
        "  a = 2",
        "  b = a",
        "  return b",
        "c = func()\n");
    assertThat(lookup("c")).isEqualTo(2);
  }

  @Test
  public void testFunctionDefLocalVariableReferencedBeforeAssignment() throws Exception {
    checkEvalErrorContains(
        "local variable 'a' is referenced before assignment.",
        "a = 1",
        "def func():",
        "  b = a",
        "  a = 2",
        "  return b",
        "c = func()\n");
  }

  @Test
  public void testFunctionDefLocalVariableReferencedInCallBeforeAssignment() throws Exception {
    checkEvalErrorContains(
        "local variable 'a' is referenced before assignment.",
        "def dummy(x):",
        "  pass",
        "a = 1",
        "def func():",
        "  dummy(a)",
        "  a = 2",
        "func()\n");
  }

  @Test
  public void testFunctionDefLocalVariableReferencedAfterAssignment() throws Exception {
    eval("a = 1",
        "def func():",
        "  a = 2",
        "  b = a",
        "  a = 3",
        "  return b",
        "c = func()\n");
    assertThat(lookup("c")).isEqualTo(2);
  }

  @SuppressWarnings("unchecked")
  @Test
  public void testSkylarkGlobalComprehensionIsAllowed() throws Exception {
    eval("a = [i for i in [1, 2, 3]]\n");
    assertThat((Iterable<Object>) lookup("a")).containsExactly(1, 2, 3).inOrder();
  }

  @Test
  public void testFunctionReturn() throws Exception {
    eval("def func():",
        "  return 2",
        "b = func()\n");
    assertThat(lookup("b")).isEqualTo(2);
  }

  @Test
  public void testFunctionReturnFromALoop() throws Exception {
    eval("def func():",
        "  for i in [1, 2, 3, 4, 5]:",
        "    return i",
        "b = func()\n");
    assertThat(lookup("b")).isEqualTo(1);
  }

  @Test
  public void testFunctionExecutesProperly() throws Exception {
    eval("def func(a):",
        "  b = 1",
        "  if a:",
        "    b = 2",
        "  return b",
        "c = func(0)",
        "d = func(1)\n");
    assertThat(lookup("c")).isEqualTo(1);
    assertThat(lookup("d")).isEqualTo(2);
  }

  @Test
  public void testFunctionCallFromFunction() throws Exception {
    final List<Object> params = new ArrayList<>();
    createOuterFunction(params);
    eval("def func2(a):",
        "  outer_func(a)",
        "def func1(b):",
        "  func2(b)",
        "func1(1)",
        "func1(2)\n");
    assertThat(params).containsExactly(1, 2).inOrder();
  }

  @Test
  public void testFunctionCallFromFunctionReadGlobalVar() throws Exception {
    eval("a = 1",
        "def func2():",
        "  return a",
        "def func1():",
        "  return func2()",
        "b = func1()\n");
    assertThat(lookup("b")).isEqualTo(1);
  }

  @Test
  public void testFunctionParamCanShadowGlobalVarAfterGlobalVarIsRead() throws Exception {
    eval("a = 1",
        "def func2(a):",
        "  return 0",
        "def func1():",
        "  dummy = a",
        "  return func2(2)",
        "b = func1()\n");
    assertThat(lookup("b")).isEqualTo(0);
  }

  @Test
  public void testSingleLineFunction() throws Exception {
    eval("def func(): return 'a'",
        "s = func()\n");
    assertThat(lookup("s")).isEqualTo("a");
  }

  @Test
  public void testFunctionReturnsDictionary() throws Exception {
    eval("def func(): return {'a' : 1}",
        "d = func()",
        "a = d['a']\n");
    assertThat(lookup("a")).isEqualTo(1);
  }

  @Test
  public void testFunctionReturnsList() throws Exception {
    eval("def func(): return [1, 2, 3]",
        "d = func()",
        "a = d[1]\n");
    assertThat(lookup("a")).isEqualTo(2);
  }

  @Test
  public void testFunctionNameAliasing() throws Exception {
    eval("def func(a):",
        "  return a + 1",
        "alias = func",
        "r = alias(1)");
    assertThat(lookup("r")).isEqualTo(2);
  }

  @Test
  public void testCallingFunctionsWithMixedModeArgs() throws Exception {
    eval("def func(a, b, c):",
        "  return a + b + c",
        "v = func(1, c = 2, b = 3)");
    assertThat(lookup("v")).isEqualTo(6);
  }

  private String functionWithOptionalArgs() {
    return "def func(a, b = None, c = None):\n"
        + "  r = a + 'a'\n"
        + "  if b:\n"
        + "    r += 'b'\n"
        + "  if c:\n"
        + "    r += 'c'\n"
        + "  return r\n";
  }

  @Test
  public void testWhichOptionalArgsAreDefinedForFunctions() throws Exception {
    eval(functionWithOptionalArgs(),
        "v1 = func('1', 1, 1)",
        "v2 = func(b = 2, a = '2', c = 2)",
        "v3 = func('3')",
        "v4 = func('4', c = 1)\n");
    assertThat(lookup("v1")).isEqualTo("1abc");
    assertThat(lookup("v2")).isEqualTo("2abc");
    assertThat(lookup("v3")).isEqualTo("3a");
    assertThat(lookup("v4")).isEqualTo("4ac");
  }

  @Test
  public void testDefaultArguments() throws Exception {
    eval("def func(a, b = 'b', c = 'c'):",
        "  return a + b + c",
        "v1 = func('a', 'x', 'y')",
        "v2 = func(b = 'x', a = 'a', c = 'y')",
        "v3 = func('a')",
        "v4 = func('a', c = 'y')\n");
    assertThat(lookup("v1")).isEqualTo("axy");
    assertThat(lookup("v2")).isEqualTo("axy");
    assertThat(lookup("v3")).isEqualTo("abc");
    assertThat(lookup("v4")).isEqualTo("aby");
  }

  @Test
  public void testDefaultArgumentsInsufficientArgNum() throws Exception {
    checkEvalError("insufficient arguments received by func(a, b = \"b\", c = \"c\") "
        + "(got 0, expected at least 1)",
        "def func(a, b = 'b', c = 'c'):",
        "  return a + b + c",
        "func()");
  }

  @Test
  public void testArgsIsNotIterable() throws Exception {
    checkEvalError(
        "argument after * must be an iterable, not int",
        "def func1(a, b): return a + b",
        "func1('a', *42)");

    checkEvalError(
        "argument after * must be an iterable, not string",
        "def func2(a, b): return a + b",
        "func2('a', *'str')");
  }

  @Test
  public void testKeywordOnlyIsForbidden() throws Exception {
    checkEvalErrorContains("forbidden", "def foo(a, b, *, c): return a + b + c");
  }

  @Test
  public void testParamAfterStarArgs() throws Exception {
    checkEvalErrorContains("forbidden", "def foo(a, *b, c): return a");
  }

  @Test
  public void testKwargsBadKey() throws Exception {
    checkEvalError(
        "keywords must be strings, not 'int'",
        "def func(a, b): return a + b",
        "func('a', **{3: 1})");
  }

  @Test
  public void testKwargsIsNotDict() throws Exception {
    checkEvalError(
        "argument after ** must be a dictionary, not 'int'",
        "def func(a, b): return a + b",
        "func('a', **42)");
  }

  @Test
  public void testKwargsCollision() throws Exception {
    checkEvalError("argument 'b' passed both by position and by name in call to func(a, b)",
        "def func(a, b): return a + b",
        "func('a', 'b', **{'b': 'foo'})");
  }

  @Test
  public void testKwargsCollisionWithNamed() throws Exception {
    checkEvalError("duplicate keyword 'b' in call to func",
        "def func(a, b): return a + b",
        "func('a', b = 'b', **{'b': 'foo'})");
  }

  @Test
  public void testDefaultArguments2() throws Exception {
    eval("a = 2",
        "def foo(x=a): return x",
        "def bar():",
        "  a = 3",
        "  return foo()",
        "v = bar()\n");
    assertThat(lookup("v")).isEqualTo(2);
  }

  @Test
  public void testMixingPositionalOptional() throws Exception {
    eval("def f(name, value = '', optional = ''): return value",
        "v = f('name', 'value')\n");
    assertThat(lookup("v")).isEqualTo("value");
  }

  @Test
  public void testStarArg() throws Exception {
    eval(
        "def f(name, value = '1', optional = '2'): return name + value + optional",
        "v1 = f(*['name', 'value'])",
        "v2 = f('0', *['name', 'value'])",
        "v3 = f('0', optional = '3', *['b'])",
        "v4 = f(name='a', *[])\n");
    assertThat(lookup("v1")).isEqualTo("namevalue2");
    assertThat(lookup("v2")).isEqualTo("0namevalue");
    assertThat(lookup("v3")).isEqualTo("0b3");
    assertThat(lookup("v4")).isEqualTo("a12");
  }

  @Test
  public void testStarParam() throws Exception {
    eval("def f(name, value = '1', optional = '2', *rest):",
        "  r = name + value + optional + '|'",
        "  for x in rest: r += x",
        "  return r",
        "v1 = f('a', 'b', 'c', 'd', 'e')",
        "v2 = f('a', optional='b', value='c')",
        "v3 = f('a')");
    assertThat(lookup("v1")).isEqualTo("abc|de");
    assertThat(lookup("v2")).isEqualTo("acb|");
    assertThat(lookup("v3")).isEqualTo("a12|");
  }
}
