Unverified Commit c23d9cd4 authored by Zachary Anderson's avatar Zachary Anderson Committed by GitHub

[flutter_tools] Print emojis in Windows Terminal (#50446)

parent 5f465897
......@@ -36,58 +36,122 @@ class CommandHelp {
final OutputPreferences _outputPreferences;
CommandHelpOption _L;
CommandHelpOption get L => _L ??= _makeOption('L', 'Dump layer tree to the console.', 'debugDumpLayerTree');
CommandHelpOption get L => _L ??= _makeOption(
'L',
'Dump layer tree to the console.',
'debugDumpLayerTree',
);
CommandHelpOption _P;
CommandHelpOption get P => _P ??= _makeOption('P', 'Toggle performance overlay.', 'WidgetsApp.showPerformanceOverlay');
CommandHelpOption get P => _P ??= _makeOption(
'P',
'Toggle performance overlay.',
'WidgetsApp.showPerformanceOverlay',
);
CommandHelpOption _R;
CommandHelpOption get R => _R ??= _makeOption('R', 'Hot restart.');
CommandHelpOption get R => _R ??= _makeOption(
'R',
'Hot restart.',
);
CommandHelpOption _S;
CommandHelpOption get S => _S ??= _makeOption('S', 'Dump accessibility tree in traversal order.', 'debugDumpSemantics');
CommandHelpOption get S => _S ??= _makeOption(
'S',
'Dump accessibility tree in traversal order.',
'debugDumpSemantics',
);
CommandHelpOption _U;
CommandHelpOption get U => _U ??= _makeOption('U', 'Dump accessibility tree in inverse hit test order.', 'debugDumpSemantics');
CommandHelpOption get U => _U ??= _makeOption(
'U',
'Dump accessibility tree in inverse hit test order.',
'debugDumpSemantics',
);
CommandHelpOption _a;
CommandHelpOption get a => _a ??= _makeOption('a', 'Toggle timeline events for all widget build methods.', 'debugProfileWidgetBuilds');
CommandHelpOption get a => _a ??= _makeOption(
'a',
'Toggle timeline events for all widget build methods.',
'debugProfileWidgetBuilds',
);
CommandHelpOption _c;
CommandHelpOption get c => _c ??= _makeOption('c', 'Clear the screen');
CommandHelpOption get c => _c ??= _makeOption(
'c',
'Clear the screen',
);
CommandHelpOption _d;
CommandHelpOption get d => _d ??= _makeOption('d', 'Detach (terminate "flutter run" but leave application running).');
CommandHelpOption get d => _d ??= _makeOption(
'd',
'Detach (terminate "flutter run" but leave application running).',
);
CommandHelpOption _h;
CommandHelpOption get h => _h ??= _makeOption('h', 'Repeat this help message.');
CommandHelpOption get h => _h ??= _makeOption(
'h',
'Repeat this help message.',
);
CommandHelpOption _i;
CommandHelpOption get i => _i ??= _makeOption('i', 'Toggle widget inspector.', 'WidgetsApp.showWidgetInspectorOverride');
CommandHelpOption get i => _i ??= _makeOption(
'i',
'Toggle widget inspector.',
'WidgetsApp.showWidgetInspectorOverride',
);
CommandHelpOption _o;
CommandHelpOption get o => _o ??= _makeOption('o', 'Simulate different operating systems.', 'defaultTargetPlatform');
CommandHelpOption get o => _o ??= _makeOption(
'o',
'Simulate different operating systems.',
'defaultTargetPlatform',
);
CommandHelpOption _p;
CommandHelpOption get p => _p ??= _makeOption('p', 'Toggle the display of construction lines.', 'debugPaintSizeEnabled');
CommandHelpOption get p => _p ??= _makeOption(
'p',
'Toggle the display of construction lines.',
'debugPaintSizeEnabled',
);
CommandHelpOption _q;
CommandHelpOption get q => _q ??= _makeOption('q', 'Quit (terminate the application on the device).');
CommandHelpOption get q => _q ??= _makeOption(
'q',
'Quit (terminate the application on the device).',
);
CommandHelpOption _r;
CommandHelpOption get r => _r ??= _makeOption('r', 'Hot reload. $fire$fire$fire');
CommandHelpOption get r => _r ??= _makeOption(
'r',
'Hot reload. $fire$fire$fire',
);
CommandHelpOption _s;
CommandHelpOption get s => _s ??= _makeOption('s', 'Save a screenshot to flutter.png.');
CommandHelpOption get s => _s ??= _makeOption(
's',
'Save a screenshot to flutter.png.',
);
CommandHelpOption _t;
CommandHelpOption get t => _t ??= _makeOption('t', 'Dump rendering tree to the console.', 'debugDumpRenderTree');
CommandHelpOption get t => _t ??= _makeOption(
't',
'Dump rendering tree to the console.',
'debugDumpRenderTree',
);
CommandHelpOption _w;
CommandHelpOption get w => _w ??= _makeOption('w', 'Dump widget hierarchy to the console.', 'debugDumpApp');
CommandHelpOption get w => _w ??= _makeOption(
'w',
'Dump widget hierarchy to the console.',
'debugDumpApp',
);
CommandHelpOption _z;
CommandHelpOption get z => _z ??= _makeOption('z', 'Toggle elevation checker.');
CommandHelpOption get z => _z ??= _makeOption(
'z',
'Toggle elevation checker.',
);
CommandHelpOption _makeOption(String key, String description, [
String inParenthesis = '',
......@@ -142,25 +206,30 @@ class CommandHelpOption {
String toString() {
final StringBuffer message = StringBuffer();
message.writeAll(<String>[_terminal.bolden(key), description], ' ');
if (!_hasTextInParenthesis) {
return message.toString();
}
if (_hasTextInParenthesis) {
bool wrap = false;
final int maxWidth = math.max(_outputPreferences.wrapColumn ?? 0, maxLineWidth);
int width = maxWidth - (_platform.stdoutSupportsAnsi ? _rawMessageLength + 1 : message.length);
final int maxWidth = math.max(
_outputPreferences.wrapColumn ?? 0,
maxLineWidth,
);
final int adjustedMessageLength = _platform.stdoutSupportsAnsi
? _rawMessageLength + 1
: message.length;
int width = maxWidth - adjustedMessageLength;
final String parentheticalText = '($inParenthesis)';
if (width < parentheticalText.length) {
width = maxWidth;
wrap = true;
}
if (wrap) {
message.write('\n');
}
// pad according to the raw text
message.write(''.padLeft(width - parentheticalText.length));
message.write(_terminal.color(parentheticalText, TerminalColor.grey));
}
return message.toString();
}
......
......@@ -5,7 +5,6 @@
import 'dart:async';
import 'package:meta/meta.dart';
import 'package:platform/platform.dart';
import '../base/context.dart';
import '../globals.dart' as globals;
......@@ -179,15 +178,13 @@ class StdoutLogger extends Logger {
@required Stdio stdio,
@required OutputPreferences outputPreferences,
@required TimeoutConfiguration timeoutConfiguration,
@required Platform platform,
StopwatchFactory stopwatchFactory = const StopwatchFactory(),
})
: _stdio = stdio,
_terminal = terminal,
_timeoutConfiguration = timeoutConfiguration,
_outputPreferences = outputPreferences,
_stopwatchFactory = stopwatchFactory,
_platform = platform;
_stopwatchFactory = stopwatchFactory;
@override
final AnsiTerminal _terminal;
......@@ -197,7 +194,6 @@ class StdoutLogger extends Logger {
final TimeoutConfiguration _timeoutConfiguration;
final Stdio _stdio;
final StopwatchFactory _stopwatchFactory;
final Platform _platform;
Status _status;
......@@ -306,8 +302,8 @@ class StdoutLogger extends Logger {
onFinish: _clearStatus,
stdio: _stdio,
timeoutConfiguration: _timeoutConfiguration,
platform: _platform,
stopwatch: _stopwatchFactory.createStopwatch(),
terminal: _terminal,
)..start();
} else {
_status = SummaryStatus(
......@@ -352,7 +348,6 @@ class WindowsStdoutLogger extends StdoutLogger {
@required Stdio stdio,
@required OutputPreferences outputPreferences,
@required TimeoutConfiguration timeoutConfiguration,
@required Platform platform,
StopwatchFactory stopwatchFactory = const StopwatchFactory(),
}) : super(
terminal: terminal,
......@@ -360,13 +355,14 @@ class WindowsStdoutLogger extends StdoutLogger {
outputPreferences: outputPreferences,
timeoutConfiguration: timeoutConfiguration,
stopwatchFactory: stopwatchFactory,
platform: platform,
);
@override
void writeToStdOut(String message) {
// TODO(jcollins-g): wrong abstraction layer for this, move to [Stdio].
final String windowsMessage = message
final String windowsMessage = _terminal.supportsEmoji
? message
: message.replaceAll('🔥', '')
.replaceAll('✗', 'X')
.replaceAll('✓', '√');
_stdio.stdoutWrite(windowsMessage);
......@@ -681,19 +677,18 @@ abstract class Status {
@required Duration timeout,
@required TimeoutConfiguration timeoutConfiguration,
@required Stopwatch stopwatch,
@required bool supportsColor,
@required Platform platform,
@required AnsiTerminal terminal,
VoidCallback onFinish,
SlowWarningCallback slowWarningCallback,
}) {
if (supportsColor) {
if (terminal.supportsColor) {
return AnsiSpinner(
timeout: timeout,
onFinish: onFinish,
slowWarningCallback: slowWarningCallback,
timeoutConfiguration: timeoutConfiguration,
stopwatch: stopwatch,
platform: platform,
terminal: terminal,
)..start();
}
return SilentStatus(
......@@ -862,12 +857,12 @@ class AnsiSpinner extends Status {
@required Duration timeout,
@required TimeoutConfiguration timeoutConfiguration,
@required Stopwatch stopwatch,
@required Platform platform,
@required AnsiTerminal terminal,
VoidCallback onFinish,
this.slowWarningCallback,
Stdio stdio,
}) : _stdio = stdio ?? globals.stdio,
_isWindows = platform.isWindows,
_terminal = terminal,
super(
timeout: timeout,
onFinish: onFinish,
......@@ -878,7 +873,7 @@ class AnsiSpinner extends Status {
final String _backspaceChar = '\b';
final String _clearChar = ' ';
final Stdio _stdio;
final bool _isWindows;
final AnsiTerminal _terminal;
bool timedOut = false;
......@@ -886,7 +881,7 @@ class AnsiSpinner extends Status {
Timer timer;
// Windows console font has a limited set of Unicode characters.
List<String> get _animation => _isWindows
List<String> get _animation => !_terminal.supportsEmoji
? const <String>[r'-', r'\', r'|', r'/']
: const <String>['⣾', '⣽', '⣻', '⢿', '⡿', '⣟', '⣯', '⣷'];
......@@ -984,7 +979,7 @@ class AnsiStatus extends AnsiSpinner {
this.padding = kDefaultStatusPadding,
@required Duration timeout,
@required Stopwatch stopwatch,
@required Platform platform,
@required AnsiTerminal terminal,
VoidCallback onFinish,
Stdio stdio,
TimeoutConfiguration timeoutConfiguration,
......@@ -997,7 +992,7 @@ class AnsiStatus extends AnsiSpinner {
stdio: stdio,
timeoutConfiguration: timeoutConfiguration,
stopwatch: stopwatch,
platform: platform,
terminal: terminal,
);
final String message;
......
......@@ -86,7 +86,10 @@ class OutputPreferences {
}
class AnsiTerminal {
AnsiTerminal({@required io.Stdio stdio, @required Platform platform})
AnsiTerminal({
@required io.Stdio stdio,
@required Platform platform,
})
: _stdio = stdio,
_platform = platform;
......@@ -121,7 +124,16 @@ class AnsiTerminal {
bool get supportsColor => _platform.stdoutSupportsAnsi ?? false;
final RegExp _boldControls = RegExp('(${RegExp.escape(resetBold)}|${RegExp.escape(bold)})');
// Assume unicode emojis are supported when not on Windows.
// If we are on Windows, unicode emojis are supported in Windows Terminal,
// which sets the WT_SESSION environment variable. See:
// https://github.com/microsoft/terminal/blob/master/doc/user-docs/index.md#tips-and-tricks
bool get supportsEmoji => !_platform.isWindows
|| _platform.environment.containsKey('WT_SESSION');
final RegExp _boldControls = RegExp(
'(${RegExp.escape(resetBold)}|${RegExp.escape(bold)})',
);
/// Whether we are interacting with the flutter tool via the terminal.
///
......
......@@ -127,14 +127,12 @@ Future<T> runInContext<T>(
stdio: globals.stdio,
outputPreferences: outputPreferences,
timeoutConfiguration: timeoutConfiguration,
platform: globals.platform,
)
: StdoutLogger(
terminal: globals.terminal,
stdio: globals.stdio,
outputPreferences: outputPreferences,
timeoutConfiguration: timeoutConfiguration,
platform: globals.platform,
),
MacOSWorkflow: () => const MacOSWorkflow(),
MDnsObservatoryDiscovery: () => MDnsObservatoryDiscovery(),
......
......@@ -258,8 +258,7 @@ class Doctor {
slowWarningCallback: () => validator.slowWarning,
timeoutConfiguration: timeoutConfiguration,
stopwatch: Stopwatch(),
supportsColor: globals.terminal.supportsColor,
platform: globals.platform,
terminal: globals.terminal,
);
ValidationResult result;
try {
......
......@@ -314,9 +314,8 @@ class XcodeProjectInterpreter {
final Status status = Status.withSpinner(
timeout: const TimeoutConfiguration().fastOperation,
timeoutConfiguration: const TimeoutConfiguration(),
platform: _platform,
stopwatch: Stopwatch(),
supportsColor: _terminal.supportsColor,
terminal: _terminal,
);
final List<String> showBuildSettingsCommand = <String>[
_executable,
......
......@@ -112,7 +112,6 @@ void main() {
stdio: stdio,
outputPreferences: OutputPreferences.test(),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus('message');
logger.printError('error message');
......@@ -125,7 +124,33 @@ void main() {
FakeStopwatch mockStopwatch;
FakeStopwatchFactory stopwatchFactory;
int called;
const List<String> testPlatforms = <String>['linux', 'macos', 'windows', 'fuchsia'];
final List<Platform> testPlatforms = <Platform>[
FakePlatform(
operatingSystem: 'linux',
environment: <String, String>{},
executableArguments: <String>[],
),
FakePlatform(
operatingSystem: 'macos',
environment: <String, String>{},
executableArguments: <String>[],
),
FakePlatform(
operatingSystem: 'windows',
environment: <String, String>{},
executableArguments: <String>[],
),
FakePlatform(
operatingSystem: 'windows',
environment: <String, String>{'WT_SESSION': ''},
executableArguments: <String>[],
),
FakePlatform(
operatingSystem: 'fuchsia',
environment: <String, String>{},
executableArguments: <String>[],
),
];
final RegExp secondDigits = RegExp(r'[0-9,.]*[0-9]m?s');
setUp(() {
......@@ -145,11 +170,28 @@ void main() {
} while (doThis());
}
for (final String testOs in testPlatforms) {
Platform currentPlatform() => FakePlatform(operatingSystem: testOs);
for (final Platform testPlatform in testPlatforms) {
group('(${testPlatform.operatingSystem})', () {
Platform platform;
Platform ansiPlatform;
AnsiTerminal terminal;
AnsiTerminal coloredTerminal;
AnsiStatus ansiStatus;
setUp(() {
platform = FakePlatform.fromPlatform(testPlatform)..stdoutSupportsAnsi = false;
ansiPlatform = FakePlatform.fromPlatform(testPlatform)..stdoutSupportsAnsi = true;
terminal = AnsiTerminal(
stdio: mockStdio,
platform: platform,
);
coloredTerminal = AnsiTerminal(
stdio: mockStdio,
platform: ansiPlatform,
);
AnsiStatus createAnsiStatus() {
return AnsiStatus(
ansiStatus = AnsiStatus(
message: 'Hello world',
timeout: const Duration(seconds: 2),
padding: 20,
......@@ -157,10 +199,11 @@ void main() {
stdio: mockStdio,
timeoutConfiguration: const TimeoutConfiguration(),
stopwatch: stopwatchFactory.createStopwatch(),
platform: currentPlatform(),
terminal: terminal,
);
}
testWithoutContext('AnsiSpinner works for $testOs (1)', () async {
});
testWithoutContext('AnsiSpinner works (1)', () async {
bool done = false;
mockStopwatch = FakeStopwatch();
FakeAsync().run((FakeAsync time) {
......@@ -169,14 +212,14 @@ void main() {
stdio: mockStdio,
timeoutConfiguration: const TimeoutConfiguration(),
stopwatch: stopwatchFactory.createStopwatch(),
platform: currentPlatform(),
terminal: terminal,
)..start();
doWhileAsync(time, () => ansiSpinner.ticks < 10);
List<String> lines = outputStdout();
expect(lines[0], startsWith(
currentPlatform().isWindows
? ' \b\\\b|\b/\b-\b\\\b|\b/\b-'
: ' \b⣽\b⣻\b⢿\b⡿\b⣟\b⣯\b⣷\b⣾\b⣽\b⣻'
terminal.supportsEmoji
? ' \b⣽\b⣻\b⢿\b⡿\b⣟\b⣯\b⣷\b⣾\b⣽\b⣻'
: ' \b\\\b|\b/\b-\b\\\b|\b/\b-'
),
);
expect(lines[0].endsWith('\n'), isFalse);
......@@ -196,7 +239,7 @@ void main() {
expect(done, isTrue);
});
testWithoutContext('AnsiSpinner works for $testOs (2)', () async {
testWithoutContext('AnsiSpinner works (2)', () async {
bool done = false;
mockStopwatch = FakeStopwatch();
FakeAsync().run((FakeAsync time) {
......@@ -205,7 +248,7 @@ void main() {
stdio: mockStdio,
timeoutConfiguration: const TimeoutConfiguration(),
stopwatch: mockStopwatch,
platform: FakePlatform(operatingSystem: testOs),
terminal: terminal,
)..start();
mockStopwatch.elapsed = const Duration(seconds: 1);
doWhileAsync(time, () => ansiSpinner.ticks < 10); // one second
......@@ -225,19 +268,15 @@ void main() {
expect(done, isTrue);
});
testWithoutContext('Stdout startProgress on colored terminal for $testOs', () async {
testWithoutContext('Stdout startProgress on colored terminal', () async {
bool done = false;
FakeAsync().run((FakeAsync time) {
final Logger logger = StdoutLogger(
terminal: AnsiTerminal(
stdio: mockStdio,
platform: FakePlatform(operatingSystem: testOs)..stdoutSupportsAnsi = true,
),
terminal: coloredTerminal,
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: true),
timeoutConfiguration: const TimeoutConfiguration(),
stopwatchFactory: stopwatchFactory,
platform: currentPlatform(),
);
final Status status = logger.startProgress(
'Hello',
......@@ -248,32 +287,36 @@ void main() {
expect(outputStderr().length, equals(1));
expect(outputStderr().first, isEmpty);
// the 5 below is the margin that is always included between the message and the time.
expect(outputStdout().join('\n'),
matches(currentPlatform().isWindows ? r'^Hello {15} {5} {8}[\b]{8} {7}\\$' :
r'^Hello {15} {5} {8}[\b]{8} {7}⣽$'));
expect(
outputStdout().join('\n'),
matches(terminal.supportsEmoji
? r'^Hello {15} {5} {8}[\b]{8} {7}⣽$'
: r'^Hello {15} {5} {8}[\b]{8} {7}\\$'),
);
status.stop();
expect(outputStdout().join('\n'),
matches(currentPlatform().isWindows ? r'^Hello {15} {5} {8}[\b]{8} {7}\\[\b]{8} {8}[\b]{8}[\d, ]{4}[\d]\.[\d]s[\n]$' :
r'^Hello {15} {5} {8}[\b]{8} {7}⣽[\b]{8} {8}[\b]{8}[\d, ]{4}[\d]\.[\d]s[\n]$'));
expect(
outputStdout().join('\n'),
matches(
terminal.supportsEmoji
? r'^Hello {15} {5} {8}[\b]{8} {7}⣽[\b]{8} {8}[\b]{8}[\d, ]{4}[\d]\.[\d]s[\n]$'
: r'^Hello {15} {5} {8}[\b]{8} {7}\\[\b]{8} {8}[\b]{8}[\d, ]{4}[\d]\.[\d]s[\n]$',
),
);
done = true;
});
expect(done, isTrue);
});
testWithoutContext('Stdout startProgress on colored terminal pauses on $testOs', () async {
testWithoutContext('Stdout startProgress on colored terminal pauses', () async {
bool done = false;
FakeAsync().run((FakeAsync time) {
mockStopwatch.elapsed = const Duration(seconds: 5);
final Logger logger = StdoutLogger(
terminal: AnsiTerminal(
stdio: mockStdio,
platform: FakePlatform(operatingSystem: testOs)..stdoutSupportsAnsi = true,
),
terminal: coloredTerminal,
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: true),
timeoutConfiguration: const TimeoutConfiguration(),
stopwatchFactory: stopwatchFactory,
platform: currentPlatform(),
);
final Status status = logger.startProgress(
'Knock Knock, Who\'s There',
......@@ -282,8 +325,8 @@ void main() {
);
logger.printStatus('Rude Interrupting Cow');
status.stop();
final String a = currentPlatform().isWindows ? r'\' : '⣽';
final String b = currentPlatform().isWindows ? '|' : '⣻';
final String a = terminal.supportsEmoji ? '⣽' : r'\';
final String b = terminal.supportsEmoji ? '⣻' : '|';
expect(
outputStdout().join('\n'),
......@@ -307,8 +350,7 @@ void main() {
expect(done, isTrue);
});
testWithoutContext('AnsiStatus works for $testOs', () {
final AnsiStatus ansiStatus = createAnsiStatus();
testWithoutContext('AnsiStatus works', () {
bool done = false;
FakeAsync().run((FakeAsync time) {
ansiStatus.start();
......@@ -340,8 +382,7 @@ void main() {
expect(done, isTrue);
});
testWithoutContext('AnsiStatus works when canceled for $testOs', () async {
final AnsiStatus ansiStatus = createAnsiStatus();
testWithoutContext('AnsiStatus works when canceled', () async {
bool done = false;
FakeAsync().run((FakeAsync time) {
ansiStatus.start();
......@@ -349,9 +390,11 @@ void main() {
doWhileAsync(time, () => ansiStatus.ticks < 10);
List<String> lines = outputStdout();
expect(lines[0], startsWith(testOs == 'windows'
? 'Hello world \b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |'
: 'Hello world \b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻\b\b\b\b\b\b\b\b ⢿\b\b\b\b\b\b\b\b ⡿\b\b\b\b\b\b\b\b ⣟\b\b\b\b\b\b\b\b ⣯\b\b\b\b\b\b\b\b ⣷\b\b\b\b\b\b\b\b ⣾\b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻'));
expect(lines[0], startsWith(
terminal.supportsEmoji
? 'Hello world \b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻\b\b\b\b\b\b\b\b ⢿\b\b\b\b\b\b\b\b ⡿\b\b\b\b\b\b\b\b ⣟\b\b\b\b\b\b\b\b ⣯\b\b\b\b\b\b\b\b ⣷\b\b\b\b\b\b\b\b ⣾\b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻'
: 'Hello world \b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |',
));
expect(lines.length, equals(1));
expect(lines[0].endsWith('\n'), isFalse);
......@@ -360,7 +403,7 @@ void main() {
lines = outputStdout();
final List<Match> matches = secondDigits.allMatches(lines[0]).toList();
expect(matches, isEmpty);
final String leading = currentPlatform().isWindows ? '|' : '⣻';
final String leading = terminal.supportsEmoji ? '⣻' : '|';
expect(lines[0], endsWith('$leading\b\b\b\b\b\b\b\b \b\b\b\b\b\b\b\b'));
expect(called, equals(1));
......@@ -375,8 +418,7 @@ void main() {
expect(done, isTrue);
});
testWithoutContext('AnsiStatus works when stopped for $testOs', () async {
final AnsiStatus ansiStatus = createAnsiStatus();
testWithoutContext('AnsiStatus works when stopped', () async {
bool done = false;
FakeAsync().run((FakeAsync time) {
ansiStatus.start();
......@@ -385,10 +427,11 @@ void main() {
List<String> lines = outputStdout();
expect(lines, hasLength(1));
expect(lines[0],
currentPlatform().isWindows
? 'Hello world \b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |'
: 'Hello world \b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻\b\b\b\b\b\b\b\b ⢿\b\b\b\b\b\b\b\b ⡿\b\b\b\b\b\b\b\b ⣟\b\b\b\b\b\b\b\b ⣯\b\b\b\b\b\b\b\b ⣷\b\b\b\b\b\b\b\b ⣾\b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻',
expect(
lines[0],
terminal.supportsEmoji
? 'Hello world \b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻\b\b\b\b\b\b\b\b ⢿\b\b\b\b\b\b\b\b ⡿\b\b\b\b\b\b\b\b ⣟\b\b\b\b\b\b\b\b ⣯\b\b\b\b\b\b\b\b ⣷\b\b\b\b\b\b\b\b ⣾\b\b\b\b\b\b\b\b ⣽\b\b\b\b\b\b\b\b ⣻'
: 'Hello world \b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |\b\b\b\b\b\b\b\b /\b\b\b\b\b\b\b\b -\b\b\b\b\b\b\b\b \\\b\b\b\b\b\b\b\b |',
);
// Verify a stop prints the time.
......@@ -396,9 +439,9 @@ void main() {
lines = outputStdout();
expect(lines, hasLength(2));
expect(lines[0], matches(
currentPlatform().isWindows
? r'Hello world {8}[\b]{8} {7}\\[\b]{8} {7}|[\b]{8} {7}/[\b]{8} {7}-[\b]{8} {7}\\[\b]{8} {7}|[\b]{8} {7}/[\b]{8} {7}-[\b]{8} {7}\\[\b]{8} {7}|[\b]{8} {7} [\b]{8}[\d., ]{6}[\d]ms$'
: r'Hello world {8}[\b]{8} {7}⣽[\b]{8} {7}⣻[\b]{8} {7}⢿[\b]{8} {7}⡿[\b]{8} {7}⣟[\b]{8} {7}⣯[\b]{8} {7}⣷[\b]{8} {7}⣾[\b]{8} {7}⣽[\b]{8} {7}⣻[\b]{8} {7} [\b]{8}[\d., ]{5}[\d]ms$'
terminal.supportsEmoji
? r'Hello world {8}[\b]{8} {7}⣽[\b]{8} {7}⣻[\b]{8} {7}⢿[\b]{8} {7}⡿[\b]{8} {7}⣟[\b]{8} {7}⣯[\b]{8} {7}⣷[\b]{8} {7}⣾[\b]{8} {7}⣽[\b]{8} {7}⣻[\b]{8} {7} [\b]{8}[\d., ]{5}[\d]ms$'
: r'Hello world {8}[\b]{8} {7}\\[\b]{8} {7}|[\b]{8} {7}/[\b]{8} {7}-[\b]{8} {7}\\[\b]{8} {7}|[\b]{8} {7}/[\b]{8} {7}-[\b]{8} {7}\\[\b]{8} {7}|[\b]{8} {7} [\b]{8}[\d., ]{6}[\d]ms$',
));
expect(lines[1], isEmpty);
final List<Match> times = secondDigits.allMatches(lines[0]).toList();
......@@ -418,6 +461,7 @@ void main() {
});
expect(done, isTrue);
});
});
}
});
......@@ -453,7 +497,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printError('0123456789' * 15);
final List<String> lines = outputStderr();
......@@ -475,7 +518,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printError('0123456789' * 15, indent: 5);
final List<String> lines = outputStderr();
......@@ -500,7 +542,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printError('0123456789' * 15, hangingIndent: 5);
final List<String> lines = outputStderr();
......@@ -525,7 +566,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printError('0123456789' * 15, indent: 4, hangingIndent: 5);
final List<String> lines = outputStderr();
......@@ -550,7 +590,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus('0123456789' * 15);
final List<String> lines = outputStdout();
......@@ -572,7 +611,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus('0123456789' * 15, indent: 5);
final List<String> lines = outputStdout();
......@@ -597,7 +635,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus('0123456789' * 15, hangingIndent: 5);
final List<String> lines = outputStdout();
......@@ -622,7 +659,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(wrapText: true, wrapColumn: 40, showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus('0123456789' * 15, indent: 4, hangingIndent: 5);
final List<String> lines = outputStdout();
......@@ -647,7 +683,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: true),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printError('Pants on fire!');
final List<String> lines = outputStderr();
......@@ -666,7 +701,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: true),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus('All good.');
......@@ -685,7 +719,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: true),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus(
null,
......@@ -710,7 +743,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.printStatus(
null,
......@@ -736,7 +768,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
final Status status = logger.startProgress(
'Hello',
......@@ -818,7 +849,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(showColor: false),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
);
logger.startProgress('AAA', timeout: const TimeoutConfiguration().fastOperation)..stop();
logger.startProgress('BBB', timeout: const TimeoutConfiguration().fastOperation)..stop();
......@@ -843,7 +873,6 @@ void main() {
stdio: mockStdio,
outputPreferences: OutputPreferences.test(),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
),
stopwatchFactory: FakeStopwatchFactory(),
);
......
......@@ -204,9 +204,11 @@ void main() {
Logger: () => StdoutLogger(
outputPreferences: OutputPreferences.test(),
stdio: mockStdio,
terminal: AnsiTerminal(stdio: mockStdio, platform: const LocalPlatform()),
terminal: AnsiTerminal(
stdio: mockStdio,
platform: const LocalPlatform(),
),
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
),
WebSocketConnector: () => (String url, {CompressionOptions compression}) async => throw const SocketException('test'),
});
......@@ -283,10 +285,12 @@ void main() {
}, overrides: <Type, Generator>{
Logger: () => StdoutLogger(
outputPreferences: outputPreferences,
terminal: AnsiTerminal(stdio: mockStdio, platform: const LocalPlatform()),
terminal: AnsiTerminal(
stdio: mockStdio,
platform: const LocalPlatform(),
),
stdio: mockStdio,
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
),
});
......@@ -301,10 +305,12 @@ void main() {
}, overrides: <Type, Generator>{
Logger: () => StdoutLogger(
outputPreferences: outputPreferences,
terminal: AnsiTerminal(stdio: mockStdio, platform: const LocalPlatform()),
terminal: AnsiTerminal(
stdio: mockStdio,
platform: const LocalPlatform(),
),
stdio: mockStdio,
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
),
});
......@@ -320,10 +326,12 @@ void main() {
}, overrides: <Type, Generator>{
Logger: () => StdoutLogger(
outputPreferences: outputPreferences,
terminal: AnsiTerminal(stdio: mockStdio, platform: const LocalPlatform()),
terminal: AnsiTerminal(
stdio: mockStdio,
platform: const LocalPlatform(),
),
stdio: mockStdio,
timeoutConfiguration: const TimeoutConfiguration(),
platform: FakePlatform(),
),
});
......
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