// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

import 'package:front_end/src/fasta/type_inference/type_constraint_gatherer.dart';
import 'package:front_end/src/fasta/type_inference/type_schema.dart';
import 'package:front_end/src/fasta/type_inference/type_schema_environment.dart';
import 'package:kernel/ast.dart';
import 'package:kernel/core_types.dart';
import 'package:kernel/class_hierarchy.dart';
import 'package:kernel/testing/mock_sdk_component.dart';
import 'package:test/test.dart';
import 'package:test_reflective_loader/test_reflective_loader.dart';

main() {
  defineReflectiveSuite(() {
    defineReflectiveTests(TypeConstraintGathererTest);
  });
}

@reflectiveTest
class TypeConstraintGathererTest {
  static const UnknownType unknownType = const UnknownType();

  static const DynamicType dynamicType = const DynamicType();

  static const VoidType voidType = const VoidType();

  final testLib =
      new Library(Uri.parse('org-dartlang:///test.dart'), name: 'lib');

  Component component;

  CoreTypes coreTypes;

  TypeParameterType T1;

  TypeParameterType T2;

  Class classP;

  Class classQ;

  TypeConstraintGathererTest() {
    component = createMockSdkComponent();
    component.libraries.add(testLib..parent = component);
    coreTypes = new CoreTypes(component);
    T1 = new TypeParameterType(
        new TypeParameter('T1', objectType), Nullability.legacy);
    T2 = new TypeParameterType(
        new TypeParameter('T2', objectType), Nullability.legacy);
    classP = _addClass(_class('P'));
    classQ = _addClass(_class('Q'));
  }

  Class get functionClass => coreTypes.functionClass;

  InterfaceType get functionType => coreTypes.functionLegacyRawType;

  Class get iterableClass => coreTypes.iterableClass;

  Class get listClass => coreTypes.listClass;

  Class get mapClass => coreTypes.mapClass;

  Class get objectClass => coreTypes.objectClass;

  InterfaceType get objectType => coreTypes.objectLegacyRawType;

  InterfaceType get P => coreTypes.legacyRawType(classP);

  InterfaceType get Q => coreTypes.legacyRawType(classQ);

  void test_any_subtype_parameter() {
    _checkConstraintsLower(T1, Q, testLib, ['lib::Q* <: T1']);
  }

  void test_any_subtype_top() {
    _checkConstraintsUpper(P, dynamicType, testLib, []);
    _checkConstraintsUpper(P, objectType, testLib, []);
    _checkConstraintsUpper(P, voidType, testLib, []);
  }

  void test_any_subtype_unknown() {
    _checkConstraintsUpper(P, unknownType, testLib, []);
    _checkConstraintsUpper(T1, unknownType, testLib, []);
  }

  void test_different_classes() {
    _checkConstraintsUpper(_list(T1), _iterable(Q), testLib, ['T1 <: lib::Q*']);
    _checkConstraintsUpper(_iterable(T1), _list(Q), testLib, null);
  }

  void test_equal_types() {
    _checkConstraintsUpper(P, P, testLib, []);
  }

