OLD | NEW |
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 library services.completion.dart.manager; | 5 library services.completion.dart.manager; |
6 | 6 |
7 import 'dart:async'; | 7 import 'dart:async'; |
8 | 8 |
9 import 'package:analysis_server/plugin/protocol/protocol.dart'; | 9 import 'package:analysis_server/plugin/protocol/protocol.dart'; |
10 import 'package:analysis_server/src/provisional/completion/completion_core.dart' | 10 import 'package:analysis_server/src/provisional/completion/completion_core.dart' |
11 show CompletionContributor, CompletionRequest; | 11 show CompletionContributor, CompletionRequest; |
12 import 'package:analysis_server/src/provisional/completion/dart/completion_dart.
dart'; | 12 import 'package:analysis_server/src/provisional/completion/dart/completion_dart.
dart'; |
13 import 'package:analysis_server/src/provisional/completion/dart/completion_plugi
n.dart'; | 13 import 'package:analysis_server/src/provisional/completion/dart/completion_plugi
n.dart'; |
14 import 'package:analysis_server/src/provisional/completion/dart/completion_targe
t.dart'; | 14 import 'package:analysis_server/src/provisional/completion/dart/completion_targe
t.dart'; |
15 import 'package:analysis_server/src/services/completion/completion_core.dart'; | 15 import 'package:analysis_server/src/services/completion/completion_core.dart'; |
16 import 'package:analysis_server/src/services/completion/completion_performance.d
art'; | 16 import 'package:analysis_server/src/services/completion/completion_performance.d
art'; |
17 import 'package:analysis_server/src/services/completion/dart/common_usage_sorter
.dart'; | 17 import 'package:analysis_server/src/services/completion/dart/common_usage_sorter
.dart'; |
18 import 'package:analysis_server/src/services/completion/dart/contribution_sorter
.dart'; | 18 import 'package:analysis_server/src/services/completion/dart/contribution_sorter
.dart'; |
19 import 'package:analysis_server/src/services/completion/dart/optype.dart'; | 19 import 'package:analysis_server/src/services/completion/dart/optype.dart'; |
20 import 'package:analysis_server/src/services/search/search_engine.dart'; | 20 import 'package:analysis_server/src/services/search/search_engine.dart'; |
21 import 'package:analyzer/dart/ast/ast.dart'; | 21 import 'package:analyzer/dart/ast/ast.dart'; |
22 import 'package:analyzer/dart/ast/token.dart'; | 22 import 'package:analyzer/dart/ast/token.dart'; |
23 import 'package:analyzer/dart/element/element.dart'; | 23 import 'package:analyzer/dart/element/element.dart'; |
24 import 'package:analyzer/dart/element/type.dart'; | 24 import 'package:analyzer/dart/element/type.dart'; |
25 import 'package:analyzer/exception/exception.dart'; | 25 import 'package:analyzer/exception/exception.dart'; |
26 import 'package:analyzer/file_system/file_system.dart'; | 26 import 'package:analyzer/file_system/file_system.dart'; |
27 import 'package:analyzer/src/context/context.dart' show AnalysisFutureHelper; | 27 import 'package:analyzer/src/context/context.dart' show AnalysisFutureHelper; |
| 28 import 'package:analyzer/src/dart/analysis/driver.dart'; |
28 import 'package:analyzer/src/dart/ast/token.dart'; | 29 import 'package:analyzer/src/dart/ast/token.dart'; |
29 import 'package:analyzer/src/generated/engine.dart'; | 30 import 'package:analyzer/src/generated/engine.dart' hide AnalysisResult; |
30 import 'package:analyzer/src/generated/source.dart'; | 31 import 'package:analyzer/src/generated/source.dart'; |
31 import 'package:analyzer/src/task/dart.dart'; | 32 import 'package:analyzer/src/task/dart.dart'; |
32 import 'package:analyzer/task/dart.dart'; | 33 import 'package:analyzer/task/dart.dart'; |
33 import 'package:analyzer/task/model.dart'; | 34 import 'package:analyzer/task/model.dart'; |
34 | 35 |
35 /** | 36 /** |
36 * [DartCompletionManager] determines if a completion request is Dart specific | 37 * [DartCompletionManager] determines if a completion request is Dart specific |
37 * and forwards those requests to all [DartCompletionContributor]s. | 38 * and forwards those requests to all [DartCompletionContributor]s. |
38 */ | 39 */ |
39 class DartCompletionManager implements CompletionContributor { | 40 class DartCompletionManager implements CompletionContributor { |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
99 request.checkAborted(); | 100 request.checkAborted(); |
100 return suggestions; | 101 return suggestions; |
101 } | 102 } |
102 } | 103 } |
103 | 104 |
104 /** | 105 /** |
105 * The information about a requested list of completions within a Dart file. | 106 * The information about a requested list of completions within a Dart file. |
106 */ | 107 */ |
107 class DartCompletionRequestImpl implements DartCompletionRequest { | 108 class DartCompletionRequestImpl implements DartCompletionRequest { |
108 @override | 109 @override |
| 110 final AnalysisResult result; |
| 111 |
| 112 @override |
109 final AnalysisContext context; | 113 final AnalysisContext context; |
110 | 114 |
111 @override | 115 @override |
112 final Source source; | 116 final Source source; |
113 | 117 |
114 @override | 118 @override |
115 final int offset; | 119 final int offset; |
116 | 120 |
117 @override | 121 @override |
118 Expression dotTarget; | 122 Expression dotTarget; |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
151 */ | 155 */ |
152 List<CompilationUnitElement> _resolvedUnits; | 156 List<CompilationUnitElement> _resolvedUnits; |
153 | 157 |
154 OpType _opType; | 158 OpType _opType; |
155 | 159 |
156 final CompletionRequest _originalRequest; | 160 final CompletionRequest _originalRequest; |
157 | 161 |
158 final CompletionPerformance performance; | 162 final CompletionPerformance performance; |
159 | 163 |
160 DartCompletionRequestImpl._( | 164 DartCompletionRequestImpl._( |
| 165 this.result, |
161 this.context, | 166 this.context, |
162 this.resourceProvider, | 167 this.resourceProvider, |
163 this.searchEngine, | 168 this.searchEngine, |
164 this.librarySource, | 169 this.librarySource, |
165 this.source, | 170 this.source, |
166 this.offset, | 171 this.offset, |
167 CompilationUnit unit, | 172 CompilationUnit unit, |
168 this._originalRequest, | 173 this._originalRequest, |
169 this.performance) { | 174 this.performance) { |
170 _updateTargets(unit); | 175 _updateTargets(unit); |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
247 } | 252 } |
248 | 253 |
249 // Gracefully degrade if librarySource cannot be determined | 254 // Gracefully degrade if librarySource cannot be determined |
250 if (librarySource == null) { | 255 if (librarySource == null) { |
251 return; | 256 return; |
252 } | 257 } |
253 | 258 |
254 // Resolve declarations in the target unit | 259 // Resolve declarations in the target unit |
255 // TODO(danrubel) resolve the expression or containing method | 260 // TODO(danrubel) resolve the expression or containing method |
256 // rather than the entire compilation unit | 261 // rather than the entire compilation unit |
257 CompilationUnit resolvedUnit = await _computeAsync( | 262 CompilationUnit resolvedUnit; |
258 this, | 263 if (result != null) { |
259 new LibrarySpecificUnit(librarySource, source), | 264 resolvedUnit = result.unit; |
260 RESOLVED_UNIT, | 265 } else { |
261 performance, | 266 resolvedUnit = await _computeAsync( |
262 'resolve expression'); | 267 this, |
| 268 new LibrarySpecificUnit(librarySource, source), |
| 269 RESOLVED_UNIT, |
| 270 performance, |
| 271 'resolve expression'); |
| 272 } |
263 | 273 |
264 // TODO(danrubel) determine if the underlying source has been modified | 274 // TODO(danrubel) determine if the underlying source has been modified |
265 // in a way that invalidates the completion request | 275 // in a way that invalidates the completion request |
266 // and return null | 276 // and return null |
267 | 277 |
268 // Gracefully degrade if unit cannot be resolved | 278 // Gracefully degrade if unit cannot be resolved |
269 if (resolvedUnit == null) { | 279 if (resolvedUnit == null) { |
270 return; | 280 return; |
271 } | 281 } |
272 | 282 |
(...skipping 22 matching lines...) Expand all Loading... |
295 } | 305 } |
296 return _resolvedImports; | 306 return _resolvedImports; |
297 } | 307 } |
298 | 308 |
299 @override | 309 @override |
300 Future<List<CompilationUnitElement>> resolveUnits() async { | 310 Future<List<CompilationUnitElement>> resolveUnits() async { |
301 checkAborted(); | 311 checkAborted(); |
302 if (_resolvedUnits != null) { | 312 if (_resolvedUnits != null) { |
303 return _resolvedUnits; | 313 return _resolvedUnits; |
304 } | 314 } |
| 315 if (result != null) { |
| 316 _resolvedUnits = result.unit.element.library.units; |
| 317 return _resolvedUnits; |
| 318 } |
305 LibraryElement libElem = libraryElement; | 319 LibraryElement libElem = libraryElement; |
306 if (libElem == null) { | 320 if (libElem == null) { |
307 return null; | 321 return null; |
308 } | 322 } |
309 _resolvedUnits = <CompilationUnitElement>[]; | 323 _resolvedUnits = <CompilationUnitElement>[]; |
310 for (CompilationUnitElement unresolvedUnit in libElem.units) { | 324 for (CompilationUnitElement unresolvedUnit in libElem.units) { |
311 CompilationUnit unit = await _computeAsync( | 325 CompilationUnit unit = await _computeAsync( |
312 this, | 326 this, |
313 new LibrarySpecificUnit(libElem.source, unresolvedUnit.source), | 327 new LibrarySpecificUnit(libElem.source, unresolvedUnit.source), |
314 RESOLVED_UNIT5, | 328 RESOLVED_UNIT5, |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
358 * if the completion request has been aborted. | 372 * if the completion request has been aborted. |
359 */ | 373 */ |
360 static Future<DartCompletionRequest> from(CompletionRequest request, | 374 static Future<DartCompletionRequest> from(CompletionRequest request, |
361 {ResultDescriptor resultDescriptor}) async { | 375 {ResultDescriptor resultDescriptor}) async { |
362 request.checkAborted(); | 376 request.checkAborted(); |
363 CompletionPerformance performance = | 377 CompletionPerformance performance = |
364 (request as CompletionRequestImpl).performance; | 378 (request as CompletionRequestImpl).performance; |
365 const BUILD_REQUEST_TAG = 'build DartCompletionRequest'; | 379 const BUILD_REQUEST_TAG = 'build DartCompletionRequest'; |
366 performance.logStartTime(BUILD_REQUEST_TAG); | 380 performance.logStartTime(BUILD_REQUEST_TAG); |
367 | 381 |
368 Source source = request.source; | 382 Source libSource; |
369 AnalysisContext context = request.context; | 383 CompilationUnit unit; |
| 384 if (request.context == null) { |
| 385 unit = request.result.unit; |
| 386 // TODO(scheglov) support for parts |
| 387 libSource = unit.element.source; |
| 388 } else { |
| 389 Source source = request.source; |
| 390 AnalysisContext context = request.context; |
370 | 391 |
371 const PARSE_TAG = 'parse unit'; | 392 const PARSE_TAG = 'parse unit'; |
372 performance.logStartTime(PARSE_TAG); | 393 performance.logStartTime(PARSE_TAG); |
373 CompilationUnit unit = request.context.computeResult(source, PARSED_UNIT); | 394 unit = request.context.computeResult(source, PARSED_UNIT); |
374 performance.logElapseTime(PARSE_TAG); | 395 performance.logElapseTime(PARSE_TAG); |
375 | 396 |
376 Source libSource; | 397 if (unit.directives.any((d) => d is PartOfDirective)) { |
377 if (unit.directives.any((d) => d is PartOfDirective)) { | 398 List<Source> libraries = context.getLibrariesContaining(source); |
378 List<Source> libraries = context.getLibrariesContaining(source); | 399 if (libraries.isNotEmpty) { |
379 if (libraries.isNotEmpty) { | 400 libSource = libraries[0]; |
380 libSource = libraries[0]; | 401 } |
| 402 } else { |
| 403 libSource = source; |
381 } | 404 } |
382 } else { | |
383 libSource = source; | |
384 } | |
385 | 405 |
386 // Most (all?) contributors need declarations in scope to be resolved | 406 // Most (all?) contributors need declarations in scope to be resolved |
387 if (libSource != null) { | 407 if (libSource != null) { |
388 unit = await _computeAsync( | 408 unit = await _computeAsync( |
389 request, | 409 request, |
390 new LibrarySpecificUnit(libSource, source), | 410 new LibrarySpecificUnit(libSource, source), |
391 resultDescriptor ?? RESOLVED_UNIT5, | 411 resultDescriptor ?? RESOLVED_UNIT5, |
392 performance, | 412 performance, |
393 'resolve declarations'); | 413 'resolve declarations'); |
| 414 } |
394 } | 415 } |
395 | 416 |
396 DartCompletionRequestImpl dartRequest = new DartCompletionRequestImpl._( | 417 DartCompletionRequestImpl dartRequest = new DartCompletionRequestImpl._( |
| 418 request.result, |
397 request.context, | 419 request.context, |
398 request.resourceProvider, | 420 request.resourceProvider, |
399 request.searchEngine, | 421 request.searchEngine, |
400 libSource, | 422 libSource, |
401 request.source, | 423 request.source, |
402 request.offset, | 424 request.offset, |
403 unit, | 425 unit, |
404 request, | 426 request, |
405 performance); | 427 performance); |
406 | 428 |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
493 if (start <= requestOffset && requestOffset <= end) { | 515 if (start <= requestOffset && requestOffset <= end) { |
494 // Replacement range for import URI | 516 // Replacement range for import URI |
495 return new ReplacementRange(start, end - start); | 517 return new ReplacementRange(start, end - start); |
496 } | 518 } |
497 } | 519 } |
498 } | 520 } |
499 } | 521 } |
500 return new ReplacementRange(requestOffset, 0); | 522 return new ReplacementRange(requestOffset, 0); |
501 } | 523 } |
502 } | 524 } |
OLD | NEW |