// 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.

library analyzer.src.task.dart_work_manager;

import 'dart:collection';

import 'package:analyzer/src/context/cache.dart';
import 'package:analyzer/src/generated/engine.dart'
    show AnalysisEngine, AnalysisErrorInfo, CacheState, InternalAnalysisContext;
import 'package:analyzer/src/generated/error.dart';
import 'package:analyzer/src/generated/source.dart';
import 'package:analyzer/src/generated/utilities_collection.dart';
import 'package:analyzer/src/task/dart.dart';
import 'package:analyzer/src/task/html.dart';
import 'package:analyzer/task/dart.dart';
import 'package:analyzer/task/model.dart';

/**
 * The manager for Dart specific analysis.
 */
class DartWorkManager implements WorkManager {
  /**
   * The list of errors that are reported for raw Dart [Source]s.
   */
  static final List<ResultDescriptor<List<AnalysisError>>> _SOURCE_ERRORS =
      <ResultDescriptor<List<AnalysisError>>>[
    BUILD_DIRECTIVES_ERRORS,
    BUILD_LIBRARY_ERRORS,
    PARSE_ERRORS,
    SCAN_ERRORS
  ];

  /**
   * The list of errors that are reported for raw Dart [LibrarySpecificUnit]s.
   */
  static final List<ResultDescriptor<List<AnalysisError>>> _UNIT_ERRORS =
      <ResultDescriptor<List<AnalysisError>>>[
    HINTS,
    LINTS,
    LIBRARY_UNIT_ERRORS,
    RESOLVE_TYPE_NAMES_ERRORS,
    RESOLVE_UNIT_ERRORS,
    STRONG_MODE_ERRORS,
    VARIABLE_REFERENCE_ERRORS,
    VERIFY_ERRORS
  ];

  final InternalAnalysisContext context;

  /**
   * The [TargetedResult]s that should be computed with priority.
   */
  final LinkedHashSet<TargetedResult> priorityResultQueue =
      new LinkedHashSet<TargetedResult>();

  /**
   * The sources whose kind we don't know yet.
   */
  final LinkedHashSet<Source> unknownSourceQueue = new LinkedHashSet<Source>();

  /**
   * The queue of library sources to process.
   */
  final LinkedHashSet<Source> librarySourceQueue = new LinkedHashSet<Source>();

  /**
   * A table mapping library sources to the part sources they include.
   */
  final HashMap<Source, List<Source>> libraryPartsMap =
      new HashMap<Source, List<Source>>();

  /**
   * A table mapping part sources to the library sources that include them.
   */
  final HashMap<Source, List<Source>> partLibrariesMap =
      new HashMap<Source, List<Source>>();

  /**
   * Initialize a newly created manager.
   */
  DartWorkManager(this.context) {
    analysisCache.onResultInvalidated.listen((InvalidatedResult event) {
      if (event.descriptor == LIBRARY_ERRORS_READY) {
        CacheEntry entry = event.entry;
        if (entry.explicitlyAdded &&
            entry.getValue(SOURCE_KIND) == SourceKind.LIBRARY) {
          librarySourceQueue.add(entry.target);
        }
      }
    });
  }

  /**
   * Returns the correctly typed result of `context.analysisCache`.
   */
  AnalysisCache get analysisCache => context.analysisCache;

  /**
   * The partition that contains analysis results that are not shared with other
   * contexts.
   */
  CachePartition get privateAnalysisCachePartition =>
      context.privateAnalysisCachePartition;

  /**
   * Specifies that the client want the given [result] of the given [target]
   * to be computed with priority.
   */
  void addPriorityResult(AnalysisTarget target, ResultDescriptor result) {
    priorityResultQueue.add(new TargetedResult(target, result));
  }

  @override
  void applyChange(List<Source> addedSources, List<Source> changedSources,
      List<Source> removedSources) {
    addedSources = addedSources.where(_isDartSource).toList();
    changedSources = changedSources.where(_isDartSource).toList();
    removedSources = removedSources.where(_isDartSource).toList();
    // unknown queue
    unknownSourceQueue.addAll(addedSources);
    unknownSourceQueue.addAll(changedSources);
    unknownSourceQueue.removeAll(removedSources);
    // library queue
    librarySourceQueue.removeAll(changedSources);
    librarySourceQueue.removeAll(removedSources);
    // parts in libraries
    for (Source changedSource in changedSources) {
      _onLibrarySourceChangedOrRemoved(changedSource);
    }
    for (Source removedSource in removedSources) {
      partLibrariesMap.remove(removedSource);
      _onLibrarySourceChangedOrRemoved(removedSource);
    }
  }

