Surface Windows build errors in non-verbose mode (#63707)
This commit is contained in:
parent
89f004e0d3
commit
6f0cfc9524
@ -257,6 +257,9 @@ abstract class ProcessUtils {
|
||||
/// If [filter] is non-null, all lines that do not match it are removed. If
|
||||
/// [mapFunction] is present, all lines that match [filter] are also forwarded
|
||||
/// to [mapFunction] for further processing.
|
||||
///
|
||||
/// If [stdoutErrorMatcher] is non-null, matching lines from stdout will be
|
||||
/// treated as errors, just as if they had been logged to stderr instead.
|
||||
Future<int> stream(
|
||||
List<String> cmd, {
|
||||
String workingDirectory,
|
||||
@ -264,6 +267,7 @@ abstract class ProcessUtils {
|
||||
String prefix = '',
|
||||
bool trace = false,
|
||||
RegExp filter,
|
||||
RegExp stdoutErrorMatcher,
|
||||
StringConverter mapFunction,
|
||||
Map<String, String> environment,
|
||||
});
|
||||
@ -485,6 +489,7 @@ class _DefaultProcessUtils implements ProcessUtils {
|
||||
String prefix = '',
|
||||
bool trace = false,
|
||||
RegExp filter,
|
||||
RegExp stdoutErrorMatcher,
|
||||
StringConverter mapFunction,
|
||||
Map<String, String> environment,
|
||||
}) async {
|
||||
@ -504,7 +509,9 @@ class _DefaultProcessUtils implements ProcessUtils {
|
||||
}
|
||||
if (line != null) {
|
||||
final String message = '$prefix$line';
|
||||
if (trace) {
|
||||
if (stdoutErrorMatcher?.hasMatch(line) == true) {
|
||||
_logger.printError(message, wrap: false);
|
||||
} else if (trace) {
|
||||
_logger.printTrace(message);
|
||||
} else {
|
||||
_logger.printStatus(message, wrap: false);
|
||||
|
@ -107,6 +107,10 @@ Future<void> _runCmakeGeneration(String cmakePath, Directory buildDir, Directory
|
||||
Future<void> _runBuild(String cmakePath, Directory buildDir, String buildModeName) async {
|
||||
final Stopwatch sw = Stopwatch()..start();
|
||||
|
||||
// MSBuild sends all output to stdout, including build errors. This surfaces
|
||||
// known error patterns.
|
||||
final RegExp errorMatcher = RegExp(r':\s*(?:warning|(?:fatal )?error).*?:');
|
||||
|
||||
int result;
|
||||
try {
|
||||
result = await processUtils.stream(
|
||||
@ -126,13 +130,13 @@ Future<void> _runBuild(String cmakePath, Directory buildDir, String buildModeNam
|
||||
'VERBOSE_SCRIPT_LOGGING': 'true'
|
||||
},
|
||||
trace: true,
|
||||
stdoutErrorMatcher: errorMatcher,
|
||||
);
|
||||
} on ArgumentError {
|
||||
throwToolExit("cmake not found. Run 'flutter doctor' for more information.");
|
||||
}
|
||||
if (result != 0) {
|
||||
final String verboseInstructions = globals.logger.isVerbose ? '' : ' To view the stack trace, please run `flutter run -d windows -v`.';
|
||||
throwToolExit('Build process failed.$verboseInstructions');
|
||||
throwToolExit('Build process failed.');
|
||||
}
|
||||
globals.flutterUsage.sendTiming('build', 'windows-cmake-build', Duration(milliseconds: sw.elapsedMilliseconds));
|
||||
}
|
||||
|
@ -80,11 +80,13 @@ add_dependencies(flutter_wrapper_app flutter_assemble)
|
||||
# _phony_ is a non-existent file to force this command to run every time,
|
||||
# since currently there's no way to get a full input/output list from the
|
||||
# flutter tool.
|
||||
set(PHONY_OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/_phony_")
|
||||
set_source_files_properties("${PHONY_OUTPUT}" PROPERTIES SYMBOLIC TRUE)
|
||||
add_custom_command(
|
||||
OUTPUT ${FLUTTER_LIBRARY} ${FLUTTER_LIBRARY_HEADERS}
|
||||
${CPP_WRAPPER_SOURCES_CORE} ${CPP_WRAPPER_SOURCES_PLUGIN}
|
||||
${CPP_WRAPPER_SOURCES_APP}
|
||||
${CMAKE_CURRENT_BINARY_DIR}/_phony_
|
||||
${PHONY_OUTPUT}
|
||||
COMMAND ${CMAKE_COMMAND} -E env
|
||||
${FLUTTER_TOOL_ENVIRONMENT}
|
||||
"${FLUTTER_ROOT}/packages/flutter_tools/bin/tool_backend.bat"
|
||||
|
@ -239,6 +239,63 @@ void main() {
|
||||
FeatureFlags: () => TestFeatureFlags(isWindowsEnabled: true),
|
||||
});
|
||||
|
||||
testUsingContext('Windows build extracts errors from stdout', () async {
|
||||
final BuildWindowsCommand command = BuildWindowsCommand()
|
||||
..visualStudioOverride = mockVisualStudio;
|
||||
applyMocksToCommand(command);
|
||||
setUpMockProjectFilesForBuild();
|
||||
when(mockVisualStudio.cmakePath).thenReturn(cmakePath);
|
||||
|
||||
// This contains a mix of routine build output and various types of errors
|
||||
// (compile error, link error, warning treated as an error) from MSBuild,
|
||||
// edited down for compactness. For instance, where similar lines are
|
||||
// repeated in actual output, one or two representative lines are chosen
|
||||
// to be included here.
|
||||
const String stdout = r'''Microsoft (R) Build Engine version 16.6.0+5ff7b0c9e for .NET Framework
|
||||
Copyright (C) Microsoft Corporation. All rights reserved.
|
||||
|
||||
Checking Build System
|
||||
Generating C:/foo/windows/flutter/ephemeral/flutter_windows.dll, [etc], _phony_
|
||||
Building Custom Rule C:/foo/windows/flutter/CMakeLists.txt
|
||||
standard_codec.cc
|
||||
Generating Code...
|
||||
flutter_wrapper_plugin.vcxproj -> C:\foo\build\windows\flutter\Debug\flutter_wrapper_plugin.lib
|
||||
C:\foo\windows\runner\main.cpp(18): error C2220: the following warning is treated as an error [C:\foo\build\windows\runner\test.vcxproj]
|
||||
C:\foo\windows\runner\main.cpp(18): warning C4706: assignment within conditional expression [C:\foo\build\windows\runner\test.vcxproj]
|
||||
main.obj : error LNK2019: unresolved external symbol "void __cdecl Bar(void)" (?Bar@@YAXXZ) referenced in function wWinMain [C:\foo\build\windows\runner\test.vcxproj]
|
||||
C:\foo\build\windows\runner\Debug\test.exe : fatal error LNK1120: 1 unresolved externals [C:\foo\build\windows\runner\test.vcxproj]
|
||||
Building Custom Rule C:/foo/windows/runner/CMakeLists.txt
|
||||
flutter_window.cpp
|
||||
main.cpp
|
||||
C:\foo\windows\runner\main.cpp(17,1): error C2065: 'Baz': undeclared identifier [C:\foo\build\windows\runner\test.vcxproj]
|
||||
-- Install configuration: "Debug"
|
||||
-- Installing: C:/foo/build/windows/runner/Debug/data/icudtl.dat
|
||||
''';
|
||||
|
||||
processManager = FakeProcessManager.list(<FakeCommand>[
|
||||
cmakeGenerationCommand(),
|
||||
buildCommand('Release',
|
||||
stdout: stdout,
|
||||
),
|
||||
]);
|
||||
|
||||
await createTestCommandRunner(command).run(
|
||||
const <String>['windows', '--no-pub']
|
||||
);
|
||||
// Just the warnings and errors should be surfaced.
|
||||
expect(testLogger.errorText, r'''C:\foo\windows\runner\main.cpp(18): error C2220: the following warning is treated as an error [C:\foo\build\windows\runner\test.vcxproj]
|
||||
C:\foo\windows\runner\main.cpp(18): warning C4706: assignment within conditional expression [C:\foo\build\windows\runner\test.vcxproj]
|
||||
main.obj : error LNK2019: unresolved external symbol "void __cdecl Bar(void)" (?Bar@@YAXXZ) referenced in function wWinMain [C:\foo\build\windows\runner\test.vcxproj]
|
||||
C:\foo\build\windows\runner\Debug\test.exe : fatal error LNK1120: 1 unresolved externals [C:\foo\build\windows\runner\test.vcxproj]
|
||||
C:\foo\windows\runner\main.cpp(17,1): error C2065: 'Baz': undeclared identifier [C:\foo\build\windows\runner\test.vcxproj]
|
||||
''');
|
||||
}, overrides: <Type, Generator>{
|
||||
FileSystem: () => fileSystem,
|
||||
ProcessManager: () => processManager,
|
||||
Platform: () => windowsPlatform,
|
||||
FeatureFlags: () => TestFeatureFlags(isWindowsEnabled: true),
|
||||
});
|
||||
|
||||
testUsingContext('Windows verbose build sets VERBOSE_SCRIPT_LOGGING', () async {
|
||||
final BuildWindowsCommand command = BuildWindowsCommand()
|
||||
..visualStudioOverride = mockVisualStudio;
|
||||
|
Loading…
x
Reference in New Issue
Block a user