Unverified Commit 5318782a authored by Dan Field's avatar Dan Field Committed by GitHub

Use package:vm_service instead of json_rpc_2 (#74215)

parent 178c87cc
......@@ -30,7 +30,6 @@ dependencies:
convert: 2.1.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
crypto: 2.1.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
fake_async: 1.2.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
json_rpc_2: 2.2.2 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
matcher: 0.12.10-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
platform: 3.0.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
process: 4.0.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
......@@ -43,7 +42,6 @@ dependencies:
test_api: 0.2.19-nullsafety.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
typed_data: 1.3.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
vector_math: 2.1.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
web_socket_channel: 1.1.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
dev_dependencies:
quiver: 2.1.5
......@@ -75,7 +73,8 @@ dev_dependencies:
source_maps: 0.10.10-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
test_core: 0.3.12-nullsafety.9 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
watcher: 0.9.7+15 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
web_socket_channel: 1.1.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
webkit_inspection_protocol: 0.7.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
yaml: 2.2.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
# PUBSPEC CHECKSUM: d99e
# PUBSPEC CHECKSUM: b25e
// 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:core';
import 'package:flutter_driver/flutter_driver.dart';
import 'package:fuchsia_remote_debug_protocol/fuchsia_remote_debug_protocol.dart';
import 'package:fuchsia_remote_debug_protocol/logging.dart';
/// Runs through a simple usage of the fuchsia_remote_debug_protocol library:
/// connects to a remote machine at the address in argument 1 (interface
/// optional for argument 2) to drive an application named 'todo_list' by
/// scrolling up and down on the main scaffold.
///
/// Make sure to set up your application (you can change the name from
/// 'todo_list') follows the setup for testing with the flutter driver:
/// https://flutter.dev/testing/#adding-the-flutter_driver-dependency
///
/// Example usage:
///
/// $ dart examples/driver_todo_list_scroll.dart \
/// fe80::8eae:4cff:fef4:9247 eno1
Future<void> main(List<String> args) async {
// Log only at info level within the library. If issues arise, this can be
// changed to [LoggingLevel.all] or [LoggingLevel.fine] to see more
// information.
Logger.globalLevel = LoggingLevel.info;
if (args.isEmpty) {
print('Expects an IP address and/or network interface');
return;
}
final String address = args[0];
final String interface = args.length > 1 ? args[1] : '';
// Example ssh config path for the Fuchsia device after having made a local
// build.
const String sshConfigPath =
'../../../fuchsia/out/x64rel/ssh-keys/ssh_config';
final FuchsiaRemoteConnection connection =
await FuchsiaRemoteConnection.connect(address, interface, sshConfigPath);
const Pattern isolatePattern = 'todo_list';
print('Finding $isolatePattern');
final List<IsolateRef> refs =
await connection.getMainIsolatesByPattern(isolatePattern);
final IsolateRef ref = refs.first;
print('Driving ${ref.name}');
final FlutterDriver driver = await FlutterDriver.connect(
dartVmServiceUrl: ref.dartVm.uri.toString(),
isolateNumber: ref.number,
printCommunication: true,
logCommunicationToFile: false);
for (int i = 0; i < 5; ++i) {
// Scrolls down 300px.
await driver.scroll(find.byType('Scaffold'), 0.0, -300.0,
const Duration(milliseconds: 300));
await Future<void>.delayed(const Duration(milliseconds: 500));
// Scrolls up 300px.
await driver.scroll(find.byType('Scaffold'), 300.0, 300.0,
const Duration(milliseconds: 300));
}
await driver.close();
await connection.stop();
}
// 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:core';
import 'package:fuchsia_remote_debug_protocol/fuchsia_remote_debug_protocol.dart';
import 'package:fuchsia_remote_debug_protocol/logging.dart';
/// Runs through a simple usage of the fuchsia_remote_debug_protocol library:
/// connects to a remote machine at the address in argument 1 (interface
/// optional for argument 2) to list all active flutter views and Dart VMs
/// running on said device. This uses an SSH config file (optional, depending
/// on your setup).
///
/// Example usage:
///
/// $ dart examples/list_vms_and_flutter_views.dart \
/// fe80::8eae:4cff:fef4:9247 eno1
Future<void> main(List<String> args) async {
// Log only at info level within the library. If issues arise, this can be
// changed to [LoggingLevel.all] or [LoggingLevel.fine] to see more
// information.
Logger.globalLevel = LoggingLevel.info;
if (args.isEmpty) {
print('Expects an IP address and/or network interface');
return;
}
final String address = args[0];
final String interface = args.length > 1 ? args[1] : '';
// Example ssh config path for the Fuchsia device after having made a local
// build.
const String sshConfigPath =
'../../../fuchsia/out/x64rel/ssh-keys/ssh_config';
final FuchsiaRemoteConnection connection =
await FuchsiaRemoteConnection.connect(address, interface, sshConfigPath);
print('On $address, the following Dart VM ports are running:');
for (final int port in await connection.getDeviceServicePorts()) {
print('\t$port');
}
print('');
print('The following Flutter views are running:');
for (final FlutterView view in await connection.getFlutterViews()) {
print('\t${view.name ?? view.id}');
}
await connection.stop();
}
......@@ -5,22 +5,17 @@
import 'dart:async';
import 'dart:io';
import 'package:json_rpc_2/json_rpc_2.dart' as json_rpc;
import 'package:web_socket_channel/io.dart';
import 'package:vm_service/vm_service.dart' as vms;
import '../common/logging.dart';
const Duration _kConnectTimeout = Duration(seconds: 9);
const Duration _kReconnectAttemptInterval = Duration(seconds: 3);
const Duration _kConnectTimeout = Duration(seconds: 3);
const Duration _kRpcTimeout = Duration(seconds: 5);
final Logger _log = Logger('DartVm');
/// Signature of an asynchronous function for establishing a JSON RPC-2
/// Signature of an asynchronous function for establishing a [vms.VmService]
/// connection to a [Uri].
typedef RpcPeerConnectionFunction = Future<json_rpc.Peer> Function(
typedef RpcPeerConnectionFunction = Future<vms.VmService> Function(
Uri uri, {
Duration timeout,
});
......@@ -31,79 +26,44 @@ typedef RpcPeerConnectionFunction = Future<json_rpc.Peer> Function(
/// custom connection function is needed.
RpcPeerConnectionFunction fuchsiaVmServiceConnectionFunction = _waitAndConnect;
/// The JSON RPC 2 spec says that a notification from a client must not respond
/// to the client. It's possible the client sent a notification as a "ping", but
/// the service isn't set up yet to respond.
///
/// For example, if the client sends a notification message to the server for
/// 'streamNotify', but the server has not finished loading, it will throw an
/// exception. Since the message is a notification, the server follows the
/// specification and does not send a response back, but is left with an
/// unhandled exception. That exception is safe for us to ignore - the client
/// is signaling that it will try again later if it doesn't get what it wants
/// here by sending a notification.
// This may be ignoring too many exceptions. It would be best to rewrite
// the client code to not use notifications so that it gets error replies back
// and can decide what to do from there.
// TODO(dnfield): https://github.com/flutter/flutter/issues/31813
bool _ignoreRpcError(dynamic error) {
if (error is json_rpc.RpcException) {
final json_rpc.RpcException exception = error;
return exception.data == null || exception.data['id'] == null;
} else if (error is String && error.startsWith('JSON-RPC error -32601')) {
return true;
}
return false;
}
void _unhandledJsonRpcError(dynamic error, dynamic stack) {
if (_ignoreRpcError(error)) {
return;
}
_log.fine('Error in internalimplementation of JSON RPC.\n$error\n$stack');
}
/// Attempts to connect to a Dart VM service.
///
/// Gives up after `timeout` has elapsed.
Future<json_rpc.Peer> _waitAndConnect(
Future<vms.VmService> _waitAndConnect(
Uri uri, {
Duration timeout = _kConnectTimeout,
}) async {
final Stopwatch timer = Stopwatch()..start();
Future<json_rpc.Peer> attemptConnection(Uri uri) async {
WebSocket socket;
json_rpc.Peer peer;
int attempts = 0;
WebSocket socket;
while (true) {
try {
socket = await WebSocket.connect(uri.toString()).timeout(timeout);
peer = json_rpc.Peer(IOWebSocketChannel(socket).cast(), onUnhandledError: _unhandledJsonRpcError)..listen();
return peer;
} on HttpException catch (e) {
// This is a fine warning as this most likely means the port is stale.
_log.fine('$e: ${e.message}');
await peer?.close();
await socket?.close();
rethrow;
socket = await WebSocket.connect(uri.toString());
final StreamController<dynamic> controller = StreamController<dynamic>();
final Completer<void> streamClosedCompleter = Completer<void>();
socket.listen(
(dynamic data) => controller.add(data),
onDone: () => streamClosedCompleter.complete(),
);
final vms.VmService service = vms.VmService(
controller.stream,
socket.add,
log: null,
disposeHandler: () => socket.close(),
streamClosed: streamClosedCompleter.future
);
// This call is to ensure we are able to establish a connection instead of
// keeping on trucking and failing farther down the process.
await service.getVersion();
return service;
} catch (e) {
_log.fine('Dart VM connection failed $e: ${e.message}');
// Other unknown errors will be handled with reconnects.
await peer?.close();
await socket?.close();
if (timer.elapsed < timeout) {
_log.info('Attempting to reconnect');
await Future<void>.delayed(_kReconnectAttemptInterval);
return attemptConnection(uri);
} else {
_log.warning("Connection to Fuchsia's Dart VM timed out at "
'${uri.toString()}');
rethrow;
if (attempts > 5) {
_log.warning('It is taking an unusually long time to connect to the VM...');
}
attempts += 1;
await Future<void>.delayed(timeout);
}
}
return attemptConnection(uri);
}
/// Restores the VM service connection function to the default implementation.
......@@ -133,9 +93,9 @@ class RpcFormatError extends Error {
/// Either wraps existing RPC calls to the Dart VM service, or runs raw RPC
/// function calls via [invokeRpc].
class DartVm {
DartVm._(this._peer, this.uri);
DartVm._(this._vmService, this.uri);
final json_rpc.Peer _peer;
final vms.VmService _vmService;
/// The URL through which this DartVM instance is connected.
final Uri uri;
......@@ -150,12 +110,12 @@ class DartVm {
if (uri.scheme == 'http') {
uri = uri.replace(scheme: 'ws', path: '/ws');
}
final json_rpc.Peer peer =
await fuchsiaVmServiceConnectionFunction(uri, timeout: timeout);
if (peer == null) {
final vms.VmService service = await fuchsiaVmServiceConnectionFunction(uri, timeout: timeout);
if (service == null) {
return null;
}
return DartVm._(peer, uri);
return DartVm._(service, uri);
}
/// Returns a [List] of [IsolateRef] objects whose name matches `pattern`.
......@@ -167,39 +127,17 @@ class DartVm {
Pattern pattern, {
Duration timeout = _kRpcTimeout,
}) async {
final Map<String, dynamic> jsonVmRef =
await invokeRpc('getVM', timeout: timeout);
final vms.VM vmRef = await _vmService.getVM();
final List<IsolateRef> result = <IsolateRef>[];
for (final Map<String, dynamic> jsonIsolate in (jsonVmRef['isolates'] as List<dynamic>).cast<Map<String, dynamic>>()) {
final String name = jsonIsolate['name'] as String;
if (pattern.matchAsPrefix(name) != null) {
_log.fine('Found Isolate matching "$pattern": "$name"');
result.add(IsolateRef._fromJson(jsonIsolate, this));
for (final vms.IsolateRef isolateRef in vmRef.isolates) {
if (pattern.matchAsPrefix(isolateRef.name) != null) {
_log.fine('Found Isolate matching "$pattern": "${isolateRef.name}"');
result.add(IsolateRef._fromJson(isolateRef.json, this));
}
}
return result;
}
/// Invokes a raw JSON RPC command with the VM service.
///
/// When `timeout` is set and reached, throws a [TimeoutException].
///
/// If the function returns, it is with a parsed JSON response.
Future<Map<String, dynamic>> invokeRpc(
String function, {
Map<String, dynamic> params,
Duration timeout = _kRpcTimeout,
}) async {
final Map<String, dynamic> result = await _peer
.sendRequest(function, params ?? <String, dynamic>{})
.timeout(timeout, onTimeout: () {
throw TimeoutException(
'Peer connection timed out during RPC call',
timeout,
);
}) as Map<String, dynamic>;
return result;
}
/// Returns a list of [FlutterView] objects running across all Dart VM's.
///
......@@ -211,9 +149,8 @@ class DartVm {
Duration timeout = _kRpcTimeout,
}) async {
final List<FlutterView> views = <FlutterView>[];
final Map<String, dynamic> rpcResponse =
await invokeRpc('_flutter.listViews', timeout: timeout);
for (final Map<String, dynamic> jsonView in (rpcResponse['views'] as List<dynamic>).cast<Map<String, dynamic>>()) {
final vms.Response rpcResponse = await _vmService.callMethod('_flutter.listViews');
for (final Map<String, dynamic> jsonView in (rpcResponse.json['views'] as List<dynamic>).cast<Map<String, dynamic>>()) {
final FlutterView flutterView = FlutterView._fromJson(jsonView);
if (flutterView != null) {
views.add(flutterView);
......@@ -222,11 +159,18 @@ class DartVm {
return views;
}
/// Tests that the connection to the [vms.VmService] is valid.
Future<void> ping() async {
final vms.Version version = await _vmService.getVersion();
_log.fine('DartVM($uri) version check result: $version');
}
/// Disconnects from the Dart VM Service.
///
/// After this function completes this object is no longer usable.
Future<void> stop() async {
await _peer?.close();
_vmService.dispose();
await _vmService.onDone;
}
}
......
......@@ -473,12 +473,9 @@ class FuchsiaRemoteConnection {
/// Removes any failing ports from the cache.
Future<void> _checkPorts([ bool queueEvents = true ]) async {
// Filters out stale ports after connecting. Ignores results.
await _invokeForAllVms<Map<String, dynamic>>(
await _invokeForAllVms<void>(
(DartVm vmService) async {
final Map<String, dynamic> res =
await vmService.invokeRpc('getVersion');
_log.fine('DartVM(${vmService.uri}) version check result: $res');
return res;
await vmService.ping();
},
queueEvents,
);
......
......@@ -8,40 +8,13 @@ environment:
sdk: ">=2.2.2 <3.0.0"
dependencies:
json_rpc_2: 2.2.2
process: 4.0.0-nullsafety.4
web_socket_channel: 1.1.0
flutter_test:
sdk: flutter
flutter_driver:
sdk: flutter
vm_service: 5.5.0
archive: 2.0.13 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
args: 1.6.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
async: 2.5.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
boolean_selector: 2.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
charcode: 1.2.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
clock: 1.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
collection: 1.15.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
convert: 2.1.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
crypto: 2.1.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
fake_async: 1.2.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
file: 6.0.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
matcher: 0.12.10-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
meta: 1.3.0-nullsafety.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
path: 1.8.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
platform: 3.0.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
source_span: 1.8.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
stack_trace: 1.10.0-nullsafety.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
stream_channel: 2.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
string_scanner: 1.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
sync_http: 0.2.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
term_glyph: 1.2.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
test_api: 0.2.19-nullsafety.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
typed_data: 1.3.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
vector_math: 2.1.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
vm_service: 5.5.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
webdriver: 2.1.2 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
dev_dependencies:
mockito: 4.1.1
......@@ -49,14 +22,22 @@ dev_dependencies:
_fe_analyzer_shared: 12.0.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
analyzer: 0.40.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
args: 1.6.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
async: 2.5.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
boolean_selector: 2.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
charcode: 1.2.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
cli_util: 0.2.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
collection: 1.15.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
convert: 2.1.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
coverage: 0.14.2 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
crypto: 2.1.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
glob: 1.2.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
http_multi_server: 2.2.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
http_parser: 3.1.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
io: 0.3.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
js: 0.6.3-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
logging: 0.11.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
matcher: 0.12.10-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
mime: 0.9.7 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
node_interop: 1.2.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
node_io: 1.1.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
......@@ -71,9 +52,17 @@ dev_dependencies:
shelf_web_socket: 0.2.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
source_map_stack_trace: 2.1.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
source_maps: 0.10.10-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
source_span: 1.8.0-nullsafety.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
stack_trace: 1.10.0-nullsafety.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
stream_channel: 2.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
string_scanner: 1.1.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
term_glyph: 1.2.0-nullsafety.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
test_api: 0.2.19-nullsafety.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
test_core: 0.3.12-nullsafety.9 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
typed_data: 1.3.0-nullsafety.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
watcher: 0.9.7+15 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
web_socket_channel: 1.1.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
webkit_inspection_protocol: 0.7.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
yaml: 2.2.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade"
# PUBSPEC CHECKSUM: 5fad
# PUBSPEC CHECKSUM: 7193
......@@ -3,7 +3,7 @@
// found in the LICENSE file.
import 'package:mockito/mockito.dart';
import 'package:json_rpc_2/json_rpc_2.dart' as json_rpc;
import 'package:vm_service/vm_service.dart' as vms;
import 'package:fuchsia_remote_debug_protocol/fuchsia_remote_debug_protocol.dart';
......@@ -12,7 +12,7 @@ import 'common.dart';
void main() {
group('FuchsiaRemoteConnection.connect', () {
List<MockPortForwarder> forwardedPorts;
List<MockPeer> mockPeerConnections;
List<MockVmService> mockVmServices;
List<Uri> uriConnections;
setUp(() {
......@@ -59,22 +59,22 @@ void main() {
];
forwardedPorts = <MockPortForwarder>[];
mockPeerConnections = <MockPeer>[];
mockVmServices = <MockVmService>[];
uriConnections = <Uri>[];
Future<json_rpc.Peer> mockVmConnectionFunction(
Future<vms.VmService> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
return Future<json_rpc.Peer>(() async {
final MockPeer mp = MockPeer();
mockPeerConnections.add(mp);
return Future<vms.VmService>(() async {
final MockVmService service = MockVmService();
mockVmServices.add(service);
uriConnections.add(uri);
when(mp.sendRequest(any, any))
when(service.callMethod('_flutter.listViews'))
// The local ports match the desired indices for now, so get the
// canned response from the URI port.
.thenAnswer((_) => Future<Map<String, dynamic>>(
() => flutterViewCannedResponses[uri.port]));
return mp;
.thenAnswer((_) => Future<vms.Response>(
() => vms.Response.parse(flutterViewCannedResponses[uri.port])));
return service;
});
}
......@@ -315,4 +315,4 @@ class MockSshCommandRunner extends Mock implements SshCommandRunner {}
class MockPortForwarder extends Mock implements PortForwarder {}
class MockPeer extends Mock implements json_rpc.Peer {}
class MockVmService extends Mock implements vms.VmService {}
......@@ -3,7 +3,8 @@
// found in the LICENSE file.
import 'package:fuchsia_remote_debug_protocol/src/common/network.dart';
import 'package:flutter_test/flutter_test.dart';
import '../../common.dart';
void main() {
final List<String> ipv4Addresses = <String>['127.0.0.1', '8.8.8.8'];
......
......@@ -5,7 +5,7 @@
import 'dart:async';
import 'package:fuchsia_remote_debug_protocol/src/dart/dart_vm.dart';
import 'package:json_rpc_2/json_rpc_2.dart' as json_rpc;
import 'package:vm_service/vm_service.dart' as vms;
import 'package:mockito/mockito.dart';
import '../../common.dart';
......@@ -17,11 +17,11 @@ void main() {
});
test('null connector', () async {
Future<json_rpc.Peer> mockServiceFunction(
Future<vms.VmService> mockServiceFunction(
Uri uri, {
Duration timeout,
}) {
return Future<json_rpc.Peer>(() => null);
return Future<vms.VmService>(() => null);
}
fuchsiaVmServiceConnectionFunction = mockServiceFunction;
......@@ -30,12 +30,12 @@ void main() {
});
test('disconnect closes peer', () async {
final MockPeer peer = MockPeer();
Future<json_rpc.Peer> mockServiceFunction(
final MockVmService service = MockVmService();
Future<vms.VmService> mockServiceFunction(
Uri uri, {
Duration timeout,
}) {
return Future<json_rpc.Peer>(() => peer);
return Future<vms.VmService>(() => service);
}
fuchsiaVmServiceConnectionFunction = mockServiceFunction;
......@@ -43,15 +43,15 @@ void main() {
await DartVm.connect(Uri.parse('http://this.whatever/ws'));
expect(vm, isNot(null));
await vm.stop();
verify(peer.close());
verify(service.dispose());
});
});
group('DartVm.getAllFlutterViews', () {
MockPeer mockPeer;
MockVmService mockService;
setUp(() {
mockPeer = MockPeer();
mockService = MockVmService();
});
tearDown(() {
......@@ -90,13 +90,13 @@ void main() {
],
};
Future<json_rpc.Peer> mockVmConnectionFunction(
Future<vms.VmService> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
when(mockPeer.sendRequest(any, any)).thenAnswer((_) =>
Future<Map<String, dynamic>>(() => flutterViewCannedResponses));
return Future<json_rpc.Peer>(() => mockPeer);
when(mockService.callMethod('_flutter.listViews')).thenAnswer((_) async =>
vms.Response.parse(flutterViewCannedResponses));
return Future<vms.VmService>(() => mockService);
}
fuchsiaVmServiceConnectionFunction = mockVmConnectionFunction;
......@@ -148,13 +148,13 @@ void main() {
],
};
Future<json_rpc.Peer> mockVmConnectionFunction(
Future<vms.VmService> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
when(mockPeer.sendRequest(any, any)).thenAnswer((_) =>
Future<Map<String, dynamic>>(() => flutterViewCannedResponses));
return Future<json_rpc.Peer>(() => mockPeer);
when(mockService.callMethod('_flutter.listViews')).thenAnswer((_) async =>
vms.Response.parse(flutterViewCannedResponses));
return Future<vms.VmService>(() => mockService);
}
fuchsiaVmServiceConnectionFunction = mockVmConnectionFunction;
......@@ -198,14 +198,13 @@ void main() {
],
};
Future<json_rpc.Peer> mockVmConnectionFunction(
Future<vms.VmService> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
when(mockPeer.sendRequest(any, any)).thenAnswer((_) =>
Future<Map<String, dynamic>>(
() => flutterViewCannedResponseMissingId));
return Future<json_rpc.Peer>(() => mockPeer);
when(mockService.callMethod('_flutter.listViews')).thenAnswer((_) async =>
vms.Response.parse(flutterViewCannedResponseMissingId));
return Future<vms.VmService>(() => mockService);
}
fuchsiaVmServiceConnectionFunction = mockVmConnectionFunction;
......@@ -221,46 +220,44 @@ void main() {
});
test('get isolates by pattern', () async {
final Map<String, dynamic> vmCannedResponse = <String, dynamic>{
'isolates': <dynamic>[
<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/1',
'name': 'file://thingThatWillNotMatch:main()',
'number': '1',
},
<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/2',
'name': '0:dart_name_pattern()',
'number': '2',
},
<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/3',
'name': 'flutterBinary.cmx',
'number': '3',
},
<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/4',
'name': '0:some_other_dart_name_pattern()',
'number': '4',
},
],
};
Future<json_rpc.Peer> mockVmConnectionFunction(
final List<vms.IsolateRef> isolates = <vms.IsolateRef>[
vms.IsolateRef.parse(<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/1',
'name': 'file://thingThatWillNotMatch:main()',
'number': '1',
}),
vms.IsolateRef.parse(<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/2',
'name': '0:dart_name_pattern()',
'number': '2',
}),
vms.IsolateRef.parse(<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/3',
'name': 'flutterBinary.cmx',
'number': '3',
}),
vms.IsolateRef.parse(<String, dynamic>{
'type': '@Isolate',
'fixedId': 'true',
'id': 'isolates/4',
'name': '0:some_other_dart_name_pattern()',
'number': '4',
}),
];
Future<vms.VmService> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
when(mockPeer.sendRequest(any, any)).thenAnswer(
(_) => Future<Map<String, dynamic>>(() => vmCannedResponse));
return Future<json_rpc.Peer>(() => mockPeer);
when(mockService.getVM()).thenAnswer((_) async =>
FakeVM(isolates: isolates));
return Future<vms.VmService>(() => mockService);
}
fuchsiaVmServiceConnectionFunction = mockVmConnectionFunction;
......@@ -292,14 +289,13 @@ void main() {
],
};
Future<json_rpc.Peer> mockVmConnectionFunction(
Future<vms.VmService> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
when(mockPeer.sendRequest(any, any)).thenAnswer((_) =>
Future<Map<String, dynamic>>(
() => flutterViewCannedResponseMissingIsolateName));
return Future<json_rpc.Peer>(() => mockPeer);
when(mockService.callMethod(any)).thenAnswer((_) async =>
vms.Response.parse(flutterViewCannedResponseMissingIsolateName));
return Future<vms.VmService>(() => mockService);
}
fuchsiaVmServiceConnectionFunction = mockVmConnectionFunction;
......@@ -314,41 +310,15 @@ void main() {
expect(failingFunction, throwsA(isA<RpcFormatError>()));
});
});
}
group('DartVm.invokeRpc', () {
MockPeer mockPeer;
setUp(() {
mockPeer = MockPeer();
});
tearDown(() {
restoreVmServiceConnectionFunction();
});
test('verify timeout fires', () async {
const Duration timeoutTime = Duration(milliseconds: 100);
Future<json_rpc.Peer> mockVmConnectionFunction(
Uri uri, {
Duration timeout,
}) {
// Return a command that will never complete.
when(mockPeer.sendRequest(any, any))
.thenAnswer((_) => Completer<Map<String, dynamic>>().future);
return Future<json_rpc.Peer>(() => mockPeer);
}
class MockVmService extends Mock implements vms.VmService {}
fuchsiaVmServiceConnectionFunction = mockVmConnectionFunction;
final DartVm vm =
await DartVm.connect(Uri.parse('http://whatever.com/ws'));
expect(vm, isNot(null));
Future<void> failingFunction() async {
await vm.invokeRpc('somesillyfunction', timeout: timeoutTime);
}
expect(failingFunction, throwsA(isA<TimeoutException>()));
});
class FakeVM extends Fake implements vms.VM {
FakeVM({
this.isolates = const <vms.IsolateRef>[],
});
}
class MockPeer extends Mock implements json_rpc.Peer {}
@override
List<vms.IsolateRef> isolates;
}
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