Update flutter_tools to use package:file throughout (#7385)

This removes direct file access from within flutter_tools
in favor of using `package:file` via a `FileSystem` that's
accessed via the `ApplicationContext`.

This lays the groundwork for us to be able to easily swap
out the underlying file system when running Flutter tools,
which will be used to provide a record/replay file system,
analogous to what we have for process invocations.
diff --git a/packages/flutter_tools/lib/src/commands/analyze.dart b/packages/flutter_tools/lib/src/commands/analyze.dart
index 9b34e38..f46ce8d 100644
--- a/packages/flutter_tools/lib/src/commands/analyze.dart
+++ b/packages/flutter_tools/lib/src/commands/analyze.dart
@@ -3,8 +3,8 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
 
+import '../base/file_system.dart';
 import '../runner/flutter_command.dart';
 import 'analyze_continuously.dart';
 import 'analyze_once.dart';
@@ -46,7 +46,7 @@
       return false;
 
     // Or we're not in a project directory.
-    if (!new File('pubspec.yaml').existsSync())
+    if (!fs.file('pubspec.yaml').existsSync())
       return false;
 
     return super.shouldRunPub;
diff --git a/packages/flutter_tools/lib/src/commands/analyze_base.dart b/packages/flutter_tools/lib/src/commands/analyze_base.dart
index 2e3ea36..69768ad 100644
--- a/packages/flutter_tools/lib/src/commands/analyze_base.dart
+++ b/packages/flutter_tools/lib/src/commands/analyze_base.dart
@@ -3,11 +3,12 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
+import 'dart:io' as io;
 
 import 'package:args/args.dart';
 import 'package:path/path.dart' as path;
 
+import '../base/file_system.dart';
 import '../base/utils.dart';
 import '../cache.dart';
 import '../globals.dart';
@@ -25,7 +26,7 @@
   void dumpErrors(Iterable<String> errors) {
     if (argResults['write'] != null) {
       try {
-        final RandomAccessFile resultsFile = new File(argResults['write']).openSync(mode: FileMode.WRITE);
+        final RandomAccessFile resultsFile = fs.file(argResults['write']).openSync(mode: FileMode.WRITE);
         try {
           resultsFile.lockSync();
           resultsFile.writeStringSync(errors.join('\n'));
@@ -45,7 +46,7 @@
       'issues': errorCount,
       'missingDartDocs': membersMissingDocumentation
     };
-    new File(benchmarkOut).writeAsStringSync(toPrettyJson(data));
+    fs.file(benchmarkOut).writeAsStringSync(toPrettyJson(data));
     printStatus('Analysis benchmark written to $benchmarkOut ($data).');
   }
 
@@ -58,11 +59,11 @@
   if (fileList == null || fileList.isEmpty)
     fileList = <String>[path.current];
   String root = path.normalize(path.absolute(Cache.flutterRoot));
-  String prefix = root + Platform.pathSeparator;
+  String prefix = root + io.Platform.pathSeparator;
   for (String file in fileList) {
     file = path.normalize(path.absolute(file));
     if (file == root || file.startsWith(prefix))
       return true;
   }
   return false;
-}
\ No newline at end of file
+}
diff --git a/packages/flutter_tools/lib/src/commands/analyze_continuously.dart b/packages/flutter_tools/lib/src/commands/analyze_continuously.dart
index b8e5534..23ce702 100644
--- a/packages/flutter_tools/lib/src/commands/analyze_continuously.dart
+++ b/packages/flutter_tools/lib/src/commands/analyze_continuously.dart
@@ -4,12 +4,13 @@
 
 import 'dart:async';
 import 'dart:convert';
-import 'dart:io';
+import 'dart:io' as io;
 
 import 'package:args/args.dart';
 import 'package:path/path.dart' as path;
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/logger.dart';
 import '../base/process_manager.dart';
 import '../base/utils.dart';
@@ -42,8 +43,8 @@
       for (String projectPath in directories)
         printTrace('  ${path.relative(projectPath)}');
     } else {
-      directories = <String>[Directory.current.path];
-      analysisTarget = Directory.current.path;
+      directories = <String>[fs.currentDirectory.path];
+      analysisTarget = fs.currentDirectory.path;
     }
 
     AnalysisServer server = new AnalysisServer(dartSdkPath, directories);
