// 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:async';

import 'package:analysis_server/lsp_protocol/protocol.dart';
import 'package:analysis_server/src/lsp/constants.dart';
import 'package:analysis_server/src/lsp/json_parsing.dart';
import 'package:test/test.dart';
import 'package:test_reflective_loader/test_reflective_loader.dart';

import '../tool/lsp_spec/matchers.dart';
import 'code_actions_abstract.dart';

void main() {
  defineReflectiveSuite(() {
    defineReflectiveTests(ExtractMethodRefactorCodeActionsTest);
    defineReflectiveTests(ExtractWidgetRefactorCodeActionsTest);
    defineReflectiveTests(
        ExtractWidgetRefactorCodeActionsWithoutNullSafetyTest);
    defineReflectiveTests(ExtractVariableRefactorCodeActionsTest);
    defineReflectiveTests(InlineLocalVariableRefactorCodeActionsTest);
    defineReflectiveTests(InlineMethodRefactorCodeActionsTest);
    defineReflectiveTests(ConvertGetterToMethodCodeActionsTest);
    defineReflectiveTests(ConvertMethodToGetterCodeActionsTest);
  });
}

@reflectiveTest
class ConvertGetterToMethodCodeActionsTest extends AbstractCodeActionsTest {
  final refactorTitle = 'Convert Getter to Method';

  Future<void> test_refactor() async {
    const content = '''
int get ^test => 42;
void f() {
  var a = test;
  var b = test;
}
''';
    const expectedContent = '''
int test() => 42;
void f() {
  var a = test();
  var b = test();
}
''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, refactorTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_setter_notAvailable() async {
    const content = '''
set ^a(String value) {}

''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, refactorTitle);

    expect(codeAction, isNull);
  }
}

@reflectiveTest
class ConvertMethodToGetterCodeActionsTest extends AbstractCodeActionsTest {
  final refactorTitle = 'Convert Method to Getter';

  Future<void> test_constructor_notAvailable() async {
    const content = '''
class A {
  ^A();
}
''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, refactorTitle);

    expect(codeAction, isNull);
  }

  Future<void> test_refactor() async {
    const content = '''
int ^test() => 42;
void f() {
  var a = test();
  var b = test();
}
''';
    const expectedContent = '''
int get test => 42;
void f() {
  var a = test;
  var b = test;
}
''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, refactorTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }
}

@reflectiveTest
class ExtractMethodRefactorCodeActionsTest extends AbstractCodeActionsTest {
  final extractMethodTitle = 'Extract Method';

  /// A stream of strings (CREATE, BEGIN, END) corresponding to progress
  /// requests and notifications for convenience in testing.
  ///
  /// Analyzing statuses are not included.
  Stream<String> get progressUpdates {
    final controller = StreamController<String>();

    requestsFromServer
        .where((r) => r.method == Method.window_workDoneProgress_create)
        .listen((request) async {
      final params = WorkDoneProgressCreateParams.fromJson(
          request.params as Map<String, Object?>);
      if (params.token != analyzingProgressToken) {
        controller.add('CREATE');
      }
    }, onDone: controller.close);
    notificationsFromServer
        .where((n) => n.method == Method.progress)
        .listen((notification) {
      final params =
          ProgressParams.fromJson(notification.params as Map<String, Object?>);
      if (params.token != analyzingProgressToken) {
        if (WorkDoneProgressBegin.canParse(params.value, nullLspJsonReporter)) {
          controller.add('BEGIN');
        } else if (WorkDoneProgressEnd.canParse(
            params.value, nullLspJsonReporter)) {
          controller.add('END');
        }
      }
    });

    return controller.stream;
  }