  @override
  void applyPriorityTargets(List<AnalysisTarget> targets) {
    // Unschedule the old targets.
    List<TargetedResult> resultsToUnschedule = <TargetedResult>[];
    for (TargetedResult result in priorityResultQueue) {
      if (result.result == LIBRARY_ERRORS_READY) {
        resultsToUnschedule.add(result);
      }
    }
    priorityResultQueue.removeAll(resultsToUnschedule);
    // Schedule new targets.
    for (AnalysisTarget target in targets) {
      if (_isDartSource(target)) {
        SourceKind sourceKind = analysisCache.getValue(target, SOURCE_KIND);
        if (sourceKind == SourceKind.UNKNOWN) {
          addPriorityResult(target, SOURCE_KIND);
        } else if (sourceKind == SourceKind.LIBRARY) {
          _schedulePriorityLibrarySourceAnalysis(target);
        } else if (sourceKind == SourceKind.PART) {
          List<Source> libraries = context.getLibrariesContaining(target);
          for (Source library in libraries) {
            addPriorityResult(library, LIBRARY_ERRORS_READY);
          }
        }
      }
    }
  }

  @override
  List<AnalysisError> getErrors(Source source) {
    if (!_isDartSource(source) && source is! DartScript) {
      return AnalysisError.NO_ERRORS;
    }
    // If analysis is finished, use all the errors.
    if (analysisCache.getState(source, DART_ERRORS) == CacheState.VALID) {
      return analysisCache.getValue(source, DART_ERRORS);
    }
    // If analysis is in progress, combine all known partial results.
    List<AnalysisError> errors = <AnalysisError>[];
    for (ResultDescriptor<List<AnalysisError>> descriptor in _SOURCE_ERRORS) {
      errors.addAll(analysisCache.getValue(source, descriptor));
    }
    for (Source library in context.getLibrariesContaining(source)) {
      LibrarySpecificUnit unit = new LibrarySpecificUnit(library, source);
      for (ResultDescriptor<List<AnalysisError>> descriptor in _UNIT_ERRORS) {
        errors.addAll(analysisCache.getValue(unit, descriptor));
      }
    }
    return errors;
  }

  /**
   * Returns libraries containing the given [part].
   * Maybe empty, but not null.
   */
  List<Source> getLibrariesContainingPart(Source part) {
    if (part.isInSystemLibrary) {
      DartWorkManager sdkDartWorkManager = _getSdkDartWorkManager();
      if (sdkDartWorkManager != this) {
        return sdkDartWorkManager.getLibrariesContainingPart(part);
      }
    }
    List<Source> libraries = partLibrariesMap[part];
    return libraries?.toList() ?? Source.EMPTY_LIST;
  }

  @override
  TargetedResult getNextResult() {
    // Try to find a priority result to compute.
    while (priorityResultQueue.isNotEmpty) {
      TargetedResult result = priorityResultQueue.first;
      if (!_needsComputing(result.target, result.result)) {
        priorityResultQueue.remove(result);
        continue;
      }
      return result;
    }
    // Try to find a new library to analyze.
    while (librarySourceQueue.isNotEmpty) {
      Source librarySource = librarySourceQueue.first;
      // Maybe done with this library.
      if (!_needsComputing(librarySource, LIBRARY_ERRORS_READY)) {
        librarySourceQueue.remove(librarySource);
        continue;
      }
      // Analyze this library.
      return new TargetedResult(librarySource, LIBRARY_ERRORS_READY);
    }
    // No libraries in the queue, check whether there are sources to organize.
    while (unknownSourceQueue.isNotEmpty) {
      Source source = unknownSourceQueue.first;
      // Maybe done with this source.
      if (!_needsComputing(source, SOURCE_KIND)) {
        unknownSourceQueue.remove(source);
        continue;
      }
      // Compute the kind of this source.
      return new TargetedResult(source, SOURCE_KIND);
    }
    // TODO(scheglov) Report errors for parts that remained in the queue after
    // all libraries had been processed.
    // No results to compute.
    return null;
  }

