// 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.
import 'dart:io';

import 'package:path/path.dart' as p;

import 'io.dart';
import 'log.dart';

Future<bool> analyzeTests(String nnbdTestDir) async {
  var files = <String, _FileInfo>{};

  for (var entry in Directory(nnbdTestDir).listSync(recursive: true)) {
    if (entry is File && entry.path.endsWith(".dart")) {
      // Skip multitests since they aren't valid Dart files.
      var isTest = entry.path.endsWith("_test.dart") &&
          !readFile(entry.path).contains("//#");

      files[entry.path] = _FileInfo(entry.path, isTest: isTest);
    }
  }

  // Pre-existing multi-line errors will modify the character length in the
  // errors reported by the analyzer. Strip all errors first before updating.
  for (var file in files.values) {
    if (!dryRun) _removeErrors(file.path);
  }

  // Analyze the directory both in legacy and NNBD modes.
  var legacyErrorsFuture = _runAnalyzer(nnbdTestDir, nnbd: false);
  var nnbdErrorsFuture = _runAnalyzer(nnbdTestDir, nnbd: true);

  var legacyErrors = await legacyErrorsFuture;
  var nnbdErrors = await nnbdErrorsFuture;

  legacyErrors.forEach((path, errors) {
    // Sometimes the analysis reaches out to things like pkg/expect.
    if (!files.containsKey(path)) {
      files[path] = _FileInfo(path, isTest: false);
    }

    files[path].legacyErrors.addAll(errors);
  });

  nnbdErrors.forEach((path, errors) {
    // Sometimes the analysis reaches out to things like pkg/expect.
    if (!files.containsKey(path)) {
      files[path] = _FileInfo(path, isTest: false);
    }

    files[path].nnbdErrors.addAll(errors);
  });

  var fileCount = 0;
  var errorFileCount = 0;
  var errorCount = 0;

  plural(int count, String name) => "$count $name${count == 1 ? '' : 's'}";

  var fileNames = files.keys.toList()..sort();
  for (var fileName in fileNames) {
    var file = files[fileName];
    if (!file.isTest) continue;

    // Only insert errors that are not already present when the file is
    // analyzed as a legacy library.
    file.calculateDifferences();

    fileCount++;
    errorCount += file.addedErrors.length;
    if (file.addedErrors.length > 0) {
      var count = file.addedErrors.length;
      print("${p.relative(file.path, from: testRoot)}: " +
          plural(count, 'error'));
      errorFileCount++;
    }

    if (!dryRun) _insertErrors(file.path, file.addedErrors);
  }

  if (errorCount == 0) {
    print(green("All ${plural(fileCount, 'file')} are static error free!"));
  } else {
    print(red("Analyzed ${plural(fileCount, 'file')} and found "
        "${plural(errorCount, 'error')} "
        "in ${plural(errorFileCount, 'file')}."));
  }

  return errorCount == 0;
}

Future<Map<String, List<_StaticError>>> _runAnalyzer(String inputDir,
    {bool nnbd}) async {
  print("Analyzing ${p.relative(inputDir, from: testRoot)}"
      "${nnbd ? ' with NNBD' : ''}...");
  var result = await Process.run("dartanalyzer", [
    "--packages=${p.join(sdkRoot, '.packages')}",
    if (nnbd) ...[
      "--dart-sdk=$nnbdSdkBuildDir",
      "--enable-experiment=non-nullable",
    ],
    "--format=machine",
    inputDir,
  ]);
  // TODO(rnystrom): How do we pass in options from the test files?

  var errors = _StaticError.parse(result.stderr as String);
  var errorsByFile = <String, List<_StaticError>>{};
  for (var error in errors) {
    errorsByFile.putIfAbsent(error.file, () => []).add(error);
  }

  for (var errors in errorsByFile.values) {
    errors.sort();
  }

  return errorsByFile;
}

/// Removes pre-existing errors in the file at [path].
void _removeErrors(String path) {
  // Sanity check.
  if (!p.isWithin(testRoot, path)) {
    throw ArgumentError("$path is outside of test directory.");
  }

  var lines = readFileLines(path);
  var result = StringBuffer();
  var changed = false;

  for (var i = 0; i < lines.length; i++) {
    // Strip out previous inserted comments.
    if (!lines[i].startsWith("//|")) {
      result.writeln(lines[i]);
    } else {
      changed = true;
    }
  }

  if (changed) {
    writeFile(path, result.toString());
  }
}

/// Inserts any new errors in [errors] into the file at [path].
void _insertErrors(String path, List<_StaticError> errors) {
  // Sanity check.
  if (!p.isWithin(testRoot, path)) {
    throw ArgumentError("$path is outside of test directory.");
  }

  var lines = readFileLines(path);
  var result = StringBuffer();
  var changed = false;

  for (var i = 0; i < lines.length; i++) {
    result.writeln(lines[i]);
    // TODO(rnystrom): Inefficient.
    for (var error in errors) {
      if (error.line == i + 1) {
        result.write("//|");
        result.write(" " * (error.column - 3));
        result.write("^" * error.length);
        result.writeln(" ${error.code}");
        result.writeln("//| ${error.message}");
        changed = true;
      }
    }
  }

  if (changed) {
    writeFile(path, result.toString());
  }
}

