// Copyright (c) 2015, 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:analysis_server/src/provisional/completion/dart/completion_dart.dart';
import 'package:analysis_server/src/services/completion/dart/suggestion_builder.dart';
import 'package:analyzer/dart/ast/ast.dart';
import 'package:analyzer/dart/element/element.dart';

/// A contributor that produces suggestions based on the static members of a
/// given class, enum, or extension. More concretely, this class produces
/// suggestions for expressions of the form `C.^`, where `C` is the name of a
/// class, enum, or extension.
class StaticMemberContributor extends DartCompletionContributor {
  @override
  Future<void> computeSuggestions(
      DartCompletionRequest request, SuggestionBuilder builder) async {
    var library = request.libraryElement;
    bool isVisible(Element element) => element.isAccessibleIn(library);
    var targetId = request.dotTarget;
    if (targetId is Identifier && !request.target.isCascade) {
      var element = targetId.staticElement;
      if (element is TypeAliasElement) {
        var aliasedType = element.aliasedType;
        element = aliasedType.element;
      }
      if (element is ClassElement) {
        for (var accessor in element.accessors) {
          if (accessor.isStatic &&
              !accessor.isSynthetic &&
              isVisible(accessor)) {
            builder.suggestAccessor(accessor, inheritanceDistance: 0.0);
          }
        }
        for (var constructor in element.constructors) {
          if (isVisible(constructor)) {
            if (!element.isAbstract || constructor.isFactory) {
              builder.suggestConstructor(constructor, hasClassName: true);
            }
          }
        }
        for (var field in element.fields) {
          if (field.isStatic &&
              (!field.isSynthetic || element.isEnum) &&
              isVisible(field)) {
            builder.suggestField(field, inheritanceDistance: 0.0);
          }
        }
        for (var method in element.methods) {
          if (method.isStatic && isVisible(method)) {
            builder.suggestMethod(method, inheritanceDistance: 0.0);
          }
        }
      } else if (element is ExtensionElement) {
        for (var accessor in element.accessors) {
          if (accessor.isStatic &&
              !accessor.isSynthetic &&
              isVisible(accessor)) {
            builder.suggestAccessor(accessor, inheritanceDistance: 0.0);
          }
        }
        for (var field in element.fields) {
          if (field.isStatic && !field.isSynthetic && isVisible(field)) {
            builder.suggestField(field, inheritanceDistance: 0.0);
          }
        }
        for (var method in element.methods) {
          if (method.isStatic && isVisible(method)) {
            builder.suggestMethod(method, inheritanceDistance: 0.0);
          }
        }
      }
    }
  }
}
