diff --git a/packages/flutter_tools/lib/src/ios/devices.dart b/packages/flutter_tools/lib/src/ios/devices.dart index 9598471926..720e61b508 100644 --- a/packages/flutter_tools/lib/src/ios/devices.dart +++ b/packages/flutter_tools/lib/src/ios/devices.dart @@ -3,7 +3,6 @@ // found in the LICENSE file. import 'dart:async'; -import 'dart:math' as math; import 'package:meta/meta.dart'; import 'package:process/process.dart'; @@ -25,7 +24,6 @@ import '../macos/xcode.dart'; import '../project.dart'; import '../protocol_discovery.dart'; import '../vmservice.dart'; -import 'fallback_discovery.dart'; import 'ios_deploy.dart'; import 'ios_workflow.dart'; import 'iproxy.dart'; @@ -152,7 +150,6 @@ class IOSDevice extends Device { @required IMobileDevice iMobileDevice, @required IProxy iProxy, @required Logger logger, - @required VmServiceConnector vmServiceConnectUri, }) : _sdkVersion = sdkVersion, _iosDeploy = iosDeploy, @@ -161,14 +158,13 @@ class IOSDevice extends Device { _fileSystem = fileSystem, _logger = logger, _platform = platform, - _vmServiceConnectUri = vmServiceConnectUri, super( id, category: Category.mobile, platformType: PlatformType.ios, ephemeral: true, ) { - if (!platform.isMacOS) { + if (!_platform.isMacOS) { assert(false, 'Control of iOS devices or simulators only supported on Mac OS.'); return; } @@ -181,7 +177,6 @@ class IOSDevice extends Device { final Platform _platform; final IMobileDevice _iMobileDevice; final IProxy _iproxy; - final VmServiceConnector _vmServiceConnectUri; /// May be 0 if version cannot be parsed. int get majorSdkVersion { @@ -312,14 +307,11 @@ class IOSDevice extends Device { Map platformArgs, bool prebuiltApplication = false, bool ipv6 = false, - @visibleForTesting Duration fallbackPollingDelay, - @visibleForTesting Duration fallbackThrottleTimeout, String userIdentifier, }) async { String packageId; if (!prebuiltApplication) { - // TODO(chinmaygarde): Use mainPath, route. _logger.printTrace('Building ${package.name} for $id'); // Step 1: Build the precompiled/DBC application if necessary. @@ -353,32 +345,16 @@ class IOSDevice extends Device { return LaunchResult.failed(); } - // Step 2.5: Generate a potential open port using the provided argument, - // or randomly with the package name as a seed. Intentionally choose - // ports within the ephemeral port range. - final int assumedObservatoryPort = debuggingOptions?.deviceVmServicePort - ?? math.Random(packageId.hashCode).nextInt(16383) + 49152; - // Step 3: Attempt to install the application on the device. final String dartVmFlags = computeDartVmFlags(debuggingOptions); final List launchArguments = [ '--enable-dart-profiling', - // These arguments are required to support the fallback connection strategy - // described in fallback_discovery.dart. - '--enable-service-port-fallback', '--disable-service-auth-codes', - '--observatory-port=$assumedObservatoryPort', if (debuggingOptions.disablePortPublication) '--disable-observatory-publication', if (debuggingOptions.startPaused) '--start-paused', if (dartVmFlags.isNotEmpty) '--dart-flags="$dartVmFlags"', if (debuggingOptions.useTestFonts) '--use-test-fonts', - // "--enable-checked-mode" and "--verify-entry-points" should always be - // passed when we launch debug build via "ios-deploy". However, we don't - // pass them if a certain environment variable is set to enable the - // "system_debug_ios" integration test in the CI, which simulates a - // home-screen launch. - if (debuggingOptions.debuggingEnabled && - _platform.environment['FLUTTER_TOOLS_DEBUG_WITHOUT_CHECKED_MODE'] != 'true') ...[ + if (debuggingOptions.debuggingEnabled) ...[ '--enable-checked-mode', '--verify-entry-points', ], @@ -413,7 +389,6 @@ class IOSDevice extends Device { launchArguments: launchArguments, interfaceType: interfaceType, ); - if (deviceLogReader is IOSDeviceLogReader) { deviceLogReader.debuggerStream = iosDeployDebugger; } @@ -421,11 +396,10 @@ class IOSDevice extends Device { observatoryDiscovery = ProtocolDiscovery.observatory( deviceLogReader, portForwarder: portForwarder, - throttleDuration: fallbackPollingDelay, - throttleTimeout: fallbackThrottleTimeout ?? const Duration(minutes: 5), hostPort: debuggingOptions.hostVmServicePort, devicePort: debuggingOptions.deviceVmServicePort, ipv6: ipv6, + logger: _logger, ); } if (iosDeployDebugger == null) { @@ -451,22 +425,12 @@ class IOSDevice extends Device { } _logger.printTrace('Application launched on the device. Waiting for observatory port.'); - final FallbackDiscovery fallbackDiscovery = FallbackDiscovery( - logger: _logger, - portForwarder: portForwarder, - protocolDiscovery: observatoryDiscovery, - flutterUsage: globals.flutterUsage, - pollingDelay: fallbackPollingDelay, - vmServiceConnectUri: _vmServiceConnectUri, - ); - final Uri localUri = await fallbackDiscovery.discover( - assumedDevicePort: assumedObservatoryPort, - device: this, - usesIpv6: ipv6, - hostVmservicePort: debuggingOptions.hostVmServicePort, - packageId: packageId, - packageName: FlutterProject.current().manifest.appName, - ); + Uri localUri; + try { + localUri = await observatoryDiscovery.uri.timeout(const Duration(seconds: 30)); + } on TimeoutException { + await observatoryDiscovery.cancel(); + } if (localUri == null) { iosDeployDebugger?.detach(); return LaunchResult.failed(); diff --git a/packages/flutter_tools/lib/src/ios/fallback_discovery.dart b/packages/flutter_tools/lib/src/ios/fallback_discovery.dart deleted file mode 100644 index 127c0fccef..0000000000 --- a/packages/flutter_tools/lib/src/ios/fallback_discovery.dart +++ /dev/null @@ -1,189 +0,0 @@ -// 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 'package:meta/meta.dart'; -import 'package:vm_service/vm_service.dart'; - -import '../base/io.dart'; -import '../base/logger.dart'; -import '../device.dart'; -import '../protocol_discovery.dart'; -import '../reporting/reporting.dart'; - -typedef VmServiceConnector = Future Function(String, {Log log}); - -/// A protocol for discovery of a vmservice on an attached iOS device with -/// multiple fallbacks. -/// -/// First, it tries to discover a vmservice by assigning a -/// specific port and then attempt to connect. This may fail if the port is -/// not available. This port value should be either random, or otherwise -/// generated with application specific input. This reduces the chance of -/// accidentally connecting to another running flutter application. -/// -/// If that does not work, attempt to scan logs from the attached debugger -/// and parse the connected port logged by the engine. -class FallbackDiscovery { - FallbackDiscovery({ - @required DevicePortForwarder portForwarder, - @required Logger logger, - @required ProtocolDiscovery protocolDiscovery, - @required Usage flutterUsage, - @required VmServiceConnector vmServiceConnectUri, - Duration pollingDelay, - }) : _logger = logger, - _portForwarder = portForwarder, - _protocolDiscovery = protocolDiscovery, - _flutterUsage = flutterUsage, - _vmServiceConnectUri = vmServiceConnectUri, - _pollingDelay = pollingDelay ?? const Duration(seconds: 2); - - static const String _kEventName = 'ios-handshake'; - - final DevicePortForwarder _portForwarder; - final Logger _logger; - final ProtocolDiscovery _protocolDiscovery; - final Usage _flutterUsage; - final VmServiceConnector _vmServiceConnectUri; - final Duration _pollingDelay; - - /// Attempt to discover the observatory port. - Future discover({ - @required int assumedDevicePort, - @required String packageId, - @required Device device, - @required bool usesIpv6, - @required int hostVmservicePort, - @required String packageName, - }) async { - final Uri result = await _attemptServiceConnection( - assumedDevicePort: assumedDevicePort, - hostVmservicePort: hostVmservicePort, - packageName: packageName, - ); - if (result != null) { - return result; - } - - try { - final Uri result = await _protocolDiscovery.uri; - if (result != null) { - UsageEvent( - _kEventName, - 'log-success', - flutterUsage: _flutterUsage, - ).send(); - return result; - } - } on ArgumentError { - // In the event of an invalid InternetAddress, this code attempts to catch - // an ArgumentError from protocol_discovery.dart - } on Exception catch (err) { - _logger.printTrace(err.toString()); - } - _logger.printTrace('Failed to connect with log scanning'); - UsageEvent( - _kEventName, - 'log-failure', - flutterUsage: _flutterUsage, - ).send(); - - return null; - } - - // Attempt to connect to the VM service and find an isolate with a matching `packageName`. - // Returns `null` if no connection can be made. - Future _attemptServiceConnection({ - @required int assumedDevicePort, - @required int hostVmservicePort, - @required String packageName, - }) async { - int hostPort; - Uri assumedWsUri; - try { - hostPort = await _portForwarder.forward( - assumedDevicePort, - hostPort: hostVmservicePort, - ); - assumedWsUri = Uri.parse('ws://localhost:$hostPort/ws'); - } on Exception catch (err) { - _logger.printTrace(err.toString()); - _logger.printTrace('Failed to connect directly, falling back to log scanning'); - _sendFailureEvent(err, assumedDevicePort); - return null; - } - - // Attempt to connect to the VM service 5 times. - int attempts = 0; - Exception firstException; - VmService vmService; - while (attempts < 5) { - try { - vmService = await _vmServiceConnectUri( - assumedWsUri.toString(), - ); - final VM vm = await vmService.getVM(); - for (final IsolateRef isolateRefs in vm.isolates) { - final Isolate isolateResponse = await vmService.getIsolate( - isolateRefs.id, - ); - final LibraryRef library = isolateResponse.rootLib; - if (library != null && - (library.uri.startsWith('package:$packageName') || - library.uri.startsWith(RegExp(r'file:\/\/\/.*\/' + packageName)))) { - UsageEvent( - _kEventName, - 'success', - flutterUsage: _flutterUsage, - ).send(); - - // This vmService instance must be disposed of, otherwise DDS will - // fail to start. - vmService.dispose(); - return Uri.parse('http://localhost:$hostPort'); - } - } - } on Exception catch (err) { - // No action, we might have failed to connect. - firstException ??= err; - _logger.printTrace(err.toString()); - } finally { - // This vmService instance must be disposed of, otherwise DDS will - // fail to start. - vmService?.dispose(); - } - - // No exponential backoff is used here to keep the amount of time the - // tool waits for a connection to be reasonable. If the vmservice cannot - // be connected to in this way, the mDNS discovery must be reached - // sooner rather than later. - await Future.delayed(_pollingDelay); - attempts += 1; - } - _logger.printTrace('Failed to connect directly, falling back to log scanning'); - _sendFailureEvent(firstException, assumedDevicePort); - return null; - } - - void _sendFailureEvent(Exception err, int assumedDevicePort) { - String eventAction; - String eventLabel; - if (err == null) { - eventAction = 'failure-attempts-exhausted'; - eventLabel = assumedDevicePort.toString(); - } else if (err is HttpException) { - eventAction = 'failure-http'; - eventLabel = '${err.message}, device port = $assumedDevicePort'; - } else { - eventAction = 'failure-other'; - eventLabel = '$err, device port = $assumedDevicePort'; - } - UsageEvent( - _kEventName, - eventAction, - label: eventLabel, - flutterUsage: _flutterUsage, - ).send(); - } -} diff --git a/packages/flutter_tools/lib/src/macos/xcode.dart b/packages/flutter_tools/lib/src/macos/xcode.dart index 72bb6db859..01968a066a 100644 --- a/packages/flutter_tools/lib/src/macos/xcode.dart +++ b/packages/flutter_tools/lib/src/macos/xcode.dart @@ -6,7 +6,6 @@ import 'dart:async'; import 'package:meta/meta.dart'; import 'package:process/process.dart'; -import 'package:vm_service/vm_service_io.dart' as vm_service_io; import '../artifacts.dart'; import '../base/common.dart'; @@ -519,7 +518,6 @@ class XCDevice { iosDeploy: _iosDeploy, iMobileDevice: _iMobileDevice, platform: globals.platform, - vmServiceConnectUri: vm_service_io.vmServiceConnectUri, )); } return devices; diff --git a/packages/flutter_tools/lib/src/protocol_discovery.dart b/packages/flutter_tools/lib/src/protocol_discovery.dart index 96d238ae5d..c47b9bb4ce 100644 --- a/packages/flutter_tools/lib/src/protocol_discovery.dart +++ b/packages/flutter_tools/lib/src/protocol_discovery.dart @@ -19,7 +19,6 @@ class ProtocolDiscovery { this.serviceName, { this.portForwarder, this.throttleDuration, - this.throttleTimeout, this.hostPort, this.devicePort, this.ipv6, @@ -37,7 +36,6 @@ class ProtocolDiscovery { DeviceLogReader logReader, { DevicePortForwarder portForwarder, Duration throttleDuration, - Duration throttleTimeout, @required int hostPort, @required int devicePort, @required bool ipv6, @@ -49,7 +47,6 @@ class ProtocolDiscovery { kObservatoryService, portForwarder: portForwarder, throttleDuration: throttleDuration ?? const Duration(milliseconds: 200), - throttleTimeout: throttleTimeout, hostPort: hostPort, devicePort: devicePort, ipv6: ipv6, @@ -68,11 +65,6 @@ class ProtocolDiscovery { /// The time to wait before forwarding a new observatory URIs from [logReader]. final Duration throttleDuration; - /// The time between URIs are discovered before timing out when scraping the [logReader]. - /// - /// If null, log scanning will continue indefinitely. - final Duration throttleTimeout; - StreamSubscription _deviceLogSubscription; _BufferedStreamController _uriStreamController; @@ -99,15 +91,10 @@ class ProtocolDiscovery { /// Port forwarding is only attempted when this is invoked, /// for each observatory URL in the stream. Stream get uris { - Stream uriStream = _uriStreamController.stream + final Stream uriStream = _uriStreamController.stream .transform(_throttle( waitDuration: throttleDuration, )); - if (throttleTimeout != null) { - // Don't throw a TimeoutException. The URL wasn't found in time, just close the stream. - uriStream = uriStream.timeout(throttleTimeout, - onTimeout: (EventSink sink) => sink.close()); - } return uriStream.asyncMap(_forwardPort); } diff --git a/packages/flutter_tools/test/general.shard/ios/devices_test.dart b/packages/flutter_tools/test/general.shard/ios/devices_test.dart index 83fbb84b38..d26a01ac38 100644 --- a/packages/flutter_tools/test/general.shard/ios/devices_test.dart +++ b/packages/flutter_tools/test/general.shard/ios/devices_test.dart @@ -37,7 +37,6 @@ void main() { group('IOSDevice', () { final List unsupportedPlatforms = [linuxPlatform, windowsPlatform]; Cache cache; - MockVmService mockVmService; Logger logger; IOSDeploy iosDeploy; IMobileDevice iMobileDevice; @@ -46,7 +45,6 @@ void main() { setUp(() { final Artifacts artifacts = Artifacts.test(); cache = Cache.test(); - mockVmService = MockVmService(); logger = BufferLogger.test(); iosDeploy = IOSDeploy( artifacts: artifacts, @@ -76,7 +74,6 @@ void main() { sdkVersion: '13.3', cpuArchitecture: DarwinArch.arm64, interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ); }); @@ -93,7 +90,6 @@ void main() { cpuArchitecture: DarwinArch.arm64, sdkVersion: '1.0.0', interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ).majorSdkVersion, 1); expect(IOSDevice( 'device-123', @@ -107,7 +103,6 @@ void main() { cpuArchitecture: DarwinArch.arm64, sdkVersion: '13.1.1', interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ).majorSdkVersion, 13); expect(IOSDevice( 'device-123', @@ -121,7 +116,6 @@ void main() { cpuArchitecture: DarwinArch.arm64, sdkVersion: '10', interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ).majorSdkVersion, 10); expect(IOSDevice( 'device-123', @@ -135,7 +129,6 @@ void main() { cpuArchitecture: DarwinArch.arm64, sdkVersion: '0', interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ).majorSdkVersion, 0); expect(IOSDevice( 'device-123', @@ -149,7 +142,6 @@ void main() { cpuArchitecture: DarwinArch.arm64, sdkVersion: 'bogus', interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ).majorSdkVersion, 0); }); @@ -166,7 +158,6 @@ void main() { sdkVersion: '13.3', cpuArchitecture: DarwinArch.arm64, interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ); expect(device.supportsRuntimeMode(BuildMode.debug), true); @@ -191,7 +182,6 @@ void main() { sdkVersion: '13.3', cpuArchitecture: DarwinArch.arm64, interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ); }, throwsAssertionError, @@ -280,7 +270,6 @@ void main() { sdkVersion: '13.3', cpuArchitecture: DarwinArch.arm64, interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService, ); logReader1 = createLogReader(device, appPackage1, mockProcess1); logReader2 = createLogReader(device, appPackage2, mockProcess2); @@ -301,8 +290,6 @@ void main() { group('polling', () { MockXcdevice mockXcdevice; Cache cache; - MockVmService mockVmService1; - MockVmService mockVmService2; FakeProcessManager fakeProcessManager; BufferLogger logger; IOSDeploy iosDeploy; @@ -315,8 +302,6 @@ void main() { mockXcdevice = MockXcdevice(); final Artifacts artifacts = Artifacts.test(); cache = Cache.test(); - mockVmService1 = MockVmService(); - mockVmService2 = MockVmService(); logger = BufferLogger.test(); mockIosWorkflow = MockIOSWorkflow(); fakeProcessManager = FakeProcessManager.any(); @@ -346,7 +331,6 @@ void main() { platform: macPlatform, fileSystem: MemoryFileSystem.test(), interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService1, ); device2 = IOSDevice( @@ -361,7 +345,6 @@ void main() { platform: macPlatform, fileSystem: MemoryFileSystem.test(), interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => mockVmService2, ); }); diff --git a/packages/flutter_tools/test/general.shard/ios/fallback_discovery_test.dart b/packages/flutter_tools/test/general.shard/ios/fallback_discovery_test.dart deleted file mode 100644 index 45130ec0e3..0000000000 --- a/packages/flutter_tools/test/general.shard/ios/fallback_discovery_test.dart +++ /dev/null @@ -1,154 +0,0 @@ -// 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 'package:flutter_tools/src/base/logger.dart'; -import 'package:flutter_tools/src/base/platform.dart'; -import 'package:flutter_tools/src/base/terminal.dart'; -import 'package:flutter_tools/src/device.dart'; -import 'package:flutter_tools/src/ios/fallback_discovery.dart'; -import 'package:flutter_tools/src/protocol_discovery.dart'; -import 'package:flutter_tools/src/reporting/reporting.dart'; -import 'package:mockito/mockito.dart'; -import 'package:vm_service/vm_service.dart'; - -import '../../src/common.dart'; -import '../../src/mocks.dart'; - -void main() { - BufferLogger logger; - FallbackDiscovery fallbackDiscovery; - MockPrototcolDiscovery mockPrototcolDiscovery; - MockPortForwarder mockPortForwarder; - MockVmService mockVmService; - - setUp(() { - logger = BufferLogger( - terminal: AnsiTerminal(stdio: MockStdio(), platform: const LocalPlatform()), - outputPreferences: OutputPreferences.test(), - ); - mockVmService = MockVmService(); - mockPrototcolDiscovery = MockPrototcolDiscovery(); - mockPortForwarder = MockPortForwarder(); - fallbackDiscovery = FallbackDiscovery( - logger: logger, - portForwarder: mockPortForwarder, - protocolDiscovery: mockPrototcolDiscovery, - flutterUsage: Usage.test(), - vmServiceConnectUri: (String uri, {Log log}) async { - return mockVmService; - }, - pollingDelay: Duration.zero, - ); - when(mockPortForwarder.forward(23, hostPort: anyNamed('hostPort'))) - .thenAnswer((Invocation invocation) async => 1); - }); - - testWithoutContext('Selects assumed port if VM service connection is successful', () async { - when(mockVmService.getVM()).thenAnswer((Invocation invocation) async { - return VM.parse({})..isolates = [ - IsolateRef.parse({}), - ]; - }); - when(mockVmService.getIsolate(any)).thenAnswer((Invocation invocation) async { - return Isolate.parse({}) - ..rootLib = (LibraryRef(name: 'main', uri: 'package:hello/main.dart', id: '2')); - }); - - expect(await fallbackDiscovery.discover( - assumedDevicePort: 23, - device: null, - hostVmservicePort: 1, - packageId: null, - usesIpv6: false, - packageName: 'hello', - ), Uri.parse('http://localhost:1')); - }); - - testWithoutContext('Selects assumed port when another isolate has no root library', () async { - when(mockVmService.getVM()).thenAnswer((Invocation invocation) async { - return VM.parse({})..isolates = [ - IsolateRef.parse({})..id = '1', - IsolateRef.parse({})..id = '2', - ]; - }); - when(mockVmService.getIsolate('1')).thenAnswer((Invocation invocation) async { - return Isolate.parse({}) - ..rootLib = null; - }); - when(mockVmService.getIsolate('2')).thenAnswer((Invocation invocation) async { - return Isolate.parse({}) - ..rootLib = (LibraryRef.parse({})..uri = 'package:hello/main.dart'); - }); - expect(await fallbackDiscovery.discover( - assumedDevicePort: 23, - device: null, - hostVmservicePort: 1, - packageId: null, - usesIpv6: false, - packageName: 'hello', - ), Uri.parse('http://localhost:1')); - }); - - testWithoutContext('Selects log scanning if VM service connecton fails due to Sentinel', () async { - when(mockVmService.getVM()).thenAnswer((Invocation invocation) async { - return VM.parse({})..isolates = [ - IsolateRef( - id: 'a', - name: 'isolate', - number: '1', - isSystemIsolate: false, - ), - ]; - }); - when(mockVmService.getIsolate(any)) - .thenThrow(SentinelException.parse('Something', {})); - when(mockPrototcolDiscovery.uri).thenAnswer((Invocation invocation) async { - return Uri.parse('http://localhost:1234'); - }); - - expect(await fallbackDiscovery.discover( - assumedDevicePort: 23, - device: null, - hostVmservicePort: 1, - packageId: 'hello', - usesIpv6: false, - packageName: 'hello', - ), Uri.parse('http://localhost:1234')); - }); - - testWithoutContext('Selects log scanning if VM service connecton fails', () async { - when(mockVmService.getVM()).thenThrow(Exception()); - - when(mockPrototcolDiscovery.uri).thenAnswer((Invocation invocation) async { - return Uri.parse('http://localhost:1234'); - }); - - expect(await fallbackDiscovery.discover( - assumedDevicePort: 23, - device: null, - hostVmservicePort: 1, - packageId: 'hello', - usesIpv6: false, - packageName: 'hello', - ), Uri.parse('http://localhost:1234')); - }); - - testWithoutContext('Fails if both VM Service and log scanning fails', () async { - when(mockVmService.getVM()).thenThrow(Exception()); - when(mockPrototcolDiscovery.uri).thenAnswer((Invocation invocation) async => null); - - expect(await fallbackDiscovery.discover( - assumedDevicePort: 23, - device: null, - hostVmservicePort: 1, - packageId: 'hello', - usesIpv6: false, - packageName: 'hello', - ), isNull); - }); -} - -class MockPrototcolDiscovery extends Mock implements ProtocolDiscovery {} -class MockPortForwarder extends Mock implements DevicePortForwarder {} -class MockVmService extends Mock implements VmService {} diff --git a/packages/flutter_tools/test/general.shard/ios/ios_device_install_test.dart b/packages/flutter_tools/test/general.shard/ios/ios_device_install_test.dart index a3ab7b8d44..cd87eab33f 100644 --- a/packages/flutter_tools/test/general.shard/ios/ios_device_install_test.dart +++ b/packages/flutter_tools/test/general.shard/ios/ios_device_install_test.dart @@ -318,7 +318,6 @@ IOSDevice setUpIOSDevice({ ), iProxy: IProxy.test(logger: logger, processManager: processManager), interfaceType: interfaceType, - vmServiceConnectUri: (String string, {Log log}) async => MockVmService(), ); } diff --git a/packages/flutter_tools/test/general.shard/ios/ios_device_project_test.dart b/packages/flutter_tools/test/general.shard/ios/ios_device_project_test.dart index 9cb78d9b03..d59ff0a32c 100644 --- a/packages/flutter_tools/test/general.shard/ios/ios_device_project_test.dart +++ b/packages/flutter_tools/test/general.shard/ios/ios_device_project_test.dart @@ -88,7 +88,6 @@ IOSDevice setUpIOSDevice(FileSystem fileSystem) { cpuArchitecture: DarwinArch.arm64, iProxy: IProxy.test(logger: BufferLogger.test(), processManager: FakeProcessManager.any()), interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => MockVmService(), ); } diff --git a/packages/flutter_tools/test/general.shard/ios/ios_device_start_nonprebuilt_test.dart b/packages/flutter_tools/test/general.shard/ios/ios_device_start_nonprebuilt_test.dart index c810605bae..d657ebc3ba 100644 --- a/packages/flutter_tools/test/general.shard/ios/ios_device_start_nonprebuilt_test.dart +++ b/packages/flutter_tools/test/general.shard/ios/ios_device_start_nonprebuilt_test.dart @@ -134,9 +134,7 @@ void main() { '--args', const [ '--enable-dart-profiling', - '--enable-service-port-fallback', '--disable-service-auth-codes', - '--observatory-port=53781', ].join(' ') ]) ); @@ -179,7 +177,7 @@ void main() { command: [...kRunReleaseArgs, '-showBuildSettings'], duration: Duration(minutes: 5), // this is longer than the timeout of 1 minute. )); - // The second call succeedes and is made after the first times out. + // The second call succeeds and is made after the first times out. processManager.addCommand( const FakeCommand( command: [...kRunReleaseArgs, '-showBuildSettings'], @@ -197,9 +195,7 @@ void main() { '--args', const [ '--enable-dart-profiling', - '--enable-service-port-fallback', '--disable-service-auth-codes', - '--observatory-port=53781', ].join(' ') ]) ); @@ -272,9 +268,7 @@ void main() { '--args', const [ '--enable-dart-profiling', - '--enable-service-port-fallback', '--disable-service-auth-codes', - '--observatory-port=53781', ].join(' ') ]) ); @@ -350,7 +344,6 @@ IOSDevice setUpIOSDevice({ ), cpuArchitecture: DarwinArch.arm64, interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: (String string, {Log log}) async => MockVmService(), ); } diff --git a/packages/flutter_tools/test/general.shard/ios/ios_device_start_prebuilt_test.dart b/packages/flutter_tools/test/general.shard/ios/ios_device_start_prebuilt_test.dart index 2533d507c9..55bd131352 100644 --- a/packages/flutter_tools/test/general.shard/ios/ios_device_start_prebuilt_test.dart +++ b/packages/flutter_tools/test/general.shard/ios/ios_device_start_prebuilt_test.dart @@ -9,19 +9,15 @@ import 'package:flutter_tools/src/application_package.dart'; import 'package:flutter_tools/src/artifacts.dart'; import 'package:flutter_tools/src/base/dds.dart'; import 'package:flutter_tools/src/base/file_system.dart'; -import 'package:flutter_tools/src/base/io.dart' as io; 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/cache.dart'; import 'package:flutter_tools/src/device.dart'; -import 'package:flutter_tools/src/globals.dart' as globals; import 'package:flutter_tools/src/ios/devices.dart'; -import 'package:flutter_tools/src/ios/fallback_discovery.dart'; import 'package:flutter_tools/src/ios/ios_deploy.dart'; import 'package:flutter_tools/src/ios/iproxy.dart'; import 'package:flutter_tools/src/ios/mac.dart'; -import 'package:flutter_tools/src/reporting/reporting.dart'; import 'package:mockito/mockito.dart'; import 'package:vm_service/vm_service.dart'; @@ -56,7 +52,7 @@ const FakeCommand kLaunchReleaseCommand = FakeCommand( '--justlaunch', // These args are the default on DebuggingOptions. '--args', - '--enable-dart-profiling --enable-service-port-fallback --disable-service-auth-codes --observatory-port=60700', + '--enable-dart-profiling --disable-service-auth-codes', ], environment: { 'PATH': '/usr/bin:null', @@ -74,7 +70,7 @@ const FakeCommand kLaunchDebugCommand = FakeCommand(command: [ '--no-wifi', '--justlaunch', '--args', - '--enable-dart-profiling --enable-service-port-fallback --disable-service-auth-codes --observatory-port=60700 --enable-checked-mode --verify-entry-points' + '--enable-dart-profiling --disable-service-auth-codes --enable-checked-mode --verify-entry-points' ], environment: { 'PATH': '/usr/bin:null', 'DYLD_LIBRARY_PATH': '/path/to/libraries', @@ -94,7 +90,7 @@ const FakeCommand kAttachDebuggerCommand = FakeCommand(command: [ '--debug', '--no-wifi', '--args', - '--enable-dart-profiling --enable-service-port-fallback --disable-service-auth-codes --observatory-port=60700 --enable-checked-mode --verify-entry-points' + '--enable-dart-profiling --disable-service-auth-codes --enable-checked-mode --verify-entry-points' ], environment: { 'PATH': '/usr/bin:null', 'DYLD_LIBRARY_PATH': '/path/to/libraries', @@ -122,8 +118,7 @@ void main() { verify(devicePortForwarder.dispose()).called(1); }); - // Still uses context for analytics. - testUsingContext('IOSDevice.startApp attaches in debug mode via log reading on iOS 13+', () async { + testWithoutContext('IOSDevice.startApp attaches in debug mode via log reading on iOS 13+', () async { final FileSystem fileSystem = MemoryFileSystem.test(); final FakeProcessManager processManager = FakeProcessManager.list([ kDeployCommand, @@ -132,12 +127,6 @@ void main() { final IOSDevice device = setUpIOSDevice( processManager: processManager, fileSystem: fileSystem, - vmServiceConnector: (String string, {Log log}) async { - throw const io.SocketException( - 'OS Error: Connection refused, errno = 61, address = localhost, port ' - '= 58943', - ); - }, ); final IOSApp iosApp = PrebuiltIOSApp( projectBundleId: 'app', @@ -159,20 +148,14 @@ void main() { prebuiltApplication: true, debuggingOptions: DebuggingOptions.enabled(BuildInfo.debug), platformArgs: {}, - fallbackPollingDelay: Duration.zero, - fallbackThrottleTimeout: const Duration(milliseconds: 10), ); expect(launchResult.started, true); expect(launchResult.hasObservatory, true); - verify(globals.flutterUsage.sendEvent('ios-handshake', 'log-success')).called(1); expect(await device.stopApp(iosApp), false); - }, overrides: { - Usage: () => MockUsage(), }); - // Still uses context for analytics. - testUsingContext('IOSDevice.startApp launches in debug mode via log reading on [ kDeployCommand, @@ -182,12 +165,6 @@ void main() { sdkVersion: '12.4.4', processManager: processManager, fileSystem: fileSystem, - vmServiceConnector: (String string, {Log log}) async { - throw const io.SocketException( - 'OS Error: Connection refused, errno = 61, address = localhost, port ' - '= 58943', - ); - }, ); final IOSApp iosApp = PrebuiltIOSApp( projectBundleId: 'app', @@ -209,74 +186,14 @@ void main() { prebuiltApplication: true, debuggingOptions: DebuggingOptions.enabled(BuildInfo.debug), platformArgs: {}, - fallbackPollingDelay: Duration.zero, - fallbackThrottleTimeout: const Duration(milliseconds: 10), ); expect(launchResult.started, true); expect(launchResult.hasObservatory, true); - verify(globals.flutterUsage.sendEvent('ios-handshake', 'log-success')).called(1); expect(await device.stopApp(iosApp), false); - }, overrides: { - Usage: () => MockUsage(), }); - // Still uses context for analytics. - testUsingContext('IOSDevice.startApp fails in debug mode when Observatory URI is malformed', () async { - final FileSystem fileSystem = MemoryFileSystem.test(); - final FakeProcessManager processManager = FakeProcessManager.list([ - kDeployCommand, - kAttachDebuggerCommand, - ]); - final IOSDevice device = setUpIOSDevice( - processManager: processManager, - fileSystem: fileSystem, - vmServiceConnector: (String string, {Log log}) async { - throw const io.SocketException( - 'OS Error: Connection refused, errno = 61, address = localhost, port ' - '= 58943', - ); - }, - ); - final IOSApp iosApp = PrebuiltIOSApp( - projectBundleId: 'app', - bundleName: 'Runner', - bundleDir: fileSystem.currentDirectory, - ); - final FakeDeviceLogReader deviceLogReader = FakeDeviceLogReader(); - - device.portForwarder = const NoOpDevicePortForwarder(); - device.setLogReader(iosApp, deviceLogReader); - - // Now that the reader is used, start writing messages to it. - Timer.run(() { - deviceLogReader.addLine('Foo'); - deviceLogReader.addLine('Observatory listening on http://127.0.0.1:456abc'); - }); - - final LaunchResult launchResult = await device.startApp(iosApp, - prebuiltApplication: true, - debuggingOptions: DebuggingOptions.enabled(BuildInfo.debug), - platformArgs: {}, - fallbackPollingDelay: Duration.zero, - // fallbackThrottleTimeout: const Duration(milliseconds: 10), - ); - - expect(launchResult.started, false); - expect(launchResult.hasObservatory, false); - verify(globals.flutterUsage.sendEvent( - 'ios-handshake', - 'failure-other', - label: anyNamed('label'), - value: anyNamed('value'), - )).called(1); - verify(globals.flutterUsage.sendEvent('ios-handshake', 'log-failure')).called(1); - }, overrides: { - Usage: () => MockUsage(), - }); - - // Still uses context for TimeoutConfiguration and usage - testUsingContext('IOSDevice.startApp succeeds in release mode', () async { + testWithoutContext('IOSDevice.startApp succeeds in release mode', () async { final FileSystem fileSystem = MemoryFileSystem.test(); final FakeProcessManager processManager = FakeProcessManager.list([ kDeployCommand, @@ -296,20 +213,15 @@ void main() { prebuiltApplication: true, debuggingOptions: DebuggingOptions.disabled(BuildInfo.release), platformArgs: {}, - fallbackPollingDelay: Duration.zero, - fallbackThrottleTimeout: const Duration(milliseconds: 10), ); expect(launchResult.started, true); expect(launchResult.hasObservatory, false); expect(await device.stopApp(iosApp), false); expect(processManager.hasRemainingExpectations, false); - }, overrides: { - Usage: () => MockUsage(), }); - // Still uses context for analytics. - testUsingContext('IOSDevice.startApp forwards all supported debugging options', () async { + testWithoutContext('IOSDevice.startApp forwards all supported debugging options', () async { final FileSystem fileSystem = MemoryFileSystem.test(); final FakeProcessManager processManager = FakeProcessManager.list([ kDeployCommand, @@ -331,9 +243,7 @@ void main() { '--args', [ '--enable-dart-profiling', - '--enable-service-port-fallback', '--disable-service-auth-codes', - '--observatory-port=60700', '--disable-observatory-publication', '--start-paused', '--dart-flags="--foo,--null_assertions"', @@ -349,9 +259,9 @@ void main() { '--purge-persistent-cache', ].join(' '), ], environment: const { - 'PATH': '/usr/bin:null', - 'DYLD_LIBRARY_PATH': '/path/to/libraries', - }, + 'PATH': '/usr/bin:null', + 'DYLD_LIBRARY_PATH': '/path/to/libraries', + }, stdout: '(lldb) run\nsuccess', ) ]); @@ -359,12 +269,6 @@ void main() { sdkVersion: '13.3', processManager: processManager, fileSystem: fileSystem, - vmServiceConnector: (String string, {Log log}) async { - throw const io.SocketException( - 'OS Error: Connection refused, errno = 61, address = localhost, port ' - '= 58943', - ); - }, ); final IOSApp iosApp = PrebuiltIOSApp( projectBundleId: 'app', @@ -401,71 +305,11 @@ void main() { nullAssertions: true, ), platformArgs: {}, - fallbackPollingDelay: Duration.zero, - fallbackThrottleTimeout: const Duration(milliseconds: 10), ); expect(launchResult.started, true); expect(await device.stopApp(iosApp), false); expect(processManager.hasRemainingExpectations, false); - }, overrides: { - Usage: () => MockUsage(), - }); - - // Still uses context for analytics. - testUsingContext( - 'IOSDevice.startApp detaches lldb when VM service connection fails', - () async { - final FileSystem fileSystem = MemoryFileSystem.test(); - - final MockIOSDeploy mockIOSDeploy = MockIOSDeploy(); - final MockIOSDeployDebugger mockIOSDeployDebugger = MockIOSDeployDebugger(); - when(mockIOSDeploy.prepareDebuggerForLaunch( - deviceId: anyNamed('deviceId'), - bundlePath: anyNamed('bundlePath'), - launchArguments: anyNamed('launchArguments'), - interfaceType: anyNamed('interfaceType'))) - .thenReturn(mockIOSDeployDebugger); - when(mockIOSDeploy.installApp( - deviceId: anyNamed('deviceId'), - bundlePath: anyNamed('bundlePath'), - launchArguments: anyNamed('launchArguments'), - interfaceType: anyNamed('interfaceType'))) - .thenAnswer((_) async => 0); - - when(mockIOSDeployDebugger.launchAndAttach()).thenAnswer((_) async => true); - - final IOSDevice device = setUpIOSDevice( - fileSystem: fileSystem, - iosDeploy: mockIOSDeploy, - vmServiceConnector: (String string, {Log log}) async { - throw const io.SocketException( - 'OS Error: Connection refused, errno = 61, address = localhost, port ' - '= 58943', - ); - }, - ); - final IOSApp iosApp = PrebuiltIOSApp( - projectBundleId: 'app', - bundleName: 'Runner', - bundleDir: fileSystem.currentDirectory, - ); - device.portForwarder = const NoOpDevicePortForwarder(); - device.setLogReader(iosApp, FakeDeviceLogReader()); - - final LaunchResult launchResult = await device.startApp( - iosApp, - prebuiltApplication: true, - debuggingOptions: DebuggingOptions.enabled(BuildInfo.debug), - platformArgs: {}, - fallbackPollingDelay: Duration.zero, - fallbackThrottleTimeout: const Duration(milliseconds: 10), - ); - - expect(launchResult.started, false); - verify(mockIOSDeployDebugger.detach()).called(1); - }, overrides: { - Usage: () => MockUsage(), }); } @@ -474,7 +318,6 @@ IOSDevice setUpIOSDevice({ FileSystem fileSystem, Logger logger, ProcessManager processManager, - VmServiceConnector vmServiceConnector, IOSDeploy iosDeploy, }) { final Artifacts artifacts = Artifacts.test(); @@ -490,7 +333,6 @@ IOSDevice setUpIOSDevice({ ], ); - vmServiceConnector ??= (String uri, {Log log}) async => MockVmService(); return IOSDevice('123', name: 'iPhone 1', sdkVersion: sdkVersion, @@ -514,13 +356,11 @@ IOSDevice setUpIOSDevice({ ), cpuArchitecture: DarwinArch.arm64, interfaceType: IOSDeviceInterface.usb, - vmServiceConnectUri: vmServiceConnector, ); } class MockDevicePortForwarder extends Mock implements DevicePortForwarder {} class MockDeviceLogReader extends Mock implements DeviceLogReader {} -class MockUsage extends Mock implements Usage {} class MockVmService extends Mock implements VmService {} class MockDartDevelopmentService extends Mock implements DartDevelopmentService {} class MockIOSDeployDebugger extends Mock implements IOSDeployDebugger {}