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

Side by Side Diff: pkg/analysis_server/lib/src/context_directory_manager.dart

Issue 341123007: Rerun "pub list" when pubspec.lock changes. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 6 years, 5 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 unified diff | Download patch | Annotate | Revision Log
OLDNEW
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 context.directory.manager; 5 library context.directory.manager;
6 6
7 import 'dart:async'; 7 import 'dart:async';
8 import 'dart:collection'; 8 import 'dart:collection';
9 9
10 import 'package:analysis_server/src/package_map_provider.dart';
10 import 'package:analysis_server/src/resource.dart'; 11 import 'package:analysis_server/src/resource.dart';
11 import 'package:analyzer/src/generated/engine.dart'; 12 import 'package:analyzer/src/generated/engine.dart';
12 import 'package:analyzer/src/generated/source.dart'; 13 import 'package:analyzer/src/generated/source.dart';
13 import 'package:watcher/watcher.dart'; 14 import 'package:watcher/watcher.dart';
14 15
15 /** 16 /**
16 * Information tracked by the [ContextDirectoryManager] for each context. 17 * Information tracked by the [ContextDirectoryManager] for each context.
17 */ 18 */
18 class _ContextDirectoryInfo { 19 class _ContextDirectoryInfo {
19 /** 20 /**
20 * Stream subscription we are using to watch the context's directory for 21 * Stream subscription we are using to watch the context's directory for
21 * changes. 22 * changes.
22 */ 23 */
23 StreamSubscription<WatchEvent> changeSubscription; 24 StreamSubscription<WatchEvent> changeSubscription;
24 25
25 /** 26 /**
26 * Map from full path to the [Source] object, for each source that has been 27 * Map from full path to the [Source] object, for each source that has been
27 * added to the context. 28 * added to the context.
28 */ 29 */
29 Map<String, Source> sources = new HashMap<String, Source>(); 30 Map<String, Source> sources = new HashMap<String, Source>();
31
32 /**
33 * Dependencies of the context's package map. If any of these files changes,
34 * the package map needs to be recomputed.
35 */
36 Set<String> packageMapDependencies;
30 } 37 }
31 38
32 /** 39 /**
33 * Class that maintains a mapping from included/excluded paths to a set of 40 * Class that maintains a mapping from included/excluded paths to a set of
34 * folders that should correspond to analysis contexts. 41 * folders that should correspond to analysis contexts.
35 */ 42 */
36 abstract class ContextDirectoryManager { 43 abstract class ContextDirectoryManager {
37 /** 44 /**
38 * File name of pubspec files. 45 * File name of pubspec files.
39 */ 46 */
40 static const String PUBSPEC_NAME = 'pubspec.yaml'; 47 static const String PUBSPEC_NAME = 'pubspec.yaml';
41 48
42 /** 49 /**
43 * [_ContextDirectoryInfo] object for each included directory in the most 50 * [_ContextDirectoryInfo] object for each included directory in the most
44 * recent successful call to [setRoots]. 51 * recent successful call to [setRoots].
45 */ 52 */
46 Map<Folder, _ContextDirectoryInfo> _currentDirectoryInfo = 53 Map<Folder, _ContextDirectoryInfo> _currentDirectoryInfo =
47 new HashMap<Folder, _ContextDirectoryInfo>(); 54 new HashMap<Folder, _ContextDirectoryInfo>();
48 55
49 /** 56 /**
50 * The [ResourceProvider] using which paths are converted into [Resource]s. 57 * The [ResourceProvider] using which paths are converted into [Resource]s.
51 */ 58 */
52 final ResourceProvider resourceProvider; 59 final ResourceProvider resourceProvider;
53 60
54 ContextDirectoryManager(this.resourceProvider); 61 /**
62 * Provider which is used to determine the mapping from package name to
63 * package folder.
64 */
65 final PackageMapProvider packageMapProvider;
66
67 ContextDirectoryManager(this.resourceProvider, this.packageMapProvider);
55 68
56 /** 69 /**
57 * Change the set of paths which should be used as starting points to 70 * Change the set of paths which should be used as starting points to
58 * determine the context directories. 71 * determine the context directories.
59 */ 72 */
60 void setRoots(List<String> includedPaths, 73 void setRoots(List<String> includedPaths,
61 List<String> excludedPaths) { 74 List<String> excludedPaths) {
62 // included 75 // included
63 Set<Folder> includedFolders = new HashSet<Folder>(); 76 Set<Folder> includedFolders = new HashSet<Folder>();
64 for (int i = 0; i < includedPaths.length; i++) { 77 for (int i = 0; i < includedPaths.length; i++) {
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
97 /** 110 /**
98 * Create a new context associated with the given folder. 111 * Create a new context associated with the given folder.
99 */ 112 */
100 void _createContext(Folder folder) { 113 void _createContext(Folder folder) {
101 _ContextDirectoryInfo info = new _ContextDirectoryInfo(); 114 _ContextDirectoryInfo info = new _ContextDirectoryInfo();
102 _currentDirectoryInfo[folder] = info; 115 _currentDirectoryInfo[folder] = info;
103 info.changeSubscription = folder.changes.listen((WatchEvent event) { 116 info.changeSubscription = folder.changes.listen((WatchEvent event) {
104 _handleWatchEvent(folder, info, event); 117 _handleWatchEvent(folder, info, event);
105 }); 118 });
106 File pubspecFile = folder.getChild(PUBSPEC_NAME); 119 File pubspecFile = folder.getChild(PUBSPEC_NAME);
107 addContext(folder); 120 PackageMapInfo packageMapInfo = packageMapProvider.computePackageMap(folder) ;
121 info.packageMapDependencies = packageMapInfo.dependencies;
122 // TODO(paulberry): if any of the dependencies is outside of [folder],
123 // we'll need to watch their parent folders as well.
124 addContext(folder, packageMapInfo.packageMap);
108 ChangeSet changeSet = new ChangeSet(); 125 ChangeSet changeSet = new ChangeSet();
109 _addSourceFiles(changeSet, folder, info); 126 _addSourceFiles(changeSet, folder, info);
110 applyChangesToContext(folder, changeSet); 127 applyChangesToContext(folder, changeSet);
111 } 128 }
112 129
113 /** 130 /**
114 * Clean up and destroy the context associated with the given folder. 131 * Clean up and destroy the context associated with the given folder.
115 */ 132 */
116 void _destroyContext(Folder folder) { 133 void _destroyContext(Folder folder) {
117 _currentDirectoryInfo[folder].changeSubscription.cancel(); 134 _currentDirectoryInfo[folder].changeSubscription.cancel();
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
153 break; 170 break;
154 case ChangeType.MODIFY: 171 case ChangeType.MODIFY:
155 Source source = info.sources[event.path]; 172 Source source = info.sources[event.path];
156 if (source != null) { 173 if (source != null) {
157 ChangeSet changeSet = new ChangeSet(); 174 ChangeSet changeSet = new ChangeSet();
158 changeSet.changedSource(source); 175 changeSet.changedSource(source);
159 applyChangesToContext(folder, changeSet); 176 applyChangesToContext(folder, changeSet);
160 } 177 }
161 break; 178 break;
162 } 179 }
180
181 if (info.packageMapDependencies.contains(event.path)) {
182 // TODO(paulberry): when computePackageMap is changed into an
183 // asynchronous API call, we'll want to suspend analysis for this context
184 // while we're rerunning "pub list", since any analysis we complete while
185 // "pub list" is in progress is just going to get thrown away anyhow.
186 PackageMapInfo packageMapInfo = packageMapProvider.computePackageMap(folde r);
187 info.packageMapDependencies = packageMapInfo.dependencies;
188 updateContextPackageMap(folder, packageMapInfo.packageMap);
189 }
163 } 190 }
164 191
165 /** 192 /**
166 * Determine if the path from [folder] to [path] contains a 'packages' 193 * Determine if the path from [folder] to [path] contains a 'packages'
167 * directory. 194 * directory.
168 */ 195 */
169 bool _isInPackagesDir(String path, Folder folder) { 196 bool _isInPackagesDir(String path, Folder folder) {
170 String relativePath = resourceProvider.pathContext.relative(path, from: fold er.path); 197 String relativePath = resourceProvider.pathContext.relative(path, from: fold er.path);
171 List<String> pathParts = resourceProvider.pathContext.split(relativePath); 198 List<String> pathParts = resourceProvider.pathContext.split(relativePath);
172 for (int i = 0; i < pathParts.length - 1; i++) { 199 for (int i = 0; i < pathParts.length - 1; i++) {
(...skipping 28 matching lines...) Expand all
201 } 228 }
202 229
203 static bool _shouldFileBeAnalyzed(String path) { 230 static bool _shouldFileBeAnalyzed(String path) {
204 return AnalysisEngine.isDartFileName(path) 231 return AnalysisEngine.isDartFileName(path)
205 || AnalysisEngine.isHtmlFileName(path); 232 || AnalysisEngine.isHtmlFileName(path);
206 } 233 }
207 234
208 /** 235 /**
209 * Called when a new context needs to be created. 236 * Called when a new context needs to be created.
210 */ 237 */
211 void addContext(Folder folder); 238 void addContext(Folder folder, Map<String, List<Folder>> packageMap);
212 239
213 /** 240 /**
214 * Called when the set of files associated with a context have changed (or 241 * Called when the set of files associated with a context have changed (or
215 * some of those files have been modified). [changeSet] is the set of 242 * some of those files have been modified). [changeSet] is the set of
216 * changes that need to be applied to the context. 243 * changes that need to be applied to the context.
217 */ 244 */
218 void applyChangesToContext(Folder contextFolder, ChangeSet changeSet); 245 void applyChangesToContext(Folder contextFolder, ChangeSet changeSet);
219 246
220 /** 247 /**
221 * Remove the context associated with the given [folder]. 248 * Remove the context associated with the given [folder].
222 */ 249 */
223 void removeContext(Folder folder); 250 void removeContext(Folder folder);
251
252 /**
253 * Called when the package map for a context has changed.
254 */
255 void updateContextPackageMap(Folder contextFolder,
256 Map<String, List<Folder>> packageMap);
224 } 257 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698