333 lines
13 KiB
Dart
333 lines
13 KiB
Dart
// Copyright 2017 The Chromium 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:async';
|
|
import 'package:flutter_tools/src/build_info.dart';
|
|
import 'package:flutter_tools/src/device.dart';
|
|
import 'package:flutter_tools/src/resident_runner.dart';
|
|
import 'package:mockito/mockito.dart';
|
|
|
|
import 'src/common.dart';
|
|
import 'src/context.dart';
|
|
|
|
void main() {
|
|
TestRunner createTestRunner() {
|
|
// TODO(jacobr): make these tests run with `trackWidgetCreation: true` as
|
|
// well as the default flags.
|
|
return TestRunner(
|
|
<FlutterDevice>[FlutterDevice(MockDevice(), trackWidgetCreation: false, buildMode: BuildMode.debug)],
|
|
);
|
|
}
|
|
|
|
group('keyboard input handling', () {
|
|
testUsingContext('single help character', () async {
|
|
final TestRunner testRunner = createTestRunner();
|
|
final TerminalHandler terminalHandler = TerminalHandler(testRunner);
|
|
expect(testRunner.hasHelpBeenPrinted, isFalse);
|
|
await terminalHandler.processTerminalInput('h');
|
|
expect(testRunner.hasHelpBeenPrinted, isTrue);
|
|
});
|
|
|
|
testUsingContext('help character surrounded with newlines', () async {
|
|
final TestRunner testRunner = createTestRunner();
|
|
final TerminalHandler terminalHandler = TerminalHandler(testRunner);
|
|
expect(testRunner.hasHelpBeenPrinted, isFalse);
|
|
await terminalHandler.processTerminalInput('\nh\n');
|
|
expect(testRunner.hasHelpBeenPrinted, isTrue);
|
|
});
|
|
|
|
testUsingContext('reload character with trailing newline', () async {
|
|
final TestRunner testRunner = createTestRunner();
|
|
final TerminalHandler terminalHandler = TerminalHandler(testRunner);
|
|
expect(testRunner.receivedCommand, isNull);
|
|
await terminalHandler.processTerminalInput('r\n');
|
|
expect(testRunner.receivedCommand, equals('r'));
|
|
});
|
|
|
|
testUsingContext('newlines', () async {
|
|
final TestRunner testRunner = createTestRunner();
|
|
final TerminalHandler terminalHandler = TerminalHandler(testRunner);
|
|
expect(testRunner.receivedCommand, isNull);
|
|
await terminalHandler.processTerminalInput('\n\n');
|
|
expect(testRunner.receivedCommand, equals(''));
|
|
});
|
|
});
|
|
|
|
group('keycode verification, brought to you by the letter r', () {
|
|
MockResidentRunner mockResidentRunner;
|
|
TerminalHandler terminalHandler;
|
|
|
|
setUp(() {
|
|
mockResidentRunner = MockResidentRunner();
|
|
terminalHandler = TerminalHandler(mockResidentRunner);
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(true);
|
|
when(mockResidentRunner.handleTerminalCommand(any)).thenReturn(null);
|
|
});
|
|
|
|
testUsingContext('a - debugToggleProfileWidgetBuilds with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('a');
|
|
|
|
verify(mockResidentRunner.debugToggleProfileWidgetBuilds()).called(1);
|
|
});
|
|
|
|
testUsingContext('a - debugToggleProfileWidgetBuilds without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('a');
|
|
|
|
verifyNever(mockResidentRunner.debugToggleProfileWidgetBuilds());
|
|
});
|
|
|
|
|
|
testUsingContext('a - debugToggleProfileWidgetBuilds', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('a');
|
|
|
|
verify(mockResidentRunner.debugToggleProfileWidgetBuilds()).called(1);
|
|
});
|
|
|
|
testUsingContext('d,D - detach', () async {
|
|
await terminalHandler.processTerminalInput('d');
|
|
await terminalHandler.processTerminalInput('D');
|
|
|
|
verify(mockResidentRunner.detach()).called(2);
|
|
});
|
|
|
|
testUsingContext('h,H,? - printHelp', () async {
|
|
await terminalHandler.processTerminalInput('h');
|
|
await terminalHandler.processTerminalInput('H');
|
|
await terminalHandler.processTerminalInput('?');
|
|
|
|
verify(mockResidentRunner.printHelp(details: true)).called(3);
|
|
});
|
|
|
|
testUsingContext('i, I - debugToggleWidgetInspector with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('i');
|
|
await terminalHandler.processTerminalInput('I');
|
|
|
|
verify(mockResidentRunner.debugToggleWidgetInspector()).called(2);
|
|
});
|
|
|
|
testUsingContext('i, I - debugToggleWidgetInspector without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('i');
|
|
await terminalHandler.processTerminalInput('I');
|
|
|
|
verifyNever(mockResidentRunner.debugToggleWidgetInspector());
|
|
});
|
|
|
|
testUsingContext('L - debugDumpLayerTree with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('L');
|
|
|
|
verify(mockResidentRunner.debugDumpLayerTree()).called(1);
|
|
});
|
|
|
|
testUsingContext('L - debugDumpLayerTree without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('L');
|
|
|
|
verifyNever(mockResidentRunner.debugDumpLayerTree());
|
|
});
|
|
|
|
testUsingContext('o,O - debugTogglePlatform with service protocol and debug mode', () async {
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('o');
|
|
await terminalHandler.processTerminalInput('O');
|
|
|
|
verify(mockResidentRunner.debugTogglePlatform()).called(2);
|
|
});
|
|
|
|
testUsingContext('o,O - debugTogglePlatform without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('o');
|
|
await terminalHandler.processTerminalInput('O');
|
|
|
|
verifyNever(mockResidentRunner.debugTogglePlatform());
|
|
});
|
|
|
|
testUsingContext('p - debugToggleDebugPaintSizeEnabled with service protocol and debug mode', () async {
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('p');
|
|
|
|
verify(mockResidentRunner.debugToggleDebugPaintSizeEnabled()).called(1);
|
|
});
|
|
|
|
testUsingContext('p - debugTogglePlatform without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('p');
|
|
|
|
verifyNever(mockResidentRunner.debugToggleDebugPaintSizeEnabled());
|
|
});
|
|
|
|
testUsingContext('p - debugToggleDebugPaintSizeEnabled with service protocol and debug mode', () async {
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('p');
|
|
|
|
verify(mockResidentRunner.debugToggleDebugPaintSizeEnabled()).called(1);
|
|
});
|
|
|
|
testUsingContext('p - debugTogglePlatform without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
await terminalHandler.processTerminalInput('p');
|
|
|
|
verifyNever(mockResidentRunner.debugToggleDebugPaintSizeEnabled());
|
|
});
|
|
|
|
testUsingContext('P - debugTogglePerformanceOverlayOverride with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('P');
|
|
|
|
verify(mockResidentRunner.debugTogglePerformanceOverlayOverride()).called(1);
|
|
});
|
|
|
|
testUsingContext('P - debugTogglePerformanceOverlayOverride without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('P');
|
|
|
|
verifyNever(mockResidentRunner.debugTogglePerformanceOverlayOverride());
|
|
});
|
|
|
|
testUsingContext('q,Q - exit', () async {
|
|
await terminalHandler.processTerminalInput('q');
|
|
await terminalHandler.processTerminalInput('Q');
|
|
|
|
verify(mockResidentRunner.exit()).called(2);
|
|
});
|
|
|
|
testUsingContext('s - screenshot', () async {
|
|
final MockDevice mockDevice = MockDevice();
|
|
final MockFlutterDevice mockFlutterDevice = MockFlutterDevice();
|
|
when(mockResidentRunner.isRunningDebug).thenReturn(true);
|
|
when(mockResidentRunner.flutterDevices).thenReturn(<FlutterDevice>[mockFlutterDevice]);
|
|
when(mockFlutterDevice.device).thenReturn(mockDevice);
|
|
when(mockDevice.supportsScreenshot).thenReturn(true);
|
|
|
|
await terminalHandler.processTerminalInput('s');
|
|
|
|
verify(mockResidentRunner.screenshot(mockFlutterDevice)).called(1);
|
|
});
|
|
|
|
testUsingContext('S - debugDumpSemanticsTreeInTraversalOrder with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('S');
|
|
|
|
verify(mockResidentRunner.debugDumpSemanticsTreeInTraversalOrder()).called(1);
|
|
});
|
|
|
|
testUsingContext('S - debugDumpSemanticsTreeInTraversalOrder without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('S');
|
|
|
|
verifyNever(mockResidentRunner.debugDumpSemanticsTreeInTraversalOrder());
|
|
});
|
|
|
|
testUsingContext('t,T - debugDumpRenderTree with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('t');
|
|
await terminalHandler.processTerminalInput('T');
|
|
|
|
verify(mockResidentRunner.debugDumpRenderTree()).called(2);
|
|
});
|
|
|
|
testUsingContext('t,T - debugDumpSemanticsTreeInTraversalOrder without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('t');
|
|
await terminalHandler.processTerminalInput('T');
|
|
|
|
verifyNever(mockResidentRunner.debugDumpRenderTree());
|
|
});
|
|
|
|
testUsingContext('U - debugDumpRenderTree with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('U');
|
|
|
|
verify(mockResidentRunner.debugDumpSemanticsTreeInInverseHitTestOrder()).called(1);
|
|
});
|
|
|
|
testUsingContext('U - debugDumpSemanticsTreeInTraversalOrder without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('U');
|
|
|
|
verifyNever(mockResidentRunner.debugDumpSemanticsTreeInInverseHitTestOrder());
|
|
});
|
|
|
|
testUsingContext('w,W - debugDumpApp with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('w');
|
|
await terminalHandler.processTerminalInput('W');
|
|
|
|
verify(mockResidentRunner.debugDumpApp()).called(2);
|
|
});
|
|
|
|
testUsingContext('w,W - debugDumpApp without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('w');
|
|
await terminalHandler.processTerminalInput('W');
|
|
|
|
verifyNever(mockResidentRunner.debugDumpApp());
|
|
});
|
|
|
|
testUsingContext('z,Z - debugToggleDebugCheckElevationsEnabled with service protocol', () async {
|
|
await terminalHandler.processTerminalInput('z');
|
|
await terminalHandler.processTerminalInput('Z');
|
|
|
|
verify(mockResidentRunner.debugToggleDebugCheckElevationsEnabled()).called(2);
|
|
});
|
|
|
|
testUsingContext('z,Z - debugToggleDebugCheckElevationsEnabled without service protocol', () async {
|
|
when(mockResidentRunner.supportsServiceProtocol).thenReturn(false);
|
|
await terminalHandler.processTerminalInput('z');
|
|
await terminalHandler.processTerminalInput('Z');
|
|
|
|
// This should probably be disable when the service protocol is not enabled.
|
|
verify(mockResidentRunner.debugToggleDebugCheckElevationsEnabled()).called(2);
|
|
});
|
|
});
|
|
}
|
|
|
|
class MockDevice extends Mock implements Device {
|
|
MockDevice() {
|
|
when(isSupported()).thenReturn(true);
|
|
}
|
|
}
|
|
|
|
class MockResidentRunner extends Mock implements ResidentRunner {}
|
|
|
|
class MockFlutterDevice extends Mock implements FlutterDevice {}
|
|
|
|
class TestRunner extends ResidentRunner {
|
|
TestRunner(List<FlutterDevice> devices)
|
|
: super(devices);
|
|
|
|
bool hasHelpBeenPrinted = false;
|
|
String receivedCommand;
|
|
|
|
@override
|
|
Future<void> cleanupAfterSignal() async { }
|
|
|
|
@override
|
|
Future<void> cleanupAtFinish() async { }
|
|
|
|
@override
|
|
Future<void> handleTerminalCommand(String code) async {
|
|
receivedCommand = code;
|
|
}
|
|
|
|
@override
|
|
void printHelp({ bool details }) {
|
|
hasHelpBeenPrinted = true;
|
|
}
|
|
|
|
@override
|
|
Future<int> run({
|
|
Completer<DebugConnectionInfo> connectionInfoCompleter,
|
|
Completer<void> appStartedCompleter,
|
|
String route,
|
|
bool shouldBuild = true,
|
|
}) async => null;
|
|
|
|
@override
|
|
Future<int> attach({
|
|
Completer<DebugConnectionInfo> connectionInfoCompleter,
|
|
Completer<void> appStartedCompleter,
|
|
}) async => null;
|
|
}
|