// Copyright (c) 2015, 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.

library constant_expression_test;

import 'dart:async';
import 'package:async_helper/async_helper.dart';
import 'package:expect/expect.dart';
import 'package:compiler/src/common_elements.dart' show KElementEnvironment;
import 'package:compiler/src/compiler.dart';
import 'package:compiler/src/constants/expressions.dart';
import 'package:compiler/src/kernel/element_map_impl.dart';
import 'package:compiler/src/elements/entities.dart';
import '../helpers/memory_compiler.dart';
import 'constant_expression_evaluate_test.dart' show MemoryEnvironment;

class TestData {
  /// Declarations needed for the [constants].
  final String declarations;

  /// Tested constants.
  final List<ConstantData> constants;

  const TestData(this.declarations, this.constants);
}

class ConstantData {
  /// Source code for the constant expression.
  final String code;

  /// The expected constant expression kind.
  final ConstantExpressionKind kind;

  /// ConstantExpression.getText() result if different from [code].
  final String text;

  /// The expected instance type for ConstructedConstantExpression.
  final String type;

  /// The expected instance fields for ConstructedConstantExpression.
  final Map<String, String> fields;

  const ConstantData(String code, this.kind,
      {String text, this.type, this.fields})
      : this.code = code,
        this.text = text ?? code;
}

