// Copyright 2014 The Flutter Authors. 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:async';

import 'package:flutter/foundation.dart';

class _AsyncScope {
  _AsyncScope(this.creationStack, this.zone);
  final StackTrace creationStack;
  final Zone zone;
}

/// Utility class for all the async APIs in the `flutter_test` library.
///
/// This class provides checking for asynchronous APIs, allowing the library to
/// verify that all the asynchronous APIs are properly `await`ed before calling
/// another.
///
/// For example, it prevents this kind of code:
///
/// ```dart
/// tester.pump(); // forgot to call "await"!
/// tester.pump();
/// ```
///
/// ...by detecting, in the second call to `pump`, that it should actually be:
///
/// ```dart
/// await tester.pump();
/// await tester.pump();
/// ```
///
/// It does this while still allowing nested calls, e.g. so that you can
/// call [expect] from inside callbacks.
///
/// You can use this in your own test functions, if you have some asynchronous
/// functions that must be used with "await". Wrap the contents of the function
/// in a call to TestAsyncUtils.guard(), as follows:
///
/// ```dart
/// Future<void> myTestFunction() => TestAsyncUtils.guard(() async {
///   // ...
/// });
/// ```
class TestAsyncUtils {
  // This class is not meant to be instantiated or extended; this constructor
  // prevents instantiation and extension.
  TestAsyncUtils._();
  static const String _className = 'TestAsyncUtils';

  static final List<_AsyncScope> _scopeStack = <_AsyncScope>[];

  /// Calls the given callback in a new async scope. The callback argument is
  /// the asynchronous body of the calling method. The calling method is said to
  /// be "guarded". Nested calls to guarded methods from within the body of this
  /// one are fine, but calls to other guarded methods from outside the body of
  /// this one before this one has finished will throw an exception.
  ///
  /// This method first calls [guardSync].
  static Future<T> guard<T>(Future<T> Function() body) {
    guardSync();
    final Zone zone = Zone.current.fork(
      zoneValues: <dynamic, dynamic>{
        _scopeStack: true, // so we can recognize this as our own zone
      }
    );
    final _AsyncScope scope = _AsyncScope(StackTrace.current, zone);
    _scopeStack.add(scope);
    final Future<T> result = scope.zone.run<Future<T>>(body);
    late T resultValue; // This is set when the body of work completes with a result value.
    Future<T> completionHandler(dynamic error, StackTrace? stack) {
      assert(_scopeStack.isNotEmpty);
      assert(_scopeStack.contains(scope));
      bool leaked = false;
      _AsyncScope closedScope;
      final List<DiagnosticsNode> information = <DiagnosticsNode>[];
      while (_scopeStack.isNotEmpty) {
        closedScope = _scopeStack.removeLast();
        if (closedScope == scope) {
          break;
        }
        if (!leaked) {
          information.add(ErrorSummary('Asynchronous call to guarded function leaked.'));
          information.add(ErrorHint('You must use "await" with all Future-returning test APIs.'));
          leaked = true;
        }
        final _StackEntry? originalGuarder = _findResponsibleMethod(closedScope.creationStack, 'guard', information);
        if (originalGuarder != null) {
          information.add(ErrorDescription(
            'The test API method "${originalGuarder.methodName}" '
            'from class ${originalGuarder.className} '
            'was called from ${originalGuarder.callerFile} '
            'on line ${originalGuarder.callerLine}, '
            'but never completed before its parent scope closed.'
          ));
        }
      }
      if (leaked) {
        if (error != null) {
          information.add(DiagnosticsProperty<dynamic>(
            'An uncaught exception may have caused the guarded function leak. The exception was',
            error,
            style: DiagnosticsTreeStyle.errorProperty,
          ));
          information.add(DiagnosticsStackTrace('The stack trace associated with this exception was', stack));
        }
        throw FlutterError.fromParts(information);
      }
      if (error != null) {
        return Future<T>.error(error! as Object, stack);
      }
      return Future<T>.value(resultValue);
    }
    return result.then<T>(
      (T value) {
        resultValue = value;
        return completionHandler(null, null);
      },
      onError: completionHandler,
    );
  }

  static Zone? get _currentScopeZone {
    Zone? zone = Zone.current;
    while (zone != null) {
      if (zone[_scopeStack] == true) {
        return zone;
      }
      zone = zone.parent;
    }
    return null;
  }

