diff --git a/dwds/lib/src/connections/app_connection.dart b/dwds/lib/src/connections/app_connection.dart index 04669c312..1dd7ed1f1 100644 --- a/dwds/lib/src/connections/app_connection.dart +++ b/dwds/lib/src/connections/app_connection.dart @@ -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'; diff --git a/dwds/lib/src/handlers/injector.dart b/dwds/lib/src/handlers/injector.dart index 4016eaf49..9ad89cbac 100644 --- a/dwds/lib/src/handlers/injector.dart +++ b/dwds/lib/src/handlers/injector.dart @@ -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'; @@ -32,7 +30,7 @@ const _clientScript = 'dwds/src/injected/client'; /// information. class DwdsInjector { final LoadStrategy _loadStrategy; - final Future _extensionUri; + final Future? _extensionUri; final _devHandlerPaths = StreamController(); final _logger = Logger('DwdsInjector'); final bool _enableDevtoolsLaunch; @@ -41,14 +39,14 @@ class DwdsInjector { DwdsInjector( this._loadStrategy, { - Future extensionUri, - bool enableDevtoolsLaunch, - bool useSseForInjectedClient, - bool emitDebugEvents, + Future? extensionUri, + bool enableDevtoolsLaunch = false, + bool useSseForInjectedClient = true, + bool emitDebugEvents = true, }) : _extensionUri = extensionUri, _enableDevtoolsLaunch = enableDevtoolsLaunch, - _useSseForInjectedClient = useSseForInjectedClient ?? true, - _emitDebugEvents = emitDebugEvents ?? true; + _useSseForInjectedClient = useSseForInjectedClient, + _emitDebugEvents = emitDebugEvents; /// Returns the embedded dev handler paths. /// @@ -60,6 +58,9 @@ class DwdsInjector { if (request.url.path.endsWith('$_clientScript.js')) { final uri = await Isolate.resolvePackageUri( Uri.parse('package:$_clientScript.js')); + if (uri == null) { + throw StateError('Cannot resolve "package:$_clientScript.js"'); + } final result = await File(uri.toFilePath()).readAsString(); return Response.ok(result, headers: { HttpHeaders.contentTypeHeader: 'application/javascript' @@ -123,8 +124,7 @@ class DwdsInjector { return response.change(body: body, headers: newHeaders); } else { final loadResponse = await _loadStrategy.handler(request); - if (loadResponse != null && - loadResponse.statusCode != HttpStatus.notFound) { + if (loadResponse.statusCode != HttpStatus.notFound) { return loadResponse; } return innerHandler(request); @@ -140,7 +140,7 @@ String _injectClientAndHoistMain( String appId, String devHandlerPath, String entrypointPath, - String extensionUri, + String? extensionUri, LoadStrategy loadStrategy, bool enableDevtoolsLaunch, bool emitDebugEvents, @@ -194,7 +194,7 @@ String _injectedClientSnippet( String appId, String devHandlerPath, String entrypointPath, - String extensionUri, + String? extensionUri, LoadStrategy loadStrategy, bool enableDevtoolsLaunch, bool emitDebugEvents, diff --git a/dwds/lib/src/readers/frontend_server_asset_reader.dart b/dwds/lib/src/readers/frontend_server_asset_reader.dart index 31326f8ba..4fc8309ee 100644 --- a/dwds/lib/src/readers/frontend_server_asset_reader.dart +++ b/dwds/lib/src/readers/frontend_server_asset_reader.dart @@ -2,11 +2,10 @@ // 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:convert'; import 'dart:io'; +import 'package:logging/logging.dart'; import 'package:package_config/package_config.dart'; import 'package:path/path.dart' as p; @@ -15,6 +14,7 @@ import '../readers/asset_reader.dart'; /// A reader for Dart sources and related source maps provided by the Frontend /// Server. class FrontendServerAssetReader implements AssetReader { + final _logger = Logger('FrontendServerAssetReader'); final File _mapOriginal; final File _mapIncremental; final File _jsonOriginal; @@ -49,29 +49,38 @@ class FrontendServerAssetReader implements AssetReader { .absolute(p.join(_packageRoot, '.dart_tool/package_config.json')))); @override - Future dartSourceContents(String serverPath) async { - if (!serverPath.endsWith('.dart')) return null; - final packageConfig = await _packageConfig; - - Uri fileUri; - if (serverPath.startsWith('packages/')) { - final packagePath = serverPath.replaceFirst('packages/', 'package:'); - fileUri = packageConfig.resolve(Uri.parse(packagePath)); - } else { - fileUri = p.toUri(p.join(_packageRoot, serverPath)); + Future dartSourceContents(String serverPath) async { + if (serverPath.endsWith('.dart')) { + final packageConfig = await _packageConfig; + + Uri? fileUri; + if (serverPath.startsWith('packages/')) { + final packagePath = serverPath.replaceFirst('packages/', 'package:'); + fileUri = packageConfig.resolve(Uri.parse(packagePath)); + } else { + fileUri = p.toUri(p.join(_packageRoot, serverPath)); + } + if (fileUri != null) { + final source = File(fileUri.toFilePath()); + if (source.existsSync()) return source.readAsString(); + } } - - final source = File(fileUri.toFilePath()); - if (!await source.exists()) return null; - return await source.readAsString(); + _logger.severe('Cannot find source contents for $serverPath'); + return null; } @override - Future sourceMapContents(String serverPath) async { - if (!serverPath.endsWith('lib.js.map')) return null; - if (!serverPath.startsWith('/')) serverPath = '/$serverPath'; - // Strip the .map, sources are looked up by their js path. - return _mapContents[p.withoutExtension(serverPath)]; + Future sourceMapContents(String serverPath) async { + if (serverPath.endsWith('lib.js.map')) { + if (!serverPath.startsWith('/')) serverPath = '/$serverPath'; + // Strip the .map, sources are looked up by their js path. + serverPath = p.withoutExtension(serverPath); + if (_mapContents.containsKey(serverPath)) { + return _mapContents[serverPath]; + } + } + _logger.severe('Cannot find source map contents for $serverPath'); + return null; } /// Updates the internal caches by reading the Frontend Server output files. diff --git a/dwds/lib/src/readers/proxy_server_asset_reader.dart b/dwds/lib/src/readers/proxy_server_asset_reader.dart index 70352a236..960809eca 100644 --- a/dwds/lib/src/readers/proxy_server_asset_reader.dart +++ b/dwds/lib/src/readers/proxy_server_asset_reader.dart @@ -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'; @@ -20,14 +18,11 @@ import 'asset_reader.dart'; class ProxyServerAssetReader implements AssetReader { final _logger = Logger('ProxyServerAssetReader'); - Handler _handler; - http.Client _client; + late final Handler _handler; + late final http.Client _client; ProxyServerAssetReader(int assetServerPort, - {String root, String host, bool isHttps}) { - host ??= 'localhost'; - root ??= ''; - isHttps ??= false; + {String root = '', String host = 'localhost', bool isHttps = false}) { final scheme = isHttps ? 'https://' : 'http://'; final inner = HttpClient() ..maxConnectionsPerHost = 200 @@ -37,19 +32,19 @@ class ProxyServerAssetReader implements AssetReader { ? IOClient(inner..badCertificateCallback = (cert, host, port) => true) : IOClient(inner); var url = '$scheme$host:$assetServerPort/'; - if (root?.isNotEmpty ?? false) url += '$root/'; + if (root.isNotEmpty) url += '$root/'; _handler = proxyHandler(url, client: _client); } @override - Future dartSourceContents(String serverPath) => + Future dartSourceContents(String serverPath) => _readResource(serverPath); @override - Future sourceMapContents(String serverPath) => + Future sourceMapContents(String serverPath) => _readResource(serverPath); - Future _readResource(String path) async { + Future _readResource(String path) async { // Handlers expect a fully formed HTML URI. The actual hostname and port // does not matter. final response = @@ -71,7 +66,7 @@ class ProxyServerAssetReader implements AssetReader { } @override - Future metadataContents(String serverPath) => + Future metadataContents(String serverPath) => _readResource(serverPath); @override diff --git a/dwds/lib/src/servers/devtools.dart b/dwds/lib/src/servers/devtools.dart index d1c696470..e1deb70e7 100644 --- a/dwds/lib/src/servers/devtools.dart +++ b/dwds/lib/src/servers/devtools.dart @@ -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:io'; typedef DevtoolsLauncher = Future Function(String hostname); @@ -17,7 +15,7 @@ class DevTools { /// Null until [close] is called. /// /// All subsequent calls to [close] will return this future. - Future _closed; + Future? _closed; DevTools(this.hostname, this.port, this._server); diff --git a/dwds/lib/src/servers/extension_backend.dart b/dwds/lib/src/servers/extension_backend.dart index 584ab7526..cf22f8792 100644 --- a/dwds/lib/src/servers/extension_backend.dart +++ b/dwds/lib/src/servers/extension_backend.dart @@ -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:io'; @@ -20,13 +18,12 @@ import 'extension_debugger.dart'; const authenticationResponse = 'Dart Debug Authentication Success!\n\n' 'You can close this tab and launch the Dart Debug Extension again.'; -Logger _logger = Logger('ExtensionBackend'); - /// A backend for the Dart Debug Extension. /// /// Sets up an SSE handler to communicate with the extension background. /// Uses that SSE channel to create an [ExtensionDebugger]. class ExtensionBackend { + static final _logger = Logger('ExtensionBackend'); final String hostname; final int port; final HttpServer _server; @@ -34,7 +31,7 @@ class ExtensionBackend { /// Null until [close] is called. /// /// All subsequent calls to [close] will return this future. - Future _closed; + Future? _closed; ExtensionBackend._( SocketHandler socketHandler, this.hostname, this.port, this._server) @@ -47,7 +44,8 @@ class ExtensionBackend { cascade = cascade.add((request) { if (request.url.path == authenticationPath) { return Response.ok(authenticationResponse, headers: { - 'Access-Control-Allow-Origin': request.headers['origin'], + if (request.headers.containsKey('origin')) + 'Access-Control-Allow-Origin': request.headers['origin']!, 'Access-Control-Allow-Credentials': 'true' }); } diff --git a/dwds/lib/src/servers/extension_debugger.dart b/dwds/lib/src/servers/extension_debugger.dart index 42e088990..09336717c 100644 --- a/dwds/lib/src/servers/extension_debugger.dart +++ b/dwds/lib/src/servers/extension_debugger.dart @@ -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:collection'; import 'dart:convert'; @@ -32,12 +30,12 @@ class ExtensionDebugger implements RemoteDebugger { /// Null until [close] is called. /// /// All subsequent calls to [close] will return this future. - Future _closed; + Future? _closed; - String instanceId; - ExecutionContext _executionContext; + String? instanceId; + ExecutionContext? _executionContext; - ExecutionContext get executionContext => _executionContext; + ExecutionContext? get executionContext => _executionContext; final _devToolsRequestController = StreamController(); @@ -139,7 +137,7 @@ class ExtensionDebugger implements RemoteDebugger { /// over the SSE connection. @override Future sendCommand(String command, - {Map params}) { + {Map? params}) { final completer = Completer(); final id = newId(); _completers[id] = completer; @@ -174,7 +172,7 @@ class ExtensionDebugger implements RemoteDebugger { Future getScriptSource(String scriptId) async => (await sendCommand('Debugger.getScriptSource', params: {'scriptId': scriptId})) - .result['scriptSource'] as String; + .result!['scriptSource'] as String; @override Future pause() => sendCommand('Debugger.pause'); @@ -194,14 +192,14 @@ class ExtensionDebugger implements RemoteDebugger { } @override - Future stepInto({Map params}) => + Future stepInto({Map? params}) => sendCommand('Debugger.stepInto', params: params); @override Future stepOut() => sendCommand('Debugger.stepOut'); @override - Future stepOver({Map params}) => + Future stepOver({Map? params}) => sendCommand('Debugger.stepOver', params: params); @override @@ -212,7 +210,7 @@ class ExtensionDebugger implements RemoteDebugger { @override Future evaluate(String expression, - {bool returnByValue, int contextId}) async { + {bool? returnByValue, int? contextId}) async { final params = { 'expression': expression, }; @@ -223,12 +221,8 @@ class ExtensionDebugger implements RemoteDebugger { params['contextId'] = contextId; } final response = await sendCommand('Runtime.evaluate', params: params); - if (response.result.containsKey('exceptionDetails')) { - throw ChromeDebugException( - response.result['exceptionDetails'] as Map); - } else { - return RemoteObject(response.result['result'] as Map); - } + final result = _validateResult(response.result); + return RemoteObject(result['result'] as Map); } @override @@ -240,12 +234,8 @@ class ExtensionDebugger implements RemoteDebugger { }; final response = await sendCommand('Debugger.evaluateOnCallFrame', params: params); - if (response.result.containsKey('exceptionDetails')) { - throw ChromeDebugException( - response.result['exceptionDetails'] as Map); - } else { - return RemoteObject(response.result['result'] as Map); - } + final result = _validateResult(response.result); + return RemoteObject(result['result'] as Map); } @override @@ -256,14 +246,10 @@ class ExtensionDebugger implements RemoteDebugger { }; final response = await sendCommand('Debugger.getPossibleBreakpoints', params: params); - if (response.result.containsKey('exceptionDetails')) { - throw ChromeDebugException( - response.result['exceptionDetails'] as Map); - } else { - final locations = response.result['locations'] as List; - return List.from(locations - .map((map) => WipBreakLocation(map as Map))); - } + final result = _validateResult(response.result); + final locations = result['locations'] as List; + return List.from( + locations.map((map) => WipBreakLocation(map as Map))); } @override @@ -315,4 +301,15 @@ class ExtensionDebugger implements RemoteDebugger { throw ArgumentError('unknown state: $state'); } } + + Map _validateResult(Map? result) { + if (result == null) { + throw ChromeDebugException({'result': null}); + } + if (result.containsKey('exceptionDetails')) { + throw ChromeDebugException( + result['exceptionDetails'] as Map); + } + return result; + } } diff --git a/dwds/lib/src/services/expression_compiler_service.dart b/dwds/lib/src/services/expression_compiler_service.dart index 0c8a9b5e3..0733918cd 100644 --- a/dwds/lib/src/services/expression_compiler_service.dart +++ b/dwds/lib/src/services/expression_compiler_service.dart @@ -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:isolate'; @@ -15,18 +13,15 @@ import '../utilities/dart_uri.dart'; import '../utilities/sdk_configuration.dart'; import 'expression_compiler.dart'; -final _logger = Logger('ExpressionCompilerService'); - class _Compiler { - final Isolate _worker; - final StreamQueue _responseQueue; + static final _logger = Logger('ExpressionCompilerService'); + final StreamQueue _responseQueue; final ReceivePort _receivePort; final SendPort _sendPort; - Future _dependencyUpdate; + Future? _dependencyUpdate; _Compiler._( - this._worker, this._responseQueue, this._receivePort, this._sendPort, @@ -71,11 +66,11 @@ class _Compiler { ) async { sdkConfiguration.validate(); - final librariesUri = sdkConfiguration.librariesUri; - final workerUri = sdkConfiguration.compilerWorkerUri; + final librariesUri = sdkConfiguration.librariesUri!; + final workerUri = sdkConfiguration.compilerWorkerUri!; final sdkSummaryUri = soundNullSafety - ? sdkConfiguration.soundSdkSummaryUri - : sdkConfiguration.unsoundSdkSummaryUri; + ? sdkConfiguration.soundSdkSummaryUri! + : sdkConfiguration.unsoundSdkSummaryUri!; final args = [ '--experimental-expression-compiler', @@ -97,29 +92,26 @@ class _Compiler { _logger.finest('$workerUri ${args.join(' ')}'); final receivePort = ReceivePort(); - final isolate = await Isolate.spawnUri( + await Isolate.spawnUri( workerUri, args, receivePort.sendPort, // Note(annagrin): ddc snapshot is generated with no asserts, so we have // to run it unchecked in case the calling isolate is checked, as it // happens, for example, when debugging webdev in VSCode or running tests - // using 'pub run' + // using 'dart run' checked: false, ); final responseQueue = StreamQueue(receivePort); final sendPort = await responseQueue.next as SendPort; - final service = _Compiler._(isolate, responseQueue, receivePort, sendPort); + final service = _Compiler._(responseQueue, receivePort, sendPort); return service; } Future updateDependencies(Map modules) async { - if (_worker == null) { - throw StateError('Expression compilation service has stopped'); - } final updateCompleter = Completer(); _dependencyUpdate = updateCompleter.future; @@ -131,14 +123,13 @@ class _Compiler { 'inputs': [ for (var moduleName in modules.keys) { - 'path': modules[moduleName].fullDillPath, - if (modules[moduleName].summaryPath != null) - 'summaryPath': modules[moduleName].summaryPath, + 'path': modules[moduleName]!.fullDillPath, + 'summaryPath': modules[moduleName]!.summaryPath, 'moduleName': moduleName }, ] }); - final result = response == null ? false : response['succeeded'] as bool; + final result = (response['succeeded'] as bool?) ?? false; if (result) { _logger.info('Updated dependencies.'); } else { @@ -160,11 +151,13 @@ class _Compiler { String moduleName, String expression, ) async { - if (_worker == null) { - throw StateError('Expression compilation service has stopped'); + _logger.finest('Waiting for dependencies to update'); + if (_dependencyUpdate == null) { + _logger + .warning('Dependencies are not updated before compiling expressions'); + return ExpressionCompilationResult('', true); } - _logger.finest('Waiting for dependencies to update'); await _dependencyUpdate; _logger.finest('Compiling "$expression" at $libraryUri:$line'); @@ -180,20 +173,16 @@ class _Compiler { 'moduleName': moduleName, }); - var succeeded = false; - var result = ''; + final errors = response['errors'] as List?; + final e = response['exception']; + final s = response['stackTrace']; + final error = (errors != null && errors.isNotEmpty) + ? errors.first + : (e != null ? '$e:$s' : ''); + final procedure = response['compiledProcedure'] as String; + final succeeded = (response['succeeded'] as bool?) ?? false; + final result = succeeded ? procedure : error; - if (response != null) { - final errors = response['errors'] as List; - final e = response['exception']; - final s = response['stackTrace']; - final error = (errors != null && errors.isNotEmpty) - ? errors.first - : (e != null ? '$e:$s' : ''); - final procedure = response['compiledProcedure'] as String; - succeeded = response['succeeded'] as bool; - result = succeeded ? procedure : error; - } if (succeeded) { _logger.finest('Compiled "$expression" to: $result'); } else { @@ -229,6 +218,7 @@ class _Compiler { /// /// Users need to stop the service by calling [stop]. class ExpressionCompilerService implements ExpressionCompiler { + final _logger = Logger('ExpressionCompilerService'); final _compiler = Completer<_Compiler>(); final String _address; final FutureOr _port; @@ -237,13 +227,10 @@ class ExpressionCompilerService implements ExpressionCompiler { final SdkConfigurationProvider _sdkConfigurationProvider; - ExpressionCompilerService( - this._address, - this._port, - this._assetHandler, { - bool verbose = false, - SdkConfigurationProvider sdkConfigurationProvider, - }) : _verbose = verbose, + ExpressionCompilerService(this._address, this._port, this._assetHandler, + {bool verbose = false, + SdkConfigurationProvider? sdkConfigurationProvider}) + : _verbose = verbose, _sdkConfigurationProvider = sdkConfigurationProvider ?? DefaultSdkConfigurationProvider(); @@ -262,7 +249,7 @@ class ExpressionCompilerService implements ExpressionCompiler { @override Future initialize( - {String moduleFormat, bool soundNullSafety = false}) async { + {required String moduleFormat, bool soundNullSafety = false}) async { if (_compiler.isCompleted) return; final compiler = await _Compiler.start( diff --git a/dwds/lib/src/utilities/dart_uri.dart b/dwds/lib/src/utilities/dart_uri.dart index 1afefb784..4b8b4af79 100644 --- a/dwds/lib/src/utilities/dart_uri.dart +++ b/dwds/lib/src/utilities/dart_uri.dart @@ -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 'package:logging/logging.dart'; import 'package:package_config/package_config.dart'; import 'package:path/path.dart' as p; @@ -30,7 +28,7 @@ class DartUri { /// served, not to the package. /// /// The optional [root] is the directory the app is served from. - factory DartUri(String uri, [String root]) { + factory DartUri(String uri, [String? root]) { final serverPath = globalLoadStrategy.serverPathForAppUri(uri); if (serverPath != null) { return DartUri._(serverPath); @@ -60,7 +58,7 @@ class DartUri { String toString() => 'DartUri: $serverPath'; /// Construct from a package: URI - factory DartUri._fromPackageUri(String uri, {String root}) { + factory DartUri._fromPackageUri(String uri, {String? root}) { final packagePath = 'packages/${uri.substring("package:".length)}'; if (root != null) { final relativePath = p.url.join(root, packagePath); @@ -70,7 +68,7 @@ class DartUri { } /// Construct from a file: URI - factory DartUri._fromFileUri(String uri, {String root}) { + factory DartUri._fromFileUri(String uri, {String? root}) { final libraryName = _resolvedUriToUri[uri]; if (libraryName != null) return DartUri(libraryName, root); // This is not one of our recorded libraries. @@ -78,7 +76,7 @@ class DartUri { } /// Construct from a path, relative to the directory being served. - factory DartUri._fromRelativePath(String uri, {String root}) { + factory DartUri._fromRelativePath(String uri, {String? root}) { uri = uri[0] == '.' ? uri.substring(1) : uri; uri = uri[0] == '/' ? uri.substring(1) : uri; @@ -98,16 +96,7 @@ class DartUri { static final _logger = Logger('DartUri'); /// The way we resolve file: URLs into package: URLs - static PackageConfig _packageConfig; - - /// SDK installation directory. - /// - /// Directory where the SDK client code built with is installed, - /// - /// For example: `/Users/me/.dart-sdks/2.15.0` - /// - /// Used to resolve SDK urls according to vm_service protocol. - static SdkConfiguration _sdkConfiguration; + static PackageConfig? _packageConfig; /// All of the known absolute library paths, indexed by their library URL. /// @@ -138,10 +127,10 @@ class DartUri { static final Map _resolvedUriToUri = {}; /// Returns package, app, or dart uri for a resolved path. - static String toPackageUri(String uri) => _resolvedUriToUri[uri]; + static String? toPackageUri(String uri) => _resolvedUriToUri[uri]; /// Returns resolved path for a package, app, or dart uri. - static String toResolvedUri(String uri) => _uriToResolvedUri[uri]; + static String? toResolvedUri(String uri) => _uriToResolvedUri[uri]; /// The directory in which we're running. /// @@ -155,15 +144,14 @@ class DartUri { /// Record library and script uris to enable resolving library and script paths. static Future initialize(SdkConfiguration sdkConfiguration) async { - _sdkConfiguration = sdkConfiguration; final packagesUri = p.toUri(p.join(currentDirectory, '.dart_tool/package_config.json')); clear(); - // Allow for tests can supplying empty configurations. - if (_sdkConfiguration.sdkDirectory != null) { - _sdkConfiguration.validateSdkDir(); + // Allow for tests to supply empty configurations. + if (sdkConfiguration.sdkDirectory != null) { + sdkConfiguration.validateSdkDir(); } await _loadPackageConfig(packagesUri); @@ -200,7 +188,7 @@ class DartUri { return; } - String libraryPath; + String? libraryPath; switch (uri.scheme) { case 'dart': // TODO(annagrin): Support resolving `dart:` uris. @@ -214,7 +202,7 @@ class DartUri { libraryPath = p.url.join(currentDirectoryUri, uri.path.substring(1)); break; case 'package': - libraryPath = _packageConfig?.resolve(uri).toString(); + libraryPath = _packageConfig?.resolve(uri)?.toString(); break; default: throw ArgumentError.value(libraryUri, 'URI scheme not allowed'); diff --git a/dwds/test/fixtures/fakes.dart b/dwds/test/fixtures/fakes.dart index d3c57a4f5..d5daad717 100644 --- a/dwds/test/fixtures/fakes.dart +++ b/dwds/test/fixtures/fakes.dart @@ -267,7 +267,7 @@ class FakeStrategy implements LoadStrategy { shelf.Handler get handler => (request) => (request.url.path == 'someDummyPath') ? shelf.Response.ok('some dummy response') - : null; + : shelf.Response.notFound('someDummyPath'); @override String get id => 'dummy-id';