// Copyright 2020 The Chromium 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 'dart:convert';
import 'dart:io';

import 'package:devtools_tool/model.dart';
import 'package:io/io.dart';
import 'package:path/path.dart' as path;

abstract class DartSdkHelper {
  static const commandDebugMessage =
      'Consider running this command from your'
      'Dart SDK directory locally to debug.';

  static Future<void> fetchAndCheckoutMaster(
    ProcessManager processManager,
  ) async {
    final dartSdkLocation = localDartSdkLocation();
    await processManager.runAll(
      workingDirectory: dartSdkLocation,
      additionalErrorMessage: commandDebugMessage,
      commands: [
        CliCommand.git(['fetch', 'origin']),
        CliCommand.git(['rebase-update']),
        CliCommand.git(['checkout', 'origin/main']),
      ],
    );
  }
}

String localDartSdkLocation() {
  final localDartSdkLocation = Platform.environment['LOCAL_DART_SDK'];
  if (localDartSdkLocation == null) {
    throw Exception(
      'LOCAL_DART_SDK environment variable not set. Please add '
      'the following to your \'.bash_profile\' or \'.bash_rc\' file:\n'
      'export LOCAL_DART_SDK=<absolute/path/to/my/dart/sdk>',
    );
  }
  return localDartSdkLocation;
}

class CliCommand {
  CliCommand(
    this.exe,
    // Args is mandatory to make it clearer to the caller that they should
    // not be passing a full exe+args into the first string argument, because
    // this can lead to bugs if paths have spaces and everything is not escaped.
    this.args, {
    this.throwOnException = true,
  });

  factory CliCommand.flutter(
    List<String> args, {
    bool throwOnException = true,
  }) {
    return CliCommand(
      FlutterSdk.current.flutterExePath,
      args,
      throwOnException: throwOnException,
    );
  }

  factory CliCommand.dart(
    List<String> args, {
    bool throwOnException = true,
    String? sdkOverride,
  }) {
    return CliCommand(
      sdkOverride ?? FlutterSdk.current.dartExePath,
      args,
      throwOnException: throwOnException,
    );
  }

  /// CliCommand helper for running git commands.
  factory CliCommand.git(List<String> args, {bool throwOnException = true}) {
    return CliCommand('git', args, throwOnException: throwOnException);
  }

  factory CliCommand.tool(List<String> args, {bool throwOnException = true}) {
    var toolPath = Platform.script.toFilePath();
    if (!File(toolPath).existsSync()) {
      // Handling https://github.com/dart-lang/sdk/issues/54493
      // Platform.script.toFilePath() duplicates next to current directory, when run recursively from itself.
      toolPath = toolPath.replaceAll(
        'devtools/tool/tool/bin/dt.dart',
        'devtools/tool/bin/dt.dart',
      );
    }

    assert(
      File(toolPath).existsSync(),
      'Tool path could not be determined, got: $toolPath.'
      'It may be result of https://github.com/dart-lang/sdk/issues/54493',
    );

    return CliCommand(
      // We must use the Dart VM from FlutterSdk.current here to ensure we
      // consistently use the selected version for child invocations. We do
      // not need to pass the --flutter-from-path flag down because using the
      // tool will automatically select the one that's running the VM and we'll
      // have selected that here.
      FlutterSdk.current.dartExePath,
      [toolPath, ...args],
      throwOnException: throwOnException,
    );
  }

  late final String exe;
  late final List<String> args;
  final bool throwOnException;

  @override
  String toString() {
    return [exe, ...args].join(' ');
  }
}

typedef DevToolsProcessResult = ({int exitCode, String stdout, String stderr});