  /// Verifies that there are no guarded methods currently pending (see [guard]).
  ///
  /// If a guarded method is currently pending, and this is not a call nested
  /// from inside that method's body (directly or indirectly), then this method
  /// will throw a detailed exception.
  static void guardSync() {
    if (_scopeStack.isEmpty) {
      // No scopes open, so we must be fine.
      return;
    }
    // Find the current TestAsyncUtils scope zone so we can see if it's the one we expect.
    final Zone? zone = _currentScopeZone;
    if (zone == _scopeStack.last.zone) {
      // We're still in the current scope zone. All good.
      return;
    }
    // If we get here, we know we've got a conflict on our hands.
    // We got an async barrier, but the current zone isn't the last scope that
    // we pushed on the stack.
    // Find which scope the conflict happened in, so that we know
    // which stack trace to report the conflict as starting from.
    //
    // For example, if we called an async method A, which ran its body in a
    // guarded block, and in its body it ran an async method B, which ran its
    // body in a guarded block, but we didn't await B, then in A's block we ran
    // an async method C, which ran its body in a guarded block, then we should
    // complain about the call to B then the call to C. BUT. If we called an async
    // method A, which ran its body in a guarded block, and in its body it ran
    // an async method B, which ran its body in a guarded block, but we didn't
    // await A, and then at the top level we called a method D, then we should
    // complain about the call to A then the call to D.
    //
    // In both examples, the scope stack would have two scopes. In the first
    // example, the current zone would be the zone of the _scopeStack[0] scope,
    // and we would want to show _scopeStack[1]'s creationStack. In the second
    // example, the current zone would not be in the _scopeStack, and we would
    // want to show _scopeStack[0]'s creationStack.
    int skipCount = 0;
    _AsyncScope candidateScope = _scopeStack.last;
    _AsyncScope scope;
    do {
      skipCount += 1;
      scope = candidateScope;
      if (skipCount >= _scopeStack.length) {
        if (zone == null) {
          break;
        }
        // Some people have reported reaching this point, but it's not clear
        // why. For now, just silently return.
        // TODO(ianh): If we ever get a test case that shows how we reach
        // this point, reduce it and report the error if there is one.
        return;
      }
      candidateScope = _scopeStack[_scopeStack.length - skipCount - 1];
      assert(candidateScope != null);
      assert(candidateScope.zone != null);
    } while (candidateScope.zone != zone);
    assert(scope != null);
    final List<DiagnosticsNode> information = <DiagnosticsNode>[
      ErrorSummary('Guarded function conflict.'),
      ErrorHint('You must use "await" with all Future-returning test APIs.'),
    ];
    final _StackEntry? originalGuarder = _findResponsibleMethod(scope.creationStack, 'guard', information);
    final _StackEntry? collidingGuarder = _findResponsibleMethod(StackTrace.current, 'guardSync', information);
    if (originalGuarder != null && collidingGuarder != null) {
      final String originalKind = originalGuarder.className == null ? 'function' : 'method';
      String originalName;
      if (originalGuarder.className == null) {
        originalName = '$originalKind (${originalGuarder.methodName})';
        information.add(ErrorDescription(
          'The guarded "${originalGuarder.methodName}" function '
          'was called from ${originalGuarder.callerFile} '
          'on line ${originalGuarder.callerLine}.'
        ));
      } else {
        originalName = '$originalKind (${originalGuarder.className}.${originalGuarder.methodName})';
        information.add(ErrorDescription(
          'The guarded method "${originalGuarder.methodName}" '
          'from class ${originalGuarder.className} '
          'was called from ${originalGuarder.callerFile} '
          'on line ${originalGuarder.callerLine}.'
        ));
      }
      final String again = (originalGuarder.callerFile == collidingGuarder.callerFile) &&
                           (originalGuarder.callerLine == collidingGuarder.callerLine) ?
                           'again ' : '';
      final String collidingKind = collidingGuarder.className == null ? 'function' : 'method';
      String collidingName;
      if ((originalGuarder.className == collidingGuarder.className) &&
          (originalGuarder.methodName == collidingGuarder.methodName)) {
        originalName = originalKind;
        collidingName = collidingKind;
        information.add(ErrorDescription(
          'Then, it '
          'was called ${again}from ${collidingGuarder.callerFile} '
          'on line ${collidingGuarder.callerLine}.'
        ));
      } else if (collidingGuarder.className == null) {
        collidingName = '$collidingKind (${collidingGuarder.methodName})';
        information.add(ErrorDescription(
          'Then, the "${collidingGuarder.methodName}" function '
          'was called ${again}from ${collidingGuarder.callerFile} '
          'on line ${collidingGuarder.callerLine}.'
        ));
      } else {
        collidingName = '$collidingKind (${collidingGuarder.className}.${collidingGuarder.methodName})';
        information.add(ErrorDescription(
          'Then, the "${collidingGuarder.methodName}" method '
          '${originalGuarder.className == collidingGuarder.className ? "(also from class ${collidingGuarder.className})"
                                                                     : "from class ${collidingGuarder.className}"} '
          'was called ${again}from ${collidingGuarder.callerFile} '
          'on line ${collidingGuarder.callerLine}.'
        ));
      }
      information.add(ErrorDescription(
        'The first $originalName '
        'had not yet finished executing at the time that '
        'the second $collidingName '
        'was called. Since both are guarded, and the second was not a nested call inside the first, the '
        'first must complete its execution before the second can be called. Typically, this is achieved by '
        'putting an "await" statement in front of the call to the first.'
      ));
      if (collidingGuarder.className == null && collidingGuarder.methodName == 'expect') {
        information.add(ErrorHint(
          'If you are confident that all test APIs are being called using "await", and '
          'this expect() call is not being called at the top level but is itself being '
          'called from some sort of callback registered before the ${originalGuarder.methodName} '
          'method was called, then consider using expectSync() instead.'
        ));
      }
      information.add(DiagnosticsStackTrace(
        '\nWhen the first $originalName was called, this was the stack',
        scope.creationStack,
      ));
    }
    throw FlutterError.fromParts(information);
  }

  /// Verifies that there are no guarded methods currently pending (see [guard]).
  ///
  /// This is used at the end of tests to ensure that nothing leaks out of the test.
  static void verifyAllScopesClosed() {
    if (_scopeStack.isNotEmpty) {
      final List<DiagnosticsNode> information = <DiagnosticsNode>[
        ErrorSummary('Asynchronous call to guarded function leaked.'),
        ErrorHint('You must use "await" with all Future-returning test APIs.'),
      ];
      for (final _AsyncScope scope in _scopeStack) {
        final _StackEntry? guarder = _findResponsibleMethod(scope.creationStack, 'guard', information);
        if (guarder != null) {
          information.add(ErrorDescription(
            'The guarded method "${guarder.methodName}" '
            '${guarder.className != null ? "from class ${guarder.className} " : ""}'
            'was called from ${guarder.callerFile} '
            'on line ${guarder.callerLine}, '
            'but never completed before its parent scope closed.'
          ));
        }
      }
      throw FlutterError.fromParts(information);
    }
  }

  static bool _stripAsynchronousSuspensions(String line) {
    return line != '<asynchronous suspension>';
  }

  static _StackEntry? _findResponsibleMethod(StackTrace rawStack, String method, List<DiagnosticsNode> information) {
    assert(method == 'guard' || method == 'guardSync');
    final List<String> stack = rawStack.toString().split('\n').where(_stripAsynchronousSuspensions).toList();
    assert(stack.last == '');
    stack.removeLast();
    final RegExp getClassPattern = RegExp(r'^#[0-9]+ +([^. ]+)');
    Match? lineMatch;
    int index = -1;
    do { // skip past frames that are from this class
      index += 1;
      assert(index < stack.length);
      lineMatch = getClassPattern.matchAsPrefix(stack[index]);
      assert(lineMatch != null);
      lineMatch = lineMatch!;
      assert(lineMatch.groupCount == 1);
    } while (lineMatch.group(1) == _className);
    // try to parse the stack to find the interesting frame
    if (index < stack.length) {
      final RegExp guardPattern = RegExp(r'^#[0-9]+ +(?:([^. ]+)\.)?([^. ]+)');
      final Match? guardMatch = guardPattern.matchAsPrefix(stack[index]); // find the class that called us
      if (guardMatch != null) {
        assert(guardMatch.groupCount == 2);
        final String? guardClass = guardMatch.group(1); // might be null
        final String? guardMethod = guardMatch.group(2);
        while (index < stack.length) { // find the last stack frame that called the class that called us
          lineMatch = getClassPattern.matchAsPrefix(stack[index]);
          if (lineMatch != null) {
            assert(lineMatch.groupCount == 1);
            if (lineMatch.group(1) == (guardClass ?? guardMethod)) {
              index += 1;
              continue;
            }
          }
          break;
        }
        if (index < stack.length) {
          final RegExp callerPattern = RegExp(r'^#[0-9]+ .* \((.+?):([0-9]+)(?::[0-9]+)?\)$');
          final Match? callerMatch = callerPattern.matchAsPrefix(stack[index]); // extract the caller's info
          if (callerMatch != null) {
            assert(callerMatch.groupCount == 2);
            final String? callerFile = callerMatch.group(1);
            final String? callerLine = callerMatch.group(2);
            return _StackEntry(guardClass, guardMethod, callerFile, callerLine);
          } else {
            // One reason you might get here is if the guarding method was called directly from
            // a 'dart:' API, like from the Future/microtask mechanism, because dart: URLs in the
            // stack trace don't have a column number and so don't match the regexp above.
            information.add(ErrorSummary('(Unable to parse the stack frame of the method that called the method that called $_className.$method(). The stack may be incomplete or bogus.)'));
            information.add(ErrorDescription(stack[index]));
          }
        } else {
          information.add(ErrorSummary('(Unable to find the stack frame of the method that called the method that called $_className.$method(). The stack may be incomplete or bogus.)'));
        }
      } else {
        information.add(ErrorSummary('(Unable to parse the stack frame of the method that called $_className.$method(). The stack may be incomplete or bogus.)'));
        information.add(ErrorDescription(stack[index]));
      }
    } else {
      information.add(ErrorSummary('(Unable to find the method that called $_className.$method(). The stack may be incomplete or bogus.)'));
    }
    return null;
  }
}

class _StackEntry {
  const _StackEntry(this.className, this.methodName, this.callerFile, this.callerLine);
  final String? className;
  final String? methodName;
  final String? callerFile;
  final String? callerLine;
}