  @override
  WorkOrderPriority getNextResultPriority() {
    if (priorityResultQueue.isNotEmpty) {
      return WorkOrderPriority.PRIORITY;
    }
    if (unknownSourceQueue.isNotEmpty || librarySourceQueue.isNotEmpty) {
      return WorkOrderPriority.NORMAL;
    }
    return WorkOrderPriority.NONE;
  }

  /**
   * Notifies the manager about analysis options changes.
   */
  void onAnalysisOptionsChanged() {
    _invalidateAllLocalResolutionInformation(false);
  }

  /**
   * Notifies the manager about [SourceFactory] changes.
   */
  void onSourceFactoryChanged() {
    _invalidateAllLocalResolutionInformation(true);
  }

  @override
  void resultsComputed(
      AnalysisTarget target, Map<ResultDescriptor, dynamic> outputs) {
    bool isDartSource = _isDartSource(target);
    // Route SDK outputs to the SDK WorkManager.
    if (isDartSource && target.source.isInSystemLibrary) {
      DartWorkManager sdkWorkManager = _getSdkDartWorkManager();
      if (sdkWorkManager != this) {
        sdkWorkManager.resultsComputed(target, outputs);
        return;
      }
    }
    // Organize sources.
    bool isDartLibrarySource = false;
    if (isDartSource) {
      Source source = target;
      SourceKind kind = outputs[SOURCE_KIND];
      if (kind != null) {
        unknownSourceQueue.remove(source);
        if (kind == SourceKind.LIBRARY) {
          isDartLibrarySource = true;
          if (context.prioritySources.contains(source)) {
            _schedulePriorityLibrarySourceAnalysis(source);
          } else {
            bool needErrors = _shouldErrorsBeComputed(source);
            if (needErrors) {
              librarySourceQueue.add(target);
            }
          }
        }
      }
    }
    // Update parts in libraries.
    if (isDartLibrarySource) {
      Source library = target;
      List<Source> includedParts = outputs[INCLUDED_PARTS] as List<Source>;
      if (includedParts != null) {
        libraryPartsMap[library] = includedParts;
        for (Source part in includedParts) {
          List<Source> libraries =
              partLibrariesMap.putIfAbsent(part, () => <Source>[]);
          if (!libraries.contains(library)) {
            libraries.add(library);
            _invalidateContainingLibraries(part);
          }
        }
      }
    }
    // Update notice.
    if (isDartSource) {
      bool shouldSetErrors = false;
      outputs.forEach((ResultDescriptor descriptor, value) {
        if (descriptor == PARSED_UNIT && value != null) {
          context.getNotice(target).parsedDartUnit = value;
          shouldSetErrors = true;
        }
        if (descriptor == DART_ERRORS) {
          shouldSetErrors = true;
        }
      });
      if (shouldSetErrors) {
        AnalysisErrorInfo info = context.getErrors(target);
        context.getNotice(target).setErrors(info.errors, info.lineInfo);
      }
    }
    if (target is LibrarySpecificUnit) {
      Source source = target.source;
      bool shouldSetErrors = false;
      outputs.forEach((ResultDescriptor descriptor, value) {
        if (descriptor == RESOLVED_UNIT && value != null) {
          context.getNotice(source).resolvedDartUnit = value;
          shouldSetErrors = true;
        }
      });
      if (shouldSetErrors) {
        AnalysisErrorInfo info = context.getErrors(source);
        context.getNotice(source).setErrors(info.errors, info.lineInfo);
      }
    }
  }

  void unitIncrementallyResolved(Source librarySource, Source unitSource) {
    librarySourceQueue.add(librarySource);
  }

  /**
   * Return the SDK [DartWorkManager] or this one.
   */
  DartWorkManager _getSdkDartWorkManager() {
    SourceFactory sourceFactory = context.sourceFactory;
    InternalAnalysisContext sdkContext = sourceFactory.dartSdk.context;
    if (sdkContext != context) {
      for (WorkManager workManager in sdkContext.workManagers) {
        if (workManager is DartWorkManager) {
          return workManager;
        }
      }
    }
    return this;
  }