  void test_function_generic() {
    var T = new TypeParameterType(
        new TypeParameter('T', objectType), Nullability.legacy);
    var U = new TypeParameterType(
        new TypeParameter('U', objectType), Nullability.legacy);
    // <T>() -> dynamic <: () -> dynamic, never
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy,
            typeParameters: [T.parameter]),
        new FunctionType([], dynamicType, Nullability.legacy),
        testLib,
        null);
    // () -> dynamic <: <T>() -> dynamic, never
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy),
        new FunctionType([], dynamicType, Nullability.legacy,
            typeParameters: [T.parameter]),
        testLib,
        null);
    // <T>(T) -> T <: <U>(U) -> U, always
    _checkConstraintsUpper(
        new FunctionType([T], T, Nullability.legacy,
            typeParameters: [T.parameter]),
        new FunctionType([U], U, Nullability.legacy,
            typeParameters: [U.parameter]),
        testLib,
        []);
  }

  void test_function_parameter_mismatch() {
    // (P) -> dynamic <: () -> dynamic, never
    _checkConstraintsUpper(
        new FunctionType([P], dynamicType, Nullability.legacy),
        new FunctionType([], dynamicType, Nullability.legacy),
        testLib,
        null);
    // () -> dynamic <: (P) -> dynamic, never
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy),
        new FunctionType([P], dynamicType, Nullability.legacy),
        testLib,
        null);
    // ([P]) -> dynamic <: () -> dynamic, always
    _checkConstraintsUpper(
        new FunctionType([P], dynamicType, Nullability.legacy,
            requiredParameterCount: 0),
        new FunctionType([], dynamicType, Nullability.legacy),
        testLib,
        []);
    // () -> dynamic <: ([P]) -> dynamic, never
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy),
        new FunctionType([P], dynamicType, Nullability.legacy,
            requiredParameterCount: 0),
        testLib,
        null);
    // ({x: P}) -> dynamic <: () -> dynamic, always
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy,
            namedParameters: [new NamedType('x', P)]),
        new FunctionType([], dynamicType, Nullability.legacy),
        testLib,
        []);
    // () -> dynamic !<: ({x: P}) -> dynamic, never
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy),
        new FunctionType([], dynamicType, Nullability.legacy,
            namedParameters: [new NamedType('x', P)]),
        testLib,
        null);
  }

  void test_function_parameter_types() {
    // (T1) -> dynamic <: (Q) -> dynamic, under constraint Q <: T1
    _checkConstraintsUpper(
        new FunctionType([T1], dynamicType, Nullability.legacy),
        new FunctionType([Q], dynamicType, Nullability.legacy),
        testLib,
        ['lib::Q* <: T1']);
    // ({x: T1}) -> dynamic <: ({x: Q}) -> dynamic, under constraint Q <: T1
    _checkConstraintsUpper(
        new FunctionType([], dynamicType, Nullability.legacy,
            namedParameters: [new NamedType('x', T1)]),
        new FunctionType([], dynamicType, Nullability.legacy,
            namedParameters: [new NamedType('x', Q)]),
        testLib,
        ['lib::Q* <: T1']);
  }

  void test_function_return_type() {
    // () -> T1 <: () -> Q, under constraint T1 <: Q
    _checkConstraintsUpper(
        new FunctionType([], T1, Nullability.legacy),
        new FunctionType([], Q, Nullability.legacy),
        testLib,
        ['T1 <: lib::Q*']);
    // () -> P <: () -> void, always
    _checkConstraintsUpper(new FunctionType([], P, Nullability.legacy),
        new FunctionType([], voidType, Nullability.legacy), testLib, []);
    // () -> void <: () -> P, never
    _checkConstraintsUpper(new FunctionType([], voidType, Nullability.legacy),
        new FunctionType([], P, Nullability.legacy), testLib, null);
  }

  void test_function_trivial_cases() {
    var F = new FunctionType([], dynamicType, Nullability.legacy);
    // () -> dynamic <: dynamic, always
    _checkConstraintsUpper(F, dynamicType, testLib, []);
    // () -> dynamic <: Function, always
    _checkConstraintsUpper(F, functionType, testLib, []);
    // () -> dynamic <: Object, always
    _checkConstraintsUpper(F, objectType, testLib, []);
  }

  void test_nonInferredParameter_subtype_any() {
    var U = new TypeParameterType(
        new TypeParameter('U', _list(P)), Nullability.legacy);
    _checkConstraintsLower(_list(T1), U, testLib, ['lib::P* <: T1']);
  }

  void test_null_subtype_any() {
    _checkConstraintsLower(T1, new NullType(), testLib, ['Null <: T1']);
    _checkConstraintsUpper(new NullType(), Q, testLib, []);
  }

  void test_parameter_subtype_any() {
    _checkConstraintsUpper(T1, Q, testLib, ['T1 <: lib::Q*']);
  }

  void test_same_classes() {
    _checkConstraintsUpper(_list(T1), _list(Q), testLib, ['T1 <: lib::Q*']);
  }

  void test_typeParameters() {
    _checkConstraintsUpper(
        _map(T1, T2), _map(P, Q), testLib, ['T1 <: lib::P*', 'T2 <: lib::Q*']);
  }

  void test_unknown_subtype_any() {
    _checkConstraintsUpper(Q, unknownType, testLib, []);
    _checkConstraintsUpper(T1, unknownType, testLib, []);
  }

  Class _addClass(Class c) {
    testLib.addClass(c);
    return c;
  }

  void _checkConstraintsLower(DartType type, DartType bound,
      Library clientLibrary, List<String> expectedConstraints) {
    _checkConstraintsHelper(type, bound, clientLibrary, expectedConstraints,
        (gatherer, type, bound) => gatherer.tryConstrainLower(type, bound));
  }

  void _checkConstraintsUpper(DartType type, DartType bound,
      Library clientLibrary, List<String> expectedConstraints) {
    _checkConstraintsHelper(type, bound, clientLibrary, expectedConstraints,
        (gatherer, type, bound) => gatherer.tryConstrainUpper(type, bound));
  }

  void _checkConstraintsHelper(
      DartType a,
      DartType b,
      Library clientLibrary,
      List<String> expectedConstraints,
      bool Function(TypeConstraintGatherer, DartType, DartType) tryConstrain) {
    var typeSchemaEnvironment = new TypeSchemaEnvironment(
        coreTypes, new ClassHierarchy(component, coreTypes));
    var typeConstraintGatherer = new TypeConstraintGatherer(
        typeSchemaEnvironment, [T1.parameter, T2.parameter], testLib);
    var constraints = tryConstrain(typeConstraintGatherer, a, b)
        ? typeConstraintGatherer.computeConstraints(clientLibrary)
        : null;
    if (expectedConstraints == null) {
      expect(constraints, isNull);
      return;
    }
    expect(constraints, isNotNull);
    var constraintStrings = <String>[];
    constraints.forEach((t, constraint) {
      if (constraint.lower is! UnknownType ||
          constraint.upper is! UnknownType) {
        var s = t.name;
        if (constraint.lower is! UnknownType) {
          s = '${typeSchemaToString(constraint.lower)} <: $s';
        }
        if (constraint.upper is! UnknownType) {
          s = '$s <: ${typeSchemaToString(constraint.upper)}';
        }
        constraintStrings.add(s);
      }
    });
    expect(constraintStrings, unorderedEquals(expectedConstraints));
  }

  Class _class(String name,
      {Supertype supertype,
      List<TypeParameter> typeParameters,
      List<Supertype> implementedTypes}) {
    return new Class(
        name: name,
        supertype: supertype ?? objectClass.asThisSupertype,
        typeParameters: typeParameters,
        implementedTypes: implementedTypes);
  }

  DartType _iterable(DartType element) =>
      new InterfaceType(iterableClass, Nullability.legacy, [element]);

  DartType _list(DartType element) =>
      new InterfaceType(listClass, Nullability.legacy, [element]);

  DartType _map(DartType key, DartType value) =>
      new InterfaceType(mapClass, Nullability.legacy, [key, value]);
}