  Future<void> test_appliesCorrectEdits() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    const expectedContent = '''
void f() {
  print('Test!');
  newMethod();
}

void newMethod() {
  print('Test!');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_cancelsInProgress() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    const expectedContent = '''
void f() {
  print('Test!');
  newMethod();
}

void newMethod() {
  print('Test!');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    // Respond to any applyEdit requests from the server with successful responses
    // and capturing the last edit.
    late WorkspaceEdit edit;
    requestsFromServer.listen((request) async {
      if (request.method == Method.workspace_applyEdit) {
        final params = ApplyWorkspaceEditParams.fromJson(
            request.params as Map<String, Object?>);
        edit = params.edit;
        respondTo(request, ApplyWorkspaceEditResult(applied: true));
      }
    });

    // Send two requests together.
    final req1 = executeCodeAction(codeAction);
    final req2 = executeCodeAction(codeAction);

    // Expect the first will have cancelled the second.
    await expectLater(
        req1, throwsA(isResponseError(ErrorCodes.RequestCancelled)));
    await req2;

    // Ensure applying the changes will give us the expected content.
    final contents = {
      mainFilePath: withoutMarkers(content),
    };
    applyChanges(contents, edit.changes!);
    expect(contents[mainFilePath], equals(expectedContent));
  }

  Future<void> test_contentModified() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    await initialize();
    await openFile(mainFileUri, withoutMarkers(content));

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    // Send an edit request immediately after the refactor request.
    final req1 = executeCodeAction(codeAction);
    await replaceFile(100, mainFileUri, 'new test content');

    // Expect the first to fail because of the modified content.
    await expectLater(
        req1, throwsA(isResponseError(ErrorCodes.ContentModified)));
  }

  Future<void> test_filtersCorrectly() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize(
      textDocumentCapabilities: withCodeActionKinds(
        emptyTextDocumentClientCapabilities,
        [CodeActionKind.Empty], // Support everything (empty prefix matches all)
      ),
    );

    ofKind(CodeActionKind kind) => getCodeActions(
          mainFileUri.toString(),
          range: rangeFromMarkers(content),
          kinds: [kind],
        );

    // Helper that requests CodeActions for [kind] and ensures all results
    // returned have either an equal kind, or a kind that is prefixed with the
    // requested kind followed by a dot.
    Future<void> checkResults(CodeActionKind kind) async {
      final results = await ofKind(kind);
      for (final result in results) {
        final resultKind = result.map(
          (cmd) => throw 'Expected CodeAction, got Command: ${cmd.title}',
          (action) => action.kind,
        );
        expect(
          '$resultKind',
          anyOf([
            equals('$kind'),
            startsWith('$kind.'),
          ]),
        );
      }
    }

    // Check a few of each that will produces multiple matches and no matches.
    await checkResults(CodeActionKind.Refactor);
    await checkResults(CodeActionKind.RefactorExtract);
    await checkResults(CodeActionKind('refactor.extract.foo'));
    await checkResults(CodeActionKind.RefactorRewrite);
  }

  Future<void> test_generatesNames() async {
    const content = '''
Object F() {
  return Container([[Text('Test!')]]);
}

Object Container(Object text) => null;
Object Text(Object text) => null;
    ''';
    const expectedContent = '''
Object F() {
  return Container(text());
}

Object text() => Text('Test!');

Object Container(Object text) => null;
Object Text(Object text) => null;
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_invalidLocation() async {
    const content = '''
import 'dart:convert';
^
void f() {}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle);
    expect(codeAction, isNull);
  }

  Future<void> test_invalidLocation_importPrefix() async {
    const content = '''
import 'dart:io' as io;

i^o.File a;
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle);
    expect(codeAction, isNull);
  }

  Future<void> test_progress_clientProvided() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    const expectedContent = '''
void f() {
  print('Test!');
  newMethod();
}

void newMethod() {
  print('Test!');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize(
        windowCapabilities:
            withWorkDoneProgressSupport(emptyWindowClientCapabilities));

    // Expect begin/end progress updates without a create, since the
    // token was supplied by us (the client).
    expect(progressUpdates, emitsInOrder(['BEGIN', 'END']));

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent,
        workDoneToken: clientProvidedTestWorkDoneToken);
  }

  Future<void> test_progress_notSupported() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    const expectedContent = '''
void f() {
  print('Test!');
  newMethod();
}

void newMethod() {
  print('Test!');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    var didGetProgressNotifications = false;
    notificationsFromServer
        .where((n) => n.method == Method.progress)
        .listen((_) => didGetProgressNotifications = true);

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);

    expect(didGetProgressNotifications, isFalse);
  }

  Future<void> test_progress_serverGenerated() async {
    const content = '''