extension DevToolsProcessManagerExtension on ProcessManager {
  Future<DevToolsProcessResult> runProcess(
    CliCommand command, {
    String? workingDirectory,
    String? additionalErrorMessage = '',
  }) async {
    print('${workingDirectory ?? ''} > $command');
    final processStdout = StringBuffer();
    final processStderr = StringBuffer();

    final process = await spawn(
      command.exe,
      command.args,
      workingDirectory: workingDirectory,
    );
    process.stdout.transform(utf8.decoder).listen(processStdout.write);
    process.stderr.transform(utf8.decoder).listen(processStderr.write);
    final code = await process.exitCode;
    if (command.throwOnException && code != 0) {
      throw ProcessException(
        command.exe,
        command.args,
        'Failed with exit code: $code. $additionalErrorMessage',
        code,
      );
    }
    return (
      exitCode: code,
      stdout: processStdout.toString(),
      stderr: processStderr.toString(),
    );
  }

  Future<void> runAll({
    required List<CliCommand> commands,
    String? workingDirectory,
    String? additionalErrorMessage = '',
  }) async {
    for (final command in commands) {
      await runProcess(
        command,
        workingDirectory: workingDirectory,
        additionalErrorMessage: additionalErrorMessage,
      );
    }
  }
}

Future<Process> startIndependentProcess(
  CliCommand command, {
  String? workingDirectory,
  String? waitForOutput,
  Duration waitForOutputTimeout = const Duration(minutes: 2),
  void Function(String line)? onOutput,
}) async {
  final commandDisplay = '${workingDirectory ?? ''} > $command';
  print(commandDisplay);
  final process = await Process.start(
    command.exe,
    command.args,
    workingDirectory: workingDirectory,
  );

  if (waitForOutput != null) {
    final completer = Completer<void>();
    final stdoutSub = process.stdout.transform(utf8.decoder).listen((line) {
      print('> [stdout] $line');
      onOutput?.call(line);
      if (line.contains(waitForOutput)) {
        completer.complete();
      }
    });
    final stderrSub = process.stderr.transform(utf8.decoder).listen((line) {
      print('> [stderr] $line');
      onOutput?.call(line);
      if (line.contains(waitForOutput)) {
        completer.complete();
      }
    });
    await completer.future.timeout(
      waitForOutputTimeout,
      onTimeout: () {
        throw Exception(
          'Expected output "$waitForOutput" not received before timeout.',
        );
      },
    );
    await stdoutSub.cancel();
    await stderrSub.cancel();
  }

  return process;
}

String pathFromRepoRoot(String pathFromRoot) {
  return path.join(DevToolsRepo.getInstance().repoPath, pathFromRoot);
}

/// Returns the name of the git remote with id [remoteId] in
/// [workingDirectory].
///
/// When [workingDirectory] is `null`, this method will look for the remote in
/// the current directory.
///
/// [remoteId] should have the form `<organization>/<repository>.git`.
/// For example: `'flutter/flutter.git'` or `'flutter/devtools.git'`.
Future<String> findRemote(
  ProcessManager processManager, {
  required String remoteId,
  String? workingDirectory,
}) async {
  print('Searching for a remote that points to $remoteId.');
  final remotesResult = await processManager.runProcess(
    CliCommand.git(['remote', '-v']),
    workingDirectory: workingDirectory,
  );
  final String remotes = remotesResult.stdout;
  final remoteRegexp = RegExp(
    r'^(?<remote>\S+)\s+(?<path>\S+)\s+\((?<action>\S+)\)',
    multiLine: true,
  );
  final remoteRegexpResults = remoteRegexp.allMatches(remotes);
  final RegExpMatch upstreamRemoteResult;

  try {
    upstreamRemoteResult = remoteRegexpResults.firstWhere(
      (element) =>
      // ignore: prefer_interpolation_to_compose_strings
      RegExp(r'' + remoteId + '\$').hasMatch(element.namedGroup('path')!),
    );
  } on StateError {
    throw StateError(
      "Couldn't find a remote that points to flutter/devtools.git. "
      "Instead got: \n$remotes",
    );
  }
  final remoteUpstream = upstreamRemoteResult.namedGroup('remote')!;
  print('Found upstream remote.');
  return remoteUpstream;
}

extension JoinExtension on List<String> {
  String joinWithNewLine() {
    return '${join('\n')}\n';
  }
}
