| 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 analyzer.file_system.memory_file_system; | 5 library analyzer.file_system.memory_file_system; |
| 6 | 6 |
| 7 import 'dart:async'; | 7 import 'dart:async'; |
| 8 import 'dart:collection'; | 8 import 'dart:collection'; |
| 9 import 'dart:core' hide Resource; | 9 import 'dart:core' hide Resource; |
| 10 | 10 |
| 11 import 'package:analyzer/file_system/file_system.dart'; | 11 import 'package:analyzer/file_system/file_system.dart'; |
| 12 import 'package:analyzer/src/generated/source_io.dart'; | 12 import 'package:analyzer/src/generated/source_io.dart'; |
| 13 import 'package:analyzer/src/source/source_resource.dart'; | 13 import 'package:analyzer/src/source/source_resource.dart'; |
| 14 import 'package:analyzer/src/util/absolute_path.dart'; | 14 import 'package:analyzer/src/util/absolute_path.dart'; |
| 15 import 'package:path/path.dart'; | 15 import 'package:path/path.dart'; |
| 16 import 'package:watcher/watcher.dart'; | 16 import 'package:watcher/watcher.dart'; |
| 17 | 17 |
| 18 /** | 18 /** |
| 19 * An in-memory implementation of [ResourceProvider]. | 19 * An in-memory implementation of [ResourceProvider]. |
| 20 * Use `/` as a path separator. | 20 * Use `/` as a path separator. |
| 21 */ | 21 */ |
| 22 class MemoryResourceProvider implements ResourceProvider { | 22 class MemoryResourceProvider implements ResourceProvider { |
| 23 final Map<String, _MemoryResource> _pathToResource = | 23 final Map<String, _MemoryResource> _pathToResource = |
| 24 new HashMap<String, _MemoryResource>(); | 24 new HashMap<String, _MemoryResource>(); |
| 25 final Map<String, String> _pathToContent = new HashMap<String, String>(); | 25 final Map<String, String> _pathToContent = new HashMap<String, String>(); |
| 26 final Map<String, List<int>> _pathToBytes = new HashMap<String, List<int>>(); | |
| 27 final Map<String, int> _pathToTimestamp = new HashMap<String, int>(); | 26 final Map<String, int> _pathToTimestamp = new HashMap<String, int>(); |
| 28 final Map<String, List<StreamController<WatchEvent>>> _pathToWatchers = | 27 final Map<String, List<StreamController<WatchEvent>>> _pathToWatchers = |
| 29 new HashMap<String, List<StreamController<WatchEvent>>>(); | 28 new HashMap<String, List<StreamController<WatchEvent>>>(); |
| 30 int nextStamp = 0; | 29 int nextStamp = 0; |
| 31 | 30 |
| 32 final Context _pathContext; | 31 final Context _pathContext; |
| 33 @override | 32 @override |
| 34 final AbsolutePathContext absolutePathContext; | 33 final AbsolutePathContext absolutePathContext; |
| 35 | 34 |
| 36 MemoryResourceProvider({bool isWindows: false}) | 35 MemoryResourceProvider({bool isWindows: false}) |
| (...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 128 _MemoryFile file = _newFile(path); | 127 _MemoryFile file = _newFile(path); |
| 129 _pathToContent[path] = content; | 128 _pathToContent[path] = content; |
| 130 _pathToTimestamp[path] = stamp ?? nextStamp++; | 129 _pathToTimestamp[path] = stamp ?? nextStamp++; |
| 131 _notifyWatchers(path, ChangeType.ADD); | 130 _notifyWatchers(path, ChangeType.ADD); |
| 132 return file; | 131 return file; |
| 133 } | 132 } |
| 134 | 133 |
| 135 File newFileWithBytes(String path, List<int> bytes, [int stamp]) { | 134 File newFileWithBytes(String path, List<int> bytes, [int stamp]) { |
| 136 path = pathContext.normalize(path); | 135 path = pathContext.normalize(path); |
| 137 _MemoryFile file = _newFile(path); | 136 _MemoryFile file = _newFile(path); |
| 138 _pathToBytes[path] = bytes; | 137 _pathToContent[path] = new String.fromCharCodes(bytes); |
| 139 _pathToTimestamp[path] = stamp ?? nextStamp++; | 138 _pathToTimestamp[path] = stamp ?? nextStamp++; |
| 140 _notifyWatchers(path, ChangeType.ADD); | 139 _notifyWatchers(path, ChangeType.ADD); |
| 141 return file; | 140 return file; |
| 142 } | 141 } |
| 143 | 142 |
| 144 Folder newFolder(String path) { | 143 Folder newFolder(String path) { |
| 145 path = pathContext.normalize(path); | 144 path = pathContext.normalize(path); |
| 146 if (!pathContext.isAbsolute(path)) { | 145 if (!pathContext.isAbsolute(path)) { |
| 147 throw new ArgumentError("Path must be absolute : $path"); | 146 throw new ArgumentError("Path must be absolute : $path"); |
| 148 } | 147 } |
| (...skipping 24 matching lines...) Expand all Loading... |
| 173 return file; | 172 return file; |
| 174 } | 173 } |
| 175 _MemoryResource existingNewResource = _pathToResource[newPath]; | 174 _MemoryResource existingNewResource = _pathToResource[newPath]; |
| 176 if (existingNewResource is _MemoryFolder) { | 175 if (existingNewResource is _MemoryFolder) { |
| 177 throw new FileSystemException( | 176 throw new FileSystemException( |
| 178 path, 'Could not be renamed: $newPath is a folder.'); | 177 path, 'Could not be renamed: $newPath is a folder.'); |
| 179 } | 178 } |
| 180 _MemoryFile newFile = _newFile(newPath); | 179 _MemoryFile newFile = _newFile(newPath); |
| 181 _pathToResource.remove(path); | 180 _pathToResource.remove(path); |
| 182 _pathToContent[newPath] = _pathToContent.remove(path); | 181 _pathToContent[newPath] = _pathToContent.remove(path); |
| 183 _pathToBytes[newPath] = _pathToBytes.remove(path); | |
| 184 _pathToTimestamp[newPath] = _pathToTimestamp.remove(path); | 182 _pathToTimestamp[newPath] = _pathToTimestamp.remove(path); |
| 185 if (existingNewResource != null) { | 183 if (existingNewResource != null) { |
| 186 _notifyWatchers(newPath, ChangeType.REMOVE); | 184 _notifyWatchers(newPath, ChangeType.REMOVE); |
| 187 } | 185 } |
| 188 _notifyWatchers(path, ChangeType.REMOVE); | 186 _notifyWatchers(path, ChangeType.REMOVE); |
| 189 _notifyWatchers(newPath, ChangeType.ADD); | 187 _notifyWatchers(newPath, ChangeType.ADD); |
| 190 return newFile; | 188 return newFile; |
| 191 } | 189 } |
| 192 | 190 |
| 193 File updateFile(String path, String content, [int stamp]) { | 191 File updateFile(String path, String content, [int stamp]) { |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 238 List<StreamController<WatchEvent>> streamControllers) { | 236 List<StreamController<WatchEvent>> streamControllers) { |
| 239 if (watcherPath == path || pathContext.isWithin(watcherPath, path)) { | 237 if (watcherPath == path || pathContext.isWithin(watcherPath, path)) { |
| 240 for (StreamController<WatchEvent> streamController | 238 for (StreamController<WatchEvent> streamController |
| 241 in streamControllers) { | 239 in streamControllers) { |
| 242 streamController.add(new WatchEvent(changeType, path)); | 240 streamController.add(new WatchEvent(changeType, path)); |
| 243 } | 241 } |
| 244 } | 242 } |
| 245 }); | 243 }); |
| 246 } | 244 } |
| 247 | 245 |
| 248 void _setFileBytes(_MemoryFile file, List<int> bytes) { | 246 void _setFileContent(_MemoryFile file, String content) { |
| 249 String path = file.path; | 247 String path = file.path; |
| 250 _pathToResource[path] = file; | 248 _pathToResource[path] = file; |
| 251 _pathToBytes[path] = bytes; | 249 _pathToContent[path] = content; |
| 252 _pathToTimestamp[path] = nextStamp++; | 250 _pathToTimestamp[path] = nextStamp++; |
| 253 _notifyWatchers(path, ChangeType.MODIFY); | 251 _notifyWatchers(path, ChangeType.MODIFY); |
| 254 } | 252 } |
| 255 } | 253 } |
| 256 | 254 |
| 257 /** | 255 /** |
| 258 * An in-memory implementation of [File] which acts like a symbolic link to a | 256 * An in-memory implementation of [File] which acts like a symbolic link to a |
| 259 * non-existent file. | 257 * non-existent file. |
| 260 */ | 258 */ |
| 261 class _MemoryDummyLink extends _MemoryResource implements File { | 259 class _MemoryDummyLink extends _MemoryResource implements File { |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 309 throw new FileSystemException(path, 'File could not be renamed'); | 307 throw new FileSystemException(path, 'File could not be renamed'); |
| 310 } | 308 } |
| 311 | 309 |
| 312 @override | 310 @override |
| 313 Uri toUri() => new Uri.file(path, windows: _provider.pathContext == windows); | 311 Uri toUri() => new Uri.file(path, windows: _provider.pathContext == windows); |
| 314 | 312 |
| 315 @override | 313 @override |
| 316 void writeAsBytesSync(List<int> bytes) { | 314 void writeAsBytesSync(List<int> bytes) { |
| 317 throw new FileSystemException(path, 'File could not be written'); | 315 throw new FileSystemException(path, 'File could not be written'); |
| 318 } | 316 } |
| 317 |
| 318 @override |
| 319 void writeAsStringSync(String content) { |
| 320 throw new FileSystemException(path, 'File could not be written'); |
| 321 } |
| 319 } | 322 } |
| 320 | 323 |
| 321 /** | 324 /** |
| 322 * An in-memory implementation of [File]. | 325 * An in-memory implementation of [File]. |
| 323 */ | 326 */ |
| 324 class _MemoryFile extends _MemoryResource implements File { | 327 class _MemoryFile extends _MemoryResource implements File { |
| 325 _MemoryFile(MemoryResourceProvider provider, String path) | 328 _MemoryFile(MemoryResourceProvider provider, String path) |
| 326 : super(provider, path); | 329 : super(provider, path); |
| 327 | 330 |
| 328 @override | 331 @override |
| (...skipping 19 matching lines...) Expand all Loading... |
| 348 _provider.deleteFile(path); | 351 _provider.deleteFile(path); |
| 349 } | 352 } |
| 350 | 353 |
| 351 @override | 354 @override |
| 352 bool isOrContains(String path) { | 355 bool isOrContains(String path) { |
| 353 return path == this.path; | 356 return path == this.path; |
| 354 } | 357 } |
| 355 | 358 |
| 356 @override | 359 @override |
| 357 List<int> readAsBytesSync() { | 360 List<int> readAsBytesSync() { |
| 358 List<int> bytes = _provider._pathToBytes[path]; | 361 String content = _provider._pathToContent[path]; |
| 359 if (bytes == null) { | 362 if (content == null) { |
| 360 throw new FileSystemException(path, 'File "$path" is not binary.'); | 363 throw new FileSystemException(path, 'File "$path" does not exist.'); |
| 361 } | 364 } |
| 362 return bytes; | 365 return content.codeUnits; |
| 363 } | 366 } |
| 364 | 367 |
| 365 @override | 368 @override |
| 366 String readAsStringSync() { | 369 String readAsStringSync() { |
| 367 String content = _provider._pathToContent[path]; | 370 String content = _provider._pathToContent[path]; |
| 368 if (content == null) { | 371 if (content == null) { |
| 369 throw new FileSystemException(path, 'File "$path" does not exist.'); | 372 throw new FileSystemException(path, 'File "$path" does not exist.'); |
| 370 } | 373 } |
| 371 return content; | 374 return content; |
| 372 } | 375 } |
| 373 | 376 |
| 374 @override | 377 @override |
| 375 File renameSync(String newPath) { | 378 File renameSync(String newPath) { |
| 376 return _provider.renameFileSync(this, newPath); | 379 return _provider.renameFileSync(this, newPath); |
| 377 } | 380 } |
| 378 | 381 |
| 379 @override | 382 @override |
| 380 Uri toUri() => new Uri.file(path, windows: _provider.pathContext == windows); | 383 Uri toUri() => new Uri.file(path, windows: _provider.pathContext == windows); |
| 381 | 384 |
| 382 @override | 385 @override |
| 383 void writeAsBytesSync(List<int> bytes) { | 386 void writeAsBytesSync(List<int> bytes) { |
| 384 _provider._setFileBytes(this, bytes); | 387 _provider._setFileContent(this, new String.fromCharCodes(bytes)); |
| 388 } |
| 389 |
| 390 @override |
| 391 void writeAsStringSync(String content) { |
| 392 _provider._setFileContent(this, content); |
| 385 } | 393 } |
| 386 } | 394 } |
| 387 | 395 |
| 388 /** | 396 /** |
| 389 * An in-memory implementation of [Folder]. | 397 * An in-memory implementation of [Folder]. |
| 390 */ | 398 */ |
| 391 class _MemoryFolder extends _MemoryResource implements Folder { | 399 class _MemoryFolder extends _MemoryResource implements Folder { |
| 392 _MemoryFolder(MemoryResourceProvider provider, String path) | 400 _MemoryFolder(MemoryResourceProvider provider, String path) |
| 393 : super(provider, path); | 401 : super(provider, path); |
| 394 | 402 |
| (...skipping 120 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 515 bool operator ==(other) { | 523 bool operator ==(other) { |
| 516 if (runtimeType != other.runtimeType) { | 524 if (runtimeType != other.runtimeType) { |
| 517 return false; | 525 return false; |
| 518 } | 526 } |
| 519 return path == other.path; | 527 return path == other.path; |
| 520 } | 528 } |
| 521 | 529 |
| 522 @override | 530 @override |
| 523 String toString() => path; | 531 String toString() => path; |
| 524 } | 532 } |
| OLD | NEW |