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

/// Representation of stack traces and logic to parse d8 stack traces.
// TODO(sigmund): we should delete this implementation and instead:
// - switch to use the stack_trace package
// - add support non-d8 frames
// - add support for secondary regexps to detect stranger frames (like eval frames)

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

import 'util.dart';

/// Represents a stack trace line.
class StackTraceLine {
  String methodName;
  String fileName;
  int lineNo;
  int columnNo;

  StackTraceLine(this.methodName, this.fileName, this.lineNo, this.columnNo);

  /// Creates a [StackTraceLine] by parsing a d8 stack trace line [text]. The
  /// expected formats are
  ///
  ///     at <methodName>(<fileName>:<lineNo>:<columnNo>)
  ///     at <methodName>(<fileName>:<lineNo>)
  ///     at <methodName>(<fileName>)
  ///     at <fileName>:<lineNo>:<columnNo>
  ///     at <fileName>:<lineNo>
  ///     at <fileName>
  ///
  factory StackTraceLine.fromText(String text) {
    text = text.trim();
    assert(text.startsWith('at '));
    text = text.substring('at '.length);
    String methodName;
    int endParen = text.indexOf(')');
    if (endParen > 0) {
      int nameEnd = text.indexOf('(');
      if (nameEnd != -1) {
        methodName = text.substring(0, nameEnd).trim();
        text = text.substring(nameEnd + 1, endParen).trim();
      } else {
        warn('Missing left-paren in: $text');
      }
    }
    int lineNo;
    int columnNo;
    String fileName;
    int lastColon = text.lastIndexOf(':');
    if (lastColon != -1) {
      int lastValue = int.tryParse(text.substring(lastColon + 1));
      if (lastValue != null) {
        int secondToLastColon = text.lastIndexOf(':', lastColon - 1);
        if (secondToLastColon != -1) {
          int secondToLastValue =
              int.tryParse(text.substring(secondToLastColon + 1, lastColon));
          if (secondToLastValue != null) {
            lineNo = secondToLastValue;
            columnNo = lastValue;
            fileName = text.substring(0, secondToLastColon);
          } else {
            lineNo = lastValue;
            fileName = text.substring(0, lastColon);
          }
        } else {
          lineNo = lastValue;
          fileName = text.substring(0, lastColon);
        }
      } else {
        fileName = text;
      }
    } else {
      fileName = text;
    }
    return new StackTraceLine(methodName, fileName, lineNo, columnNo ?? 1);
  }

  String toString() {
    StringBuffer sb = new StringBuffer();
    sb.write('  at ');
    if (methodName != null) {
      sb.write(methodName);
      sb.write(' (');
      sb.write(fileName ?? '?');
      sb.write(':');
      sb.write(lineNo);
      sb.write(':');
      sb.write(columnNo);
      sb.write(')');
    } else {
      sb.write(fileName ?? '?');
      sb.write(':');
      sb.write(lineNo);
      sb.write(':');
      sb.write(columnNo);
    }
    return sb.toString();
  }

  String get inlineString {
    StringBuffer sb = new StringBuffer();
    var padding = 20;
    if (methodName != null) {
      sb.write(methodName);
      padding -= (methodName.length);
      if (padding <= 0) {
        sb.write('\n');
        padding = 20;
      }
    }
    sb.write(' ' * padding);
    if (fileName != null) {
      sb.write(p.url.basename(fileName));
      sb.write(' ');
      sb.write(lineNo);
      sb.write(':');
      sb.write(columnNo);
    }
    return sb.toString();
  }
}

List<StackTraceLine> parseStackTrace(String trace) {
  List<String> lines = trace.split(new RegExp(r'(\r|\n|\r\n)'));
  List<StackTraceLine> jsStackTrace = <StackTraceLine>[];
  for (String line in lines) {
    line = line.trim();
    if (line.startsWith('at ')) {
      jsStackTrace.add(new StackTraceLine.fromText(line));
    }
  }
  return jsStackTrace;
}

/// Returns the portion of the output that corresponds to the error message.
///
/// Note: some errors can span multiple lines.
String extractErrorMessage(String trace) {
  var firstStackFrame = trace.indexOf(new RegExp('\n +at'));
  if (firstStackFrame == -1) return null;
  var errorMarker = trace.indexOf('^') + 1;
  return trace.substring(errorMarker, firstStackFrame).trim();
}
