| // Copyright 2014 The Flutter Authors. All rights reserved. | |
| // Use of this source code is governed by a BSD-style license that can be | |
| // found in the LICENSE file. | |
| import 'dart:async'; | |
| import 'dart:io' as io show IOSink, ProcessSignal, Stdout, StdoutException; | |
| import 'package:dds/dds_launcher.dart'; | |
| import 'package:file/memory.dart'; | |
| import 'package:flutter_tools/src/android/android_sdk.dart'; | |
| import 'package:flutter_tools/src/android/android_studio.dart'; | |
| import 'package:flutter_tools/src/android/gradle_utils.dart'; | |
| import 'package:flutter_tools/src/android/java.dart'; | |
| import 'package:flutter_tools/src/artifacts.dart'; | |
| import 'package:flutter_tools/src/base/bot_detector.dart'; | |
| import 'package:flutter_tools/src/base/config.dart'; | |
| import 'package:flutter_tools/src/base/file_system.dart'; | |
| import 'package:flutter_tools/src/base/io.dart'; | |
| import 'package:flutter_tools/src/base/logger.dart'; | |
| import 'package:flutter_tools/src/base/os.dart'; | |
| import 'package:flutter_tools/src/base/platform.dart'; | |
| import 'package:flutter_tools/src/base/process.dart'; | |
| import 'package:flutter_tools/src/base/signals.dart'; | |
| import 'package:flutter_tools/src/base/template.dart'; | |
| import 'package:flutter_tools/src/base/terminal.dart'; | |
| import 'package:flutter_tools/src/base/time.dart'; | |
| import 'package:flutter_tools/src/base/user_messages.dart'; | |
| import 'package:flutter_tools/src/base/version.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_targets.dart'; | |
| import 'package:flutter_tools/src/cache.dart'; | |
| import 'package:flutter_tools/src/context/android_context.dart'; | |
| import 'package:flutter_tools/src/context/apple_context.dart'; | |
| import 'package:flutter_tools/src/context/tool_context.dart'; | |
| import 'package:flutter_tools/src/context/tool_dependencies.dart'; | |
| import 'package:flutter_tools/src/convert.dart'; | |
| import 'package:flutter_tools/src/custom_devices/custom_devices_config.dart'; | |
| import 'package:flutter_tools/src/doctor.dart'; | |
| import 'package:flutter_tools/src/doctor_validator.dart'; | |
| import 'package:flutter_tools/src/emulator.dart'; | |
| import 'package:flutter_tools/src/features.dart'; | |
| import 'package:flutter_tools/src/git.dart'; | |
| import 'package:flutter_tools/src/globals.dart' as globals; | |
| import 'package:flutter_tools/src/ios/ios_workflow.dart'; | |
| import 'package:flutter_tools/src/ios/plist_parser.dart'; | |
| import 'package:flutter_tools/src/ios/simulators.dart'; | |
| import 'package:flutter_tools/src/ios/xcodeproj.dart'; | |
| import 'package:flutter_tools/src/macos/cocoapods.dart'; | |
| import 'package:flutter_tools/src/macos/cocoapods_validator.dart'; | |
| import 'package:flutter_tools/src/macos/xcdevice.dart'; | |
| import 'package:flutter_tools/src/macos/xcode.dart'; | |
| import 'package:flutter_tools/src/native_assets.dart'; | |
| import 'package:flutter_tools/src/persistent_tool_state.dart'; | |
| import 'package:flutter_tools/src/pre_run_validator.dart'; | |
| import 'package:flutter_tools/src/project.dart'; | |
| import 'package:flutter_tools/src/reporting/crash_reporting.dart'; | |
| import 'package:flutter_tools/src/resident_runner.dart'; | |
| import 'package:flutter_tools/src/runner/local_engine.dart'; | |
| import 'package:flutter_tools/src/version.dart'; | |
| import 'package:test/fake.dart'; | |
| import 'package:unified_analytics/unified_analytics.dart'; | |
| import 'context.dart'; | |
| class FakeDyldEnvironmentArtifact extends ArtifactSet { | |
| FakeDyldEnvironmentArtifact() : super(DevelopmentArtifact.iOS); | |
| @override | |
| Map<String, String> get environment => <String, String>{ | |
| 'DYLD_LIBRARY_PATH': '/path/to/libraries', | |
| }; | |
| @override | |
| Future<bool> isUpToDate(FileSystem fileSystem) => Future<bool>.value(true); | |
| @override | |
| String get name => 'fake'; | |
| @override | |
| Future<void> update( | |
| ArtifactUpdater artifactUpdater, | |
| Logger logger, | |
| FileSystem fileSystem, | |
| OperatingSystemUtils operatingSystemUtils, { | |
| bool offline = false, | |
| }) async {} | |
| } | |
| /// A fake process implementation which can be provided all necessary values. | |
| class FakeProcess implements Process { | |
| FakeProcess({ | |
| this.pid = 1, | |
| Future<int>? exitCode, | |
| IOSink? stdin, | |
| this.stdout = const Stream<List<int>>.empty(), | |
| this.stderr = const Stream<List<int>>.empty(), | |
| }) : exitCode = exitCode ?? Future<int>.value(0), | |
| stdin = stdin ?? MemoryIOSink(); | |
| @override | |
| final int pid; | |
| @override | |
| final Future<int> exitCode; | |
| @override | |
| final io.IOSink stdin; | |
| @override | |
| final Stream<List<int>> stdout; | |
| @override | |
| final Stream<List<int>> stderr; | |
| @override | |
| bool kill([io.ProcessSignal signal = io.ProcessSignal.sigterm]) { | |
| return true; | |
| } | |
| } | |
| /// A [ShutdownHooks] implementation that does not actually execute any hooks. | |
| class FakeShutdownHooks extends Fake implements ShutdownHooks { | |
| @override | |
| bool get isShuttingDown => _isShuttingDown; | |
| var _isShuttingDown = false; | |
| @override | |
| final registeredHooks = <ShutdownHook>[]; | |
| @override | |
| void addShutdownHook(ShutdownHook shutdownHook) { | |
| registeredHooks.add(shutdownHook); | |
| } | |
| @override | |
| Future<void> runShutdownHooks(Logger logger) async { | |
| _isShuttingDown = true; | |
| } | |
| } | |
| /// An IOSink that completes a future with the first line written to it. | |
| class CompleterIOSink extends MemoryIOSink { | |
| CompleterIOSink({this.throwOnAdd = false}); | |
| final bool throwOnAdd; | |
| final _completer = Completer<List<int>>(); | |
| Future<List<int>> get future => _completer.future; | |
| @override | |
| void add(List<int> data) { | |
| if (!_completer.isCompleted) { | |
| // When throwOnAdd is true, complete with empty so any expected output | |
| // doesn't appear. | |
| _completer.complete(throwOnAdd ? <int>[] : data); | |
| } | |
| if (throwOnAdd) { | |
| throw Exception('CompleterIOSink Error'); | |
| } | |
| super.add(data); | |
| } | |
| } | |
| /// An IOSink that collects whatever is written to it. | |
| class MemoryIOSink implements IOSink { | |
| @override | |
| Encoding encoding = utf8; | |
| final writes = <List<int>>[]; | |
| @override | |
| void add(List<int> data) { | |
| writes.add(data); | |
| } | |
| @override | |
| Future<void> addStream(Stream<List<int>> stream) { | |
| final completer = Completer<void>(); | |
| late StreamSubscription<List<int>> sub; | |
| sub = stream.listen( | |
| (List<int> data) { | |
| try { | |
| add(data); | |
| // Catches all exceptions to propagate them to the completer. | |
| } catch (err, stack) { | |
| sub.cancel(); | |
| completer.completeError(err, stack); | |
| } | |
| }, | |
| onError: completer.completeError, | |
| onDone: completer.complete, | |
| cancelOnError: true, | |
| ); | |
| return completer.future; | |
| } | |
| @override | |
| void writeCharCode(int charCode) { | |
| add(<int>[charCode]); | |
| } | |
| @override | |
| void write(Object? obj) { | |
| add(encoding.encode('$obj')); | |
| } | |
| @override | |
| void writeln([Object? obj = '']) { | |
| add(encoding.encode('$obj\n')); | |
| } | |
| @override | |
| void writeAll(Iterable<dynamic> objects, [String separator = '']) { | |
| var addSeparator = false; | |
| for (final dynamic object in objects) { | |
| if (addSeparator) { | |
| write(separator); | |
| } | |
| write(object); | |
| addSeparator = true; | |
| } | |
| } | |
| @override | |
| void addError(dynamic error, [StackTrace? stackTrace]) { | |
| throw UnimplementedError(); | |
| } | |
| @override | |
| Future<void> get done => close(); | |
| @override | |
| Future<void> close() async {} | |
| @override | |
| Future<void> flush() async {} | |
| void clear() { | |
| writes.clear(); | |
| } | |
| String getAndClear() { | |
| final String result = utf8.decode(writes.expand((List<int> l) => l).toList()); | |
| clear(); | |
| return result; | |
| } | |
| } | |
| class MemoryStdout extends MemoryIOSink implements io.Stdout { | |
| @override | |
| bool get hasTerminal => _hasTerminal; | |
| set hasTerminal(bool value) { | |
| _hasTerminal = value; | |
| } | |
| var _hasTerminal = true; | |
| @override | |
| String get lineTerminator => '\n'; | |
| @override | |
| set lineTerminator(String value) { | |
| throw UnimplementedError('Setting the line terminator is not supported'); | |
| } | |
| @override | |
| io.IOSink get nonBlocking => this; | |
| @override | |
| bool get supportsAnsiEscapes => _supportsAnsiEscapes; | |
| set supportsAnsiEscapes(bool value) { | |
| _supportsAnsiEscapes = value; | |
| } | |
| var _supportsAnsiEscapes = true; | |
| @override | |
| int get terminalColumns { | |
| if (_terminalColumns != null) { | |
| return _terminalColumns!; | |
| } | |
| throw const io.StdoutException('unspecified mock value'); | |
| } | |
| set terminalColumns(int value) => _terminalColumns = value; | |
| int? _terminalColumns; | |
| @override | |
| int get terminalLines { | |
| if (_terminalLines != null) { | |
| return _terminalLines!; | |
| } | |
| throw const io.StdoutException('unspecified mock value'); | |
| } | |
| set terminalLines(int value) => _terminalLines = value; | |
| int? _terminalLines; | |
| } | |
| /// A Stdio that collects stdout and supports simulated stdin. | |
| class FakeStdio extends Stdio { | |
| final _stdout = MemoryStdout()..terminalColumns = 80; | |
| final _stderr = MemoryIOSink(); | |
| final _stdin = FakeStdin(); | |
| @override | |
| MemoryStdout get stdout => _stdout; | |
| @override | |
| MemoryIOSink get stderr => _stderr; | |
| @override | |
| Stream<List<int>> get stdin => _stdin; | |
| void simulateStdin(String line) { | |
| _stdin.controller.add(utf8.encode('$line\n')); | |
| } | |
| @override | |
| bool hasTerminal = false; | |
| List<String> get writtenToStdout => _stdout.writes.map<String>(_stdout.encoding.decode).toList(); | |
| List<String> get writtenToStderr => _stderr.writes.map<String>(_stderr.encoding.decode).toList(); | |
| } | |
| class FakeStdin extends Fake implements Stdin { | |
| final controller = StreamController<List<int>>(); | |
| void Function(bool mode)? echoModeCallback; | |
| var _echoMode = true; | |
| @override | |
| bool get echoMode => _echoMode; | |
| @override | |
| set echoMode(bool mode) { | |
| _echoMode = mode; | |
| if (echoModeCallback != null) { | |
| echoModeCallback!(mode); | |
| } | |
| } | |
| @override | |
| bool lineMode = true; | |
| @override | |
| bool hasTerminal = false; | |
| @override | |
| Stream<S> transform<S>(StreamTransformer<List<int>, S> transformer) { | |
| return controller.stream.transform(transformer); | |
| } | |
| @override | |
| StreamSubscription<List<int>> listen( | |
| void Function(List<int> event)? onData, { | |
| Function? onError, | |
| void Function()? onDone, | |
| bool? cancelOnError, | |
| }) { | |
| return controller.stream.listen( | |
| onData, | |
| onError: onError, | |
| onDone: onDone, | |
| cancelOnError: cancelOnError, | |
| ); | |
| } | |
| } | |
| class FakePlistParser implements PlistParser { | |
| FakePlistParser([Map<String, Object>? underlyingValues]) | |
| : _underlyingValues = underlyingValues ?? <String, Object>{}; | |
| final Map<String, Object> _underlyingValues; | |
| void setProperty(String key, Object value) { | |
| _underlyingValues[key] = value; | |
| } | |
| @override | |
| String? plistXmlContent(String plistFilePath) => throw UnimplementedError(); | |
| @override | |
| String? plistJsonContent(String filePath, {bool sorted = false}) { | |
| throw UnimplementedError(); | |
| } | |
| @override | |
| Map<String, Object> parseFile(String plistFilePath) { | |
| return _underlyingValues; | |
| } | |
| @override | |
| T? getValueFromFile<T>(String plistFilePath, String key) { | |
| return _underlyingValues[key] as T?; | |
| } | |
| @override | |
| bool replaceKey(String plistFilePath, {required String key, String? value}) { | |
| if (value == null) { | |
| _underlyingValues.remove(key); | |
| return true; | |
| } | |
| setProperty(key, value); | |
| return true; | |
| } | |
| @override | |
| bool insertKeyWithJson(String plistFilePath, {required String key, required String json}) { | |
| return false; | |
| } | |
| } | |
| class FakeBotDetector implements BotDetector { | |
| const FakeBotDetector(bool isRunningOnBot) : _isRunningOnBot = isRunningOnBot; | |
| @override | |
| Future<bool> get isRunningOnBot async => _isRunningOnBot; | |
| final bool _isRunningOnBot; | |
| } | |
| class FakeFlutterVersion implements FlutterVersion { | |
| FakeFlutterVersion({ | |
| this.branch = 'master', | |
| this.dartSdkVersion = '12', | |
| this.devToolsVersion = '2.8.0', | |
| this.engineRevision = 'abcdefghijklmnopqrstuvwxyz', | |
| this.engineRevisionShort = 'abcde', | |
| this.engineAge = '0 hours ago', | |
| this.engineCommitDate = '12/01/01', | |
| this.repositoryUrl = 'https://github.com/flutter/flutter.git', | |
| this.frameworkVersion = '0.0.0', | |
| this.frameworkRevision = '11111111111111111111', | |
| this.frameworkRevisionShort = '11111', | |
| this.frameworkAge = '0 hours ago', | |
| this.frameworkCommitDate = '12/01/01', | |
| this.gitTagVersion = const GitTagVersion.unknown(), | |
| this.flutterRoot = '/path/to/flutter', | |
| this.nextFlutterVersion, | |
| this.engineBuildDate = '12/01/02', | |
| this.engineContentHash = 'cccccccccccccccccccccccccccccccccccccccc', | |
| }); | |
| final String branch; | |
| bool get didFetchTagsAndUpdate => _didFetchTagsAndUpdate; | |
| var _didFetchTagsAndUpdate = false; | |
| bool get didEnsureVersionFile => _didEnsureVersionFile; | |
| var _didEnsureVersionFile = false; | |
| bool get didDeleteVersionFile => _didDeleteVersionFile; | |
| var _didDeleteVersionFile = false; | |
| /// Will be returned by [fetchTagsAndGetVersion] if not null. | |
| final FlutterVersion? nextFlutterVersion; | |
| @override | |
| FlutterVersion fetchTagsAndGetVersion({SystemClock clock = const SystemClock()}) { | |
| _didFetchTagsAndUpdate = true; | |
| return nextFlutterVersion ?? this; | |
| } | |
| bool get didCheckFlutterVersionFreshness => _didCheckFlutterVersionFreshness; | |
| var _didCheckFlutterVersionFreshness = false; | |
| @override | |
| String get channel { | |
| if (kOfficialChannels.contains(branch) || kObsoleteBranches.containsKey(branch)) { | |
| return branch; | |
| } | |
| return kUserBranch; | |
| } | |
| @override | |
| final String flutterRoot; | |
| @override | |
| final String devToolsVersion; | |
| @override | |
| final String dartSdkVersion; | |
| @override | |
| final String engineRevision; | |
| @override | |
| final String engineRevisionShort; | |
| @override | |
| final String? engineCommitDate; | |
| @override | |
| final String engineAge; | |
| @override | |
| final String? repositoryUrl; | |
| @override | |
| final String frameworkVersion; | |
| @override | |
| final String frameworkRevision; | |
| @override | |
| final String frameworkRevisionShort; | |
| @override | |
| final String frameworkAge; | |
| @override | |
| final String frameworkCommitDate; | |
| @override | |
| final GitTagVersion gitTagVersion; | |
| @override | |
| FileSystem get fs => throw UnimplementedError('FakeFlutterVersion.fs is not implemented'); | |
| @override | |
| Future<void> checkFlutterVersionFreshness() async { | |
| _didCheckFlutterVersionFreshness = true; | |
| } | |
| @override | |
| Future<void> ensureVersionFile() async { | |
| _didEnsureVersionFile = true; | |
| } | |
| @override | |
| void deleteVersionFile() { | |
| _didDeleteVersionFile = true; | |
| } | |
| @override | |
| String getBranchName({bool redactUnknownBranches = false}) { | |
| if (!redactUnknownBranches || | |
| kOfficialChannels.contains(branch) || | |
| kObsoleteBranches.containsKey(branch)) { | |
| return branch; | |
| } | |
| return kUserBranch; | |
| } | |
| @override | |
| String getVersionString({bool redactUnknownBranches = false}) { | |
| return '${getBranchName(redactUnknownBranches: redactUnknownBranches)}/$frameworkRevision'; | |
| } | |
| @override | |
| Map<String, Object> toJson() { | |
| return <String, Object>{}; | |
| } | |
| @override | |
| final String? engineBuildDate; | |
| @override | |
| final String? engineContentHash; | |
| } | |
| // A test implementation of [FeatureFlags] that allows enabling without reading | |
| // config. If not otherwise specified, all values default to false. | |
| class TestFeatureFlags implements FeatureFlags { | |
| TestFeatureFlags({ | |
| this.isLinuxEnabled = false, | |
| this.isMacOSEnabled = false, | |
| this.isWebEnabled = false, | |
| this.isWindowsEnabled = false, | |
| this.isAndroidEnabled = true, | |
| this.isIOSEnabled = true, | |
| this.isFuchsiaEnabled = false, | |
| this.areCustomDevicesEnabled = false, | |
| this.isCliAnimationEnabled = true, | |
| this.isNativeAssetsEnabled = false, | |
| this.isDartDataAssetsEnabled = false, | |
| this.isRecordUseEnabled = false, | |
| this.isSwiftPackageManagerEnabled = false, | |
| this.isOmitLegacyVersionFileEnabled = false, | |
| this.isWindowingEnabled = false, | |
| this.isLLDBDebuggingEnabled = false, | |
| this.isUISceneMigrationEnabled = false, | |
| this.isRiscv64SupportEnabled = false, | |
| this.isMacOSArm64OnlyEnabled = false, | |
| this.isHcppEnabled = false, | |
| this.isToolExtensionsEnabled = false, | |
| }); | |
| @override | |
| final bool isLinuxEnabled; | |
| @override | |
| final bool isMacOSEnabled; | |
| @override | |
| final bool isWebEnabled; | |
| @override | |
| final bool isWindowsEnabled; | |
| @override | |
| final bool isAndroidEnabled; | |
| @override | |
| final bool isIOSEnabled; | |
| @override | |
| final bool isFuchsiaEnabled; | |
| @override | |
| final bool areCustomDevicesEnabled; | |
| @override | |
| final bool isCliAnimationEnabled; | |
| @override | |
| final bool isNativeAssetsEnabled; | |
| @override | |
| final bool isDartDataAssetsEnabled; | |
| @override | |
| final bool isRecordUseEnabled; | |
| @override | |
| final bool isSwiftPackageManagerEnabled; | |
| @override | |
| final bool isOmitLegacyVersionFileEnabled; | |
| @override | |
| final bool isWindowingEnabled; | |
| @override | |
| final bool isLLDBDebuggingEnabled; | |
| @override | |
| final bool isUISceneMigrationEnabled; | |
| @override | |
| final bool isRiscv64SupportEnabled; | |
| @override | |
| final bool isMacOSArm64OnlyEnabled; | |
| @override | |
| final bool isHcppEnabled; | |
| @override | |
| final bool isToolExtensionsEnabled; | |
| @override | |
| bool isEnabled(Feature feature) { | |
| return switch (feature) { | |
| flutterWebFeature => isWebEnabled, | |
| flutterLinuxDesktopFeature => isLinuxEnabled, | |
| flutterMacOSDesktopFeature => isMacOSEnabled, | |
| flutterWindowsDesktopFeature => isWindowsEnabled, | |
| flutterAndroidFeature => isAndroidEnabled, | |
| flutterIOSFeature => isIOSEnabled, | |
| flutterFuchsiaFeature => isFuchsiaEnabled, | |
| flutterCustomDevicesFeature => areCustomDevicesEnabled, | |
| cliAnimation => isCliAnimationEnabled, | |
| nativeAssets => isNativeAssetsEnabled, | |
| swiftPackageManager => isSwiftPackageManagerEnabled, | |
| omitLegacyVersionFile => isOmitLegacyVersionFileEnabled, | |
| windowingFeature => isWindowingEnabled, | |
| lldbDebugging => isLLDBDebuggingEnabled, | |
| uiSceneMigration => isUISceneMigrationEnabled, | |
| riscv64 => isRiscv64SupportEnabled, | |
| macOSArm64Only => isMacOSArm64OnlyEnabled, | |
| recordUse => isRecordUseEnabled, | |
| hcpp => isHcppEnabled, | |
| toolExtensionsFeature => isToolExtensionsEnabled, | |
| _ => false, | |
| }; | |
| } | |
| @override | |
| List<Feature> get allFeatures => const <Feature>[ | |
| flutterWebFeature, | |
| flutterLinuxDesktopFeature, | |
| flutterMacOSDesktopFeature, | |
| flutterWindowsDesktopFeature, | |
| flutterAndroidFeature, | |
| flutterIOSFeature, | |
| flutterFuchsiaFeature, | |
| flutterCustomDevicesFeature, | |
| cliAnimation, | |
| dartDataAssets, | |
| nativeAssets, | |
| recordUse, | |
| swiftPackageManager, | |
| omitLegacyVersionFile, | |
| windowingFeature, | |
| lldbDebugging, | |
| uiSceneMigration, | |
| riscv64, | |
| macOSArm64Only, | |
| hcpp, | |
| toolExtensionsFeature, | |
| ]; | |
| @override | |
| Iterable<Feature> get allConfigurableFeatures { | |
| return allFeatures.where((Feature feature) => feature.configSetting != null); | |
| } | |
| @override | |
| Iterable<Feature> get allEnabledFeatures { | |
| return allFeatures.where(isEnabled); | |
| } | |
| } | |
| class FakeOperatingSystemUtils extends Fake implements OperatingSystemUtils { | |
| FakeOperatingSystemUtils({this.hostPlatform = HostPlatform.linux_x64}); | |
| final chmods = <List<String>>[]; | |
| @override | |
| void makeExecutable(File file) {} | |
| @override | |
| HostPlatform? hostPlatformOverride; | |
| @override | |
| HostPlatform hostPlatform = HostPlatform.linux_x64; | |
| @override | |
| void chmod(FileSystemEntity entity, String mode) { | |
| chmods.add(<String>[entity.path, mode]); | |
| } | |
| @override | |
| File? which(String execName) => null; | |
| @override | |
| List<File> whichAll(String execName) => <File>[]; | |
| @override | |
| int? getDirectorySize(Directory directory) => 10000000; // 10 MB / 9.5 MiB | |
| @override | |
| void unzip(File file, Directory targetDirectory) {} | |
| @override | |
| void unpack(File gzippedTarFile, Directory targetDirectory) {} | |
| @override | |
| Stream<List<int>> gzipLevel1Stream(Stream<List<int>> stream) => stream; | |
| @override | |
| String get name => 'fake OS name and version'; | |
| @override | |
| String get pathVarSeparator => ';'; | |
| @override | |
| Future<int> findFreePort({bool ipv6 = false}) async => 12345; | |
| } | |
| class FakeStopwatch implements Stopwatch { | |
| @override | |
| bool get isRunning => _isRunning; | |
| var _isRunning = false; | |
| @override | |
| void start() => _isRunning = true; | |
| @override | |
| void stop() => _isRunning = false; | |
| @override | |
| Duration elapsed = Duration.zero; | |
| @override | |
| int get elapsedMicroseconds => elapsed.inMicroseconds; | |
| @override | |
| int get elapsedMilliseconds => elapsed.inMilliseconds; | |
| @override | |
| int get elapsedTicks => elapsed.inMilliseconds; | |
| @override | |
| int get frequency => 1000; | |
| @override | |
| void reset() { | |
| _isRunning = false; | |
| elapsed = Duration.zero; | |
| } | |
| @override | |
| String toString() => '$runtimeType $elapsed $isRunning'; | |
| } | |
| class FakeStopwatchFactory implements StopwatchFactory { | |
| FakeStopwatchFactory({Stopwatch? stopwatch, Map<String, Stopwatch>? stopwatches}) | |
| : stopwatches = <String, Stopwatch>{...?stopwatches, '': ?stopwatch}; | |
| Map<String, Stopwatch> stopwatches; | |
| @override | |
| Stopwatch createStopwatch([String name = '']) { | |
| return stopwatches[name] ?? FakeStopwatch(); | |
| } | |
| } | |
| class FakeFlutterProjectFactory implements FlutterProjectFactory { | |
| @override | |
| FlutterProject fromDirectory(Directory directory) { | |
| return FlutterProject.fromDirectoryTest(directory); | |
| } | |
| @override | |
| Map<String, FlutterProject> get projects => throw UnimplementedError(); | |
| @override | |
| void invalidate(Directory directory) {} | |
| } | |
| class FakeAndroidSdk extends Fake implements AndroidSdk { | |
| @override | |
| late bool platformToolsAvailable; | |
| @override | |
| late bool licensesAvailable; | |
| @override | |
| AndroidSdkVersion? latestVersion; | |
| } | |
| class FakeAndroidStudio extends Fake implements AndroidStudio { | |
| @override | |
| String get javaPath => 'java'; | |
| } | |
| class FakeJava extends Fake implements Java { | |
| FakeJava({ | |
| this.javaHome = '/android-studio/jbr', | |
| this.javaSource = JavaSource.androidStudio, | |
| String binary = '/android-studio/jbr/bin/java', | |
| Version? version, | |
| this._canRun = true, | |
| }) : binaryPath = binary, | |
| version = version ?? const Version.withText(19, 0, 2, 'openjdk 19.0.2 2023-01-17'), | |
| _environment = <String, String>{ | |
| Java.javaHomeEnvironmentVariable: ?javaHome, | |
| 'PATH': '/android-studio/jbr/bin', | |
| }; | |
| @override | |
| String? javaHome; | |
| @override | |
| String binaryPath; | |
| @override | |
| JavaSource javaSource; | |
| final Map<String, String> _environment; | |
| final bool _canRun; | |
| @override | |
| Map<String, String> get environment => _environment; | |
| @override | |
| Version? version; | |
| @override | |
| bool canRun() { | |
| return _canRun; | |
| } | |
| } | |
| class FakeDartDevelopmentServiceLauncher extends Fake implements DartDevelopmentServiceLauncher { | |
| FakeDartDevelopmentServiceLauncher({required this.uri, this.devToolsUri, this.dtdUri}); | |
| @override | |
| final Uri uri; | |
| @override | |
| final Uri? devToolsUri; | |
| @override | |
| final Uri? dtdUri; | |
| @override | |
| Future<void> get done => _completer.future; | |
| @override | |
| Future<void> shutdown() async => _completer.complete(); | |
| final _completer = Completer<void>(); | |
| } | |
| class FakeDevtoolsLauncher extends Fake implements DevtoolsLauncher { | |
| FakeDevtoolsLauncher({this._serverAddress}); | |
| @override | |
| Future<void> get processStart => _processStarted.future; | |
| final _processStarted = Completer<void>(); | |
| @override | |
| Future<void> get ready => readyCompleter.future; | |
| Completer<void> readyCompleter = Completer<void>()..complete(); | |
| @override | |
| DevToolsServerAddress? activeDevToolsServer; | |
| @override | |
| Uri? devToolsUrl; | |
| @override | |
| Uri? dtdUri; | |
| @override | |
| bool printDtdUri = false; | |
| final DevToolsServerAddress? _serverAddress; | |
| @override | |
| Future<DevToolsServerAddress?> serve() async => _serverAddress; | |
| @override | |
| Future<void> launch(Uri vmServiceUri, {List<String>? additionalArguments}) { | |
| _processStarted.complete(); | |
| return Completer<void>().future; | |
| } | |
| bool closed = false; | |
| @override | |
| Future<void> close() async { | |
| closed = true; | |
| } | |
| } | |
| /// A fake [Logger] that throws the [Invocation] for any method call. | |
| class FakeLogger implements Logger { | |
| @override | |
| dynamic noSuchMethod(Invocation invocation) => throw invocation; // ignore: only_throw_errors | |
| } | |
| class ClosedStdinController extends Fake implements StreamSink<List<int>> { | |
| @override | |
| Future<Object?> addStream(Stream<List<int>> stream) async => | |
| throw const SocketException('Bad pipe'); | |
| @override | |
| Future<Object?> close() async { | |
| return null; | |
| } | |
| } | |
| class FakeConfig extends Fake implements Config { | |
| FakeConfig([Map<String, Object?>? values, this.configPath = '/.flutter_settings']) | |
| : _values = values ?? <String, Object?>{}; | |
| final Map<String, Object?> _values; | |
| @override | |
| final String configPath; | |
| @override | |
| Object? getValue(String key) => _values[key]; | |
| @override | |
| void setValue(String key, Object value) { | |
| _values[key] = value; | |
| } | |
| @override | |
| void removeValue(String key) { | |
| _values.remove(key); | |
| } | |
| @override | |
| bool containsKey(String key) => _values.containsKey(key); | |
| @override | |
| Iterable<String> get keys => _values.keys; | |
| } | |
| class FakeFileSystemUtils extends Fake implements FileSystemUtils {} | |
| class FakeTerminal extends Fake implements AnsiTerminal { | |
| @override | |
| String get successMark => '✓'; | |
| @override | |
| String get warningMark => '!'; | |
| @override | |
| String bolden(String message) => message; | |
| @override | |
| String clearScreen() => ''; | |
| @override | |
| String color(String message, TerminalColor color) => message; | |
| } | |
| class FakeProcessUtils extends Fake implements ProcessUtils {} | |
| class FakeTemplateRenderer extends Fake implements TemplateRenderer {} | |
| class FakeXcode extends Fake implements Xcode { | |
| FakeXcode({ | |
| this.currentVersion, | |
| this.isDevicectlInstalled = true, | |
| this.isInstalled = true, | |
| this.isRecommendedVersionSatisfactory = true, | |
| this.isRequiredVersionSatisfactory = true, | |
| }); | |
| @override | |
| Version? currentVersion; | |
| @override | |
| bool isDevicectlInstalled; | |
| @override | |
| bool isInstalled; | |
| @override | |
| bool isRecommendedVersionSatisfactory; | |
| @override | |
| bool isRequiredVersionSatisfactory; | |
| @override | |
| Future<List<String>> fetchDependenciesAndGenerateXcodebuildArgs( | |
| XcodeBasedProject xcodeProject, | |
| Directory buildDirectory, { | |
| bool skipPackageValidation = true, | |
| }) async => <String>[...xcrunCommand(), 'xcodebuild']; | |
| @override | |
| Future<String> sdkLocation(EnvironmentType environmentType) async => '/fake/sdk/path'; | |
| @override | |
| List<String> xcrunCommand() => <String>['xcrun']; | |
| } | |
| class FakeArtifacts extends Fake implements Artifacts { | |
| FakeArtifacts({FileSystem? fileSystem, this.sdkPath}) | |
| : _delegate = Artifacts.test(fileSystem: fileSystem); | |
| final Artifacts _delegate; | |
| final String? sdkPath; | |
| @override | |
| LocalEngineInfo? get localEngineInfo => _delegate.localEngineInfo; | |
| @override | |
| bool get usesLocalArtifacts => _delegate.usesLocalArtifacts; | |
| @override | |
| FileSystemEntity getHostArtifact(HostArtifact artifact) => _delegate.getHostArtifact(artifact); | |
| @override | |
| String getArtifactPath( | |
| Artifact artifact, { | |
| TargetPlatform? platform, | |
| BuildMode? mode, | |
| EnvironmentType? environmentType, | |
| }) { | |
| if (artifact == Artifact.engineDartSdkPath && sdkPath != null) { | |
| return sdkPath!; | |
| } | |
| return _delegate.getArtifactPath( | |
| artifact, | |
| platform: platform, | |
| mode: mode, | |
| environmentType: environmentType, | |
| ); | |
| } | |
| @override | |
| String getEngineType(TargetPlatform platform, [BuildMode? mode]) => | |
| _delegate.getEngineType(platform, mode); | |
| } | |
| class FakeCache extends Fake implements Cache { | |
| FakeCache({FileSystem? fileSystem}) : _fileSystem = fileSystem ?? MemoryFileSystem.test(); | |
| final FileSystem _fileSystem; | |
| @override | |
| Future<void> lock() async {} | |
| @override | |
| void releaseLock() {} | |
| @override | |
| Future<void> updateAll( | |
| Set<DevelopmentArtifact> requiredArtifacts, { | |
| bool offline = false, | |
| }) async {} | |
| @override | |
| Directory getRoot() => _fileSystem.directory('/bin/cache'); | |
| @override | |
| Directory getCacheDir(String name, {bool shouldCreate = true}) => | |
| _fileSystem.directory('/bin/cache/$name'); | |
| @override | |
| Directory getArtifactDirectory(String name) => | |
| _fileSystem.directory('/bin/cache/artifacts/$name'); | |
| @override | |
| Directory getWebSdkDirectory() => _fileSystem.directory('/bin/cache/flutter_web_sdk'); | |
| @override | |
| String get dartSdkBuild => '12345'; | |
| @override | |
| MapEntry<String, String> get dyLdLibEntry => | |
| const MapEntry<String, String>('DYLD_LIBRARY_PATH', 'fake_path'); | |
| } | |
| class FakeGit extends Fake implements Git {} | |
| class FakeGradleUtils extends Fake implements GradleUtils {} | |
| class FakeCocoaPods extends Fake implements CocoaPods {} | |
| class FakeCocoaPodsValidator extends Fake implements CocoaPodsValidator {} | |
| class FakeIOSSimulatorUtils extends Fake implements IOSSimulatorUtils {} | |
| class FakeIOSWorkflow extends Fake implements IOSWorkflow {} | |
| class FakeXCDevice extends Fake implements XCDevice {} | |
| class FakeBuildSystem extends Fake implements BuildSystem {} | |
| class FakeBuildTargets extends Fake implements BuildTargets {} | |
| class FakeCrashReporter extends Fake implements CrashReporter {} | |
| class FakeDoctor extends Fake implements Doctor { | |
| FakeDoctor({this.canListEmulators = true, this.canLaunchAnything = true}); | |
| final bool canListEmulators; | |
| @override | |
| final bool canLaunchAnything; | |
| @override | |
| List<Workflow> get workflows => <Workflow>[FakeWorkflow(canListEmulators: canListEmulators)]; | |
| @override | |
| List<DoctorValidator> get validators => const <DoctorValidator>[]; | |
| } | |
| class FakeWorkflow extends Fake implements Workflow { | |
| FakeWorkflow({this.canListEmulators = true}); | |
| @override | |
| final bool canListEmulators; | |
| } | |
| class FakeEmulatorManager extends Fake implements EmulatorManager { | |
| FakeEmulatorManager({this.createResult, this.emulators = const <Emulator>[]}); | |
| final List<Emulator> emulators; | |
| final CreateEmulatorResult? createResult; | |
| String? lastCreatedName; | |
| @override | |
| Future<List<Emulator>> getAllAvailableEmulators() async => emulators; | |
| @override | |
| Future<List<Emulator>> getEmulatorsMatching(String id) async { | |
| return emulators | |
| .where( | |
| (Emulator e) => | |
| e.id.toLowerCase().contains(id.toLowerCase()) || | |
| e.name.toLowerCase().contains(id.toLowerCase()), | |
| ) | |
| .toList(); | |
| } | |
| @override | |
| Future<CreateEmulatorResult> createEmulator({String? name}) async { | |
| lastCreatedName = name; | |
| return createResult ?? CreateEmulatorResult('fake_emulator', success: true); | |
| } | |
| } | |
| class FakeToolDependencies extends Fake implements ToolDependencies { | |
| FakeToolDependencies({ | |
| this._analytics, | |
| this._androidContext, | |
| this._appleContext, | |
| this._buildSystem, | |
| this._buildTargets, | |
| this._crashReporter, | |
| this._doctor, | |
| this._emulatorManager, | |
| this._featureFlags, | |
| this._toolContext, | |
| }); | |
| final Analytics? _analytics; | |
| final AndroidContext? _androidContext; | |
| final AppleContext? _appleContext; | |
| final BuildSystem? _buildSystem; | |
| final BuildTargets? _buildTargets; | |
| final CrashReporter? _crashReporter; | |
| final Doctor? _doctor; | |
| final EmulatorManager? _emulatorManager; | |
| final FeatureFlags? _featureFlags; | |
| final ToolContext? _toolContext; | |
| @override | |
| Analytics get analytics => _analytics ?? const NoOpAnalytics(); | |
| @override | |
| AndroidContext get androidContext => _androidContext ?? FakeAndroidContext(); | |
| @override | |
| AppleContext get appleContext => _appleContext ?? FakeAppleContext(); | |
| @override | |
| BuildSystem get buildSystem => _buildSystem ?? FakeBuildSystem(); | |
| @override | |
| BuildTargets get buildTargets => _buildTargets ?? FakeBuildTargets(); | |
| @override | |
| CrashReporter get crashReporter => _crashReporter ?? FakeCrashReporter(); | |
| @override | |
| Doctor get doctor => _doctor ?? FakeDoctor(); | |
| @override | |
| EmulatorManager get emulatorManager => _emulatorManager ?? FakeEmulatorManager(); | |
| @override | |
| FeatureFlags get featureFlags => _featureFlags ?? TestFeatureFlags(); | |
| @override | |
| ToolContext get toolContext => _toolContext ?? FakeToolContext(); | |
| } | |
| class FakeToolContext extends Fake implements ToolContext { | |
| FakeToolContext({ | |
| this._artifacts, | |
| this._botDetector, | |
| this._cache, | |
| this._config, | |
| this._customDevicesConfig, | |
| this._flutterVersion, | |
| this._fs, | |
| this._git, | |
| this._localEngineLocator, | |
| this._logger, | |
| this._nativeAssetsBuilder, | |
| this._os, | |
| this._outputPreferences, | |
| this._persistentToolState, | |
| this._platform, | |
| this._preRunValidator, | |
| this._processInfo, | |
| this._processManager, | |
| this._processUtils, | |
| this._projectFactory, | |
| this._shutdownHooks, | |
| this._signals, | |
| this._stdio, | |
| this._systemClock, | |
| this._terminal, | |
| this._userMessages, | |
| }); | |
| final Artifacts? _artifacts; | |
| final BotDetector? _botDetector; | |
| final Cache? _cache; | |
| final Config? _config; | |
| final CustomDevicesConfig? _customDevicesConfig; | |
| final FlutterVersion? _flutterVersion; | |
| final FileSystem? _fs; | |
| final Git? _git; | |
| final LocalEngineLocator? _localEngineLocator; | |
| final Logger? _logger; | |
| final TestCompilerNativeAssetsBuilder? _nativeAssetsBuilder; | |
| final OperatingSystemUtils? _os; | |
| final OutputPreferences? _outputPreferences; | |
| final PersistentToolState? _persistentToolState; | |
| final Platform? _platform; | |
| final PreRunValidator? _preRunValidator; | |
| final ProcessInfo? _processInfo; | |
| final ProcessManager? _processManager; | |
| final ProcessUtils? _processUtils; | |
| final FlutterProjectFactory? _projectFactory; | |
| final ShutdownHooks? _shutdownHooks; | |
| final Signals? _signals; | |
| final Stdio? _stdio; | |
| final SystemClock? _systemClock; | |
| final AnsiTerminal? _terminal; | |
| final UserMessages? _userMessages; | |
| @override | |
| late final Artifacts artifacts = _artifacts ?? FakeArtifacts(fileSystem: fs); | |
| @override | |
| late final BotDetector botDetector = _botDetector ?? const FakeBotDetector(false); | |
| @override | |
| late final Cache cache = _cache ?? FakeCache(fileSystem: fs); | |
| @override | |
| late final Config config = _config ?? FakeConfig(); | |
| @override | |
| late final CustomDevicesConfig customDevicesConfig = | |
| _customDevicesConfig ?? | |
| CustomDevicesConfig.test(fileSystem: fs, logger: logger, platform: platform); | |
| @override | |
| late final FlutterVersion flutterVersion = _flutterVersion ?? FakeFlutterVersion(); | |
| @override | |
| late final FileSystem fs = _fs ?? MemoryFileSystem.test(); | |
| @override | |
| late final Git git = _git ?? Git(currentPlatform: platform, runProcessWith: processUtils); | |
| @override | |
| late final LocalEngineLocator localEngineLocator = | |
| _localEngineLocator ?? | |
| LocalEngineLocator( | |
| userMessages: userMessages, | |
| logger: logger, | |
| platform: platform, | |
| fileSystem: fs, | |
| flutterRoot: Cache.flutterRoot ?? '', | |
| ); | |
| @override | |
| late final Logger logger = _logger ?? BufferLogger.test(); | |
| @override | |
| TestCompilerNativeAssetsBuilder? get nativeAssetsBuilder => _nativeAssetsBuilder; | |
| @override | |
| late final OperatingSystemUtils os = _os ?? FakeOperatingSystemUtils(); | |
| @override | |
| late final OutputPreferences outputPreferences = _outputPreferences ?? OutputPreferences.test(); | |
| @override | |
| late final PersistentToolState persistentToolState = | |
| _persistentToolState ?? | |
| PersistentToolState.test( | |
| directory: fs.systemTempDirectory.createTempSync('persistent_tool_state'), | |
| logger: logger, | |
| ); | |
| @override | |
| late final Platform platform = _platform ?? FakePlatform(); | |
| @override | |
| late final PreRunValidator preRunValidator = _preRunValidator ?? const NoOpPreRunValidator(); | |
| @override | |
| late final ProcessInfo processInfo = _processInfo ?? ProcessInfo.test(fs); | |
| @override | |
| late final ProcessManager processManager = _processManager ?? FakeProcessManager.any(); | |
| @override | |
| late final ProcessUtils processUtils = | |
| _processUtils ?? ProcessUtils(processManager: processManager, logger: logger); | |
| @override | |
| late final FlutterProjectFactory projectFactory = | |
| _projectFactory ?? FlutterProjectFactory(fileSystem: fs, logger: logger); | |
| @override | |
| late final ShutdownHooks shutdownHooks = _shutdownHooks ?? ShutdownHooks(); | |
| @override | |
| late final Signals signals = _signals ?? Signals.test(); | |
| @override | |
| late final Stdio stdio = _stdio ?? FakeStdio(); | |
| @override | |
| late final SystemClock systemClock = _systemClock ?? const SystemClock(); | |
| @override | |
| late final AnsiTerminal terminal = _terminal ?? AnsiTerminal(stdio: stdio, platform: platform); | |
| @override | |
| late final UserMessages userMessages = _userMessages ?? UserMessages(); | |
| @override | |
| FileSystemUtils get fileSystemUtils => FileSystemUtils(fileSystem: fs, platform: platform); | |
| } | |
| /// A [ToolContext] that dynamically delegates to [globals] for use in [testUsingContext]. | |
| class DelegatingToolContext extends Fake implements ToolContext { | |
| DelegatingToolContext({ | |
| this._artifacts, | |
| this._botDetector, | |
| this._cache, | |
| this._config, | |
| this._customDevicesConfig, | |
| this._flutterVersion, | |
| this._fs, | |
| this._git, | |
| this._localEngineLocator, | |
| this._logger, | |
| this._os, | |
| this._outputPreferences, | |
| this._persistentToolState, | |
| this._platform, | |
| this._preRunValidator, | |
| this._processInfo, | |
| this._processManager, | |
| this._processUtils, | |
| this._projectFactory, | |
| this._shutdownHooks, | |
| this._signals, | |
| this._stdio, | |
| this._systemClock, | |
| this._terminal, | |
| this._userMessages, | |
| }); | |
| final Artifacts? _artifacts; | |
| final BotDetector? _botDetector; | |
| final Cache? _cache; | |
| final Config? _config; | |
| final CustomDevicesConfig? _customDevicesConfig; | |
| final FlutterVersion? _flutterVersion; | |
| final FileSystem? _fs; | |
| final Git? _git; | |
| final LocalEngineLocator? _localEngineLocator; | |
| final Logger? _logger; | |
| final OperatingSystemUtils? _os; | |
| final OutputPreferences? _outputPreferences; | |
| final PersistentToolState? _persistentToolState; | |
| final Platform? _platform; | |
| final PreRunValidator? _preRunValidator; | |
| final ProcessInfo? _processInfo; | |
| final ProcessManager? _processManager; | |
| final ProcessUtils? _processUtils; | |
| final FlutterProjectFactory? _projectFactory; | |
| final ShutdownHooks? _shutdownHooks; | |
| final Signals? _signals; | |
| final Stdio? _stdio; | |
| final SystemClock? _systemClock; | |
| final AnsiTerminal? _terminal; | |
| final UserMessages? _userMessages; | |
| @override | |
| Artifacts get artifacts => _artifacts ?? globals.artifacts!; | |
| @override | |
| BotDetector get botDetector => _botDetector ?? globals.botDetector; | |
| @override | |
| Cache get cache => _cache ?? globals.cache; | |
| @override | |
| Config get config => _config ?? globals.config; | |
| @override | |
| CustomDevicesConfig get customDevicesConfig => | |
| _customDevicesConfig ?? globals.customDevicesConfig; | |
| @override | |
| FlutterVersion get flutterVersion => _flutterVersion ?? globals.flutterVersion; | |
| @override | |
| FileSystem get fs => _fs ?? globals.fs; | |
| @override | |
| Git get git => _git ?? globals.git; | |
| @override | |
| LocalEngineLocator get localEngineLocator => | |
| _localEngineLocator ?? | |
| globals.localEngineLocator ?? | |
| LocalEngineLocator( | |
| userMessages: userMessages, | |
| logger: logger, | |
| platform: platform, | |
| fileSystem: fs, | |
| flutterRoot: Cache.flutterRoot ?? '', | |
| ); | |
| @override | |
| Logger get logger => _logger ?? globals.logger; | |
| @override | |
| OperatingSystemUtils get os => _os ?? globals.os; | |
| @override | |
| OutputPreferences get outputPreferences => _outputPreferences ?? globals.outputPreferences; | |
| @override | |
| PersistentToolState get persistentToolState => | |
| _persistentToolState ?? | |
| globals.persistentToolState ?? | |
| PersistentToolState.test( | |
| directory: fs.systemTempDirectory.createTempSync('persistent_tool_state'), | |
| logger: logger, | |
| ); | |
| @override | |
| Platform get platform => _platform ?? globals.platform; | |
| @override | |
| PreRunValidator get preRunValidator => _preRunValidator ?? const NoOpPreRunValidator(); | |
| @override | |
| ProcessInfo get processInfo => _processInfo ?? globals.processInfo; | |
| @override | |
| ProcessManager get processManager => _processManager ?? globals.processManager; | |
| @override | |
| ProcessUtils get processUtils => _processUtils ?? globals.processUtils; | |
| @override | |
| FlutterProjectFactory get projectFactory => _projectFactory ?? globals.projectFactory; | |
| @override | |
| ShutdownHooks get shutdownHooks => _shutdownHooks ?? globals.shutdownHooks; | |
| @override | |
| Signals get signals => _signals ?? globals.signals; | |
| @override | |
| Stdio get stdio => _stdio ?? globals.stdio; | |
| @override | |
| SystemClock get systemClock => _systemClock ?? globals.systemClock; | |
| @override | |
| AnsiTerminal get terminal => _terminal ?? globals.terminal; | |
| @override | |
| UserMessages get userMessages => _userMessages ?? globals.userMessages; | |
| @override | |
| FileSystemUtils get fileSystemUtils => FileSystemUtils(fileSystem: fs, platform: platform); | |
| } | |
| class FakeAndroidContext extends Fake implements AndroidContext { | |
| FakeAndroidContext({ | |
| this._androidSdk, | |
| this._androidStudio, | |
| this._gradleUtils, | |
| this._java, | |
| this._javaBuilder, | |
| }); | |
| final AndroidSdk? _androidSdk; | |
| final AndroidStudio? _androidStudio; | |
| final GradleUtils? _gradleUtils; | |
| final Java? _java; | |
| final Java? Function()? _javaBuilder; | |
| @override | |
| AndroidSdk? get androidSdk => _androidSdk; | |
| @override | |
| AndroidStudio? get androidStudio => _androidStudio; | |
| @override | |
| late final GradleUtils gradleUtils = _gradleUtils ?? FakeGradleUtils(); | |
| @override | |
| Java? get java => _javaBuilder != null ? _javaBuilder() : _java; | |
| } | |
| class FakeAppleContext extends Fake implements AppleContext { | |
| FakeAppleContext({ | |
| this._cocoaPods, | |
| this._cocoapodsValidator, | |
| this._iosSimulatorUtils, | |
| this._iosWorkflow, | |
| this._plistParser, | |
| this._xcdevice, | |
| this._xcode, | |
| this._xcodeProjectInterpreter, | |
| }); | |
| final CocoaPods? _cocoaPods; | |
| final CocoaPodsValidator? _cocoapodsValidator; | |
| final IOSSimulatorUtils? _iosSimulatorUtils; | |
| final IOSWorkflow? _iosWorkflow; | |
| final PlistParser? _plistParser; | |
| final XCDevice? _xcdevice; | |
| final Xcode? _xcode; | |
| final XcodeProjectInterpreter? _xcodeProjectInterpreter; | |
| @override | |
| late final CocoaPods cocoaPods = _cocoaPods ?? FakeCocoaPods(); | |
| @override | |
| late final CocoaPodsValidator cocoapodsValidator = | |
| _cocoapodsValidator ?? FakeCocoaPodsValidator(); | |
| @override | |
| late final IOSSimulatorUtils iosSimulatorUtils = _iosSimulatorUtils ?? FakeIOSSimulatorUtils(); | |
| @override | |
| late final IOSWorkflow iosWorkflow = _iosWorkflow ?? FakeIOSWorkflow(); | |
| @override | |
| late final PlistParser plistParser = _plistParser ?? FakePlistParser(); | |
| @override | |
| late final XCDevice xcdevice = _xcdevice ?? FakeXCDevice(); | |
| @override | |
| late final Xcode xcode = _xcode ?? FakeXcode(); | |
| @override | |
| late final XcodeProjectInterpreter xcodeProjectInterpreter = | |
| _xcodeProjectInterpreter ?? FakeXcodeProjectInterpreter(); | |
| } |