Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(79)

Unified Diff: pkg/analysis_server/lib/src/services/index2/index2.dart

Issue 1778113002: Separate index objects for each analysis context. (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | pkg/analysis_server/test/services/index2/index2_test.dart » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: pkg/analysis_server/lib/src/services/index2/index2.dart
diff --git a/pkg/analysis_server/lib/src/services/index2/index2.dart b/pkg/analysis_server/lib/src/services/index2/index2.dart
index a3da32b1fdd3e94ebbb82a7f3b67e797284d6a26..6e6d704ac6fa7b62ce516ab8b29318ad97f49a4f 100644
--- a/pkg/analysis_server/lib/src/services/index2/index2.dart
+++ b/pkg/analysis_server/lib/src/services/index2/index2.dart
@@ -6,6 +6,7 @@ import 'dart:async';
import 'package:analyzer/dart/ast/ast.dart';
import 'package:analyzer/dart/element/element.dart';
+import 'package:analyzer/src/generated/engine.dart' show AnalysisContext;
import 'package:analyzer/src/generated/source.dart';
import 'package:analyzer/src/summary/format.dart';
import 'package:analyzer/src/summary/idl.dart';
@@ -16,8 +17,7 @@ import 'package:collection/collection.dart';
* Return a new [Index2] instance that keeps information in memory.
*/
Index2 createMemoryIndex2() {
- _MemoryPackageIndexStore store = new _MemoryPackageIndexStore();
- return new Index2(store);
+ return new Index2._();
}
/**
@@ -41,71 +41,80 @@ int _findFirstOccurrence(List<int> sortedList, int value) {
* Interface for storing and requesting relations.
*/
class Index2 {
- final PackageIndexStore _store;
+ final Map<AnalysisContext, _ContextIndex> _contextIndexMap =
+ <AnalysisContext, _ContextIndex>{};
- Index2(this._store);
+ Index2._();
/**
* Complete with a list of locations where elements of the given [kind] with
* names satisfying the given [regExp] are defined.
*/
- Future<List<Location>> getDefinedNames(
- RegExp regExp, IndexNameKind kind) async {
- List<Location> locations = <Location>[];
- Iterable<PackageIndexId> ids = await _store.getIds();
- for (PackageIndexId id in ids) {
- PackageIndex index = await _store.getIndex(id);
- _PackageIndexRequester requester = new _PackageIndexRequester(index);
- List<Location> packageLocations = requester.getDefinedNames(regExp, kind);
- locations.addAll(packageLocations);
- }
- return locations;
+ Future<List<Location>> getDefinedNames(RegExp regExp, IndexNameKind kind) {
+ return _mergeLocations((_ContextIndex index) {
+ return index.getDefinedNames(regExp, kind);
+ });
}
/**
* Complete with a list of locations where the given [element] has relation
* of the given [kind].
*/
- Future<List<Location>> getRelations(
- Element element, IndexRelationKind kind) async {
- List<Location> locations = <Location>[];
- Iterable<PackageIndexId> ids = await _store.getIds();
- for (PackageIndexId id in ids) {
- PackageIndex index = await _store.getIndex(id);
- _PackageIndexRequester requester = new _PackageIndexRequester(index);
- List<Location> packageLocations = requester.getRelations(element, kind);
- locations.addAll(packageLocations);
- }
- return locations;
+ Future<List<Location>> getRelations(Element element, IndexRelationKind kind) {
+ return _mergeLocations((_ContextIndex index) {
+ return index.getRelations(element, kind);
+ });
}
/**
* Complete with a list of locations where a class members with the given
* [name] is referenced with a qualifier, but is not resolved.
*/
- Future<List<Location>> getUnresolvedMemberReferences(String name) async {
- List<Location> locations = <Location>[];
- Iterable<PackageIndexId> ids = await _store.getIds();
- for (PackageIndexId id in ids) {
- PackageIndex index = await _store.getIndex(id);
- _PackageIndexRequester requester = new _PackageIndexRequester(index);
- List<Location> packageLocations =
- requester.getUnresolvedMemberReferences(name);
- locations.addAll(packageLocations);
- }
- return locations;
+ Future<List<Location>> getUnresolvedMemberReferences(String name) {
+ return _mergeLocations((_ContextIndex index) {
+ return index.getUnresolvedMemberReferences(name);
+ });
}
/**
* Index the given fully resolved [unit].
*/
void indexUnit(CompilationUnit unit) {
- PackageIndexAssembler assembler = new PackageIndexAssembler();
- assembler.index(unit);
- PackageIndexBuilder indexBuilder = assembler.assemble();
- String unitLibraryUri = unit.element.library.source.uri.toString();
- String unitUnitUri = unit.element.source.uri.toString();
- _store.putIndex(unitLibraryUri, unitUnitUri, indexBuilder);
+ if (unit == null || unit.element == null) {
+ return;
+ }
+ AnalysisContext context = unit.element.context;
+ _getContextIndex(context).indexUnit(unit);
+ }
+
+ /**
+ * Remove all index information for the given [context].
+ */
+ void removeContext(AnalysisContext context) {
+ _contextIndexMap.remove(context);
+ }
+
+ /**
+ * Return the [_ContextIndex] instance for the given [context].
+ */
+ _ContextIndex _getContextIndex(AnalysisContext context) {
+ return _contextIndexMap.putIfAbsent(context, () {
+ return new _ContextIndex(context);
+ });
+ }
+
+ /**
+ * Complete with a list of all results returned by the [callback] for every
+ * context specific index.
+ */
+ Future<List<Location>> _mergeLocations(
+ Future<List<Location>> callback(_ContextIndex index)) async {
+ List<Location> locations = <Location>[];
+ for (_ContextIndex index in _contextIndexMap.values) {
+ List<Location> contextLocations = await callback(index);
+ locations.addAll(contextLocations);
+ }
+ return locations;
}
}
@@ -119,6 +128,11 @@ class Index2 {
*/
class Location {
/**
+ * The [AnalysisContext] containing this location.
+ */
+ final AnalysisContext context;
+
+ /**
* The URI of the source of the library containing this location.
*/
final String libraryUri;
@@ -143,8 +157,8 @@ class Location {
*/
final bool isQualified;
- Location(this.libraryUri, this.unitUri, this.offset, this.length,
- this.isQualified);
+ Location(this.context, this.libraryUri, this.unitUri, this.offset,
+ this.length, this.isQualified);
@override
String toString() => 'Location{librarySourceUri: $libraryUri, '
@@ -179,38 +193,84 @@ abstract class PackageIndexStore {
}
/**
- * A [PackageIndexId] for [_MemoryPackageIndexStore].
+ * The [AnalysisContext] specific index.
*/
-class _MemoryPackageIndexId implements PackageIndexId {
- final String key;
+class _ContextIndex {
+ final AnalysisContext context;
+ final Map<String, PackageIndex> indexMap = <String, PackageIndex>{};
- _MemoryPackageIndexId(this.key);
-}
+ _ContextIndex(this.context);
-/**
- * A [PackageIndexStore] that keeps objects in memory;
- */
-class _MemoryPackageIndexStore implements PackageIndexStore {
- final Map<String, PackageIndex> indexMap = <String, PackageIndex>{};
+ /**
+ * Complete with a list of locations where elements of the given [kind] with
+ * names satisfying the given [regExp] are defined.
+ */
+ Future<List<Location>> getDefinedNames(
+ RegExp regExp, IndexNameKind kind) async {
+ return _mergeLocations((PackageIndex index) {
+ _PackageIndexRequester requester = new _PackageIndexRequester(index);
+ return requester.getDefinedNames(context, regExp, kind);
+ });
+ }
- @override
- Future<Iterable<PackageIndexId>> getIds() async {
- return indexMap.keys.map((key) => new _MemoryPackageIndexId(key));
+ /**
+ * Complete with a list of locations where the given [element] has relation
+ * of the given [kind].
+ */
+ Future<List<Location>> getRelations(Element element, IndexRelationKind kind) {
+ return _mergeLocations((PackageIndex index) {
+ _PackageIndexRequester requester = new _PackageIndexRequester(index);
+ return requester.getRelations(context, element, kind);
+ });
}
- @override
- Future<PackageIndex> getIndex(PackageIndexId id) async {
- return indexMap[(id as _MemoryPackageIndexId).key];
+ /**
+ * Complete with a list of locations where a class members with the given
+ * [name] is referenced with a qualifier, but is not resolved.
+ */
+ Future<List<Location>> getUnresolvedMemberReferences(String name) async {
+ return _mergeLocations((PackageIndex index) {
+ _PackageIndexRequester requester = new _PackageIndexRequester(index);
+ return requester.getUnresolvedMemberReferences(context, name);
+ });
}
- @override
- putIndex(String unitLibraryUri, String unitUnitUri,
- PackageIndexBuilder indexBuilder) {
+ /**
+ * Index the given fully resolved [unit].
+ */
+ void indexUnit(CompilationUnit unit) {
+ // Index the unit.
+ PackageIndexAssembler assembler = new PackageIndexAssembler();
+ assembler.index(unit);
+ PackageIndexBuilder indexBuilder = assembler.assemble();
+ // Put the index into the map.
List<int> indexBytes = indexBuilder.toBuffer();
PackageIndex index = new PackageIndex.fromBuffer(indexBytes);
- String key = '$unitLibraryUri;$unitUnitUri';
+ String key = _getUnitKeyForElement(unit.element);
indexMap[key] = index;
}
+
+ String _getUnitKeyForElement(CompilationUnitElement unitElement) {
+ Source librarySource = unitElement.library.source;
+ Source unitSource = unitElement.source;
+ return _getUnitKeyForSource(librarySource, unitSource);
+ }
+
+ String _getUnitKeyForSource(Source librarySource, Source unitSource) {
+ String unitLibraryUri = librarySource.uri.toString();
+ String unitUnitUri = unitSource.uri.toString();
+ return '$unitLibraryUri;$unitUnitUri';
+ }
+
+ Future<List<Location>> _mergeLocations(
+ List<Location> callback(PackageIndex index)) async {
+ List<Location> locations = <Location>[];
+ for (PackageIndex index in indexMap.values) {
+ List<Location> indexLocations = callback(index);
+ locations.addAll(indexLocations);
+ }
+ return locations;
+ }
}
/**
@@ -260,11 +320,13 @@ class _PackageIndexRequester {
* Complete with a list of locations where elements of the given [kind] with
* names satisfying the given [regExp] are defined.
*/
- List<Location> getDefinedNames(RegExp regExp, IndexNameKind kind) {
+ List<Location> getDefinedNames(
+ AnalysisContext context, RegExp regExp, IndexNameKind kind) {
List<Location> locations = <Location>[];
for (UnitIndex unitIndex in index.units) {
_UnitIndexRequester requester = new _UnitIndexRequester(this, unitIndex);
- List<Location> unitLocations = requester.getDefinedNames(regExp, kind);
+ List<Location> unitLocations =
+ requester.getDefinedNames(context, regExp, kind);
locations.addAll(unitLocations);
}
return locations;
@@ -274,7 +336,8 @@ class _PackageIndexRequester {
* Complete with a list of locations where the given [element] has relation
* of the given [kind].
*/
- List<Location> getRelations(Element element, IndexRelationKind kind) {
+ List<Location> getRelations(
+ AnalysisContext context, Element element, IndexRelationKind kind) {
int elementId = findElementId(element);
if (elementId == -1) {
return const <Location>[];
@@ -282,7 +345,8 @@ class _PackageIndexRequester {
List<Location> locations = <Location>[];
for (UnitIndex unitIndex in index.units) {
_UnitIndexRequester requester = new _UnitIndexRequester(this, unitIndex);
- List<Location> unitLocations = requester.getRelations(elementId, kind);
+ List<Location> unitLocations =
+ requester.getRelations(context, elementId, kind);
locations.addAll(unitLocations);
}
return locations;
@@ -340,12 +404,13 @@ class _PackageIndexRequester {
* Complete with a list of locations where a class members with the given
* [name] is referenced with a qualifier, but is not resolved.
*/
- List<Location> getUnresolvedMemberReferences(String name) {
+ List<Location> getUnresolvedMemberReferences(
+ AnalysisContext context, String name) {
List<Location> locations = <Location>[];
for (UnitIndex unitIndex in index.units) {
_UnitIndexRequester requester = new _UnitIndexRequester(this, unitIndex);
List<Location> unitLocations =
- requester.getUnresolvedMemberReferences(name);
+ requester.getUnresolvedMemberReferences(context, name);
locations.addAll(unitLocations);
}
return locations;
@@ -374,7 +439,8 @@ class _UnitIndexRequester {
* Complete with a list of locations where elements of the given [kind] with
* names satisfying the given [regExp] are defined.
*/
- List<Location> getDefinedNames(RegExp regExp, IndexNameKind kind) {
+ List<Location> getDefinedNames(
+ AnalysisContext context, RegExp regExp, IndexNameKind kind) {
List<Location> locations = <Location>[];
String unitLibraryUri = null;
String unitUnitUri = null;
@@ -385,7 +451,7 @@ class _UnitIndexRequester {
if (regExp.matchAsPrefix(name) != null) {
unitLibraryUri ??= packageRequester.getUnitLibraryUri(unitIndex.unit);
unitUnitUri ??= packageRequester.getUnitUnitUri(unitIndex.unit);
- locations.add(new Location(unitLibraryUri, unitUnitUri,
+ locations.add(new Location(context, unitLibraryUri, unitUnitUri,
unitIndex.definedNameOffsets[i], name.length, false));
}
}
@@ -397,7 +463,8 @@ class _UnitIndexRequester {
* Return a list of locations where an element with the given [elementId] has
* relation of the given [kind].
*/
- List<Location> getRelations(int elementId, IndexRelationKind kind) {
+ List<Location> getRelations(
+ AnalysisContext context, int elementId, IndexRelationKind kind) {
// Find the first usage of the element.
int i = _findFirstOccurrence(unitIndex.usedElements, elementId);
if (i == -1) {
@@ -415,6 +482,7 @@ class _UnitIndexRequester {
unitLibraryUri ??= packageRequester.getUnitLibraryUri(unitIndex.unit);
unitUnitUri ??= packageRequester.getUnitUnitUri(unitIndex.unit);
locations.add(new Location(
+ context,
unitLibraryUri,
unitUnitUri,
unitIndex.usedElementOffsets[i],
@@ -429,14 +497,15 @@ class _UnitIndexRequester {
* Complete with a list of locations where a class members with the given
* [name] is referenced with a qualifier, but is not resolved.
*/
- List<Location> getUnresolvedMemberReferences(String name) {
+ List<Location> getUnresolvedMemberReferences(
+ AnalysisContext context, String name) {
// Find the name ID in the package index.
int nameId = packageRequester.getStringId(name);
if (nameId == -1) {
return const <Location>[];
}
// Find the first usage of the name.
- int i =_findFirstOccurrence(unitIndex.usedNames, nameId);
+ int i = _findFirstOccurrence(unitIndex.usedNames, nameId);
if (i == -1) {
return const <Location>[];
}
@@ -444,11 +513,12 @@ class _UnitIndexRequester {
List<Location> locations = <Location>[];
String unitLibraryUri = null;
String unitUnitUri = null;
- for (; i < unitIndex.usedNames.length &&
- unitIndex.usedNames[i] == nameId; i++) {
+ for (;
+ i < unitIndex.usedNames.length && unitIndex.usedNames[i] == nameId;
+ i++) {
unitLibraryUri ??= packageRequester.getUnitLibraryUri(unitIndex.unit);
unitUnitUri ??= packageRequester.getUnitUnitUri(unitIndex.unit);
- locations.add(new Location(unitLibraryUri, unitUnitUri,
+ locations.add(new Location(context, unitLibraryUri, unitUnitUri,
unitIndex.usedNameOffsets[i], name.length, true));
}
return locations;
« no previous file with comments | « no previous file | pkg/analysis_server/test/services/index2/index2_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698