Skip to content

Migrate rest of the services and dwds_vm_client.dart to null safety #1688

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
4 changes: 1 addition & 3 deletions dwds/lib/src/connections/debug_connection.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

// @dart = 2.9

import 'dart:async';

import 'package:vm_service/vm_service.dart';
Expand All @@ -22,7 +20,7 @@ class DebugConnection {
/// Null until [close] is called.
///
/// All subsequent calls to [close] will return this future.
Future<void> _closed;
Future<void>? _closed;

DebugConnection(this._appDebugServices) {
_appDebugServices.chromeProxyService.remoteDebugger.onClose.first.then((_) {
Expand Down
3 changes: 1 addition & 2 deletions dwds/lib/src/debugging/inspector.dart
Original file line number Diff line number Diff line change
Expand Up @@ -403,8 +403,7 @@ class AppInspector implements AppInspectorInterface {
}
final libraryId = _scriptIdToLibraryId[scriptId];
if (libraryId == null) {
throwInvalidParam('getObject',
'No library for script $scriptRef with libraryId: $libraryId');
throwInvalidParam('getObject', 'No library for script $scriptRef');
}
return Script(
uri: scriptRef.uri,
Expand Down
64 changes: 32 additions & 32 deletions dwds/lib/src/dwds_vm_client.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

// @dart = 2.9

import 'dart:async';
import 'dart:convert';

Expand Down Expand Up @@ -32,7 +30,7 @@ class DwdsVmClient {
/// Null until [close] is called.
///
/// All subsequent calls to [close] will return this future.
Future<void> _closed;
Future<void>? _closed;

DwdsVmClient(this.client, this._requestController, this._responseController);

Expand All @@ -57,7 +55,7 @@ class DwdsVmClient {
'$request');
return;
}
requestController.sink.add(jsonDecode(request) as Map<String, dynamic>);
requestController.sink.add(jsonDecode(request) as Map<String, Object>);
});
final chromeProxyService =
debugService.chromeProxyService as ChromeProxyService;
Expand All @@ -73,7 +71,7 @@ class DwdsVmClient {
return <String, dynamic>{
'result': <String, Object>{
'views': <Object>[
for (var isolate in isolates)
for (var isolate in isolates ?? [])
<String, Object>{
'id': isolate.id,
'isolate': isolate.toJson(),
Expand Down Expand Up @@ -119,7 +117,7 @@ class DwdsVmClient {
await client.registerService('ext.dwds.emitEvent', 'DWDS');

client.registerServiceCallback('_yieldControlToDDS', (request) async {
final ddsUri = request['uri'] as String;
final ddsUri = request['uri'] as String?;
if (ddsUri == null) {
return RPCError(
request['method'] as String,
Expand All @@ -146,30 +144,26 @@ class DwdsVmClient {

void _processSendEvent(Map<String, dynamic> event,
ChromeProxyService chromeProxyService, DwdsStats dwdsStats) {
final type = event['type'] as String;
final payload = event['payload'] as Map<String, dynamic>;
final type = event['type'] as String?;
final payload = event['payload'] as Map<String, dynamic>?;
switch (type) {
case 'DevtoolsEvent':
{
_logger.finest('Received DevTools event: $event');
final action = payload == null ? null : payload['action'] as String;
final screen = payload == null ? null : payload['screen'] as String;
if (action == 'pageReady') {
final action = payload?['action'] as String?;
final screen = payload?['screen'] as String?;
if (screen != null && action == 'pageReady') {
if (dwdsStats.isFirstDebuggerReady) {
if (dwdsStats.devToolsStart != null) {
final time = DateTime.now()
.difference(dwdsStats.devToolsStart)
.inMilliseconds;
emitEvent(DwdsEvent.devToolsLoad(time, screen));
_logger.fine('DevTools load time: $time ms');
}
if (dwdsStats.debuggerStart != null) {
final time = DateTime.now()
.difference(dwdsStats.debuggerStart)
.inMilliseconds;
emitEvent(DwdsEvent.debuggerReady(time, screen));
_logger.fine('Debugger ready time: $time ms');
}
final debuggerReadyTime = DateTime.now()
.difference(dwdsStats.devToolsStart)
.inMilliseconds;
emitEvent(DwdsEvent.devToolsLoad(debuggerReadyTime, screen));
_logger.fine('DevTools load time: $debuggerReadyTime ms');
final debuggerStartTime = DateTime.now()
.difference(dwdsStats.debuggerStart)
.inMilliseconds;
emitEvent(DwdsEvent.debuggerReady(debuggerStartTime, screen));
_logger.fine('Debugger ready time: $debuggerStartTime ms');
} else {
_logger
.finest('Debugger and DevTools startup times alredy recorded.'
Expand Down Expand Up @@ -213,14 +207,15 @@ Future<Map<String, dynamic>> _hotRestart(
.jsEvaluate('\$dartHotRestartDwds(\'$runId\');', awaitPromise: true);
_logger.info('\$dartHotRestartDwds request complete.');
} on WipError catch (exception) {
final code = exception.error['code'];
final code = exception.error?['code'];
final message = exception.error?['message'];
// This corresponds to `Execution context was destroyed` which can
// occur during a hot restart that must fall back to a full reload.
if (code != RPCError.kServerError) {
return {
'error': {
'code': exception.error['code'],
'message': exception.error['message'],
'code': code,
'message': message,
'data': exception,
}
};
Expand Down Expand Up @@ -255,9 +250,14 @@ Future<void> _disableBreakpointsAndResume(
VmService client, ChromeProxyService chromeProxyService) async {
_logger.info('Attempting to disable breakpoints and resume the isolate');
final vm = await client.getVM();
if (vm.isolates.isEmpty) throw StateError('No active isolate to resume.');
final isolateRef = vm.isolates.first;

final isolates = vm.isolates;
if (isolates == null || isolates.isEmpty) {
throw StateError('No active isolate to resume.');
}
final isolateId = isolates.first.id;
if (isolateId == null) {
throw StateError('No active isolate to resume.');
}
await chromeProxyService.disableBreakpoints();
try {
// Any checks for paused status result in race conditions or hangs
Expand All @@ -274,7 +274,7 @@ Future<void> _disableBreakpointsAndResume(
// ignore failures indicating that the app is already running:
//
// WipError -32000 Can only perform operation while paused.
await client.resume(isolateRef.id);
await client.resume(isolateId);
} on RPCError catch (e, s) {
if (!e.message.contains('Can only perform operation while paused')) {
_logger.severe('Hot restart failed to resume exiting isolate', e, s);
Expand Down
6 changes: 2 additions & 4 deletions dwds/lib/src/services/app_debug_services.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

// @dart = 2.9

import 'dart:async';

import '../dwds_vm_client.dart';
Expand All @@ -23,12 +21,12 @@ class AppDebugServices {
/// Null until [close] is called.
///
/// All subsequent calls to [close] will return this future.
Future<void> _closed;
Future<void>? _closed;

/// The instance ID for the currently connected application, if there is one.
///
/// We only allow a given app to be debugged in a single tab at a time.
String connectedInstanceId;
String? connectedInstanceId;

AppDebugServices(this.debugService, this.dwdsVmClient, this.dwdsStats);

Expand Down
2 changes: 1 addition & 1 deletion dwds/lib/src/services/chrome_proxy_service.dart
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ class ChromeProxyService implements VmServiceInterface {
LoadStrategy loadStrategy,
AppConnection appConnection,
ExecutionContext executionContext,
ExpressionCompiler expressionCompiler,
ExpressionCompiler? expressionCompiler,
SdkConfigurationProvider sdkConfigurationProvider,
) async {
final vm = VM(
Expand Down
50 changes: 24 additions & 26 deletions dwds/lib/src/services/debug_service.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

// @dart = 2.9

import 'dart:async';
import 'dart:convert';
import 'dart:io';
Expand Down Expand Up @@ -38,8 +36,8 @@ Logger _logger = Logger('DebugService');
void Function(WebSocketChannel, String) _createNewConnectionHandler(
ChromeProxyService chromeProxyService,
ServiceExtensionRegistry serviceExtensionRegistry, {
void Function(Map<String, dynamic>) onRequest,
void Function(Map<String, dynamic>) onResponse,
void Function(Map<String, dynamic>)? onRequest,
void Function(Map<String, dynamic>)? onResponse,
}) {
return (webSocket, protocol) {
final responseController = StreamController<Map<String, Object>>();
Expand All @@ -49,7 +47,7 @@ void Function(WebSocketChannel, String) _createNewConnectionHandler(
}));
final inputStream = webSocket.stream.map((value) {
if (value is List<int>) {
value = utf8.decode(value as List<int>);
value = utf8.decode(value);
} else if (value is! String) {
throw StateError(
'Got value with unexpected type ${value.runtimeType} from web '
Expand Down Expand Up @@ -78,8 +76,8 @@ Future<void> _handleSseConnections(
SseHandler handler,
ChromeProxyService chromeProxyService,
ServiceExtensionRegistry serviceExtensionRegistry, {
void Function(Map<String, dynamic>) onRequest,
void Function(Map<String, dynamic>) onResponse,
void Function(Map<String, dynamic>)? onRequest,
void Function(Map<String, dynamic>)? onResponse,
}) async {
while (await handler.connections.hasNext) {
final connection = await handler.connections.next;
Expand Down Expand Up @@ -116,7 +114,7 @@ Future<void> _handleSseConnections(
///
/// Creates a [ChromeProxyService] from an existing Chrome instance.
class DebugService {
static String _ddsUri;
static String? _ddsUri;

final VmServiceInterface chromeProxyService;
final String hostname;
Expand All @@ -126,13 +124,13 @@ class DebugService {
final HttpServer _server;
final bool _useSse;
final bool _spawnDds;
final UrlEncoder _urlEncoder;
DartDevelopmentService _dds;
final UrlEncoder? _urlEncoder;
DartDevelopmentService? _dds;

/// Null until [close] is called.
///
/// All subsequent calls to [close] will return this future.
Future<void> _closed;
Future<void>? _closed;

DebugService._(
this.chromeProxyService,
Expand All @@ -147,7 +145,7 @@ class DebugService {

Future<void> close() => _closed ??= Future.wait([
_server.close(),
if (_dds != null) _dds.shutdown(),
if (_dds != null) _dds!.shutdown(),
]);

Future<void> startDartDevelopmentService() async {
Expand All @@ -170,8 +168,9 @@ class DebugService {
}

String get uri {
if (_spawnDds && _dds != null) {
return (_useSse ? _dds.sseUri : _dds.wsUri).toString();
final dds = _dds;
if (_spawnDds && dds != null) {
return (_useSse ? dds.sseUri : dds.wsUri).toString();
}
return (_useSse
? Uri(
Expand All @@ -189,12 +188,12 @@ class DebugService {
.toString();
}

String _encodedUri;
String? _encodedUri;
Future<String> get encodedUri async {
if (_encodedUri != null) return _encodedUri;
var encodedUri = uri;
if (_urlEncoder != null) encodedUri = await _urlEncoder(encodedUri);
return _encodedUri = encodedUri;
if (_encodedUri != null) return _encodedUri!;
var encoded = uri;
if (_urlEncoder != null) encoded = await _urlEncoder!(encoded);
return _encodedUri = encoded;
}

static bool yieldControlToDDS(String uri) {
Expand All @@ -214,15 +213,14 @@ class DebugService {
AssetReader assetReader,
LoadStrategy loadStrategy,
AppConnection appConnection,
UrlEncoder urlEncoder, {
void Function(Map<String, dynamic>) onRequest,
void Function(Map<String, dynamic>) onResponse,
UrlEncoder? urlEncoder, {
void Function(Map<String, dynamic>)? onRequest,
void Function(Map<String, dynamic>)? onResponse,
bool spawnDds = true,
bool useSse,
ExpressionCompiler expressionCompiler,
SdkConfigurationProvider sdkConfigurationProvider,
bool useSse = false,
ExpressionCompiler? expressionCompiler,
required SdkConfigurationProvider sdkConfigurationProvider,
}) async {
useSse ??= false;
final chromeProxyService = await ChromeProxyService.create(
remoteDebugger,
root,
Expand Down