@@ -78,7 +79,7 @@
       // Remove errors for deleted files, sort, and print errors.
       final List<AnalysisError> errors = <AnalysisError>[];
       for (String path in analysisErrors.keys.toList()) {
-        if (FileSystemEntity.isFileSync(path)) {
+        if (fs.isFileSync(path)) {
           errors.addAll(analysisErrors[path]);
         } else {
           analysisErrors.remove(path);
@@ -149,7 +150,7 @@
   final String sdk;
   final List<String> directories;
 
-  Process _process;
+  io.Process _process;
   StreamController<bool> _analyzingController = new StreamController<bool>.broadcast();
   StreamController<FileAnalysisErrors> _errorsController = new StreamController<FileAnalysisErrors>.broadcast();
 
diff --git a/packages/flutter_tools/lib/src/commands/analyze_once.dart b/packages/flutter_tools/lib/src/commands/analyze_once.dart
index 7b4c266..8792330 100644
--- a/packages/flutter_tools/lib/src/commands/analyze_once.dart
+++ b/packages/flutter_tools/lib/src/commands/analyze_once.dart
@@ -4,13 +4,13 @@
 
 import 'dart:async';
 import 'dart:collection';
-import 'dart:io';
 
 import 'package:args/args.dart';
 import 'package:path/path.dart' as path;
 import 'package:yaml/yaml.dart' as yaml;
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../cache.dart';
 import '../dart/analysis.dart';
 import '../globals.dart';
@@ -36,11 +36,11 @@
     for (String file in argResults.rest.toList()) {
       file = path.normalize(path.absolute(file));
       String root = path.rootPrefix(file);
-      dartFiles.add(new File(file));
+      dartFiles.add(fs.file(file));
       while (file != root) {
         file = path.dirname(file);
-        if (FileSystemEntity.isFileSync(path.join(file, 'pubspec.yaml'))) {
-          pubSpecDirectories.add(new Directory(file));
+        if (fs.isFileSync(path.join(file, 'pubspec.yaml'))) {
+          pubSpecDirectories.add(fs.directory(file));
           break;
         }
       }
@@ -54,7 +54,7 @@
 
     if (currentDirectory  && !flutterRepo) {
       // ./*.dart
-      Directory currentDirectory = new Directory('.');
+      Directory currentDirectory = fs.directory('.');
       bool foundOne = false;
       for (FileSystemEntity entry in currentDirectory.listSync()) {
         if (isDartFile(entry)) {
@@ -68,7 +68,7 @@
 
     if (currentPackage && !flutterRepo) {
       // **/.*dart
-      Directory currentDirectory = new Directory('.');
+      Directory currentDirectory = fs.directory('.');
       _collectDartFiles(currentDirectory, dartFiles);
       pubSpecDirectories.add(currentDirectory);
     }
@@ -89,18 +89,18 @@
     PackageDependencyTracker dependencies = new PackageDependencyTracker();
     for (Directory directory in pubSpecDirectories) {
       String pubSpecYamlPath = path.join(directory.path, 'pubspec.yaml');
-      File pubSpecYamlFile = new File(pubSpecYamlPath);
+      File pubSpecYamlFile = fs.file(pubSpecYamlPath);
       if (pubSpecYamlFile.existsSync()) {
         // we are analyzing the actual canonical source for this package;
         // make sure we remember that, in case all the packages are actually
         // pointing elsewhere somehow.
-        yaml.YamlMap pubSpecYaml = yaml.loadYaml(new File(pubSpecYamlPath).readAsStringSync());
+        yaml.YamlMap pubSpecYaml = yaml.loadYaml(fs.file(pubSpecYamlPath).readAsStringSync());
         String packageName = pubSpecYaml['name'];
         String packagePath = path.normalize(path.absolute(path.join(directory.path, 'lib')));
         dependencies.addCanonicalCase(packageName, packagePath, pubSpecYamlPath);
       }
       String dotPackagesPath = path.join(directory.path, '.packages');
-      File dotPackages = new File(dotPackagesPath);
+      File dotPackages = fs.file(dotPackagesPath);
       if (dotPackages.existsSync()) {
         // this directory has opinions about what we should be using
         dotPackages
@@ -228,7 +228,7 @@
 
   List<File> _collectDartFiles(Directory dir, List<File> collected, {FileFilter exclude}) {
     // Bail out in case of a .dartignore.
-    if (FileSystemEntity.isFileSync(path.join(path.dirname(dir.path), '.dartignore')))
+    if (fs.isFileSync(path.join(path.dirname(dir.path), '.dartignore')))
       return collected;
 
     for (FileSystemEntity entity in dir.listSync(recursive: false, followLinks: false)) {
diff --git a/packages/flutter_tools/lib/src/commands/build.dart b/packages/flutter_tools/lib/src/commands/build.dart
index 21eff64..1957d85 100644
--- a/packages/flutter_tools/lib/src/commands/build.dart
+++ b/packages/flutter_tools/lib/src/commands/build.dart
@@ -3,10 +3,11 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
+import 'dart:io' as io;
 
 import 'package:meta/meta.dart';
 
+import '../base/file_system.dart';
 import '../build_info.dart';
 import '../globals.dart';
 import '../runner/flutter_command.dart';
@@ -54,14 +55,14 @@
   @mustCallSuper
   Future<Null> runCommand() async {
     if (isRunningOnBot) {
-      File dotPackages = new File('.packages');
+      File dotPackages = fs.file('.packages');
       printStatus('Contents of .packages:');
       if (dotPackages.existsSync())
         printStatus(dotPackages.readAsStringSync());
       else
         printError('File not found: ${dotPackages.absolute.path}');
 
-      File pubspecLock = new File('pubspec.lock');
+      File pubspecLock = fs.file('pubspec.lock');
       printStatus('Contents of pubspec.lock:');
       if (pubspecLock.existsSync())
         printStatus(pubspecLock.readAsStringSync());
@@ -86,8 +87,8 @@
 
   @override
   Future<Null> runCommand() async {
-    Directory buildDir = new Directory(getBuildDirectory());
-    printStatus("Deleting '${buildDir.path}${Platform.pathSeparator}'.");
+    Directory buildDir = fs.directory(getBuildDirectory());
+    printStatus("Deleting '${buildDir.path}${io.Platform.pathSeparator}'.");
 
     if (!buildDir.existsSync())
       return;
diff --git a/packages/flutter_tools/lib/src/commands/build_aot.dart b/packages/flutter_tools/lib/src/commands/build_aot.dart
index e5b31a9..f8e8c44 100644
--- a/packages/flutter_tools/lib/src/commands/build_aot.dart
+++ b/packages/flutter_tools/lib/src/commands/build_aot.dart
@@ -3,11 +3,12 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
+import 'dart:io' as io;
 
 import 'package:path/path.dart' as path;
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/logger.dart';
 import '../base/process.dart';
 import '../base/utils.dart';
@@ -64,7 +65,7 @@
     if (outputPath == null)
       throwToolExit(null);
 
-    printStatus('Built to $outputPath${Platform.pathSeparator}.');
+    printStatus('Built to $outputPath${io.Platform.pathSeparator}.');
   }
 }
 
@@ -142,7 +143,7 @@
     }
   }
 
-  Directory outputDir = new Directory(outputPath);
+  Directory outputDir = fs.directory(outputPath);
   outputDir.createSync(recursive: true);
   String vmIsolateSnapshot = path.join(outputDir.path, 'snapshot_aot_vmisolate');
   String isolateSnapshot = path.join(outputDir.path, 'snapshot_aot_isolate');
@@ -201,7 +202,7 @@
       assert(false);
   }
 
-  List<String> missingFiles = filePaths.where((String p) => !FileSystemEntity.isFileSync(p)).toList();
+  List<String> missingFiles = filePaths.where((String p) => !fs.isFileSync(p)).toList();
   if (missingFiles.isNotEmpty) {
     printError('Missing files: $missingFiles');
     return null;
diff --git a/packages/flutter_tools/lib/src/commands/build_apk.dart b/packages/flutter_tools/lib/src/commands/build_apk.dart
index 114b862..b6a1b8f 100644
--- a/packages/flutter_tools/lib/src/commands/build_apk.dart
+++ b/packages/flutter_tools/lib/src/commands/build_apk.dart
@@ -4,14 +4,13 @@
 
 import 'dart:async';
 import 'dart:convert' show JSON;
-import 'dart:io';
 
 import 'package:path/path.dart' as path;
 
 import '../android/android_sdk.dart';
 import '../android/gradle.dart';
 import '../base/common.dart';
-import '../base/file_system.dart' show ensureDirectoryExists;
+import '../base/file_system.dart';
 import '../base/logger.dart';
 import '../base/os.dart';
 import '../base/process.dart';
@@ -49,7 +48,7 @@
   Directory _assetDir;
 
   _AssetBuilder(this.outDir, String assetDirName) {
-    _assetDir = new Directory('${outDir.path}/$assetDirName');
+    _assetDir = fs.directory('${outDir.path}/$assetDirName');
     _assetDir.createSync(recursive:  true);
   }
 
@@ -73,10 +72,10 @@
   File _jarsigner;
 
   _ApkBuilder(this.sdk) {
-    _androidJar = new File(sdk.androidJarPath);
-    _aapt = new File(sdk.aaptPath);
-    _dx = new File(sdk.dxPath);
-    _zipalign = new File(sdk.zipalignPath);
+    _androidJar = fs.file(sdk.androidJarPath);
+    _aapt = fs.file(sdk.aaptPath);
+    _dx = fs.file(sdk.dxPath);
+    _zipalign = fs.file(sdk.zipalignPath);
     _jarsigner = os.which('jarsigner');
   }
 
@@ -284,8 +283,8 @@
   Map<String, File> extraFiles
 ) async {
   _ApkComponents components = new _ApkComponents();
-  components.manifest = new File(manifest);
-  components.resources = resources == null ? null : new Directory(resources);
+  components.manifest = fs.file(manifest);
+  components.resources = resources == null ? null : fs.directory(resources);
   components.extraFiles = extraFiles != null ? extraFiles : <String, File>{};
 
   if (tools.isLocalEngine) {
@@ -293,21 +292,21 @@
     String enginePath = tools.engineSrcPath;
     String buildDir = tools.getEngineArtifactsDirectory(platform, buildMode).path;
 
-    components.icuData = new File('$enginePath/third_party/icu/android/icudtl.dat');
+    components.icuData = fs.file('$enginePath/third_party/icu/android/icudtl.dat');
     components.jars = <File>[
-      new File('$buildDir/gen/flutter/shell/platform/android/android/classes.dex.jar')
+      fs.file('$buildDir/gen/flutter/shell/platform/android/android/classes.dex.jar')
     ];
-    components.libSkyShell = new File('$buildDir/gen/flutter/shell/platform/android/android/android/libs/$abiDir/libsky_shell.so');
-    components.debugKeystore = new File('$enginePath/build/android/ant/chromium-debug.keystore');
+    components.libSkyShell = fs.file('$buildDir/gen/flutter/shell/platform/android/android/android/libs/$abiDir/libsky_shell.so');
+    components.debugKeystore = fs.file('$enginePath/build/android/ant/chromium-debug.keystore');
   } else {
     Directory artifacts = tools.getEngineArtifactsDirectory(platform, buildMode);
 
-    components.icuData = new File(path.join(artifacts.path, 'icudtl.dat'));
+    components.icuData = fs.file(path.join(artifacts.path, 'icudtl.dat'));
     components.jars = <File>[
-      new File(path.join(artifacts.path, 'classes.dex.jar'))
+      fs.file(path.join(artifacts.path, 'classes.dex.jar'))
     ];
-    components.libSkyShell = new File(path.join(artifacts.path, 'libsky_shell.so'));
-    components.debugKeystore = new File(path.join(artifacts.path, 'chromium-debug.keystore'));
+    components.libSkyShell = fs.file(path.join(artifacts.path, 'libsky_shell.so'));
+    components.debugKeystore = fs.file(path.join(artifacts.path, 'chromium-debug.keystore'));
   }
 
   await parseServiceConfigs(components.services, jars: components.jars);
@@ -338,7 +337,7 @@
   assert(platform != null);
   assert(buildMode != null);
 
-  Directory tempDir = Directory.systemTemp.createTempSync('flutter_tools');
+  Directory tempDir = fs.systemTempDirectory.createTempSync('flutter_tools');
 
   printTrace('Building APK; buildMode: ${getModeName(buildMode)}.');
 
@@ -350,7 +349,7 @@
       return 1;
     }
 
-    File classesDex = new File('${tempDir.path}/classes.dex');
+    File classesDex = fs.file('${tempDir.path}/classes.dex');
     builder.compileClassesDex(classesDex, components.jars);
 
     File servicesConfig =
@@ -358,7 +357,7 @@
 
     _AssetBuilder assetBuilder = new _AssetBuilder(tempDir, 'assets');
     assetBuilder.add(components.icuData, 'icudtl.dat');
-    assetBuilder.add(new File(flxPath), 'app.flx');
+    assetBuilder.add(fs.file(flxPath), 'app.flx');
     assetBuilder.add(servicesConfig, 'services.json');
 
     _AssetBuilder artifactBuilder = new _AssetBuilder(tempDir, 'artifacts');
@@ -369,7 +368,7 @@
     for (String relativePath in components.extraFiles.keys)
       artifactBuilder.add(components.extraFiles[relativePath], relativePath);
 
-    File unalignedApk = new File('${tempDir.path}/app.apk.unaligned');
+    File unalignedApk = fs.file('${tempDir.path}/app.apk.unaligned');
     builder.package(
       unalignedApk, components.manifest, assetBuilder.directory,
       artifactBuilder.directory, components.resources, buildMode
@@ -379,12 +378,12 @@
     if (signResult != 0)
       return signResult;
 
-    File finalApk = new File(outputFile);
+    File finalApk = fs.file(outputFile);
     ensureDirectoryExists(finalApk.path);
     builder.align(unalignedApk, finalApk);
 
     printTrace('calculateSha: $outputFile');
-    File apkShaFile = new File('$outputFile.sha1');
+    File apkShaFile = fs.file('$outputFile.sha1');
     apkShaFile.writeAsStringSync(calculateSha(finalApk));
 
     return 0;
@@ -417,7 +416,7 @@
     keyAlias = _kDebugKeystoreKeyAlias;
     keyPassword = _kDebugKeystorePassword;
   } else {
-    keystore = new File(keystoreInfo.keystore);
+    keystore = fs.file(keystoreInfo.keystore);
     keystorePassword = keystoreInfo.password ?? '';
     keyAlias = keystoreInfo.keyAlias ?? '';
     if (keystorePassword.isEmpty || keyAlias.isEmpty) {
@@ -442,7 +441,7 @@
   BuildMode buildMode,
   Map<String, File> extraFiles
 ) {
-  FileStat apkStat = FileStat.statSync(apkPath);
+  FileStat apkStat = fs.statSync(apkPath);
   // Note: This list of dependencies is imperfect, but will do for now. We
   // purposely don't include the .dart files, because we can load those
   // over the network without needing to rebuild (at least on Android).
@@ -453,7 +452,7 @@
   ];
   dependencies.addAll(extraFiles.values.map((File file) => file.path));
   Iterable<FileStat> dependenciesStat =
-    dependencies.map((String path) => FileStat.statSync(path));
+    dependencies.map((String path) => fs.statSync(path));
 
   if (apkStat.type == FileSystemEntityType.NOT_FOUND)
     return true;
@@ -463,11 +462,11 @@
       return true;
   }
 
-  if (!FileSystemEntity.isFileSync('$apkPath.sha1'))
+  if (!fs.isFileSync('$apkPath.sha1'))
     return true;
 
   String lastBuildType = _readBuildMeta(path.dirname(apkPath))['targetBuildType'];
-  String targetBuildType = _getTargetBuildTypeToken(platform, buildMode, new File(apkPath));
+  String targetBuildType = _getTargetBuildTypeToken(platform, buildMode, fs.file(apkPath));
   if (lastBuildType != targetBuildType)
     return true;
 
@@ -499,8 +498,8 @@
   }
 
   Map<String, File> extraFiles = <String, File>{};
-  if (FileSystemEntity.isDirectorySync(_kDefaultAssetsPath)) {
-    Directory assetsDir = new Directory(_kDefaultAssetsPath);
+  if (fs.isDirectorySync(_kDefaultAssetsPath)) {
+    Directory assetsDir = fs.directory(_kDefaultAssetsPath);
     for (FileSystemEntity entity in assetsDir.listSync(recursive: true)) {
       if (entity is File) {
         String targetPath = entity.path.substring(assetsDir.path.length);
@@ -520,10 +519,10 @@
   }
 
   if (resources != null) {
-    if (!FileSystemEntity.isDirectorySync(resources))
+    if (!fs.isDirectorySync(resources))
       throwToolExit('Resources directory "$resources" not found.');
   } else {
-    if (FileSystemEntity.isDirectorySync(_kDefaultResourcesPath))
+    if (fs.isDirectorySync(_kDefaultResourcesPath))
       resources = _kDefaultResourcesPath;
   }
 
@@ -536,7 +535,7 @@
   Status status = logger.startProgress('Building APK in ${getModeName(buildMode)} mode ($typeName)...');
 
   if (flxPath != null && flxPath.isNotEmpty) {
-    if (!FileSystemEntity.isFileSync(flxPath)) {
+    if (!fs.isFileSync(flxPath)) {
       throwToolExit('FLX does not exist: $flxPath\n'
         '(Omit the --flx option to build the FLX automatically)');
     }
@@ -561,13 +560,13 @@
   if (aotPath != null) {
     if (!isAotBuildMode(buildMode))
       throwToolExit('AOT snapshot can not be used in build mode $buildMode');
-    if (!FileSystemEntity.isDirectorySync(aotPath))
+    if (!fs.isDirectorySync(aotPath))
       throwToolExit('AOT snapshot does not exist: $aotPath');
     for (String aotFilename in kAotSnapshotFiles) {
       String aotFilePath = path.join(aotPath, aotFilename);
-      if (!FileSystemEntity.isFileSync(aotFilePath))
+      if (!fs.isFileSync(aotFilePath))
         throwToolExit('Missing AOT snapshot file: $aotFilePath');
-      components.extraFiles['assets/$aotFilename'] = new File(aotFilePath);
+      components.extraFiles['assets/$aotFilename'] = fs.file(aotFilePath);
     }
   }
 
@@ -577,13 +576,13 @@
   if (result != 0)
     throwToolExit('Build APK failed ($result)', exitCode: result);
 
-  File apkFile = new File(outputFile);
+  File apkFile = fs.file(outputFile);
   printTrace('Built $outputFile (${getSizeAsMB(apkFile.lengthSync())}).');
 
   _writeBuildMetaEntry(
     path.dirname(outputFile),
     'targetBuildType',
-    _getTargetBuildTypeToken(platform, buildMode, new File(outputFile))
+    _getTargetBuildTypeToken(platform, buildMode, fs.file(outputFile))
   );
 }
 
@@ -619,7 +618,7 @@
       target: target
     );
   } else {
-    if (!FileSystemEntity.isFileSync(_kDefaultAndroidManifestPath))
+    if (!fs.isFileSync(_kDefaultAndroidManifestPath))
       throwToolExit('Cannot build APK: missing $_kDefaultAndroidManifestPath.');
 
     return await buildAndroid(
@@ -632,7 +631,7 @@
 }
 
 Map<String, dynamic> _readBuildMeta(String buildDirectoryPath) {
-  File buildMetaFile = new File(path.join(buildDirectoryPath, 'build_meta.json'));
+  File buildMetaFile = fs.file(path.join(buildDirectoryPath, 'build_meta.json'));
   if (buildMetaFile.existsSync())
     return JSON.decode(buildMetaFile.readAsStringSync());
   return <String, dynamic>{};
@@ -641,7 +640,7 @@
 void _writeBuildMetaEntry(String buildDirectoryPath, String key, dynamic value) {
   Map<String, dynamic> meta = _readBuildMeta(buildDirectoryPath);
   meta[key] = value;
-  File buildMetaFile = new File(path.join(buildDirectoryPath, 'build_meta.json'));
+  File buildMetaFile = fs.file(path.join(buildDirectoryPath, 'build_meta.json'));
   buildMetaFile.writeAsStringSync(toPrettyJson(meta));
 }
 
diff --git a/packages/flutter_tools/lib/src/commands/create.dart b/packages/flutter_tools/lib/src/commands/create.dart
index 3d21f16..83f3e7d 100644
--- a/packages/flutter_tools/lib/src/commands/create.dart
+++ b/packages/flutter_tools/lib/src/commands/create.dart
@@ -3,12 +3,12 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
 
 import 'package:path/path.dart' as path;
 
 import '../android/android.dart' as android;
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/utils.dart';
 import '../cache.dart';
 import '../dart/pub.dart';
@@ -72,14 +72,14 @@
 
     String flutterPackagesDirectory = path.join(flutterRoot, 'packages');
     String flutterPackagePath = path.join(flutterPackagesDirectory, 'flutter');
-    if (!FileSystemEntity.isFileSync(path.join(flutterPackagePath, 'pubspec.yaml')))
+    if (!fs.isFileSync(path.join(flutterPackagePath, 'pubspec.yaml')))
       throwToolExit('Unable to find package:flutter in $flutterPackagePath', exitCode: 2);
 
     String flutterDriverPackagePath = path.join(flutterRoot, 'packages', 'flutter_driver');
-    if (!FileSystemEntity.isFileSync(path.join(flutterDriverPackagePath, 'pubspec.yaml')))
+    if (!fs.isFileSync(path.join(flutterDriverPackagePath, 'pubspec.yaml')))
       throwToolExit('Unable to find package:flutter_driver in $flutterDriverPackagePath', exitCode: 2);
 
-    Directory projectDir = new Directory(argResults.rest.first);
+    Directory projectDir = fs.directory(argResults.rest.first);
     String dirPath = path.normalize(projectDir.absolute.path);
     String relativePath = path.relative(dirPath);
     String projectName = _normalizeProjectName(path.basename(dirPath));
@@ -139,7 +139,7 @@
 
   int _renderTemplates(String projectName, String projectDescription, String dirPath,
       String flutterPackagesDirectory, { bool renderDriverTest: false }) {
-    new Directory(dirPath).createSync(recursive: true);
+    fs.directory(dirPath).createSync(recursive: true);
 
     flutterPackagesDirectory = path.normalize(flutterPackagesDirectory);
     flutterPackagesDirectory = _relativePath(from: dirPath, to: flutterPackagesDirectory);
@@ -161,14 +161,14 @@
 
     Template createTemplate = new Template.fromName('create');
     fileCount += createTemplate.render(
-      new Directory(dirPath),
+      fs.directory(dirPath),
       templateContext, overwriteExisting: false,
       projectName: projectName
     );
 
     if (renderDriverTest) {
       Template driverTemplate = new Template.fromName('driver');
-      fileCount += driverTemplate.render(new Directory(path.join(dirPath, 'test_driver')),
+      fileCount += driverTemplate.render(fs.directory(path.join(dirPath, 'test_driver')),
           templateContext, overwriteExisting: false);
     }
 
@@ -234,7 +234,7 @@
       "Target directory '$dirPath' is within the Flutter SDK at '$flutterRoot'.";
   }
 
-  FileSystemEntityType type = FileSystemEntity.typeSync(dirPath);
+  FileSystemEntityType type = fs.typeSync(dirPath);
 
   if (type != FileSystemEntityType.NOT_FOUND) {
     switch(type) {
@@ -253,7 +253,7 @@
 String _relativePath({ String from, String to }) {
   String result = path.relative(to, from: from);
   // `path.relative()` doesn't always return a correct result: dart-lang/path#12.
-  if (FileSystemEntity.isDirectorySync(path.join(from, result)))
+  if (fs.isDirectorySync(path.join(from, result)))
     return result;
   return to;
 }
diff --git a/packages/flutter_tools/lib/src/commands/daemon.dart b/packages/flutter_tools/lib/src/commands/daemon.dart
index c59a8fc..4f7483d 100644
--- a/packages/flutter_tools/lib/src/commands/daemon.dart
+++ b/packages/flutter_tools/lib/src/commands/daemon.dart
@@ -4,11 +4,12 @@
 
 import 'dart:async';
 import 'dart:convert';
-import 'dart:io';
+import 'dart:io' as io;
 
 import '../android/android_device.dart';
 import '../base/common.dart';
 import '../base/context.dart';
+import '../base/file_system.dart';
 import '../base/logger.dart';
 import '../base/utils.dart';
 import '../build_info.dart';
@@ -119,7 +120,7 @@
     dynamic id = request['id'];
 
     if (id == null) {
-      stderr.writeln('no id for request: $request');
+      io.stderr.writeln('no id for request: $request');
       return;
     }
 
@@ -234,9 +235,9 @@
           // capture the print output for testing.
           print(message.message);
         } else if (message.level == 'error') {
-          stderr.writeln(message.message);
+          io.stderr.writeln(message.message);
           if (message.stackTrace != null)
-            stderr.writeln(message.stackTrace.toString().trimRight());
+            io.stderr.writeln(message.stackTrace.toString().trimRight());
         }
       } else {
         if (message.stackTrace != null) {
@@ -302,7 +303,7 @@
     if (device == null)
       throw "device '$deviceId' not found";
 
-    if (!FileSystemEntity.isDirectorySync(projectDirectory))
+    if (!fs.isDirectorySync(projectDirectory))
       throw "'$projectDirectory' does not exist";
 
     BuildMode buildMode = getBuildModeForName(mode) ?? BuildMode.debug;
@@ -341,8 +342,8 @@
       throw '${toTitleCase(getModeName(buildMode))} mode is not supported for emulators.';
 
     // We change the current working directory for the duration of the `start` command.
-    Directory cwd = Directory.current;
-    Directory.current = new Directory(projectDirectory);
+    Directory cwd = fs.currentDirectory;
+    fs.currentDirectory = fs.directory(projectDirectory);
 
     ResidentRunner runner;
 
@@ -400,7 +401,7 @@
       } catch (error) {
         _sendAppEvent(app, 'stop', <String, dynamic>{'error': error.toString()});
       } finally {
-        Directory.current = cwd;
+        fs.currentDirectory = cwd;
         _apps.remove(app);
       }
     });
@@ -589,7 +590,7 @@
   }
 }
 
-Stream<Map<String, dynamic>> get stdinCommandStream => stdin
+Stream<Map<String, dynamic>> get stdinCommandStream => io.stdin
   .transform(UTF8.decoder)
   .transform(const LineSplitter())
   .where((String line) => line.startsWith('[{') && line.endsWith('}]'))
@@ -599,7 +600,7 @@
   });
 
 void stdoutCommandResponse(Map<String, dynamic> command) {
-  stdout.writeln('[${JSON.encode(command, toEncodable: _jsonEncodeObject)}]');
+  io.stdout.writeln('[${JSON.encode(command, toEncodable: _jsonEncodeObject)}]');
 }
 
 dynamic _jsonEncodeObject(dynamic object) {
@@ -709,9 +710,9 @@
   @override
   void printError(String message, [StackTrace stackTrace]) {
     if (logToStdout) {
-      stderr.writeln(message);
+      io.stderr.writeln(message);
       if (stackTrace != null)
-        stderr.writeln(stackTrace.toString().trimRight());
+        io.stderr.writeln(stackTrace.toString().trimRight());
     } else {
       if (stackTrace != null) {
         _sendLogEvent(<String, dynamic>{
diff --git a/packages/flutter_tools/lib/src/commands/run.dart b/packages/flutter_tools/lib/src/commands/run.dart
index ddd06f7..7486648 100644
--- a/packages/flutter_tools/lib/src/commands/run.dart
+++ b/packages/flutter_tools/lib/src/commands/run.dart
@@ -3,9 +3,10 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
+import 'dart:io' as io;
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/utils.dart';
 import '../build_info.dart';
 import '../cache.dart';
@@ -174,7 +175,7 @@
       AppInstance app;
       try {
         app = daemon.appDomain.startApp(
-          device, Directory.current.path, targetFile, route,
+          device, fs.currentDirectory.path, targetFile, route,
           getBuildMode(), argResults['start-paused'], hotMode);
       } catch (error) {
         throwToolExit(error.toString());
@@ -217,7 +218,7 @@
     String pidFile = argResults['pid-file'];
     if (pidFile != null) {
       // Write our pid to the file.
-      new File(pidFile).writeAsStringSync(pid.toString());
+      fs.file(pidFile).writeAsStringSync(io.pid.toString());
     }
     ResidentRunner runner;
 
diff --git a/packages/flutter_tools/lib/src/commands/screenshot.dart b/packages/flutter_tools/lib/src/commands/screenshot.dart
index f2208e5..398d213 100644
--- a/packages/flutter_tools/lib/src/commands/screenshot.dart
+++ b/packages/flutter_tools/lib/src/commands/screenshot.dart
@@ -3,12 +3,13 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
+import 'dart:io' as io;
 
 import 'package:http/http.dart' as http;
 import 'package:path/path.dart' as path;
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/utils.dart';
 import '../device.dart';
 import '../globals.dart';
@@ -72,7 +73,7 @@
   Future<Null> runCommand() async {
     File outputFile;
     if (argResults.wasParsed(_kOut))
-      outputFile = new File(argResults[_kOut]);
+      outputFile = fs.file(argResults[_kOut]);
 
     if (argResults[_kSkia] != null) {
       return runSkia(outputFile);
@@ -82,7 +83,7 @@
   }
 
   Future<Null> runScreenshot(File outputFile) async {
-    outputFile ??= getUniqueFile(Directory.current, 'flutter', 'png');
+    outputFile ??= getUniqueFile(fs.currentDirectory, 'flutter', 'png');
     try {
       if (!await device.takeScreenshot(outputFile))
         throwToolExit('Screenshot failed');
@@ -105,10 +106,10 @@
     http.StreamedResponse skpResponse;
     try {
       skpResponse = await new http.Request('GET', skpUri).send();
-    } on SocketException catch (e) {
+    } on io.SocketException catch (e) {
       throwToolExit('Skia screenshot failed: $skpUri\n$e\n\n$errorHelpText');
     }
-    if (skpResponse.statusCode != HttpStatus.OK) {
+    if (skpResponse.statusCode != io.HttpStatus.OK) {
       String error = await skpResponse.stream.toStringStream().join();
       throwToolExit('Error: $error\n\n$errorHelpText');
     }
@@ -121,10 +122,10 @@
           'file', skpResponse.stream, skpResponse.contentLength));
 
       http.StreamedResponse postResponse = await postRequest.send();
-      if (postResponse.statusCode != HttpStatus.OK)
+      if (postResponse.statusCode != io.HttpStatus.OK)
         throwToolExit('Failed to post Skia picture to skiaserve.\n\n$errorHelpText');
     } else {
-      outputFile ??= getUniqueFile(Directory.current, 'flutter', 'skp');
+      outputFile ??= getUniqueFile(fs.currentDirectory, 'flutter', 'skp');
       IOSink sink = outputFile.openWrite();
       await sink.addStream(skpResponse.stream);
       await sink.close();
diff --git a/packages/flutter_tools/lib/src/commands/test.dart b/packages/flutter_tools/lib/src/commands/test.dart
index 9e6ed72..11e4a2b 100644
--- a/packages/flutter_tools/lib/src/commands/test.dart
+++ b/packages/flutter_tools/lib/src/commands/test.dart
@@ -3,12 +3,13 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
+import 'dart:io' as io;
 
 import 'package:path/path.dart' as path;
 import 'package:test/src/executable.dart' as test; // ignore: implementation_imports
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/logger.dart';
 import '../base/process_manager.dart';
 import '../base/os.dart';
@@ -39,7 +40,7 @@
       help: 'Where to store coverage information (if coverage is enabled).'
     );
     commandValidator = () {
-      if (!FileSystemEntity.isFileSync('pubspec.yaml')) {
+      if (!fs.isFileSync('pubspec.yaml')) {
         throwToolExit(
           'Error: No pubspec.yaml file found in the current working directory.\n'
           'Run this command from the root of your project. Test files must be\n'
@@ -58,31 +59,31 @@
   Iterable<String> _findTests(Directory directory) {
     return directory.listSync(recursive: true, followLinks: false)
                     .where((FileSystemEntity entity) => entity.path.endsWith('_test.dart') &&
-                      FileSystemEntity.isFileSync(entity.path))
+                      fs.isFileSync(entity.path))
                     .map((FileSystemEntity entity) => path.absolute(entity.path));
   }
 
   Directory get _currentPackageTestDir {
     // We don't scan the entire package, only the test/ subdirectory, so that
     // files with names like like "hit_test.dart" don't get run.
-    return new Directory('test');
+    return fs.directory('test');
   }
 
   Future<int> _runTests(List<String> testArgs, Directory testDirectory) async {
-    Directory currentDirectory = Directory.current;
+    Directory currentDirectory = fs.currentDirectory;
     try {
       if (testDirectory != null) {
         printTrace('switching to directory $testDirectory to run tests');
         PackageMap.globalPackagesPath = path.normalize(path.absolute(PackageMap.globalPackagesPath));
-        Directory.current = testDirectory;
+        fs.currentDirectory = testDirectory;
       }
       printTrace('running test package with arguments: $testArgs');
       await test.main(testArgs);
       // test.main() sets dart:io's exitCode global.
-      printTrace('test package returned with exit code $exitCode');
-      return exitCode;
+      printTrace('test package returned with exit code ${io.exitCode}');
+      return io.exitCode;
     } finally {
-      Directory.current = currentDirectory;
+      fs.currentDirectory = currentDirectory;
     }
   }
 
@@ -94,7 +95,7 @@
       return false;
 
     String coveragePath = argResults['coverage-path'];
-    File coverageFile = new File(coveragePath)
+    File coverageFile = fs.file(coveragePath)
       ..createSync(recursive: true)
       ..writeAsStringSync(coverageData, flush: true);
     printTrace('wrote coverage data to $coveragePath (size=${coverageData.length})');
@@ -109,7 +110,7 @@
         return false;
       }
 
-      if (!FileSystemEntity.isFileSync(baseCoverageData)) {
+      if (!fs.isFileSync(baseCoverageData)) {
         printError('Missing "$baseCoverageData". Unable to merge coverage data.');
         return false;
       }
@@ -124,10 +125,10 @@
         return false;
       }
 
-      Directory tempDir = Directory.systemTemp.createTempSync('flutter_tools');
+      Directory tempDir = fs.systemTempDirectory.createTempSync('flutter_tools');
       try {
         File sourceFile = coverageFile.copySync(path.join(tempDir.path, 'lcov.source.info'));
-        ProcessResult result = processManager.runSync('lcov', <String>[
+        io.ProcessResult result = processManager.runSync('lcov', <String>[
           '--add-tracefile', baseCoverageData,
           '--add-tracefile', sourceFile.path,
           '--output-file', coverageFile.path,
@@ -164,8 +165,8 @@
     if (argResults['coverage'])
       testArgs.insert(0, '--concurrency=1');
 
-    final String shellPath = tools.getHostToolPath(HostTool.SkyShell) ?? Platform.environment['SKY_SHELL'];
-    if (!FileSystemEntity.isFileSync(shellPath))
+    final String shellPath = tools.getHostToolPath(HostTool.SkyShell) ?? io.Platform.environment['SKY_SHELL'];
+    if (!fs.isFileSync(shellPath))
       throwToolExit('Cannot find Flutter shell at $shellPath');
     loader.installHook(shellPath: shellPath);
 
diff --git a/packages/flutter_tools/lib/src/commands/trace.dart b/packages/flutter_tools/lib/src/commands/trace.dart
index 1bbaf6f..db011bf 100644
--- a/packages/flutter_tools/lib/src/commands/trace.dart
+++ b/packages/flutter_tools/lib/src/commands/trace.dart
@@ -4,11 +4,11 @@
 
 import 'dart:async';
 import 'dart:convert';
-import 'dart:io';
 
 import 'package:path/path.dart' as path;
 
 import '../base/common.dart';
+import '../base/file_system.dart';
 import '../base/utils.dart';
 import '../build_info.dart';
 import '../cache.dart';
@@ -90,9 +90,9 @@
     File localFile;
 
     if (argResults['out'] != null) {
-      localFile = new File(argResults['out']);
+      localFile = fs.file(argResults['out']);
     } else {
-      localFile = getUniqueFile(Directory.current, 'trace', 'json');
+      localFile = getUniqueFile(fs.currentDirectory, 'trace', 'json');
     }
 
     await localFile.writeAsString(JSON.encode(timeline));
@@ -161,7 +161,7 @@
 /// store it to build/start_up_info.json.
 Future<Null> downloadStartupTrace(VMService observatory) async {
   String traceInfoFilePath = path.join(getBuildDirectory(), 'start_up_info.json');
-  File traceInfoFile = new File(traceInfoFilePath);
+  File traceInfoFile = fs.file(traceInfoFilePath);
 
   // Delete old startup data, if any.
   if (await traceInfoFile.exists())
diff --git a/packages/flutter_tools/lib/src/commands/update_packages.dart b/packages/flutter_tools/lib/src/commands/update_packages.dart
index 30a869f..90b62bd 100644
--- a/packages/flutter_tools/lib/src/commands/update_packages.dart
+++ b/packages/flutter_tools/lib/src/commands/update_packages.dart
@@ -3,10 +3,10 @@
 // found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
 
 import 'package:path/path.dart' as path;
 
+import '../base/file_system.dart';
 import '../base/logger.dart';
 import '../base/net.dart';
 import '../cache.dart';
@@ -36,10 +36,10 @@
     Status status = logger.startProgress("Downloading lcov data for package:flutter...");
     final List<int> data = await fetchUrl(Uri.parse('https://storage.googleapis.com/flutter_infra/flutter/coverage/lcov.info'));
     final String coverageDir = path.join(Cache.flutterRoot, 'packages/flutter/coverage');
-    new File(path.join(coverageDir, 'lcov.base.info'))
+    fs.file(path.join(coverageDir, 'lcov.base.info'))
       ..createSync(recursive: true)
       ..writeAsBytesSync(data, flush: true);
-    new File(path.join(coverageDir, 'lcov.info'))
+    fs.file(path.join(coverageDir, 'lcov.info'))
       ..createSync(recursive: true)
       ..writeAsBytesSync(data, flush: true);
     status.stop();