const List<TestData> DATA = const [
  const TestData('''
class Class<T, S> {
  final a;
  final b;
  final c;
  const Class(this.a, {this.b, this.c: true});
  const Class.named([this.a, this.b = 0, this.c = 2]);

  static const staticConstant = 0;
  static staticFunction() {}
}
const t = true;
const f = false;
const toplevelConstant = 0;
toplevelFunction() {}
''', const [
    const ConstantData('null', ConstantExpressionKind.NULL),
    const ConstantData('false', ConstantExpressionKind.BOOL),
    const ConstantData('true', ConstantExpressionKind.BOOL),
    const ConstantData('0', ConstantExpressionKind.INT),
    const ConstantData('0.0', ConstantExpressionKind.DOUBLE),
    const ConstantData('"foo"', ConstantExpressionKind.STRING),
    const ConstantData('1 + 2', ConstantExpressionKind.BINARY),
    const ConstantData('1 == 2', ConstantExpressionKind.BINARY),
    const ConstantData('1 != 2', ConstantExpressionKind.UNARY,
        // a != b is encoded as !(a == b) by CFE.
        text: '!(1 == 2)'),
    const ConstantData('1 ?? 2', ConstantExpressionKind.BINARY),
    const ConstantData('-(1)', ConstantExpressionKind.UNARY, text: '-1'),
    const ConstantData('"foo".length', ConstantExpressionKind.STRING_LENGTH),
    const ConstantData('identical(0, 1)', ConstantExpressionKind.IDENTICAL),
    const ConstantData('"a" "b"', ConstantExpressionKind.CONCATENATE,
        text: '"ab"'),
    const ConstantData('identical', ConstantExpressionKind.FUNCTION),
    const ConstantData('true ? 0 : 1', ConstantExpressionKind.CONDITIONAL),
    const ConstantData('proxy', ConstantExpressionKind.FIELD),
    const ConstantData('Object', ConstantExpressionKind.TYPE),
    const ConstantData('#name', ConstantExpressionKind.SYMBOL),
    const ConstantData('const []', ConstantExpressionKind.LIST),
    const ConstantData('const [0, 1]', ConstantExpressionKind.LIST,
        text: 'const <int>[0, 1]'),
    const ConstantData('const <int>[0, 1]', ConstantExpressionKind.LIST),
    const ConstantData('const <dynamic>[0, 1]', ConstantExpressionKind.LIST,
        text: 'const [0, 1]'),
    const ConstantData('const {}', ConstantExpressionKind.MAP),
    const ConstantData('const {0: 1, 2: 3}', ConstantExpressionKind.MAP,
        text: 'const <int, int>{0: 1, 2: 3}'),
    const ConstantData(
        'const <int, int>{0: 1, 2: 3}', ConstantExpressionKind.MAP),
    const ConstantData(
        'const <String, int>{"0": 1, "2": 3}', ConstantExpressionKind.MAP),
    const ConstantData(
        'const <String, dynamic>{"0": 1, "2": 3}', ConstantExpressionKind.MAP),
    const ConstantData(
        'const <dynamic, dynamic>{"0": 1, "2": 3}', ConstantExpressionKind.MAP,
        text: 'const {"0": 1, "2": 3}'),
    const ConstantData('const bool.fromEnvironment("foo", defaultValue: false)',
        ConstantExpressionKind.BOOL_FROM_ENVIRONMENT),
    const ConstantData('const int.fromEnvironment("foo", defaultValue: 42)',
        ConstantExpressionKind.INT_FROM_ENVIRONMENT),
    const ConstantData(
        'const String.fromEnvironment("foo", defaultValue: "bar")',
        ConstantExpressionKind.STRING_FROM_ENVIRONMENT),
    const ConstantData('const Class(0)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class(0, b: 1)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class(0, c: 2)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class(0, b: 3, c: 4)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class.named()', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class.named(0)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class.named(0, 1)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class.named(0, 1, 2)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class<String, int>(0)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class<String, dynamic>(0)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class<dynamic, String>(0)', ConstantExpressionKind.CONSTRUCTED),
    const ConstantData(
        'const Class<dynamic, dynamic>(0)', ConstantExpressionKind.CONSTRUCTED,
        text: 'const Class(0)'),
    const ConstantData('toplevelConstant', ConstantExpressionKind.FIELD),
    const ConstantData('toplevelFunction', ConstantExpressionKind.FUNCTION),
    const ConstantData('Class.staticConstant', ConstantExpressionKind.FIELD),
    const ConstantData('Class.staticFunction', ConstantExpressionKind.FUNCTION),
    const ConstantData('1 + 2', ConstantExpressionKind.BINARY),
    const ConstantData('1 + 2 + 3', ConstantExpressionKind.BINARY),
    const ConstantData('1 + -2', ConstantExpressionKind.BINARY),
    const ConstantData('-1 + 2', ConstantExpressionKind.BINARY),
    const ConstantData('(1 + 2) + 3', ConstantExpressionKind.BINARY,
        text: '1 + 2 + 3'),
    const ConstantData('1 + (2 + 3)', ConstantExpressionKind.BINARY,
        text: '1 + 2 + 3'),
    const ConstantData('1 * 2', ConstantExpressionKind.BINARY),
    const ConstantData('1 * 2 + 3', ConstantExpressionKind.BINARY),
    const ConstantData('1 * (2 + 3)', ConstantExpressionKind.BINARY),
    const ConstantData('1 + 2 * 3', ConstantExpressionKind.BINARY),
    const ConstantData('(1 + 2) * 3', ConstantExpressionKind.BINARY),
    const ConstantData(
        'false || identical(0, 1)', ConstantExpressionKind.BINARY),
    const ConstantData('!identical(0, 1)', ConstantExpressionKind.UNARY),
    const ConstantData(
        '!identical(0, 1) || false', ConstantExpressionKind.BINARY),
    const ConstantData(
        '!(identical(0, 1) || false)', ConstantExpressionKind.UNARY),
    const ConstantData('identical(0, 1) ? 3 * 4 + 5 : 6 + 7 * 8',
        ConstantExpressionKind.CONDITIONAL),
    const ConstantData('t ? f ? 0 : 1 : 2', ConstantExpressionKind.CONDITIONAL),
    const ConstantData(
        '(t ? t : f) ? f ? 0 : 1 : 2', ConstantExpressionKind.CONDITIONAL),
    const ConstantData(
        't ? t : f ? f ? 0 : 1 : 2', ConstantExpressionKind.CONDITIONAL),
    const ConstantData(
        't ? t ? t : t : t ? t : t', ConstantExpressionKind.CONDITIONAL),
    const ConstantData(
        't ? (t ? t : t) : (t ? t : t)', ConstantExpressionKind.CONDITIONAL,
        text: 't ? t ? t : t : t ? t : t'),
    const ConstantData(
        'const [const <dynamic, dynamic>{0: true, "1": "c" "d"}, '
        'const Class(const Class<dynamic, dynamic>(toplevelConstant))]',
        ConstantExpressionKind.LIST,
        text: 'const <Object>[const {0: true, "1": "cd"}, '
            'const Class(const Class(toplevelConstant))]'),
  ]),
  const TestData('''
class A {
  const A();
}
class B {
  final field1;
  const B(this.field1);
}
class C extends B {
  final field2;
  const C({field1: 42, this.field2: false}) : super(field1);
  const C.named([field = false]) : this(field1: field, field2: field);
}
''', const [
    const ConstantData('const Object()', ConstantExpressionKind.CONSTRUCTED,
        type: 'Object', fields: const {}),
    const ConstantData('const A()', ConstantExpressionKind.CONSTRUCTED,
        type: 'A', fields: const {}),
    const ConstantData('const B(0)', ConstantExpressionKind.CONSTRUCTED,
        type: 'B', fields: const {'field(B#field1)': '0'}),
    const ConstantData('const B(const A())', ConstantExpressionKind.CONSTRUCTED,
        type: 'B', fields: const {'field(B#field1)': 'const A()'}),
    const ConstantData('const C()', ConstantExpressionKind.CONSTRUCTED,
        type: 'C',
        fields: const {
          'field(B#field1)': '42',
          'field(C#field2)': 'false',
        }),
    const ConstantData(
        'const C(field1: 87)', ConstantExpressionKind.CONSTRUCTED,
        type: 'C',
        fields: const {
          'field(B#field1)': '87',
          'field(C#field2)': 'false',
        }),
    const ConstantData(
        'const C(field2: true)', ConstantExpressionKind.CONSTRUCTED,
        type: 'C',
        fields: const {
          'field(B#field1)': '42',
          'field(C#field2)': 'true',
        }),
    const ConstantData('const C.named()', ConstantExpressionKind.CONSTRUCTED,
        type: 'C',
        fields: const {
          'field(B#field1)': 'false',
          'field(C#field2)': 'false',
        }),
    const ConstantData('const C.named(87)', ConstantExpressionKind.CONSTRUCTED,
        type: 'C',
        fields: const {
          'field(B#field1)': '87',
          'field(C#field2)': '87',
        }),
  ]),
  const TestData('''
class A<T> implements B<Null> {
  final field1;
  const A({this.field1:42});
}
class B<S> implements C<Null> {
  const factory B({field1}) = A<B<S>>;
  const factory B.named() = A<S>;
}
class C<U> {
  const factory C({field1}) = A<B<double>>;
}
''', const [
    const ConstantData('const A()', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<dynamic>', fields: const {'field(A#field1)': '42'}),
    const ConstantData(
        'const A<int>(field1: 87)', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<int>', fields: const {'field(A#field1)': '87'}),
    const ConstantData('const B()', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<B<dynamic>>',
        fields: const {
          'field(A#field1)': '42',
        },
        // Redirecting factories are replaced by their effective targets by CFE.
        text: 'const A<B<dynamic>>()'),
    const ConstantData('const B<int>()', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<B<int>>',
        fields: const {
          'field(A#field1)': '42',
        },
        // Redirecting factories are replaced by their effective targets by CFE.
        text: 'const A<B<int>>()'),
    const ConstantData(
        'const B<int>(field1: 87)', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<B<int>>',
        fields: const {
          'field(A#field1)': '87',
        },
        // Redirecting factories are replaced by their effective targets by CFE.
        text: 'const A<B<int>>(field1: 87)'),
    const ConstantData(
        'const C<int>(field1: 87)', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<B<double>>',
        fields: const {
          'field(A#field1)': '87',
        },
        // Redirecting factories are replaced by their effective targets by CFE.
        text: 'const A<B<double>>(field1: 87)'),
    const ConstantData(
        'const B<int>.named()', ConstantExpressionKind.CONSTRUCTED,
        type: 'A<int>',
        fields: const {
          'field(A#field1)': '42',
        },
        // Redirecting factories are replaced by their effective targets by CFE.
        text: 'const A<int>()'),
  ]),
  const TestData('''
T identity<T>(T t) => t;
class C<T> {
  final T defaultValue;
  final T Function(T t) identityFunction;

  const C(this.defaultValue, this.identityFunction);
}
  ''', const <ConstantData>[
    const ConstantData('identity', ConstantExpressionKind.FUNCTION),
    const ConstantData(
        'const C<int>(0, identity)', ConstantExpressionKind.CONSTRUCTED,
        type: 'C<int>', text: 'const C<int>(0, <int>(identity))'),
    const ConstantData(
        'const C<double>(0.5, identity)', ConstantExpressionKind.CONSTRUCTED,
        type: 'C<double>', text: 'const C<double>(0.5, <double>(identity))'),
  ])
];

main() {
  asyncTest(() async {
    await runTest();
  });
}

Future runTest() async {
  for (TestData data in DATA) {
    await testData(data);
  }
}

Future testData(TestData data) async {
  StringBuffer sb = new StringBuffer();
  sb.writeln('${data.declarations}');
  Map<String, ConstantData> constants = {};
  List<String> names = <String>[];
  data.constants.forEach((ConstantData constantData) {
    String name = 'c${constants.length}';
    names.add(name);
    sb.writeln('const $name = ${constantData.code};');
    constants[name] = constantData;
  });
  sb.writeln('main() {');
  for (String name in names) {
    sb.writeln('  print($name);');
  }
  sb.writeln('}');
  String source = sb.toString();
  CompilationResult result =
      await runCompiler(memorySourceFiles: {'main.dart': source});
  Compiler compiler = result.compiler;
  KElementEnvironment elementEnvironment =
      compiler.frontendStrategy.elementEnvironment;

  MemoryEnvironment environment = new MemoryEnvironment(
      new KernelEvaluationEnvironment(
          (compiler.frontendStrategy as dynamic).elementMap,
          compiler.environment,
          null));
  dynamic library = elementEnvironment.mainLibrary;
  constants.forEach((String name, ConstantData data) {
    FieldEntity field = elementEnvironment.lookupLibraryMember(library, name);
    dynamic constant = elementEnvironment.getFieldConstantForTesting(field);
    Expect.equals(
        data.kind,
        constant.kind,
        "Unexpected kind '${constant.kind}' for constant "
        "`${constant.toDartText()}`, expected '${data.kind}'.");
    String text = data.text;
    Expect.equals(
        text,
        constant.toDartText(),
        "Unexpected text '${constant.toDartText()}' for constant, "
        "expected '${text}'.");
    if (data.type != null) {
      String instanceType =
          constant.computeInstanceType(environment).toString();
      Expect.equals(
          data.type,
          instanceType,
          "Unexpected type '$instanceType' for constant "
          "`${constant.toDartText()}`, expected '${data.type}'.");
    }
    if (data.fields != null) {
      Map instanceFields = constant.computeInstanceData(environment).fieldMap;
      Expect.equals(
          data.fields.length,
          instanceFields.length,
          "Unexpected field count ${instanceFields.length} for constant "
          "`${constant.toDartText()}`, expected '${data.fields.length}'.");
      instanceFields.forEach((field, expression) {
        String name = '$field';
        Expect.isTrue(name.startsWith('k:'));
        name = name.substring(2).replaceAll('.', "#");
        String expression = instanceFields[field].toDartText();
        String expected = data.fields[name];
        Expect.equals(
            expected,
            expression,
            "Unexpected field expression ${expression} for field '$name' in "
            "constant `${constant.toDartText()}`, expected '${expected}'.");
      });
    }
  });
}