void f() {
  print('Test!');
  [[print('Test!');]]
}
    ''';
    const expectedContent = '''
void f() {
  print('Test!');
  newMethod();
}

void newMethod() {
  print('Test!');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize(
        windowCapabilities:
            withWorkDoneProgressSupport(emptyWindowClientCapabilities));

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    // Ensure the progress messages come through and in the correct order.
    expect(progressUpdates, emitsInOrder(['CREATE', 'BEGIN', 'END']));

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_validLocation_failsInitialValidation() async {
    const content = '''
f() {
  var a = 0;
  doFoo([[() => print(a)]]);
  print(a);
}

void doFoo(void Function() a) => a();

    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    final command = codeAction.map(
      (command) => command,
      (codeAction) => codeAction.command!,
    );

    // Call the `refactor.validate` command with the same arguments.
    // Clients that want validation behaviour will need to implement this
    // themselves (via middleware).
    final response = await executeCommand(
      Command(
          title: command.title,
          command: Commands.validateRefactor,
          arguments: command.arguments),
      decoder: ValidateRefactorResult.fromJson,
    );

    expect(response.valid, isFalse);
    expect(response.message, contains('Cannot extract closure as method'));
  }

  /// Test if the client does not call refactor.validate it still gets a
  /// sensible `showMessage` call and not a failed request.
  Future<void> test_validLocation_failsInitialValidation_noValidation() async {
    const content = '''
f() {
  var a = 0;
  doFoo([[() => print(a)]]);
  print(a);
}

void doFoo(void Function() a) => a();

    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize(
      // We expect an error notification so don't fail on it.
      failTestOnAnyErrorNotification: false,
    );

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    final command = codeAction.map(
      (command) => command,
      (codeAction) => codeAction.command!,
    );

    // Call the refactor without any validation and expected an error message
    // without a request failure.
    final errorNotification = await expectErrorNotification(() async {
      final response = await executeCommand(
        Command(
            title: command.title,
            command: command.command,
            arguments: command.arguments),
      );
      expect(response, isNull);
    });
    expect(
      errorNotification.message,
      contains('Cannot extract closure as method'),
    );
  }

  Future<void> test_validLocation_passesInitialValidation() async {
    const content = '''
f() {
  doFoo([[() => print(1)]]);
}

void doFoo(void Function() a) => a();

    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractMethodTitle)!;

    final command = codeAction.map(
      (command) => command,
      (codeAction) => codeAction.command!,
    );

    // Call the `Commands.validateRefactor` command with the same arguments.
    // Clients that want validation behaviour will need to implement this
    // themselves (via middleware).
    final response = await executeCommand(
      Command(
          title: command.title,
          command: Commands.validateRefactor,
          arguments: command.arguments),
      decoder: ValidateRefactorResult.fromJson,
    );

    expect(response.valid, isTrue);
    expect(response.message, isNull);
  }
}

@reflectiveTest
class ExtractVariableRefactorCodeActionsTest extends AbstractCodeActionsTest {
  final extractVariableTitle = 'Extract Local Variable';

  Future<void> test_appliesCorrectEdits() async {
    const content = '''
void f() {
  foo([[1 + 2]]);
}

void foo(int arg) {}
    ''';
    const expectedContent = '''
void f() {
  var arg = 1 + 2;
  foo(arg);
}

void foo(int arg) {}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction = findCommand(
        codeActions, Commands.performRefactor, extractVariableTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_doesNotCreateNameConflicts() async {
    const content = '''
void f() {
  var arg = "test";
  foo([[1 + 2]]);
}

void foo(int arg) {}
    ''';
    const expectedContent = '''
void f() {
  var arg = "test";
  var arg2 = 1 + 2;
  foo(arg2);
}

void foo(int arg) {}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction = findCommand(
        codeActions, Commands.performRefactor, extractVariableTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }
}

@reflectiveTest
class ExtractWidgetRefactorCodeActionsTest extends AbstractCodeActionsTest {
  final extractWidgetTitle = 'Extract Widget';

  /// Nullability suffix expected in this test class.
  String get expectedNullableSuffix => '?';

  @override
  void setUp() {
    super.setUp();
    writePackageConfig(
      projectFolderPath,
      flutter: true,
    );
  }

  Future<void> test_appliesCorrectEdits() async {
    const content = '''
import 'package:flutter/material.dart';

class MyWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new Row(
      children: <Widget>[
        new [[Column]](
          children: <Widget>[
            new Text('AAA'),
            new Text('BBB'),
          ],
        ),
        new Text('CCC'),
        new Text('DDD'),
      ],
    );
  }
}
    ''';
    final expectedContent = '''
import 'package:flutter/material.dart';

class MyWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new Row(
      children: <Widget>[
        NewWidget(),
        new Text('CCC'),
        new Text('DDD'),
      ],
    );
  }
}