  /**
   * Invalidate all of the resolution results computed by this context. The flag
   * [invalidateUris] should be `true` if the cached results of converting URIs
   * to source files should also be invalidated.
   */
  void _invalidateAllLocalResolutionInformation(bool invalidateUris) {
    CachePartition partition = privateAnalysisCachePartition;
    // Prepare targets and values to invalidate.
    List<Source> dartSources = <Source>[];
    List<LibrarySpecificUnit> unitTargets = <LibrarySpecificUnit>[];
    MapIterator<AnalysisTarget, CacheEntry> iterator = partition.iterator();
    while (iterator.moveNext()) {
      AnalysisTarget target = iterator.key;
      // Optionally gather Dart sources to invalidate URIs resolution.
      if (invalidateUris && _isDartSource(target)) {
        dartSources.add(target);
      }
      // LibrarySpecificUnit(s) are roots of Dart resolution.
      // When one is invalidated, invalidation is propagated to all resolution.
      if (target is LibrarySpecificUnit) {
        unitTargets.add(target);
        Source library = target.library;
        if (context.exists(library)) {
          CacheEntry entry = iterator.value;
          if (entry.explicitlyAdded) {
            librarySourceQueue.add(library);
          }
        }
      }
    }
    // Invalidate targets and values.
    unitTargets.forEach(partition.remove);
    for (Source dartSource in dartSources) {
      CacheEntry entry = partition.get(dartSource);
      if (entry != null) {
        // TODO(scheglov) we invalidate too much.
        // Would be nice to invalidate just URLs resolution.
        entry.setState(PARSED_UNIT, CacheState.INVALID);
        entry.setState(IMPORTED_LIBRARIES, CacheState.INVALID);
        entry.setState(EXPLICITLY_IMPORTED_LIBRARIES, CacheState.INVALID);
        entry.setState(EXPORTED_LIBRARIES, CacheState.INVALID);
        entry.setState(INCLUDED_PARTS, CacheState.INVALID);
        entry.setState(LIBRARY_SPECIFIC_UNITS, CacheState.INVALID);
        entry.setState(UNITS, CacheState.INVALID);
      }
    }
  }

  /**
   * Invalidate  [CONTAINING_LIBRARIES] for the given [source].
   * [CONTAINING_LIBRARIES] does not have dependencies, so we manage it here.
   * The [source] may be a part, or a library whose contents is updated so
   * will be a part.
   */
  void _invalidateContainingLibraries(Source source) {
    CacheEntry entry = analysisCache.get(source);
    if (entry != null) {
      entry.setState(CONTAINING_LIBRARIES, CacheState.INVALID);
    }
  }

  /**
   * Returns `true` if the given [result] of the given [target] needs
   * computing, i.e. it is not in the valid and not in the error state.
   */
  bool _needsComputing(AnalysisTarget target, ResultDescriptor result) {
    CacheState state = analysisCache.getState(target, result);
    return state != CacheState.VALID && state != CacheState.ERROR;
  }

  /**
   * The given [library] source was changed or removed.
   * Update [libraryPartsMap] and [partLibrariesMap].
   */
  void _onLibrarySourceChangedOrRemoved(Source library) {
    List<Source> parts = libraryPartsMap.remove(library);
    if (parts != null) {
      for (Source part in parts) {
        List<Source> libraries = partLibrariesMap[part];
        if (libraries != null) {
          libraries.remove(library);
          _invalidateContainingLibraries(part);
        }
      }
    }
    _invalidateContainingLibraries(library);
  }

  /**
   * Schedule computing [RESOLVED_UNIT] for the given [librarySource].
   * If errors should be computed, then schedule [LIBRARY_ERRORS_READY] instead,
   * it also computes [RESOLVED_UNIT] in process.
   */
  void _schedulePriorityLibrarySourceAnalysis(Source librarySource) {
    bool needErrors = _shouldErrorsBeComputed(librarySource);
    if (needErrors) {
      addPriorityResult(librarySource, LIBRARY_ERRORS_READY);
    } else {
      var target = new LibrarySpecificUnit(librarySource, librarySource);
      addPriorityResult(target, RESOLVED_UNIT);
    }
  }

  bool _shouldErrorsBeComputed(Source source) =>
      context.shouldErrorsBeAnalyzed(source);

  static bool _isDartSource(AnalysisTarget target) {
    return target is Source && AnalysisEngine.isDartFileName(target.fullName);
  }
}
