// Copyright (c) 2017, 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 'package:analyzer/dart/analysis/session.dart';
import 'package:analyzer/src/generated/source.dart';
import 'package:analyzer_plugin/protocol/protocol_common.dart';
import 'package:analyzer_plugin/src/utilities/change_builder/change_builder_core.dart';
import 'package:analyzer_plugin/utilities/change_builder/change_builder_dart.dart';
import 'package:analyzer_plugin/utilities/change_builder/change_workspace.dart';

/// A builder used to build a [SourceChange].
///
/// Clients may not extend, implement or mix-in this class.
abstract class ChangeBuilder {
  /// Initialize a newly created change builder. If the builder will be used to
  /// create changes for Dart files, then either a [session] or a [workspace]
  /// must be provided (but not both).
  factory ChangeBuilder({AnalysisSession session, ChangeWorkspace workspace}) =
      ChangeBuilderImpl;

  /// Return the range of the selection for the change being built, or `null` if
  /// there is no selection.
  SourceRange get selectionRange;

  /// Return the source change that was built. The source change will not be
  /// complete until all of the futures returned by the add*FileEdit methods
  /// have completed.
  SourceChange get sourceChange;

  /// Use the [buildFileEdit] function to create a collection of edits to the
  /// file with the given [path]. The edits will be added to the source change
  /// that is being built.
  ///
  /// The builder passed to the [buildFileEdit] function has additional support
  /// for working with Dart source files.
  Future<void> addDartFileEdit(
      String path, void Function(DartFileEditBuilder builder) buildFileEdit,
      {ImportPrefixGenerator importPrefixGenerator});

  /// Use the [buildFileEdit] function to create a collection of edits to the
  /// file with the given [path]. The edits will be added to the source change
  /// that is being built.
  @Deprecated('Use either addDartFileEdit or addGenericFileEdit')
  Future<void> addFileEdit(
      String path, void Function(FileEditBuilder builder) buildFileEdit);

  /// Use the [buildFileEdit] function to create a collection of edits to the
  /// file with the given [path]. The edits will be added to the source change
  /// that is being built.
  ///
  /// The builder passed to the [buildFileEdit] function has no special support
  /// for any particular kind of file.
  Future<void> addGenericFileEdit(
      String path, void Function(FileEditBuilder builder) buildFileEdit);

  /// Set the selection for the change being built to the given [position].
  void setSelection(Position position);
}

/// A builder used to build a [SourceEdit] as part of a [SourceFileEdit].
///
/// Clients may not extend, implement or mix-in this class.
abstract class EditBuilder {
  /// Add a region of text that is part of the linked edit group with the given
  /// [groupName]. The [buildLinkedEdit] function is used to write the content
  /// of the region of text and to add suggestions for other possible values for
  /// that region.
  void addLinkedEdit(String groupName,
      void Function(LinkedEditBuilder builder) buildLinkedEdit);

  /// Add the given text as a linked edit group with the given [groupName]. If
  /// both a [kind] and a list of [suggestions] are provided, they will be added
  /// as suggestions to the group with the given kind.
  ///
  /// Throws an [ArgumentError] if either [kind] or [suggestions] are provided
  /// without the other.
  void addSimpleLinkedEdit(String groupName, String text,
      {LinkedEditSuggestionKind kind, List<String> suggestions});

  /// Set the selection to cover all of the code written by the given [writer].
  void selectAll(void Function() writer);

  /// Set the selection to the current location within the edit being built.
  void selectHere();

  /// Add the given [string] to the content of the current edit.
  void write(String string);

  /// Add the given [string] to the content of the current edit and then add an
  /// end-of-line marker.
  void writeln([String string]);
}

/// A builder used to build a [SourceFileEdit] within a [SourceChange].
///
/// Clients may not extend, implement or mix-in this class.
abstract class FileEditBuilder {
  /// Add a deletion of text specified by the given [range]. The [range] is
  /// relative to the original source. This is fully equivalent to
  ///
  ///     addSimpleReplacement(range, '');
  void addDeletion(SourceRange range);

  /// Add an insertion of text at the given [offset]. The [offset] is relative
  /// to the original source. The [buildEdit] function is used to write the text
  /// to be inserted. This is fully equivalent to
  ///
  ///     addReplacement(new SourceRange(offset, 0), buildEdit);
  void addInsertion(int offset, void Function(EditBuilder builder) buildEdit);

  /// Add the region of text specified by the given [range] to the linked edit
  /// group with the given [groupName]. The [range] is relative to the original
  /// source. This is typically used to include pre-existing regions of text in
  /// a group. If the region to be included is part of newly generated text,
  /// then the method [EditBuilder.addLinkedEdit] should be used instead.
  void addLinkedPosition(SourceRange range, String groupName);

  /// Add a replacement of text specified by the given [range]. The [range] is
  /// relative to the original source. The [buildEdit] function is used to write
  /// the text that will replace the specified region.
  void addReplacement(
      SourceRange range, void Function(EditBuilder builder) buildEdit);

  /// Add an insertion of the given [text] at the given [offset]. The [offset]
  /// is relative to the original source. This is fully equivalent to
  ///
  ///     addInsertion(offset, (EditBuilder builder) {
  ///       builder.write(text);
  ///     });
  void addSimpleInsertion(int offset, String text);

  /// Add a replacement of the text specified by the given [range]. The [range]
  /// is relative to the original source. The original content will be replaced
  /// by the given [text]. This is fully equivalent to
  ///
  ///     addReplacement(offset, length, (EditBuilder builder) {
  ///       builder.write(text);
  ///     });
  void addSimpleReplacement(SourceRange range, String text);
}

/// A builder used to build a [LinkedEdit] region within an edit.
///
/// Clients may not extend, implement or mix-in this class.
abstract class LinkedEditBuilder {
  /// Add the given [value] as a suggestion with the given [kind].
  void addSuggestion(LinkedEditSuggestionKind kind, String value);

  /// Add each of the given [values] as a suggestion with the given [kind].
  void addSuggestions(LinkedEditSuggestionKind kind, Iterable<String> values);

  /// Add the given [string] to the content of the current edit.
  void write(String string);

  /// Add the given [string] to the content of the current edit and then add an
  /// end-of-line marker.
  void writeln([String string]);
}