class NewWidget extends StatelessWidget {
  const NewWidget({
    Key$expectedNullableSuffix key,
  }) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return new Column(
      children: <Widget>[
        new Text('AAA'),
        new Text('BBB'),
      ],
    );
  }
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        range: rangeFromMarkers(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractWidgetTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_invalidLocation() async {
    const content = '''
import 'dart:convert';
^
void f() {}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, extractWidgetTitle);
    expect(codeAction, isNull);
  }
}

@reflectiveTest
class ExtractWidgetRefactorCodeActionsWithoutNullSafetyTest
    extends ExtractWidgetRefactorCodeActionsTest {
  @override
  String get expectedNullableSuffix => '';

  @override
  String get testPackageLanguageVersion => '2.9';
}

@reflectiveTest
class InlineLocalVariableRefactorCodeActionsTest
    extends AbstractCodeActionsTest {
  final inlineVariableTitle = 'Inline Local Variable';

  Future<void> test_appliesCorrectEdits() async {
    const content = '''
void f() {
  var a^ = 1;
  print(a);
  print(a);
  print(a);
}
    ''';
    const expectedContent = '''
void f() {
  print(1);
  print(1);
  print(1);
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction = findCommand(
        codeActions, Commands.performRefactor, inlineVariableTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }
}

@reflectiveTest
class InlineMethodRefactorCodeActionsTest extends AbstractCodeActionsTest {
  final inlineMethodTitle = 'Inline Method';

  Future<void> test_inlineAtCallSite() async {
    const content = '''
void foo1() {
  ba^r();
}

void foo2() {
  bar();
}

void bar() {
  print('test');
}
    ''';
    const expectedContent = '''
void foo1() {
  print('test');
}

void foo2() {
  bar();
}

void bar() {
  print('test');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, inlineMethodTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }

  Future<void> test_inlineAtMethod() async {
    const content = '''
void foo1() {
  bar();
}

void foo2() {
  bar();
}

void ba^r() {
  print('test');
}
    ''';
    const expectedContent = '''
void foo1() {
  print('test');
}

void foo2() {
  print('test');
}
    ''';
    newFile(mainFilePath, withoutMarkers(content));
    await initialize();

    final codeActions = await getCodeActions(mainFileUri.toString(),
        position: positionFromMarker(content));
    final codeAction =
        findCommand(codeActions, Commands.performRefactor, inlineMethodTitle)!;

    await verifyCodeActionEdits(
        codeAction, withoutMarkers(content), expectedContent);
  }
}
