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

// @dart = 2.7

import 'dart:async';
import 'dart:io';

import 'package:async_helper/async_helper.dart';
import 'package:compiler/compiler.dart';
import 'package:compiler/src/commandline_options.dart';
import 'package:expect/expect.dart';
import 'package:source_maps/source_maps.dart';

import '../helpers/memory_compiler.dart';

const List<String> TESTS = const <String>[
  '''
main() {}
''',
];

void main(List<String> arguments) {
  bool verbose = false;
  bool writeJs = false;
  List<int> indices;
  for (String arg in arguments) {
    if (arg == '-v') {
      verbose = true;
    } else if (arg == '--write-js') {
      writeJs = true;
    } else {
      int index = int.tryParse(arg);
      if (index != null) {
        indices ??= <int>[];
        if (index < 0 || index >= TESTS.length * 2) {
          print('Index $index out of bounds: [0;${TESTS.length - 1}]');
        } else {
          indices.add(index);
        }
      }
    }
  }
  if (indices == null) {
    indices = new List<int>.generate(TESTS.length * 2, (i) => i);
  }
  asyncTest(() async {
    for (int index in indices) {
      bool useNewSourceInfo = index % 2 == 1;
      await runTest(index, TESTS[index ~/ 2],
          writeJs: writeJs,
          verbose: verbose,
          useNewSourceInfo: useNewSourceInfo);
    }
  });
}

Future runTest(int index, String code,
    {bool writeJs, bool verbose: false, bool useNewSourceInfo: false}) async {
  print("--$index------------------------------------------------------------");
  print("Compiling dart2js ${useNewSourceInfo ? Flags.useNewSourceInfo : ''}\n"
      "${code}");
  OutputCollector collector = new OutputCollector();
  List<String> options = <String>['--out=out.js', '--source-map=out.js.map'];
  if (useNewSourceInfo) {
    options.add(Flags.useNewSourceInfo);
  }
  CompilationResult compilationResult = await runCompiler(
      entryPoint: Uri.parse('memory:main.dart'),
      memorySourceFiles: {'main.dart': code},
      outputProvider: collector,
      options: options);
  Expect.isTrue(compilationResult.isSuccess,
      "Unsuccessful compilation of test:\n${code}");
  String sourceMapText = collector.getOutput('', OutputType.sourceMap);
  SingleMapping sourceMap = parse(sourceMapText);
  if (writeJs) {
    new File('out.js')
        .writeAsStringSync(collector.getOutput('', OutputType.js));
    new File('out.js.map').writeAsStringSync(sourceMapText);
  }
  Expect.isTrue(sourceMap.lines.isNotEmpty);
  TargetLineEntry firstLineEntry = sourceMap.lines.first;
  Expect.isTrue(firstLineEntry.entries.isNotEmpty);
  TargetEntry firstEntry = firstLineEntry.entries.first;
  Expect.isNull(
      firstEntry.sourceUrlId,
      "Unexpected first entry: "
      "${entryToString(firstLineEntry, firstEntry, sourceMap)}");
  TargetLineEntry lastLineEntry = sourceMap.lines.last;
  Expect.isTrue(lastLineEntry.entries.isNotEmpty);
  TargetEntry lastEntry = firstLineEntry.entries.last;
  Expect.isNull(
      lastEntry.sourceUrlId,
      "Unexpected last entry: "
      "${entryToString(lastLineEntry, lastEntry, sourceMap)}");
}

String entryToString(
    TargetLineEntry lineEntry, TargetEntry entry, SingleMapping mapping) {
  StringBuffer sb = new StringBuffer();
  sb.write('[line=');
  sb.write(lineEntry.line);
  sb.write(',column=');
  sb.write(entry.column);
  sb.write(',');
  if (entry.sourceUrlId != null) {
    sb.write('sourceUrl=');
    sb.write(mapping.urls[entry.sourceUrlId]);
    sb.write(',');
  }
  if (entry.sourceNameId != null) {
    sb.write('sourceName=');
    sb.write(mapping.names[entry.sourceNameId]);
    sb.write(',');
  }
  if (entry.sourceLine != null) {
    sb.write('sourceLine=');
    sb.write(entry.sourceLine);
    sb.write(',sourceColumn=');
    sb.write(entry.sourceColumn);
  }
  sb.write(']');
  return sb.toString();
}
