Skip to content
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

[flutter_tools] add vm service method to pull SkSL #57813

Merged
merged 3 commits into from May 27, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
11 changes: 9 additions & 2 deletions packages/flutter_tools/lib/src/resident_runner.dart
Expand Up @@ -186,6 +186,7 @@ class FlutterDevice {
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
}) {
final Completer<void> completer = Completer<void>();
StreamSubscription<void> subscription;
Expand All @@ -204,6 +205,7 @@ class FlutterDevice {
restart: restart,
compileExpression: compileExpression,
reloadMethod: reloadMethod,
getSkSLMethod: getSkSLMethod,
device: device,
);
} on Exception catch (exception) {
Expand Down Expand Up @@ -853,7 +855,9 @@ abstract class ResidentRunner {
}

/// Write the SkSL shaders to a zip file in build directory.
Future<void> writeSkSL() async {
///
/// Returns the name of the file, or `null` on failures.
Future<String> writeSkSL() async {
if (!supportsWriteSkSL) {
throw Exception('writeSkSL is not supported by this runner.');
}
Expand All @@ -870,7 +874,7 @@ abstract class ResidentRunner {
' 1. Pass "--cache-sksl" as an argument to flutter run.\n'
' 2. Interact with the application to force shaders to be compiled.\n'
);
return;
return null;
}
final File outputFile = globals.fsUtils.getUniqueFile(
globals.fs.currentDirectory,
Expand Down Expand Up @@ -899,6 +903,7 @@ abstract class ResidentRunner {
};
outputFile.writeAsStringSync(json.encode(manifest));
globals.logger.printStatus('Wrote SkSL data to ${outputFile.path}.');
return outputFile.path;
}

/// The resident runner API for interaction with the reloadMethod vmservice
Expand Down Expand Up @@ -1103,6 +1108,7 @@ abstract class ResidentRunner {
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
}) async {
if (!debuggingOptions.debuggingEnabled) {
throw 'The service protocol is not enabled.';
Expand All @@ -1115,6 +1121,7 @@ abstract class ResidentRunner {
restart: restart,
compileExpression: compileExpression,
reloadMethod: reloadMethod,
getSkSLMethod: getSkSLMethod
);
// This will wait for at least one flutter view before returning.
final Status status = globals.logger.startProgress(
Expand Down
4 changes: 3 additions & 1 deletion packages/flutter_tools/lib/src/run_cold.dart
Expand Up @@ -129,7 +129,9 @@ class ColdRunner extends ResidentRunner {
}) async {
_didAttach = true;
try {
await connectToServiceProtocol();
await connectToServiceProtocol(
getSkSLMethod: writeSkSL,
);
} on Exception catch (error) {
globals.printError('Error connecting to the service protocol: $error');
// https://github.com/flutter/flutter/issues/33050
Expand Down
1 change: 1 addition & 0 deletions packages/flutter_tools/lib/src/run_hot.dart
Expand Up @@ -225,6 +225,7 @@ class HotRunner extends ResidentRunner {
restart: _restartService,
compileExpression: _compileExpressionService,
reloadMethod: reloadMethod,
getSkSLMethod: writeSkSL,
);
// Catches all exceptions, non-Exception objects are rethrown.
} catch (error) { // ignore: avoid_catches_without_on_clauses
Expand Down
24 changes: 24 additions & 0 deletions packages/flutter_tools/lib/src/vmservice.dart
Expand Up @@ -81,6 +81,12 @@ typedef ReloadMethod = Future<void> Function({
String libraryId,
});


/// A method that pulls an SkSL shader from the device and writes it to a file.
///
/// The name of the file returned as a result.
typedef GetSkSLMethod = Future<String> Function();

Future<io.WebSocket> _defaultOpenChannel(String url, {
io.CompressionOptions compression = io.CompressionOptions.compressionDefault
}) async {
Expand Down Expand Up @@ -126,6 +132,7 @@ typedef VMServiceConnector = Future<vm_service.VmService> Function(Uri httpUri,
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
io.CompressionOptions compression,
Device device,
});
Expand All @@ -151,6 +158,7 @@ vm_service.VmService setUpVmService(
CompileExpression compileExpression,
Device device,
ReloadMethod reloadMethod,
GetSkSLMethod skSLMethod,
vm_service.VmService vmService
) {
if (reloadSources != null) {
Expand Down Expand Up @@ -257,6 +265,18 @@ vm_service.VmService setUpVmService(
});
vmService.registerService('flutterMemoryInfo', 'Flutter Tools');
}
if (skSLMethod != null) {
vmService.registerServiceCallback('flutterGetSkSL', (Map<String, dynamic> params) async {
final String filename = await skSLMethod();
return <String, dynamic>{
'result': <String, Object>{
'type': 'Success',
'filename': filename,
}
};
});
vmService.registerService('flutterGetSkSL', 'Flutter Tools');
}
return vmService;
}

Expand All @@ -274,6 +294,7 @@ Future<vm_service.VmService> connectToVmService(
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
io.CompressionOptions compression = io.CompressionOptions.compressionDefault,
Device device,
}) async {
Expand All @@ -285,6 +306,7 @@ Future<vm_service.VmService> connectToVmService(
compression: compression,
device: device,
reloadMethod: reloadMethod,
getSkSLMethod: getSkSLMethod,
);
}

Expand All @@ -294,6 +316,7 @@ Future<vm_service.VmService> _connect(
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
io.CompressionOptions compression = io.CompressionOptions.compressionDefault,
Device device,
}) async {
Expand All @@ -320,6 +343,7 @@ Future<vm_service.VmService> _connect(
compileExpression,
device,
reloadMethod,
getSkSLMethod,
delegateService,
);
_httpAddressExpando[service] = httpUri;
Expand Down
Expand Up @@ -678,6 +678,7 @@ VMServiceConnector getFakeVmServiceFactory({
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
CompressionOptions compression,
Device device,
}) async {
Expand Down
1 change: 1 addition & 0 deletions packages/flutter_tools/test/general.shard/cold_test.dart
Expand Up @@ -184,6 +184,7 @@ class TestFlutterDevice extends FlutterDevice {
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
}) async {
throw exception;
}
Expand Down
1 change: 1 addition & 0 deletions packages/flutter_tools/test/general.shard/hot_test.dart
Expand Up @@ -541,6 +541,7 @@ class TestFlutterDevice extends FlutterDevice {
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
}) async {
throw exception;
}
Expand Down
Expand Up @@ -144,6 +144,7 @@ void main() {
reloadSources: anyNamed('reloadSources'),
restart: anyNamed('restart'),
compileExpression: anyNamed('compileExpression'),
getSkSLMethod: anyNamed('getSkSLMethod'),
)).thenAnswer((Invocation invocation) async { });
when(mockFlutterDevice.setupDevFS(any, any, packagesFilePath: anyNamed('packagesFilePath')))
.thenAnswer((Invocation invocation) async {
Expand Down Expand Up @@ -1191,6 +1192,7 @@ void main() {
Restart restart,
CompileExpression compileExpression,
ReloadMethod reloadMethod,
GetSkSLMethod getSkSLMethod,
io.CompressionOptions compression,
Device device,
}) async => mockVMService,
Expand Down
21 changes: 21 additions & 0 deletions packages/flutter_tools/test/general.shard/vmservice_test.dart
Expand Up @@ -101,6 +101,7 @@ void main() {
null,
null,
null,
null,
mockVMService,
);

Expand All @@ -119,6 +120,7 @@ void main() {
null,
null,
reloadMethod,
null,
mockVMService,
);

Expand All @@ -137,6 +139,7 @@ void main() {
null,
mockDevice,
null,
null,
mockVMService,
);

Expand All @@ -145,6 +148,23 @@ void main() {
Logger: () => BufferLogger.test()
});

testUsingContext('VmService registers flutterGetSkSL service', () async {
final MockVMService mockVMService = MockVMService();
setUpVmService(
null,
null,
null,
null,
null,
() async => 'hello',
mockVMService,
);

verify(mockVMService.registerService('flutterGetSkSL', 'Flutter Tools')).called(1);
}, overrides: <Type, Generator>{
Logger: () => BufferLogger.test()
});

testUsingContext('VMService returns correct FlutterVersion', () async {
final MockVMService mockVMService = MockVMService();
setUpVmService(
Expand All @@ -153,6 +173,7 @@ void main() {
null,
null,
null,
null,
mockVMService,
);

Expand Down
Expand Up @@ -82,6 +82,12 @@ void main() {
expect(response, throwsA(const TypeMatcher<RPCError>()));
});

test('flutterGetSkSL can be called', () async {
final Response response = await vmService.callMethod('s0.flutterGetSkSL');

expect(response.type, 'Success');
});

// TODO(devoncarew): These tests fail on cirrus-ci windows.
}, skip: Platform.isWindows);
}