| OLD | NEW |
| 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, 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 analysis.server; | 5 library analysis.server; |
| 6 | 6 |
| 7 import 'dart:async'; | 7 import 'dart:async'; |
| 8 import 'dart:collection'; | 8 import 'dart:collection'; |
| 9 | 9 |
| 10 import 'package:analyzer/file_system/file_system.dart'; | 10 import 'package:analyzer/file_system/file_system.dart'; |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 49 AnalysisContext context = AnalysisEngine.instance.createAnalysisContext(); | 49 AnalysisContext context = AnalysisEngine.instance.createAnalysisContext(); |
| 50 analysisServer.folderMap[folder] = context; | 50 analysisServer.folderMap[folder] = context; |
| 51 context.sourceFactory = _createSourceFactory(packageMap); | 51 context.sourceFactory = _createSourceFactory(packageMap); |
| 52 context.analysisOptions = new AnalysisOptionsImpl.con1(defaultOptions); | 52 context.analysisOptions = new AnalysisOptionsImpl.con1(defaultOptions); |
| 53 analysisServer.schedulePerformAnalysisOperation(context); | 53 analysisServer.schedulePerformAnalysisOperation(context); |
| 54 } | 54 } |
| 55 | 55 |
| 56 @override | 56 @override |
| 57 void applyChangesToContext(Folder contextFolder, ChangeSet changeSet) { | 57 void applyChangesToContext(Folder contextFolder, ChangeSet changeSet) { |
| 58 AnalysisContext context = analysisServer.folderMap[contextFolder]; | 58 AnalysisContext context = analysisServer.folderMap[contextFolder]; |
| 59 context.applyChanges(changeSet); | 59 if (context != null) { |
| 60 analysisServer.schedulePerformAnalysisOperation(context); | 60 context.applyChanges(changeSet); |
| 61 analysisServer.schedulePerformAnalysisOperation(context); |
| 62 } |
| 61 } | 63 } |
| 62 | 64 |
| 63 @override | 65 @override |
| 64 void removeContext(Folder folder) { | 66 void removeContext(Folder folder) { |
| 65 analysisServer.folderMap.remove(folder); | 67 AnalysisContext context = analysisServer.folderMap.remove(folder); |
| 68 analysisServer.sendContextAnalysisCancelledNotifications( |
| 69 context, |
| 70 'Context was removed'); |
| 66 } | 71 } |
| 67 | 72 |
| 68 @override | 73 @override |
| 69 void updateContextPackageMap(Folder contextFolder, | 74 void updateContextPackageMap(Folder contextFolder, |
| 70 Map<String, List<Folder>> packageMap) { | 75 Map<String, List<Folder>> packageMap) { |
| 71 AnalysisContext context = analysisServer.folderMap[contextFolder]; | 76 AnalysisContext context = analysisServer.folderMap[contextFolder]; |
| 72 context.sourceFactory = _createSourceFactory(packageMap); | 77 context.sourceFactory = _createSourceFactory(packageMap); |
| 73 analysisServer.schedulePerformAnalysisOperation(context); | 78 analysisServer.schedulePerformAnalysisOperation(context); |
| 74 } | 79 } |
| 75 | 80 |
| (...skipping 489 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 565 // if library has not been resolved yet, the unit will be resolved later | 570 // if library has not been resolved yet, the unit will be resolved later |
| 566 Source librarySource = librarySources[0]; | 571 Source librarySource = librarySources[0]; |
| 567 if (context.getLibraryElement(librarySource) == null) { | 572 if (context.getLibraryElement(librarySource) == null) { |
| 568 return null; | 573 return null; |
| 569 } | 574 } |
| 570 // if library has been already resolved, resolve unit | 575 // if library has been already resolved, resolve unit |
| 571 return context.resolveCompilationUnit2(unitSource, librarySource); | 576 return context.resolveCompilationUnit2(unitSource, librarySource); |
| 572 } | 577 } |
| 573 | 578 |
| 574 /** | 579 /** |
| 575 * Returns all the [AnalysisErrorInfo] for [file]. | 580 * Return an analysis error info containing the array of all of the errors and |
| 576 * It does not wait for all errors to be computed, and returns just the | 581 * the line info associated with [file]. |
| 577 * current state. | |
| 578 * | 582 * |
| 579 * May return `null`. | 583 * Returns `null` if [file] does not belong to any [AnalysisContext]. |
| 584 * |
| 585 * The array of errors will be empty if [file] does not exist or if there are |
| 586 * no errors in [file]. The errors contained in the array can be incomplete. |
| 587 * |
| 588 * This method does not wait for all errors to be computed, and returns just |
| 589 * the current state. |
| 580 */ | 590 */ |
| 581 AnalysisErrorInfo getErrors(String file) { | 591 AnalysisErrorInfo getErrors(String file) { |
| 582 // prepare AnalysisContext | 592 // prepare AnalysisContext |
| 583 AnalysisContext context = getAnalysisContext(file); | 593 AnalysisContext context = getAnalysisContext(file); |
| 584 if (context == null) { | 594 if (context == null) { |
| 585 return null; | 595 return null; |
| 586 } | 596 } |
| 587 // get errors for the file | 597 // get errors for the file |
| 588 Source source = getSource(file); | 598 Source source = getSource(file); |
| 589 return context.getErrors(source); | 599 return context.getErrors(source); |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 636 /** | 646 /** |
| 637 * Returns a [Future] completing when [file] has been completely analyzed, in | 647 * Returns a [Future] completing when [file] has been completely analyzed, in |
| 638 * particular, all its errors have been computed. | 648 * particular, all its errors have been computed. |
| 639 * | 649 * |
| 640 * TODO(scheglov) this method should be improved. | 650 * TODO(scheglov) this method should be improved. |
| 641 * | 651 * |
| 642 * 1. The analysis context should be told to analyze this particular file ASAP
. | 652 * 1. The analysis context should be told to analyze this particular file ASAP
. |
| 643 * | 653 * |
| 644 * 2. We should complete the future as soon as the file is analyzed (not wait | 654 * 2. We should complete the future as soon as the file is analyzed (not wait |
| 645 * until the context is completely finished) | 655 * until the context is completely finished) |
| 646 * | |
| 647 * 3. Since contexts can be created and deleted asynchronously as a result of | |
| 648 * changes to the filesystem, there's a danger that the future might never | |
| 649 * get completed. We should add a mechanism to make sure that we return an | |
| 650 * error for any getErrors request that is unsatisfiable due to its context | |
| 651 * being deleted. | |
| 652 */ | 656 */ |
| 653 Future onFileAnalysisComplete(String file) { | 657 Future onFileAnalysisComplete(String file) { |
| 654 // prepare AnalysisContext | 658 // prepare AnalysisContext |
| 655 AnalysisContext context = getAnalysisContext(file); | 659 AnalysisContext context = getAnalysisContext(file); |
| 656 if (context == null) { | 660 if (context == null) { |
| 657 return new Future.value(); | 661 return new Future.value(); |
| 658 } | 662 } |
| 659 // schedule context analysis | 663 // schedule context analysis |
| 660 schedulePerformAnalysisOperation(context); | 664 schedulePerformAnalysisOperation(context); |
| 661 // associate with the context completer | 665 // associate with the context completer |
| 662 Completer completer = contextAnalysisDoneCompleters[context]; | 666 Completer completer = contextAnalysisDoneCompleters[context]; |
| 663 if (completer == null) { | 667 if (completer == null) { |
| 664 completer = new Completer(); | 668 completer = new Completer(); |
| 665 contextAnalysisDoneCompleters[context] = completer; | 669 contextAnalysisDoneCompleters[context] = completer; |
| 666 } | 670 } |
| 667 return completer.future; | 671 return completer.future; |
| 668 } | 672 } |
| 669 | 673 |
| 670 /** | 674 /** |
| 671 * This method is called when analysis of the given [AnalysisContext] is | 675 * This method is called when analysis of the given [AnalysisContext] is |
| 672 * done. | 676 * done. |
| 673 */ | 677 */ |
| 674 void sendContextAnalysisDoneNotifications(AnalysisContext context) { | 678 void sendContextAnalysisDoneNotifications(AnalysisContext context) { |
| 675 Completer completer = contextAnalysisDoneCompleters[context]; | 679 Completer completer = contextAnalysisDoneCompleters.remove(context); |
| 676 if (completer != null) { | 680 if (completer != null) { |
| 677 completer.complete(); | 681 completer.complete(); |
| 678 } | 682 } |
| 679 } | 683 } |
| 680 | 684 |
| 681 /** | 685 /** |
| 686 * This method is called when analysis of the given [AnalysisContext] is |
| 687 * cancelled. |
| 688 */ |
| 689 void sendContextAnalysisCancelledNotifications(AnalysisContext context, String
message) { |
| 690 Completer completer = contextAnalysisDoneCompleters.remove(context); |
| 691 if (completer != null) { |
| 692 completer.completeError(message); |
| 693 } |
| 694 } |
| 695 |
| 696 /** |
| 682 * Return the [CompilationUnit] of the Dart file with the given [path]. | 697 * Return the [CompilationUnit] of the Dart file with the given [path]. |
| 683 * Return `null` if the file is not a part of any context. | 698 * Return `null` if the file is not a part of any context. |
| 684 */ | 699 */ |
| 685 CompilationUnit test_getResolvedCompilationUnit(String path) { | 700 CompilationUnit test_getResolvedCompilationUnit(String path) { |
| 686 // prepare AnalysisContext | 701 // prepare AnalysisContext |
| 687 AnalysisContext context = getAnalysisContext(path); | 702 AnalysisContext context = getAnalysisContext(path); |
| 688 if (context == null) { | 703 if (context == null) { |
| 689 return null; | 704 return null; |
| 690 } | 705 } |
| 691 // prepare sources | 706 // prepare sources |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 737 /** | 752 /** |
| 738 * An enumeration of the services provided by the server domain. | 753 * An enumeration of the services provided by the server domain. |
| 739 */ | 754 */ |
| 740 class ServerService extends Enum2<ServerService> { | 755 class ServerService extends Enum2<ServerService> { |
| 741 static const ServerService STATUS = const ServerService('STATUS', 0); | 756 static const ServerService STATUS = const ServerService('STATUS', 0); |
| 742 | 757 |
| 743 static const List<ServerService> VALUES = const [STATUS]; | 758 static const List<ServerService> VALUES = const [STATUS]; |
| 744 | 759 |
| 745 const ServerService(String name, int ordinal) : super(name, ordinal); | 760 const ServerService(String name, int ordinal) : super(name, ordinal); |
| 746 } | 761 } |
| OLD | NEW |