Unverified Commit 06c3de32 authored by Jonah Williams's avatar Jonah Williams Committed by GitHub

[flutter_tools] remove most globals from build system and tests (#63697)

Remove globals and testbed to simplify test cases, using the existing environment configuration. This is some pre-factoring work to make landing #63610 easier
parent 32ee0084
...@@ -6,7 +6,7 @@ import '../../artifacts.dart'; ...@@ -6,7 +6,7 @@ import '../../artifacts.dart';
import '../../base/build.dart'; import '../../base/build.dart';
import '../../base/file_system.dart'; import '../../base/file_system.dart';
import '../../build_info.dart'; import '../../build_info.dart';
import '../../globals.dart' as globals; import '../../globals.dart' as globals hide fs, artifacts, logger, processManager;
import '../build_system.dart'; import '../build_system.dart';
import '../depfile.dart'; import '../depfile.dart';
import '../exceptions.dart'; import '../exceptions.dart';
...@@ -52,13 +52,13 @@ abstract class AndroidAssetBundle extends Target { ...@@ -52,13 +52,13 @@ abstract class AndroidAssetBundle extends Target {
// Only copy the prebuilt runtimes and kernel blob in debug mode. // Only copy the prebuilt runtimes and kernel blob in debug mode.
if (buildMode == BuildMode.debug) { if (buildMode == BuildMode.debug) {
final String vmSnapshotData = globals.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug); final String vmSnapshotData = environment.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug);
final String isolateSnapshotData = globals.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug); final String isolateSnapshotData = environment.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug);
environment.buildDir.childFile('app.dill') environment.buildDir.childFile('app.dill')
.copySync(outputDirectory.childFile('kernel_blob.bin').path); .copySync(outputDirectory.childFile('kernel_blob.bin').path);
globals.fs.file(vmSnapshotData) environment.fileSystem.file(vmSnapshotData)
.copySync(outputDirectory.childFile('vm_snapshot_data').path); .copySync(outputDirectory.childFile('vm_snapshot_data').path);
globals.fs.file(isolateSnapshotData) environment.fileSystem.file(isolateSnapshotData)
.copySync(outputDirectory.childFile('isolate_snapshot_data').path); .copySync(outputDirectory.childFile('isolate_snapshot_data').path);
} }
if (_copyAssets) { if (_copyAssets) {
...@@ -68,8 +68,8 @@ abstract class AndroidAssetBundle extends Target { ...@@ -68,8 +68,8 @@ abstract class AndroidAssetBundle extends Target {
targetPlatform: TargetPlatform.android, targetPlatform: TargetPlatform.android,
); );
final DepfileService depfileService = DepfileService( final DepfileService depfileService = DepfileService(
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
); );
depfileService.writeToFile( depfileService.writeToFile(
assetDepfile, assetDepfile,
...@@ -215,11 +215,11 @@ class AndroidAot extends AotElfBase { ...@@ -215,11 +215,11 @@ class AndroidAot extends AotElfBase {
Future<void> build(Environment environment) async { Future<void> build(Environment environment) async {
final AOTSnapshotter snapshotter = AOTSnapshotter( final AOTSnapshotter snapshotter = AOTSnapshotter(
reportTimings: false, reportTimings: false,
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
xcode: globals.xcode, xcode: globals.xcode,
processManager: globals.processManager, processManager: environment.processManager,
artifacts: globals.artifacts, artifacts: environment.artifacts,
); );
final Directory output = environment.buildDir.childDirectory(_androidAbiName); final Directory output = environment.buildDir.childDirectory(_androidAbiName);
final String splitDebugInfo = environment.defines[kSplitDebugInfo]; final String splitDebugInfo = environment.defines[kSplitDebugInfo];
......
...@@ -11,7 +11,6 @@ import '../../base/logger.dart'; ...@@ -11,7 +11,6 @@ import '../../base/logger.dart';
import '../../build_info.dart'; import '../../build_info.dart';
import '../../convert.dart'; import '../../convert.dart';
import '../../devfs.dart'; import '../../devfs.dart';
import '../../globals.dart' as globals;
import '../build_system.dart'; import '../build_system.dart';
import '../depfile.dart'; import '../depfile.dart';
import 'common.dart'; import 'common.dart';
...@@ -44,10 +43,12 @@ Future<Depfile> copyAssets(Environment environment, Directory outputDirectory, { ...@@ -44,10 +43,12 @@ Future<Depfile> copyAssets(Environment environment, Directory outputDirectory, {
); );
final File pubspecFile = environment.projectDir.childFile('pubspec.yaml'); final File pubspecFile = environment.projectDir.childFile('pubspec.yaml');
final AssetBundle assetBundle = AssetBundleFactory.instance.createBundle(); // Only the default asset bundle style is supported in assemble.
final AssetBundle assetBundle = AssetBundleFactory.defaultInstance.createBundle();
final int resultCode = await assetBundle.build( final int resultCode = await assetBundle.build(
manifestPath: pubspecFile.path, manifestPath: pubspecFile.path,
packagesPath: environment.projectDir.childFile('.packages').path, packagesPath: environment.projectDir.childFile('.packages').path,
assetDirPath: null,
); );
if (resultCode != 0) { if (resultCode != 0) {
throw Exception('Failed to bundle asset files.'); throw Exception('Failed to bundle asset files.');
...@@ -63,10 +64,10 @@ Future<Depfile> copyAssets(Environment environment, Directory outputDirectory, { ...@@ -63,10 +64,10 @@ Future<Depfile> copyAssets(Environment environment, Directory outputDirectory, {
final IconTreeShaker iconTreeShaker = IconTreeShaker( final IconTreeShaker iconTreeShaker = IconTreeShaker(
environment, environment,
assetBundle.entries[kFontManifestJson] as DevFSStringContent, assetBundle.entries[kFontManifestJson] as DevFSStringContent,
processManager: globals.processManager, processManager: environment.processManager,
logger: globals.logger, logger: environment.logger,
fileSystem: globals.fs, fileSystem: environment.fileSystem,
artifacts: globals.artifacts, artifacts: environment.artifacts,
); );
final Map<String, DevFSContent> assetEntries = <String, DevFSContent>{ final Map<String, DevFSContent> assetEntries = <String, DevFSContent>{
...@@ -85,7 +86,8 @@ Future<Depfile> copyAssets(Environment environment, Directory outputDirectory, { ...@@ -85,7 +86,8 @@ Future<Depfile> copyAssets(Environment environment, Directory outputDirectory, {
// to `%23.ext`. However, we have to keep it this way since the // to `%23.ext`. However, we have to keep it this way since the
// platform channels in the framework will URI encode these values, // platform channels in the framework will URI encode these values,
// and the native APIs will look for files this way. // and the native APIs will look for files this way.
final File file = globals.fs.file(globals.fs.path.join(outputDirectory.path, entry.key)); final File file = environment.fileSystem.file(
environment.fileSystem.path.join(outputDirectory.path, entry.key));
outputs.add(file); outputs.add(file);
file.parent.createSync(recursive: true); file.parent.createSync(recursive: true);
final DevFSContent content = entry.value; final DevFSContent content = entry.value;
...@@ -222,8 +224,8 @@ class CopyAssets extends Target { ...@@ -222,8 +224,8 @@ class CopyAssets extends Target {
targetPlatform: TargetPlatform.android, targetPlatform: TargetPlatform.android,
); );
final DepfileService depfileService = DepfileService( final DepfileService depfileService = DepfileService(
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
); );
depfileService.writeToFile( depfileService.writeToFile(
depfile, depfile,
......
...@@ -10,8 +10,7 @@ import '../../base/file_system.dart'; ...@@ -10,8 +10,7 @@ import '../../base/file_system.dart';
import '../../build_info.dart'; import '../../build_info.dart';
import '../../compile.dart'; import '../../compile.dart';
import '../../dart/package_map.dart'; import '../../dart/package_map.dart';
import '../../globals.dart' as globals; import '../../globals.dart' as globals hide fs, processManager, artifacts, logger;
import '../../project.dart';
import '../build_system.dart'; import '../build_system.dart';
import '../depfile.dart'; import '../depfile.dart';
import '../exceptions.dart'; import '../exceptions.dart';
...@@ -107,13 +106,13 @@ class CopyFlutterBundle extends Target { ...@@ -107,13 +106,13 @@ class CopyFlutterBundle extends Target {
// Only copy the prebuilt runtimes and kernel blob in debug mode. // Only copy the prebuilt runtimes and kernel blob in debug mode.
if (buildMode == BuildMode.debug) { if (buildMode == BuildMode.debug) {
final String vmSnapshotData = globals.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug); final String vmSnapshotData = environment.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug);
final String isolateSnapshotData = globals.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug); final String isolateSnapshotData = environment.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug);
environment.buildDir.childFile('app.dill') environment.buildDir.childFile('app.dill')
.copySync(environment.outputDir.childFile('kernel_blob.bin').path); .copySync(environment.outputDir.childFile('kernel_blob.bin').path);
globals.fs.file(vmSnapshotData) environment.fileSystem.file(vmSnapshotData)
.copySync(environment.outputDir.childFile('vm_snapshot_data').path); .copySync(environment.outputDir.childFile('vm_snapshot_data').path);
globals.fs.file(isolateSnapshotData) environment.fileSystem.file(isolateSnapshotData)
.copySync(environment.outputDir.childFile('isolate_snapshot_data').path); .copySync(environment.outputDir.childFile('isolate_snapshot_data').path);
} }
final Depfile assetDepfile = await copyAssets( final Depfile assetDepfile = await copyAssets(
...@@ -122,8 +121,8 @@ class CopyFlutterBundle extends Target { ...@@ -122,8 +121,8 @@ class CopyFlutterBundle extends Target {
targetPlatform: TargetPlatform.android, targetPlatform: TargetPlatform.android,
); );
final DepfileService depfileService = DepfileService( final DepfileService depfileService = DepfileService(
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
); );
depfileService.writeToFile( depfileService.writeToFile(
assetDepfile, assetDepfile,
...@@ -191,8 +190,11 @@ class KernelSnapshot extends Target { ...@@ -191,8 +190,11 @@ class KernelSnapshot extends Target {
@override @override
Future<void> build(Environment environment) async { Future<void> build(Environment environment) async {
final KernelCompiler compiler = await kernelCompilerFactory.create( final KernelCompiler compiler = KernelCompiler(
FlutterProject.fromDirectory(environment.projectDir), fileSystem: environment.fileSystem,
logger: environment.logger,
processManager: environment.processManager,
artifacts: environment.artifacts,
); );
if (environment.defines[kBuildMode] == null) { if (environment.defines[kBuildMode] == null) {
throw MissingDefineException(kBuildMode, 'kernel_snapshot'); throw MissingDefineException(kBuildMode, 'kernel_snapshot');
...@@ -201,9 +203,9 @@ class KernelSnapshot extends Target { ...@@ -201,9 +203,9 @@ class KernelSnapshot extends Target {
throw MissingDefineException(kTargetPlatform, 'kernel_snapshot'); throw MissingDefineException(kTargetPlatform, 'kernel_snapshot');
} }
final BuildMode buildMode = getBuildModeForName(environment.defines[kBuildMode]); final BuildMode buildMode = getBuildModeForName(environment.defines[kBuildMode]);
final String targetFile = environment.defines[kTargetFile] ?? globals.fs.path.join('lib', 'main.dart'); final String targetFile = environment.defines[kTargetFile] ?? environment.fileSystem.path.join('lib', 'main.dart');
final File packagesFile = environment.projectDir.childFile('.packages'); final File packagesFile = environment.projectDir.childFile('.packages');
final String targetFileAbsolute = globals.fs.file(targetFile).absolute.path; final String targetFileAbsolute = environment.fileSystem.file(targetFile).absolute.path;
// everything besides 'false' is considered to be enabled. // everything besides 'false' is considered to be enabled.
final bool trackWidgetCreation = environment.defines[kTrackWidgetCreation] != 'false'; final bool trackWidgetCreation = environment.defines[kTrackWidgetCreation] != 'false';
final TargetPlatform targetPlatform = getTargetPlatformForName(environment.defines[kTargetPlatform]); final TargetPlatform targetPlatform = getTargetPlatformForName(environment.defines[kTargetPlatform]);
...@@ -238,7 +240,7 @@ class KernelSnapshot extends Target { ...@@ -238,7 +240,7 @@ class KernelSnapshot extends Target {
); );
final CompilerOutput output = await compiler.compile( final CompilerOutput output = await compiler.compile(
sdkRoot: globals.artifacts.getArtifactPath( sdkRoot: environment.artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath, Artifact.flutterPatchedSdkPath,
platform: targetPlatform, platform: targetPlatform,
mode: buildMode, mode: buildMode,
...@@ -275,11 +277,11 @@ abstract class AotElfBase extends Target { ...@@ -275,11 +277,11 @@ abstract class AotElfBase extends Target {
Future<void> build(Environment environment) async { Future<void> build(Environment environment) async {
final AOTSnapshotter snapshotter = AOTSnapshotter( final AOTSnapshotter snapshotter = AOTSnapshotter(
reportTimings: false, reportTimings: false,
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
xcode: globals.xcode, xcode: globals.xcode,
processManager: globals.processManager, processManager: environment.processManager,
artifacts: globals.artifacts, artifacts: environment.artifacts,
); );
final String outputPath = environment.buildDir.path; final String outputPath = environment.buildDir.path;
if (environment.defines[kBuildMode] == null) { if (environment.defines[kBuildMode] == null) {
......
...@@ -9,7 +9,7 @@ import '../../base/file_system.dart'; ...@@ -9,7 +9,7 @@ import '../../base/file_system.dart';
import '../../base/io.dart'; import '../../base/io.dart';
import '../../base/process.dart'; import '../../base/process.dart';
import '../../build_info.dart'; import '../../build_info.dart';
import '../../globals.dart' as globals; import '../../globals.dart' as globals hide fs, logger, processManager, artifacts;
import '../../macos/xcode.dart'; import '../../macos/xcode.dart';
import '../../project.dart'; import '../../project.dart';
import '../build_system.dart'; import '../build_system.dart';
...@@ -33,11 +33,11 @@ abstract class AotAssemblyBase extends Target { ...@@ -33,11 +33,11 @@ abstract class AotAssemblyBase extends Target {
Future<void> build(Environment environment) async { Future<void> build(Environment environment) async {
final AOTSnapshotter snapshotter = AOTSnapshotter( final AOTSnapshotter snapshotter = AOTSnapshotter(
reportTimings: false, reportTimings: false,
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
xcode: globals.xcode, xcode: globals.xcode,
artifacts: globals.artifacts, artifacts: environment.artifacts,
processManager: globals.processManager, processManager: environment.processManager,
); );
final String buildOutputPath = environment.buildDir.path; final String buildOutputPath = environment.buildDir.path;
if (environment.defines[kBuildMode] == null) { if (environment.defines[kBuildMode] == null) {
...@@ -76,7 +76,7 @@ abstract class AotAssemblyBase extends Target { ...@@ -76,7 +76,7 @@ abstract class AotAssemblyBase extends Target {
buildMode: buildMode, buildMode: buildMode,
mainPath: environment.buildDir.childFile('app.dill').path, mainPath: environment.buildDir.childFile('app.dill').path,
packagesPath: environment.projectDir.childFile('.packages').path, packagesPath: environment.projectDir.childFile('.packages').path,
outputPath: globals.fs.path.join(buildOutputPath, getNameForDarwinArch(iosArch)), outputPath: environment.fileSystem.path.join(buildOutputPath, getNameForDarwinArch(iosArch)),
darwinArch: iosArch, darwinArch: iosArch,
bitcode: bitcode, bitcode: bitcode,
quiet: true, quiet: true,
...@@ -89,12 +89,12 @@ abstract class AotAssemblyBase extends Target { ...@@ -89,12 +89,12 @@ abstract class AotAssemblyBase extends Target {
if (results.any((int result) => result != 0)) { if (results.any((int result) => result != 0)) {
throw Exception('AOT snapshotter exited with code ${results.join()}'); throw Exception('AOT snapshotter exited with code ${results.join()}');
} }
final String resultPath = globals.fs.path.join(environment.buildDir.path, 'App.framework', 'App'); final String resultPath = environment.fileSystem.path.join(environment.buildDir.path, 'App.framework', 'App');
globals.fs.directory(resultPath).parent.createSync(recursive: true); environment.fileSystem.directory(resultPath).parent.createSync(recursive: true);
final ProcessResult result = await globals.processManager.run(<String>[ final ProcessResult result = await environment.processManager.run(<String>[
'lipo', 'lipo',
...iosArchs.map((DarwinArch iosArch) => ...iosArchs.map((DarwinArch iosArch) =>
globals.fs.path.join(buildOutputPath, getNameForDarwinArch(iosArch), 'App.framework', 'App')), environment.fileSystem.path.join(buildOutputPath, getNameForDarwinArch(iosArch), 'App.framework', 'App')),
'-create', '-create',
'-output', '-output',
resultPath, resultPath,
...@@ -294,13 +294,13 @@ abstract class IosAssetBundle extends Target { ...@@ -294,13 +294,13 @@ abstract class IosAssetBundle extends Target {
.childFile('App') .childFile('App')
.copySync(frameworkDirectory.childFile('App').path); .copySync(frameworkDirectory.childFile('App').path);
final String vmSnapshotData = globals.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug); final String vmSnapshotData = environment.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug);
final String isolateSnapshotData = globals.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug); final String isolateSnapshotData = environment.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug);
environment.buildDir.childFile('app.dill') environment.buildDir.childFile('app.dill')
.copySync(assetDirectory.childFile('kernel_blob.bin').path); .copySync(assetDirectory.childFile('kernel_blob.bin').path);
globals.fs.file(vmSnapshotData) environment.fileSystem.file(vmSnapshotData)
.copySync(assetDirectory.childFile('vm_snapshot_data').path); .copySync(assetDirectory.childFile('vm_snapshot_data').path);
globals.fs.file(isolateSnapshotData) environment.fileSystem.file(isolateSnapshotData)
.copySync(assetDirectory.childFile('isolate_snapshot_data').path); .copySync(assetDirectory.childFile('isolate_snapshot_data').path);
} else { } else {
environment.buildDir.childDirectory('App.framework').childFile('App') environment.buildDir.childDirectory('App.framework').childFile('App')
...@@ -314,8 +314,8 @@ abstract class IosAssetBundle extends Target { ...@@ -314,8 +314,8 @@ abstract class IosAssetBundle extends Target {
targetPlatform: TargetPlatform.ios, targetPlatform: TargetPlatform.ios,
); );
final DepfileService depfileService = DepfileService( final DepfileService depfileService = DepfileService(
fileSystem: globals.fs, fileSystem: environment.fileSystem,
logger: globals.logger, logger: environment.logger,
); );
depfileService.writeToFile( depfileService.writeToFile(
assetDepfile, assetDepfile,
...@@ -406,7 +406,8 @@ Future<RunResult> createStubAppFramework(File outputFile, SdkType sdk, { bool in ...@@ -406,7 +406,8 @@ Future<RunResult> createStubAppFramework(File outputFile, SdkType sdk, { bool in
throwToolExit('Failed to create App.framework stub at ${outputFile.path}: $e'); throwToolExit('Failed to create App.framework stub at ${outputFile.path}: $e');
} }
final Directory tempDir = globals.fs.systemTempDirectory.createTempSync('flutter_tools_stub_source.'); final Directory tempDir = outputFile.fileSystem.systemTempDirectory
.createTempSync('flutter_tools_stub_source.');
try { try {
final File stubSource = tempDir.childFile('debug_app.cc') final File stubSource = tempDir.childFile('debug_app.cc')
..writeAsStringSync(r''' ..writeAsStringSync(r'''
...@@ -444,7 +445,7 @@ Future<RunResult> createStubAppFramework(File outputFile, SdkType sdk, { bool in ...@@ -444,7 +445,7 @@ Future<RunResult> createStubAppFramework(File outputFile, SdkType sdk, { bool in
} finally { } finally {
try { try {
tempDir.deleteSync(recursive: true); tempDir.deleteSync(recursive: true);
} on FileSystemException catch (_) { } on FileSystemException {
// Best effort. Sometimes we can't delete things from system temp. // Best effort. Sometimes we can't delete things from system temp.
} on Exception catch (e) { } on Exception catch (e) {
throwToolExit('Failed to create App.framework stub at ${outputFile.path}: $e'); throwToolExit('Failed to create App.framework stub at ${outputFile.path}: $e');
......
...@@ -2,83 +2,93 @@ ...@@ -2,83 +2,93 @@
// Use of this source code is governed by a BSD-style license that can be // Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file. // found in the LICENSE file.
import 'package:file/memory.dart';
import 'package:file_testing/file_testing.dart'; import 'package:file_testing/file_testing.dart';
import 'package:flutter_tools/src/artifacts.dart'; import 'package:flutter_tools/src/artifacts.dart';
import 'package:flutter_tools/src/base/file_system.dart'; import 'package:flutter_tools/src/base/file_system.dart';
import 'package:flutter_tools/src/base/logger.dart';
import 'package:flutter_tools/src/base/platform.dart'; import 'package:flutter_tools/src/base/platform.dart';
import 'package:flutter_tools/src/build_info.dart'; import 'package:flutter_tools/src/build_info.dart';
import 'package:flutter_tools/src/build_system/build_system.dart'; import 'package:flutter_tools/src/build_system/build_system.dart';
import 'package:flutter_tools/src/build_system/targets/android.dart'; import 'package:flutter_tools/src/build_system/targets/android.dart';
import 'package:flutter_tools/src/build_system/targets/assets.dart'; import 'package:flutter_tools/src/build_system/targets/assets.dart';
import 'package:flutter_tools/src/build_system/targets/common.dart'; import 'package:flutter_tools/src/build_system/targets/common.dart';
import 'package:flutter_tools/src/cache.dart';
import 'package:flutter_tools/src/convert.dart'; import 'package:flutter_tools/src/convert.dart';
import 'package:flutter_tools/src/globals.dart' as globals;
import 'package:mockito/mockito.dart';
import '../../../src/common.dart'; import '../../../src/common.dart';
import '../../../src/context.dart';
import '../../../src/fake_process_manager.dart'; import '../../../src/fake_process_manager.dart';
import '../../../src/testbed.dart';
final Platform platform = FakePlatform(operatingSystem: 'linux', environment: const <String, String>{});
void main() { void main() {
FakeProcessManager fakeProcessManager; FakeProcessManager processManager;
final Testbed testbed = Testbed(overrides: <Type, Generator>{ FileSystem fileSystem;
Cache: () => FakeCache(), Artifacts artifacts;
Platform: () => FakePlatform(operatingSystem: 'linux', environment: const <String, String>{}), Logger logger;
setUp(() {
logger = BufferLogger.test();
fileSystem = MemoryFileSystem.test();
processManager = FakeProcessManager.list(<FakeCommand>[]);
artifacts = Artifacts.test();
}); });
test('Android AOT targets has analyicsName', () { testWithoutContext('Android AOT targets has analyicsName', () {
expect(androidArmProfile.analyticsName, 'android_aot'); expect(androidArmProfile.analyticsName, 'android_aot');
}); });
testbed.test('debug bundle contains expected resources', () async { testUsingContext('debug bundle contains expected resources', () async {
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'debug', kBuildMode: 'debug',
}, },
processManager: fakeProcessManager, processManager: processManager,
artifacts: MockArtifacts(), artifacts: artifacts,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
); );
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
// create pre-requisites. // create pre-requisites.
environment.buildDir.childFile('app.dill') environment.buildDir.childFile('app.dill')
.writeAsStringSync('abcd'); .writeAsStringSync('abcd');
final Directory hostDirectory = globals.fs.currentDirectory fileSystem
.childDirectory(getNameForHostPlatform(getCurrentHostPlatform())) .file(artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug))
..createSync(recursive: true); .createSync(recursive: true);
hostDirectory.childFile('vm_isolate_snapshot.bin').createSync(); fileSystem
hostDirectory.childFile('isolate_snapshot.bin').createSync(); .file(artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug))
.createSync(recursive: true);
await const DebugAndroidApplication().build(environment); await const DebugAndroidApplication().build(environment);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'isolate_snapshot_data')).existsSync(), true); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'isolate_snapshot_data')).existsSync(), true);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'vm_snapshot_data')).existsSync(), true); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'vm_snapshot_data')).existsSync(), true);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'kernel_blob.bin')).existsSync(), true); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'kernel_blob.bin')).existsSync(), true);
}, overrides: <Type, Generator>{
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
}); });
testbed.test('debug bundle contains expected resources with bundle SkSL', () async { testUsingContext('debug bundle contains expected resources with bundle SkSL', () async {
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'debug', kBuildMode: 'debug',
}, },
inputs: <String, String>{ inputs: <String, String>{
kBundleSkSLPath: 'bundle.sksl' kBundleSkSLPath: 'bundle.sksl'
}, },
processManager: fakeProcessManager, processManager: processManager,
artifacts: MockArtifacts(), artifacts: artifacts,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
engineVersion: '2', engineVersion: '2',
); );
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
globals.fs.file('bundle.sksl').writeAsStringSync(json.encode( fileSystem.file('bundle.sksl').writeAsStringSync(json.encode(
<String, Object>{ <String, Object>{
'engineRevision': '2', 'engineRevision': '2',
'platform': 'android', 'platform': 'android',
...@@ -91,31 +101,35 @@ void main() { ...@@ -91,31 +101,35 @@ void main() {
// create pre-requisites. // create pre-requisites.
environment.buildDir.childFile('app.dill') environment.buildDir.childFile('app.dill')
.writeAsStringSync('abcd'); .writeAsStringSync('abcd');
final Directory hostDirectory = globals.fs.currentDirectory fileSystem
.childDirectory(getNameForHostPlatform(getCurrentHostPlatform())) .file(artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug))
..createSync(recursive: true); .createSync(recursive: true);
hostDirectory.childFile('vm_isolate_snapshot.bin').createSync(); fileSystem
hostDirectory.childFile('isolate_snapshot.bin').createSync(); .file(artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug))
.createSync(recursive: true);
await const DebugAndroidApplication().build(environment); await const DebugAndroidApplication().build(environment);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'isolate_snapshot_data')), exists); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'isolate_snapshot_data')), exists);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'vm_snapshot_data')), exists); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'vm_snapshot_data')), exists);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'kernel_blob.bin')), exists); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'kernel_blob.bin')), exists);
expect(globals.fs.file(globals.fs.path.join('out', 'flutter_assets', 'io.flutter.shaders.json')), exists); expect(fileSystem.file(fileSystem.path.join('out', 'flutter_assets', 'io.flutter.shaders.json')), exists);
}, overrides: <Type, Generator>{
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
}); });
testbed.test('profile bundle contains expected resources', () async { testUsingContext('profile bundle contains expected resources', () async {
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'profile', kBuildMode: 'profile',
}, },
artifacts: MockArtifacts(), artifacts: artifacts,
processManager: fakeProcessManager, processManager: processManager,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
); );
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
...@@ -125,20 +139,23 @@ void main() { ...@@ -125,20 +139,23 @@ void main() {
await const ProfileAndroidApplication().build(environment); await const ProfileAndroidApplication().build(environment);
expect(globals.fs.file(globals.fs.path.join('out', 'app.so')).existsSync(), true); expect(fileSystem.file(fileSystem.path.join('out', 'app.so')).existsSync(), true);
}, overrides: <Type, Generator>{
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
}); });
testbed.test('release bundle contains expected resources', () async { testWithoutContext('release bundle contains expected resources', () async {
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'release', kBuildMode: 'release',
}, },
artifacts: MockArtifacts(), artifacts: artifacts,
processManager: fakeProcessManager, processManager: processManager,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
); );
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
...@@ -148,34 +165,37 @@ void main() { ...@@ -148,34 +165,37 @@ void main() {
await const ReleaseAndroidApplication().build(environment); await const ReleaseAndroidApplication().build(environment);
expect(globals.fs.file(globals.fs.path.join('out', 'app.so')).existsSync(), true); expect(fileSystem.file(fileSystem.path.join('out', 'app.so')).existsSync(), true);
}); });
testbed.test('AndroidAot can build provided target platform', () async { testUsingContext('AndroidAot can build provided target platform', () async {
fakeProcessManager = FakeProcessManager.list(<FakeCommand>[]); processManager = FakeProcessManager.list(<FakeCommand>[]);
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'release', kBuildMode: 'release',
}, },
artifacts: MockArtifacts(), artifacts: artifacts,
processManager: FakeProcessManager.list(<FakeCommand>[]), processManager: processManager,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
);
fakeProcessManager.addCommand(FakeCommand(command: <String>[
globals.fs.path.absolute(globals.fs.path.join('android-arm64-release', 'linux-x64', 'gen_snapshot')),
'--deterministic',
'--snapshot_kind=app-aot-elf',
'--elf=${environment.buildDir.childDirectory('arm64-v8a').childFile('app.so').path}',
'--strip',
'--no-causal-async-stacks',
'--lazy-async-stacks',
environment.buildDir.childFile('app.dill').path,
],
)
); );
processManager.addCommand(FakeCommand(command: <String>[
artifacts.getArtifactPath(
Artifact.genSnapshot,
platform: TargetPlatform.android_arm64,
mode: BuildMode.release,
),
'--deterministic',
'--snapshot_kind=app-aot-elf',
'--elf=${environment.buildDir.childDirectory('arm64-v8a').childFile('app.so').path}',
'--strip',
'--no-causal-async-stacks',
'--lazy-async-stacks',
environment.buildDir.childFile('app.dill').path,
],
));
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
environment.buildDir.childFile('app.dill').createSync(); environment.buildDir.childFile('app.dill').createSync();
environment.projectDir.childFile('.packages').writeAsStringSync('\n'); environment.projectDir.childFile('.packages').writeAsStringSync('\n');
...@@ -183,29 +203,34 @@ void main() { ...@@ -183,29 +203,34 @@ void main() {
await androidAot.build(environment); await androidAot.build(environment);
expect(fakeProcessManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
}, overrides: <Type, Generator>{ }, overrides: <Type, Generator>{
ProcessManager: () => fakeProcessManager, FileSystem: () => fileSystem,
ProcessManager: () => processManager,
}); });
testbed.test('kExtraGenSnapshotOptions passes values to gen_snapshot', () async { testUsingContext('kExtraGenSnapshotOptions passes values to gen_snapshot', () async {
fakeProcessManager = FakeProcessManager.list(<FakeCommand>[]); processManager = FakeProcessManager.list(<FakeCommand>[]);
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'release', kBuildMode: 'release',
kExtraGenSnapshotOptions: 'foo,bar,baz=2', kExtraGenSnapshotOptions: 'foo,bar,baz=2',
kTargetPlatform: 'android-arm', kTargetPlatform: 'android-arm',
}, },
processManager: fakeProcessManager, processManager: processManager,
artifacts: MockArtifacts(), artifacts: artifacts,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
); );
fakeProcessManager.addCommand( processManager.addCommand(
FakeCommand(command: <String>[ FakeCommand(command: <String>[
globals.fs.path.absolute(globals.fs.path.join('android-arm64-release', 'linux-x64', 'gen_snapshot')), artifacts.getArtifactPath(
Artifact.genSnapshot,
platform: TargetPlatform.android_arm64,
mode: BuildMode.release,
),
'--deterministic', '--deterministic',
'foo', 'foo',
'bar', 'bar',
...@@ -216,7 +241,8 @@ void main() { ...@@ -216,7 +241,8 @@ void main() {
'--no-causal-async-stacks', '--no-causal-async-stacks',
'--lazy-async-stacks', '--lazy-async-stacks',
environment.buildDir.childFile('app.dill').path environment.buildDir.childFile('app.dill').path
])); ],
));
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
environment.buildDir.childFile('app.dill').createSync(); environment.buildDir.childFile('app.dill').createSync();
environment.projectDir.childFile('.packages').writeAsStringSync('\n'); environment.projectDir.childFile('.packages').writeAsStringSync('\n');
...@@ -224,20 +250,21 @@ void main() { ...@@ -224,20 +250,21 @@ void main() {
await const AndroidAot(TargetPlatform.android_arm64, BuildMode.release) await const AndroidAot(TargetPlatform.android_arm64, BuildMode.release)
.build(environment); .build(environment);
}, overrides: <Type, Generator>{ }, overrides: <Type, Generator>{
ProcessManager: () => fakeProcessManager, FileSystem: () => fileSystem,
ProcessManager: () => processManager,
}); });
testbed.test('android aot bundle copies so from abi directory', () async { testWithoutContext('android aot bundle copies so from abi directory', () async {
final Environment environment = Environment.test( final Environment environment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
outputDir: globals.fs.directory('out')..createSync(), outputDir: fileSystem.directory('out')..createSync(),
defines: <String, String>{ defines: <String, String>{
kBuildMode: 'release', kBuildMode: 'release',
}, },
processManager: fakeProcessManager, processManager: processManager,
artifacts: MockArtifacts(), artifacts: artifacts,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
); );
environment.buildDir.createSync(recursive: true); environment.buildDir.createSync(recursive: true);
const AndroidAot androidAot = AndroidAot(TargetPlatform.android_arm64, BuildMode.release); const AndroidAot androidAot = AndroidAot(TargetPlatform.android_arm64, BuildMode.release);
...@@ -255,5 +282,3 @@ void main() { ...@@ -255,5 +282,3 @@ void main() {
.childFile('app.so').existsSync(), true); .childFile('app.so').existsSync(), true);
}); });
} }
class MockArtifacts extends Mock implements Artifacts {}
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
import 'package:file/memory.dart'; import 'package:file/memory.dart';
import 'package:flutter_tools/src/artifacts.dart'; import 'package:flutter_tools/src/artifacts.dart';
import 'package:flutter_tools/src/base/file_system.dart'; import 'package:flutter_tools/src/base/file_system.dart';
import 'package:flutter_tools/src/base/logger.dart';
import 'package:flutter_tools/src/base/platform.dart'; import 'package:flutter_tools/src/base/platform.dart';
import 'package:flutter_tools/src/build_info.dart'; import 'package:flutter_tools/src/build_info.dart';
import 'package:flutter_tools/src/build_system/build_system.dart'; import 'package:flutter_tools/src/build_system/build_system.dart';
...@@ -13,83 +14,80 @@ import 'package:flutter_tools/src/build_system/targets/common.dart'; ...@@ -13,83 +14,80 @@ import 'package:flutter_tools/src/build_system/targets/common.dart';
import 'package:flutter_tools/src/build_system/targets/ios.dart'; import 'package:flutter_tools/src/build_system/targets/ios.dart';
import 'package:flutter_tools/src/cache.dart'; import 'package:flutter_tools/src/cache.dart';
import 'package:flutter_tools/src/compile.dart'; import 'package:flutter_tools/src/compile.dart';
import 'package:flutter_tools/src/globals.dart' as globals;
import 'package:process/process.dart';
import '../../../src/common.dart'; import '../../../src/common.dart';
import '../../../src/context.dart';
import '../../../src/fake_process_manager.dart'; import '../../../src/fake_process_manager.dart';
import '../../../src/testbed.dart';
const String kBoundaryKey = '4d2d9609-c662-4571-afde-31410f96caa6'; const String kBoundaryKey = '4d2d9609-c662-4571-afde-31410f96caa6';
const String kElfAot = '--snapshot_kind=app-aot-elf'; const String kElfAot = '--snapshot_kind=app-aot-elf';
const String kAssemblyAot = '--snapshot_kind=app-aot-assembly'; const String kAssemblyAot = '--snapshot_kind=app-aot-assembly';
final Platform macPlatform = FakePlatform(operatingSystem: 'macos', environment: <String, String>{});
void main() { void main() {
Testbed testbed;
FakeProcessManager processManager; FakeProcessManager processManager;
Environment androidEnvironment; Environment androidEnvironment;
Environment iosEnvironment; Environment iosEnvironment;
Artifacts artifacts; Artifacts artifacts;
FileSystem fileSystem;
Logger logger;
setUpAll(() { setUpAll(() {
Cache.disableLocking(); Cache.disableLocking();
}); });
setUp(() { setUp(() {
testbed = Testbed(setup: () { processManager = FakeProcessManager.list(<FakeCommand>[]);
androidEnvironment = Environment.test( logger = BufferLogger.test();
globals.fs.currentDirectory, artifacts = Artifacts.test();
defines: <String, String>{ fileSystem = MemoryFileSystem.test(style: FileSystemStyle.posix);
kBuildMode: getNameForBuildMode(BuildMode.profile), androidEnvironment = Environment.test(
kTargetPlatform: getNameForTargetPlatform(TargetPlatform.android_arm), fileSystem.currentDirectory,
}, defines: <String, String>{
artifacts: artifacts, kBuildMode: getNameForBuildMode(BuildMode.profile),
processManager: processManager, kTargetPlatform: getNameForTargetPlatform(TargetPlatform.android_arm),
fileSystem: globals.fs, },
logger: globals.logger, artifacts: artifacts,
); processManager: processManager,
androidEnvironment.buildDir.createSync(recursive: true); fileSystem: fileSystem,
iosEnvironment = Environment.test( logger: logger,
globals.fs.currentDirectory, );
defines: <String, String>{ androidEnvironment.buildDir.createSync(recursive: true);
kBuildMode: getNameForBuildMode(BuildMode.profile), iosEnvironment = Environment.test(
kTargetPlatform: getNameForTargetPlatform(TargetPlatform.ios), fileSystem.currentDirectory,
}, defines: <String, String>{
artifacts: artifacts, kBuildMode: getNameForBuildMode(BuildMode.profile),
processManager: processManager, kTargetPlatform: getNameForTargetPlatform(TargetPlatform.ios),
fileSystem: globals.fs, },
logger: globals.logger, artifacts: artifacts,
); processManager: processManager,
iosEnvironment.buildDir.createSync(recursive: true); fileSystem: fileSystem,
artifacts = CachedArtifacts( logger: logger,
cache: globals.cache, );
platform: globals.platform, iosEnvironment.buildDir.createSync(recursive: true);
fileSystem: globals.fs,
);
}, overrides: <Type, Generator>{
Platform: () => FakePlatform(operatingSystem: 'macos', environment: <String, String>{}),
FileSystem: () => MemoryFileSystem.test(style: FileSystemStyle.posix),
ProcessManager: () => processManager,
});
}); });
test('KernelSnapshot throws error if missing build mode', () => testbed.run(() async { testWithoutContext('KernelSnapshot throws error if missing build mode', () async {
androidEnvironment.defines.remove(kBuildMode); androidEnvironment.defines.remove(kBuildMode);
expect( expect(
const KernelSnapshot().build(androidEnvironment), const KernelSnapshot().build(androidEnvironment),
throwsA(isA<MissingDefineException>())); throwsA(isA<MissingDefineException>()));
})); });
test('KernelSnapshot handles null result from kernel compilation', () => testbed.run(() async { testWithoutContext('KernelSnapshot handles null result from kernel compilation', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.android_arm,
mode: BuildMode.profile,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=false', '-Ddart.developer.causal_async_stacks=false',
...buildModeOptions(BuildMode.profile), ...buildModeOptions(BuildMode.profile),
...@@ -108,18 +106,22 @@ void main() { ...@@ -108,18 +106,22 @@ void main() {
await expectLater(() => const KernelSnapshot().build(androidEnvironment), await expectLater(() => const KernelSnapshot().build(androidEnvironment),
throwsA(isA<Exception>())); throwsA(isA<Exception>()));
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('KernelSnapshot does not use track widget creation on profile builds', () => testbed.run(() async { testWithoutContext('KernelSnapshot does not use track widget creation on profile builds', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.android_arm,
mode: BuildMode.profile,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=false', '-Ddart.developer.causal_async_stacks=false',
...buildModeOptions(BuildMode.profile), ...buildModeOptions(BuildMode.profile),
...@@ -138,18 +140,22 @@ void main() { ...@@ -138,18 +140,22 @@ void main() {
await const KernelSnapshot().build(androidEnvironment); await const KernelSnapshot().build(androidEnvironment);
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('KernelSnapshot correctly handles an empty string in ExtraFrontEndOptions', () => testbed.run(() async { testWithoutContext('KernelSnapshot correctly handles an empty string in ExtraFrontEndOptions', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.android_arm,
mode: BuildMode.profile,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=false', '-Ddart.developer.causal_async_stacks=false',
...buildModeOptions(BuildMode.profile), ...buildModeOptions(BuildMode.profile),
...@@ -169,18 +175,22 @@ void main() { ...@@ -169,18 +175,22 @@ void main() {
.build(androidEnvironment..defines[kExtraFrontEndOptions] = ''); .build(androidEnvironment..defines[kExtraFrontEndOptions] = '');
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('KernelSnapshot correctly forwards ExtraFrontEndOptions', () => testbed.run(() async { testWithoutContext('KernelSnapshot correctly forwards ExtraFrontEndOptions', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.android_arm,
mode: BuildMode.profile,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=false', '-Ddart.developer.causal_async_stacks=false',
...buildModeOptions(BuildMode.profile), ...buildModeOptions(BuildMode.profile),
...@@ -202,18 +212,22 @@ void main() { ...@@ -202,18 +212,22 @@ void main() {
.build(androidEnvironment..defines[kExtraFrontEndOptions] = 'foo,bar'); .build(androidEnvironment..defines[kExtraFrontEndOptions] = 'foo,bar');
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('KernelSnapshot can disable track-widget-creation on debug builds', () => testbed.run(() async { testWithoutContext('KernelSnapshot can disable track-widget-creation on debug builds', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.android_arm,
mode: BuildMode.debug,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=true', '-Ddart.developer.causal_async_stacks=true',
...buildModeOptions(BuildMode.debug), ...buildModeOptions(BuildMode.debug),
...@@ -233,18 +247,22 @@ void main() { ...@@ -233,18 +247,22 @@ void main() {
..defines[kTrackWidgetCreation] = 'false'); ..defines[kTrackWidgetCreation] = 'false');
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('KernelSnapshot forces platform linking on debug for darwin target platforms', () => testbed.run(() async { testWithoutContext('KernelSnapshot forces platform linking on debug for darwin target platforms', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.darwin_x64,
mode: BuildMode.debug,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=true', '-Ddart.developer.causal_async_stacks=true',
...buildModeOptions(BuildMode.debug), ...buildModeOptions(BuildMode.debug),
...@@ -265,29 +283,33 @@ void main() { ...@@ -265,29 +283,33 @@ void main() {
); );
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('KernelSnapshot does use track widget creation on debug builds', () => testbed.run(() async { testWithoutContext('KernelSnapshot does use track widget creation on debug builds', () async {
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
final Environment testEnvironment = Environment.test( final Environment testEnvironment = Environment.test(
globals.fs.currentDirectory, fileSystem.currentDirectory,
defines: <String, String>{ defines: <String, String>{
kBuildMode: getNameForBuildMode(BuildMode.debug), kBuildMode: getNameForBuildMode(BuildMode.debug),
kTargetPlatform: getNameForTargetPlatform(TargetPlatform.android_arm), kTargetPlatform: getNameForTargetPlatform(TargetPlatform.android_arm),
}, },
processManager: processManager, processManager: processManager,
artifacts: artifacts, artifacts: artifacts,
fileSystem: globals.fs, fileSystem: fileSystem,
logger: globals.logger, logger: logger,
); );
final String build = testEnvironment.buildDir.path; final String build = testEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.engineDartBinary), artifacts.getArtifactPath(Artifact.engineDartBinary),
'--disable-dart-dev', '--disable-dart-dev',
artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk), artifacts.getArtifactPath(Artifact.frontendServerSnapshotForEngineDartSdk),
'--sdk-root', '--sdk-root',
artifacts.getArtifactPath(Artifact.flutterPatchedSdkPath) + '/', artifacts.getArtifactPath(
Artifact.flutterPatchedSdkPath,
platform: TargetPlatform.android_arm,
mode: BuildMode.debug,
) + '/',
'--target=flutter', '--target=flutter',
'-Ddart.developer.causal_async_stacks=true', '-Ddart.developer.causal_async_stacks=true',
...buildModeOptions(BuildMode.debug), ...buildModeOptions(BuildMode.debug),
...@@ -306,13 +328,17 @@ void main() { ...@@ -306,13 +328,17 @@ void main() {
await const KernelSnapshot().build(testEnvironment); await const KernelSnapshot().build(testEnvironment);
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('AotElfProfile Produces correct output directory', () => testbed.run(() async { testUsingContext('AotElfProfile Produces correct output directory', () async {
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.genSnapshot, mode: BuildMode.profile), artifacts.getArtifactPath(
Artifact.genSnapshot,
platform: TargetPlatform.android_arm,
mode: BuildMode.profile,
),
'--deterministic', '--deterministic',
kElfAot, kElfAot,
'--elf=$build/app.so', '--elf=$build/app.so',
...@@ -329,47 +355,60 @@ void main() { ...@@ -329,47 +355,60 @@ void main() {
await const AotElfProfile(TargetPlatform.android_arm).build(androidEnvironment); await const AotElfProfile(TargetPlatform.android_arm).build(androidEnvironment);
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
test('AotElfProfile throws error if missing build mode', () => testbed.run(() async { testUsingContext('AotElfProfile throws error if missing build mode', () async {
androidEnvironment.defines.remove(kBuildMode); androidEnvironment.defines.remove(kBuildMode);
expect(const AotElfProfile(TargetPlatform.android_arm).build(androidEnvironment), expect(const AotElfProfile(TargetPlatform.android_arm).build(androidEnvironment),
throwsA(isA<MissingDefineException>())); throwsA(isA<MissingDefineException>()));
})); });
test('AotElfProfile throws error if missing target platform', () => testbed.run(() async { testUsingContext('AotElfProfile throws error if missing target platform', () async {
androidEnvironment.defines.remove(kTargetPlatform); androidEnvironment.defines.remove(kTargetPlatform);
expect(const AotElfProfile(TargetPlatform.android_arm).build(androidEnvironment), expect(const AotElfProfile(TargetPlatform.android_arm).build(androidEnvironment),
throwsA(isA<MissingDefineException>())); throwsA(isA<MissingDefineException>()));
})); });
test('AotAssemblyProfile throws error if missing build mode', () => testbed.run(() async { testUsingContext('AotAssemblyProfile throws error if missing build mode', () async {
iosEnvironment.defines.remove(kBuildMode); iosEnvironment.defines.remove(kBuildMode);
expect(const AotAssemblyProfile().build(iosEnvironment), expect(const AotAssemblyProfile().build(iosEnvironment),
throwsA(isA<MissingDefineException>())); throwsA(isA<MissingDefineException>()));
})); }, overrides: <Type, Generator>{
Platform: () => macPlatform,
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
});
test('AotAssemblyProfile throws error if missing target platform', () => testbed.run(() async { testUsingContext('AotAssemblyProfile throws error if missing target platform', () async {
iosEnvironment.defines.remove(kTargetPlatform); iosEnvironment.defines.remove(kTargetPlatform);
expect(const AotAssemblyProfile().build(iosEnvironment), expect(const AotAssemblyProfile().build(iosEnvironment),
throwsA(isA<MissingDefineException>())); throwsA(isA<MissingDefineException>()));
})); }, overrides: <Type, Generator>{
Platform: () => macPlatform,
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
});
test('AotAssemblyProfile throws error if built for non-iOS platform', () => testbed.run(() async { testUsingContext('AotAssemblyProfile throws error if built for non-iOS platform', () async {
expect(const AotAssemblyProfile().build(androidEnvironment), expect(const AotAssemblyProfile().build(androidEnvironment),
throwsA(isA<Exception>())); throwsA(isA<Exception>()));
})); }, overrides: <Type, Generator>{
Platform: () => macPlatform,
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
});
test('AotAssemblyProfile generates multiple arches and lipos together', () => testbed.run(() async { testUsingContext('AotAssemblyProfile generates multiple arches and lipos together', () async {
final String build = iosEnvironment.buildDir.path; final String build = iosEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
// This path is not known by the cache due to the iOS gen_snapshot split. // This path is not known by the cache due to the iOS gen_snapshot split.
'bin/cache/artifacts/engine/ios-profile/gen_snapshot_armv7', 'Artifact.genSnapshot.TargetPlatform.ios.profile_armv7',
'--deterministic', '--deterministic',
kAssemblyAot, kAssemblyAot,
'--assembly=$build/armv7/snapshot_assembly.S', '--assembly=$build/armv7/snapshot_assembly.S',
...@@ -382,7 +421,7 @@ void main() { ...@@ -382,7 +421,7 @@ void main() {
]), ]),
FakeCommand(command: <String>[ FakeCommand(command: <String>[
// This path is not known by the cache due to the iOS gen_snapshot split. // This path is not known by the cache due to the iOS gen_snapshot split.
'bin/cache/artifacts/engine/ios-profile/gen_snapshot_arm64', 'Artifact.genSnapshot.TargetPlatform.ios.profile_arm64',
'--deterministic', '--deterministic',
kAssemblyAot, kAssemblyAot,
'--assembly=$build/arm64/snapshot_assembly.S', '--assembly=$build/arm64/snapshot_assembly.S',
...@@ -487,16 +526,20 @@ void main() { ...@@ -487,16 +526,20 @@ void main() {
await const AotAssemblyProfile().build(iosEnvironment); await const AotAssemblyProfile().build(iosEnvironment);
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); }, overrides: <Type, Generator>{
Platform: () => macPlatform,
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
});
test('AotAssemblyProfile with bitcode sends correct argument to snapshotter (one arch)', () => testbed.run(() async { testUsingContext('AotAssemblyProfile with bitcode sends correct argument to snapshotter (one arch)', () async {
iosEnvironment.defines[kIosArchs] = 'arm64'; iosEnvironment.defines[kIosArchs] = 'arm64';
iosEnvironment.defines[kBitcodeFlag] = 'true'; iosEnvironment.defines[kBitcodeFlag] = 'true';
final String build = iosEnvironment.buildDir.path; final String build = iosEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
// This path is not known by the cache due to the iOS gen_snapshot split. // This path is not known by the cache due to the iOS gen_snapshot split.
'bin/cache/artifacts/engine/ios-profile/gen_snapshot_arm64', 'Artifact.genSnapshot.TargetPlatform.ios.profile_arm64',
'--deterministic', '--deterministic',
kAssemblyAot, kAssemblyAot,
'--assembly=$build/arm64/snapshot_assembly.S', '--assembly=$build/arm64/snapshot_assembly.S',
...@@ -562,16 +605,24 @@ void main() { ...@@ -562,16 +605,24 @@ void main() {
await const AotAssemblyProfile().build(iosEnvironment); await const AotAssemblyProfile().build(iosEnvironment);
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); }, overrides: <Type, Generator>{
Platform: () => macPlatform,
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
});
test('kExtraGenSnapshotOptions passes values to gen_snapshot', () => testbed.run(() async { testUsingContext('kExtraGenSnapshotOptions passes values to gen_snapshot', () async {
androidEnvironment.defines[kExtraGenSnapshotOptions] = 'foo,bar,baz=2'; androidEnvironment.defines[kExtraGenSnapshotOptions] = 'foo,bar,baz=2';
androidEnvironment.defines[kBuildMode] = getNameForBuildMode(BuildMode.profile); androidEnvironment.defines[kBuildMode] = getNameForBuildMode(BuildMode.profile);
final String build = androidEnvironment.buildDir.path; final String build = androidEnvironment.buildDir.path;
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
FakeCommand(command: <String>[ FakeCommand(command: <String>[
artifacts.getArtifactPath(Artifact.genSnapshot, mode: BuildMode.profile), artifacts.getArtifactPath(
Artifact.genSnapshot,
platform: TargetPlatform.android_arm,
mode: BuildMode.profile,
),
'--deterministic', '--deterministic',
'foo', 'foo',
'bar', 'bar',
...@@ -590,5 +641,5 @@ void main() { ...@@ -590,5 +641,5 @@ void main() {
await const AotElfRelease(TargetPlatform.android_arm).build(androidEnvironment); await const AotElfRelease(TargetPlatform.android_arm).build(androidEnvironment);
expect(processManager.hasRemainingExpectations, false); expect(processManager.hasRemainingExpectations, false);
})); });
} }
...@@ -7,18 +7,19 @@ import 'package:file_testing/file_testing.dart'; ...@@ -7,18 +7,19 @@ import 'package:file_testing/file_testing.dart';
import 'package:flutter_tools/src/artifacts.dart'; import 'package:flutter_tools/src/artifacts.dart';
import 'package:flutter_tools/src/base/file_system.dart'; import 'package:flutter_tools/src/base/file_system.dart';
import 'package:flutter_tools/src/base/logger.dart'; import 'package:flutter_tools/src/base/logger.dart';
import 'package:flutter_tools/src/base/platform.dart';
import 'package:flutter_tools/src/build_info.dart'; import 'package:flutter_tools/src/build_info.dart';
import 'package:flutter_tools/src/build_system/build_system.dart'; import 'package:flutter_tools/src/build_system/build_system.dart';
import 'package:flutter_tools/src/build_system/targets/assets.dart'; import 'package:flutter_tools/src/build_system/targets/assets.dart';
import 'package:flutter_tools/src/build_system/targets/common.dart'; import 'package:flutter_tools/src/build_system/targets/common.dart';
import 'package:flutter_tools/src/build_system/targets/ios.dart'; import 'package:flutter_tools/src/build_system/targets/ios.dart';
import 'package:flutter_tools/src/convert.dart'; import 'package:flutter_tools/src/convert.dart';
import 'package:flutter_tools/src/globals.dart' as globals;
import 'package:mockito/mockito.dart';
import '../../../src/common.dart'; import '../../../src/common.dart';
import '../../../src/context.dart';
import '../../../src/fake_process_manager.dart'; import '../../../src/fake_process_manager.dart';
import '../../../src/testbed.dart';
final Platform macPlatform = FakePlatform(operatingSystem: 'macos', environment: <String, String>{});
const List<String> _kSharedConfig = <String>[ const List<String> _kSharedConfig = <String>[
'-dynamiclib', '-dynamiclib',
...@@ -37,35 +38,39 @@ const List<String> _kSharedConfig = <String>[ ...@@ -37,35 +38,39 @@ const List<String> _kSharedConfig = <String>[
]; ];
void main() { void main() {
Testbed testbed;
Environment environment; Environment environment;
ProcessManager processManager; FileSystem fileSystem;
FakeProcessManager processManager;
Artifacts artifacts;
Logger logger;
setUp(() { setUp(() {
testbed = Testbed(setup: () { fileSystem = MemoryFileSystem.test();
environment = Environment.test( processManager = FakeProcessManager.list(<FakeCommand>[]);
globals.fs.currentDirectory, logger = BufferLogger.test();
defines: <String, String>{ artifacts = Artifacts.test();
kTargetPlatform: 'ios', environment = Environment.test(
}, fileSystem.currentDirectory,
inputs: <String, String>{}, defines: <String, String>{
processManager: processManager, kTargetPlatform: 'ios',
artifacts: MockArtifacts(), },
logger: globals.logger, inputs: <String, String>{},
fileSystem: globals.fs, processManager: processManager,
engineVersion: '2', artifacts: artifacts,
); logger: logger,
}); fileSystem: fileSystem,
engineVersion: '2',
);
}); });
test('iOS AOT targets has analyicsName', () { testWithoutContext('iOS AOT targets has analyicsName', () {
expect(const AotAssemblyRelease().analyticsName, 'ios_aot'); expect(const AotAssemblyRelease().analyticsName, 'ios_aot');
expect(const AotAssemblyProfile().analyticsName, 'ios_aot'); expect(const AotAssemblyProfile().analyticsName, 'ios_aot');
}); });
test('DebugUniveralFramework creates expected binary with arm64 only arch', () => testbed.run(() async { testUsingContext('DebugUniveralFramework creates expected binary with arm64 only arch', () async {
environment.defines[kIosArchs] = 'arm64'; environment.defines[kIosArchs] = 'arm64';
processManager = FakeProcessManager.list(<FakeCommand>[ processManager.addCommands(<FakeCommand>[
// Create iphone stub. // Create iphone stub.
const FakeCommand(command: <String>['xcrun', '--sdk', 'iphoneos', '--show-sdk-path']), const FakeCommand(command: <String>['xcrun', '--sdk', 'iphoneos', '--show-sdk-path']),
FakeCommand(command: <String>[ FakeCommand(command: <String>[
...@@ -76,7 +81,7 @@ void main() { ...@@ -76,7 +81,7 @@ void main() {
// iphone only gets 64 bit arch based on kIosArchs // iphone only gets 64 bit arch based on kIosArchs
'-arch', '-arch',
'arm64', 'arm64',
globals.fs.path.absolute(globals.fs.path.join('.tmp_rand0', 'flutter_tools_stub_source.rand0', 'debug_app.cc')), fileSystem.path.absolute(fileSystem.path.join('.tmp_rand0', 'flutter_tools_stub_source.rand0', 'debug_app.cc')),
..._kSharedConfig, ..._kSharedConfig,
'', '',
'-o', '-o',
...@@ -92,7 +97,7 @@ void main() { ...@@ -92,7 +97,7 @@ void main() {
// Simulator only as x86_64 arch // Simulator only as x86_64 arch
'-arch', '-arch',
'x86_64', 'x86_64',
globals.fs.path.absolute(globals.fs.path.join('.tmp_rand0', 'flutter_tools_stub_source.rand0', 'debug_app.cc')), fileSystem.path.absolute(fileSystem.path.join('.tmp_rand0', 'flutter_tools_stub_source.rand0', 'debug_app.cc')),
..._kSharedConfig, ..._kSharedConfig,
'', '',
'-o', '-o',
...@@ -112,24 +117,25 @@ void main() { ...@@ -112,24 +117,25 @@ void main() {
await const DebugUniveralFramework().build(environment); await const DebugUniveralFramework().build(environment);
}, overrides: <Type, Generator>{ }, overrides: <Type, Generator>{
FileSystem: () => fileSystem,
ProcessManager: () => processManager, ProcessManager: () => processManager,
})); Platform: () => macPlatform,
});
test('DebugIosApplicationBundle', () => testbed.run(() async { testUsingContext('DebugIosApplicationBundle', () async {
environment.inputs[kBundleSkSLPath] = 'bundle.sksl'; environment.inputs[kBundleSkSLPath] = 'bundle.sksl';
environment.defines[kBuildMode] = 'debug'; environment.defines[kBuildMode] = 'debug';
// Precompiled dart data // Precompiled dart data
when(globals.artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug))
.thenReturn('vm_snapshot_data'); fileSystem.file(artifacts.getArtifactPath(Artifact.vmSnapshotData, mode: BuildMode.debug))
when(globals.artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug)) .createSync();
.thenReturn('isolate_snapshot_data'); fileSystem.file(artifacts.getArtifactPath(Artifact.isolateSnapshotData, mode: BuildMode.debug))
globals.fs.file('vm_snapshot_data').createSync(); .createSync();
globals.fs.file('isolate_snapshot_data').createSync();
// Project info // Project info
globals.fs.file('pubspec.yaml').writeAsStringSync('name: hello'); fileSystem.file('pubspec.yaml').writeAsStringSync('name: hello');
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
// Plist file // Plist file
globals.fs.file(globals.fs.path.join('ios', 'Flutter', 'AppFrameworkInfo.plist')) fileSystem.file(fileSystem.path.join('ios', 'Flutter', 'AppFrameworkInfo.plist'))
.createSync(recursive: true); .createSync(recursive: true);
// App kernel // App kernel
environment.buildDir.childFile('app.dill').createSync(recursive: true); environment.buildDir.childFile('app.dill').createSync(recursive: true);
...@@ -139,7 +145,7 @@ void main() { ...@@ -139,7 +145,7 @@ void main() {
.childFile('App') .childFile('App')
.createSync(recursive: true); .createSync(recursive: true);
// sksl bundle // sksl bundle
globals.fs.file('bundle.sksl').writeAsStringSync(json.encode( fileSystem.file('bundle.sksl').writeAsStringSync(json.encode(
<String, Object>{ <String, Object>{
'engineRevision': '2', 'engineRevision': '2',
'platform': 'ios', 'platform': 'ios',
...@@ -162,18 +168,16 @@ void main() { ...@@ -162,18 +168,16 @@ void main() {
expect(assetDirectory.childFile('isolate_snapshot_data'), exists); expect(assetDirectory.childFile('isolate_snapshot_data'), exists);
expect(assetDirectory.childFile('io.flutter.shaders.json'), exists); expect(assetDirectory.childFile('io.flutter.shaders.json'), exists);
expect(assetDirectory.childFile('io.flutter.shaders.json').readAsStringSync(), '{"data":{"A":"B"}}'); expect(assetDirectory.childFile('io.flutter.shaders.json').readAsStringSync(), '{"data":{"A":"B"}}');
}, overrides: <Type, Generator>{ });
Artifacts: () => MockArtifacts(),
}));
test('ReleaseIosApplicationBundle', () => testbed.run(() async { testUsingContext('ReleaseIosApplicationBundle', () async {
environment.defines[kBuildMode] = 'release'; environment.defines[kBuildMode] = 'release';
// Project info // Project info
globals.fs.file('pubspec.yaml').writeAsStringSync('name: hello'); fileSystem.file('pubspec.yaml').writeAsStringSync('name: hello');
globals.fs.file('.packages').writeAsStringSync('\n'); fileSystem.file('.packages').writeAsStringSync('\n');
// Plist file // Plist file
globals.fs.file(globals.fs.path.join('ios', 'Flutter', 'AppFrameworkInfo.plist')) fileSystem.file(fileSystem.path.join('ios', 'Flutter', 'AppFrameworkInfo.plist'))
.createSync(recursive: true); .createSync(recursive: true);
// Real framework // Real framework
...@@ -193,9 +197,13 @@ void main() { ...@@ -193,9 +197,13 @@ void main() {
expect(assetDirectory.childFile('AssetManifest.json'), exists); expect(assetDirectory.childFile('AssetManifest.json'), exists);
expect(assetDirectory.childFile('vm_snapshot_data'), isNot(exists)); expect(assetDirectory.childFile('vm_snapshot_data'), isNot(exists));
expect(assetDirectory.childFile('isolate_snapshot_data'), isNot(exists)); expect(assetDirectory.childFile('isolate_snapshot_data'), isNot(exists));
})); }, overrides: <Type, Generator>{
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
Platform: () => macPlatform,
});
test('AotAssemblyRelease throws exception if asked to build for x86 target', () => testbed.run(() async { testUsingContext('AotAssemblyRelease throws exception if asked to build for x86 target', () async {
final FileSystem fileSystem = MemoryFileSystem.test(); final FileSystem fileSystem = MemoryFileSystem.test();
final Environment environment = Environment.test( final Environment environment = Environment.test(
fileSystem.currentDirectory, fileSystem.currentDirectory,
...@@ -203,8 +211,8 @@ void main() { ...@@ -203,8 +211,8 @@ void main() {
kTargetPlatform: 'ios', kTargetPlatform: 'ios',
}, },
processManager: processManager, processManager: processManager,
artifacts: MockArtifacts(), artifacts: artifacts,
logger: BufferLogger.test(), logger: logger,
fileSystem: fileSystem, fileSystem: fileSystem,
); );
environment.defines[kBuildMode] = 'release'; environment.defines[kBuildMode] = 'release';
...@@ -217,7 +225,9 @@ void main() { ...@@ -217,7 +225,9 @@ void main() {
contains('release/profile builds are only supported for physical devices.'), contains('release/profile builds are only supported for physical devices.'),
) )
)); ));
})); }, overrides: <Type, Generator>{
FileSystem: () => fileSystem,
ProcessManager: () => processManager,
Platform: () => macPlatform,
});
} }
class MockArtifacts extends Mock implements Artifacts {}
...@@ -10,6 +10,7 @@ import 'package:flutter_tools/src/base/io.dart'; ...@@ -10,6 +10,7 @@ import 'package:flutter_tools/src/base/io.dart';
import 'package:meta/meta.dart'; import 'package:meta/meta.dart';
import 'package:process/process.dart'; import 'package:process/process.dart';
import 'common.dart'; import 'common.dart';
import 'context.dart';
export 'package:process/process.dart' show ProcessManager; export 'package:process/process.dart' show ProcessManager;
...@@ -199,6 +200,11 @@ abstract class FakeProcessManager implements ProcessManager { ...@@ -199,6 +200,11 @@ abstract class FakeProcessManager implements ProcessManager {
/// This is a no-op on [FakeProcessManager.any]. /// This is a no-op on [FakeProcessManager.any].
void addCommand(FakeCommand command); void addCommand(FakeCommand command);
/// Add multiple [FakeCommand] to the current process manager.
void addCommands(Iterable<FakeCommand> commands) {
commands.forEach(addCommand);
}
/// Whether this fake has more [FakeCommand]s that are expected to run. /// Whether this fake has more [FakeCommand]s that are expected to run.
/// ///
/// This is always `true` for [FakeProcessManager.any]. /// This is always `true` for [FakeProcessManager.any].
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment