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

import 'dart:convert';
import 'dart:io';
import 'package:compiler/src/commandline_options.dart';

main(List<String> args) async {
  Stopwatch stopwatch = new Stopwatch();
  String input;
  String serializedInput;
  String output = 'out.js';
  List<String> arguments = [];
  int start = 0;
  int stop = 3;
  int shards;
  bool enableAssertions = false;
  for (String arg in args) {
    if (arg.startsWith('-')) {
      if (arg.startsWith('--start=')) {
        start = int.parse(arg.substring('--start='.length));
      } else if (arg.startsWith('--stop=')) {
        stop = int.parse(arg.substring('--stop='.length));
      } else if (arg.startsWith('--shards=')) {
        shards = int.parse(arg.substring('--shards='.length));
      } else if (arg == '-ea' || arg == '--enable_asserts') {
        enableAssertions = true;
      } else if (arg.startsWith('--in=')) {
        serializedInput = arg.substring('--in='.length);
      } else if (arg.startsWith('-o')) {
        output = arg.substring('-o'.length);
      } else if (arg.startsWith('--out=')) {
        output = arg.substring('--out='.length);
      } else {
        arguments.add(arg);
      }
    } else {
      if (input != null) {
        print("Multiple entrypoints provided: '${input}' and '${arg}'.");
        exit(-1);
      }
      input = arg;
    }
  }

  if (input == null) {
    print("No entrypoint provided.");
    exit(-1);
  }

  serializedInput ??= output;

  String inputPrefix = serializedInput;
  if (serializedInput.endsWith('.js')) {
    inputPrefix = output.substring(0, output.length - '.js'.length);
  }
  String outputPrefix = output;
  if (output.endsWith('.js')) {
    outputPrefix = output.substring(0, output.length - '.js'.length);
  }

  List<String> baseOptions = ['--packages=${Platform.packageConfig}'];
  if (enableAssertions) {
    baseOptions.add('--enable_asserts');
  }
  baseOptions.add('package:compiler/src/dart2js.dart');
  baseOptions.addAll(arguments);

  String cfeOutput = '${inputPrefix}0.dill';
  String dillOutput = '${inputPrefix}.dill';
  String dataOutput = '${inputPrefix}.dill.data';
  String codeOutput = '${outputPrefix}.code';
  shards ??= 2;

  stopwatch.start();
  if (start <= 0 && stop >= 0) {
    await subProcess(
        baseOptions, [input, Flags.cfeOnly, '--out=$cfeOutput'], '0:\t');
  }
  if (start <= 1 && stop >= 1) {
    await subProcess(
        baseOptions,
        [cfeOutput, '--out=$dillOutput', '${Flags.writeData}=${dataOutput}'],
        '1:\t');
  }
  if (shards <= 1) {
    await subProcess(
        baseOptions,
        [dillOutput, '${Flags.readData}=${dataOutput}', '--out=${output}'],
        '3:\t');
  } else {
    if (start <= 2 && stop >= 2) {
      List<List<String>> additionalArguments = [];
      List<String> outputPrefixes = [];
      for (int shard = 0; shard < shards; shard++) {
        additionalArguments.add([
          dillOutput,
          '${Flags.readData}=${dataOutput}',
          '${Flags.codegenShard}=$shard',
          '${Flags.codegenShards}=$shards',
          '${Flags.writeCodegen}=${codeOutput}'
        ]);
        outputPrefixes.add('2:${shard + 1}/$shards\t');
      }

      Stopwatch subwatch = new Stopwatch();
      subwatch.start();
      await Future.wait(new List<Future>.generate(shards, (int shard) {
        return subProcess(
            baseOptions, additionalArguments[shard], outputPrefixes[shard]);
      }));
      subwatch.stop();
      print('2:\tTotal time: ${_formatMs(subwatch.elapsedMilliseconds)}');
    }
    if (start <= 3 && stop >= 3) {
      await subProcess(
          baseOptions,
          [
            dillOutput,
            '${Flags.readData}=${dataOutput}',
            '${Flags.readCodegen}=${codeOutput}',
            '${Flags.codegenShards}=$shards',
            '--out=${output}'
          ],
          '3:\t');
    }
  }
  stopwatch.stop();
  print('Total time: ${_formatMs(stopwatch.elapsedMilliseconds)}');
}

Future subProcess(List<String> baseOptions, List<String> additionalOptions,
    String outputPrefix) async {
  List<String> options = []
    ..addAll(baseOptions)
    ..addAll(additionalOptions);
  print(
      '${outputPrefix}Command: ${Platform.resolvedExecutable} ${options.join(' ')}');
  Process process = await Process.start(Platform.resolvedExecutable, options,
      runInShell: true);
  _Prefixer stdoutPrefixer = new _Prefixer(outputPrefix, stdout);
  _Prefixer stderrOutputter = new _Prefixer(outputPrefix, stderr);
  process.stdout.transform(utf8.decoder).listen(stdoutPrefixer);
  process.stderr.transform(utf8.decoder).listen(stderrOutputter);

  int exitCode = await process.exitCode;
  if (exitCode != 0) {
    exit(exitCode);
  }
}

class _Prefixer {
  final String _prefix;
  final Stdout _stdout;
  bool _atNewLine = true;

  _Prefixer(this._prefix, this._stdout);

  void call(String text) {
    int index = 0;
    while (index < text.length) {
      if (_atNewLine) {
        _stdout.write(_prefix);
        _atNewLine = false;
      }
      int pos = text.indexOf('\n', index);
      if (pos != -1) {
        _stdout.write(text.substring(index, pos + 1));
        _atNewLine = true;
        index = pos + 1;
      } else {
        _stdout.write(text.substring(index));
        index = text.length;
      }
    }
  }
}

String _formatMs(int ms) {
  return (ms / 1000).toStringAsFixed(3) + 's';
}