class _FileInfo {
  final String path;
  final bool isTest;

  final Set<_StaticError> legacyErrors = {};
  final Set<_StaticError> nnbdErrors = {};

  final List<_StaticError> removedErrors = [];
  final List<_StaticError> addedErrors = [];

  _FileInfo(this.path, {this.isTest});

  void calculateDifferences() {
    removedErrors.addAll(legacyErrors.toSet().difference(nnbdErrors.toSet()));
    addedErrors.addAll(nnbdErrors.toSet().difference(legacyErrors.toSet()));
  }
}

class _StaticError implements Comparable<_StaticError> {
  static List<_StaticError> parse(String stderr) {
    List<String> splitMachineError(String line) {
      var field = StringBuffer();
      var result = <String>[];
      var escaped = false;
      for (var i = 0; i < line.length; i++) {
        var c = line[i];
        if (!escaped && c == '\\') {
          escaped = true;
          continue;
        }
        escaped = false;
        if (c == '|') {
          result.add(field.toString());
          field = StringBuffer();
          continue;
        }
        field.write(c);
      }
      result.add(field.toString());
      return result;
    }

    var errors = <_StaticError>[];
    for (var line in stderr.split("\n")) {
      if (line.isEmpty) continue;

      var fields = splitMachineError(line);

      // Lines without enough fields are other output we don't care about.
      if (fields.length >= 8) {
        var error = _StaticError(fields[3],
            line: int.parse(fields[4]),
            column: int.parse(fields[5]),
            length: int.parse(fields[6]),
            code: "${fields[1]}.${fields[2]}",
            message: fields[7]);

        errors.add(error);
      } else {
        print(line);
      }
    }

    return errors;
  }

  final String file;

  /// The one-based line number of the beginning of the error's location.
  final int line;

  /// The one-based column number of the beginning of the error's location.
  final int column;

  /// The number of characters in the error location.
  ///
  /// This is optional. The CFE only reports error location, but not length.
  final int length;

  /// The expected analyzer error code for the error or `null` if this error
  /// isn't expected to be reported by analyzer.
  final String code;

  /// The expected CFE error message or `null` if this error isn't expected to
  /// be reported by the CFE.
  final String message;

  /// Creates a new StaticError at the given location with the given expected
  /// error code and message.
  ///
  /// In order to make it easier to incrementally add error tests before a
  /// feature is fully implemented or specified, an error expectation can be in
  /// an "unspecified" state for either or both platforms by having the error
  /// code or message be the special string "unspecified". When an unspecified
  /// error is tested, a front end is expected to report *some* error on that
  /// error's line, but it can be any location, error code, or message.
  _StaticError(this.file,
      {this.line, this.column, this.length, this.code, this.message}) {
    // Must have a location.
    assert(line != null);
    assert(column != null);

    // Must have at least one piece of description.
    assert(code != null || message != null);
  }

  /// A textual description of this error's location.
  String get location {
    var result = "line $line, column $column";
    if (length != null) result += ", length $length";
    return result;
  }

  String toString() => "Error $code in $file at $location: $message";

  String toStringWithoutPath() => "[$location] $code: $message";

  /// Orders errors primarily by location, then by other fields if needed.
  @override
  int compareTo(_StaticError other) {
    if (file != other.file) return file.compareTo(other.file);
    if (line != other.line) return line.compareTo(other.line);
    if (column != other.column) return column.compareTo(other.column);

    // Sort no length after all other lengths.
    if (length == null && other.length != null) return 1;
    if (length != null && other.length == null) return -1;
    if (length != other.length) return length.compareTo(other.length);

    var thisCode = code ?? "";
    var otherCode = other.code ?? "";
    if (thisCode != otherCode) return thisCode.compareTo(otherCode);

    var thisMessage = message ?? "";
    var otherMessage = other.message ?? "";
    return thisMessage.compareTo(otherMessage);
  }

  bool operator ==(dynamic other) =>
      other is _StaticError &&
      file == other.file &&
      line == other.line &&
      column == other.column &&
      length == other.length &&
      normalizeCode(code) == normalizeCode(other.code);

  int get hashCode =>
      line.hashCode ^
      column.hashCode ^
      length.hashCode ^
      normalizeCode(code).hashCode;

  String normalizeCode(String code) {
    // Pre-NNBD has a limited form of implicit downcast checking for
    // constructors.
    if (code == "COMPILE_TIME_ERROR.INVALID_CAST_NEW_EXPR") {
      return "STATIC_WARNING.ARGUMENT_TYPE_NOT_ASSIGNABLE";
    }

    return code;
  }
}
