Include exception classes in Crash-type FailureDetails.message text
Provides better at-a-glance summaries of crashes when exceptions lack
message text.
RELNOTES: None.
PiperOrigin-RevId: 318324099
diff --git a/src/main/java/com/google/devtools/build/lib/util/CrashFailureDetails.java b/src/main/java/com/google/devtools/build/lib/util/CrashFailureDetails.java
index 6629132..0b68223 100644
--- a/src/main/java/com/google/devtools/build/lib/util/CrashFailureDetails.java
+++ b/src/main/java/com/google/devtools/build/lib/util/CrashFailureDetails.java
@@ -57,17 +57,22 @@
: Crash.Code.CRASH_UNKNOWN);
addCause(crashBuilder, throwable, Sets.newIdentityHashSet());
return FailureDetail.newBuilder()
- .setMessage("Crashed: " + joinCauseMessages(crashBuilder))
+ .setMessage("Crashed: " + joinSummarizedCauses(crashBuilder))
.setCrash(crashBuilder)
.build();
}
- private static String joinCauseMessages(Crash.Builder crashBuilder) {
+ private static String joinSummarizedCauses(Crash.Builder crashBuilder) {
return crashBuilder.getCausesOrBuilderList().stream()
- .map(ThrowableOrBuilder::getMessage)
+ .map(CrashFailureDetails::summarizeCause)
.collect(Collectors.joining(", "));
}
+ private static String summarizeCause(ThrowableOrBuilder throwableOrBuilder) {
+ return String.format(
+ "(%s) %s", throwableOrBuilder.getThrowableClass(), throwableOrBuilder.getMessage());
+ }
+
private static void addCause(
Crash.Builder crashBuilder, Throwable throwable, Set<Object> addedThrowables) {
addedThrowables.add(throwable);
diff --git a/src/test/java/com/google/devtools/build/lib/bugreport/BugReportTest.java b/src/test/java/com/google/devtools/build/lib/bugreport/BugReportTest.java
index 5598b79..992075e 100644
--- a/src/test/java/com/google/devtools/build/lib/bugreport/BugReportTest.java
+++ b/src/test/java/com/google/devtools/build/lib/bugreport/BugReportTest.java
@@ -47,6 +47,8 @@
@RunWith(JUnit4.class)
public class BugReportTest {
+ private static final String TEST_EXCEPTION_NAME =
+ "com.google.devtools.build.lib.bugreport.BugReportTest$TestException";
@Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder();
@After
@@ -82,15 +84,15 @@
FailureDetail failureDetail =
FailureDetail.parseFrom(
Files.readAllBytes(failureDetailFilePath), ExtensionRegistry.getEmptyRegistry());
- assertThat(failureDetail.getMessage()).isEqualTo("Crashed: myMessage");
+ assertThat(failureDetail.getMessage())
+ .isEqualTo(String.format("Crashed: (%s) myMessage", TEST_EXCEPTION_NAME));
assertThat(failureDetail.hasCrash()).isTrue();
Crash crash = failureDetail.getCrash();
assertThat(crash.getCode()).isEqualTo(Code.CRASH_UNKNOWN);
assertThat(crash.getCausesList()).hasSize(1);
Throwable cause = crash.getCauses(0);
assertThat(cause.getMessage()).isEqualTo("myMessage");
- assertThat(cause.getThrowableClass())
- .isEqualTo("com.google.devtools.build.lib.bugreport.BugReportTest$TestException");
+ assertThat(cause.getThrowableClass()).isEqualTo(TEST_EXCEPTION_NAME);
assertThat(cause.getStackTraceCount()).isAtLeast(1);
assertThat(cause.getStackTrace(0))
.contains(
diff --git a/src/test/java/com/google/devtools/build/lib/util/CrashFailureDetailsTest.java b/src/test/java/com/google/devtools/build/lib/util/CrashFailureDetailsTest.java
index f919992..63f3fea 100644
--- a/src/test/java/com/google/devtools/build/lib/util/CrashFailureDetailsTest.java
+++ b/src/test/java/com/google/devtools/build/lib/util/CrashFailureDetailsTest.java
@@ -31,6 +31,9 @@
@RunWith(JUnit4.class)
public class CrashFailureDetailsTest {
+ private static final String TEST_EXCEPTION_NAME =
+ "com.google.devtools.build.lib.util.CrashFailureDetailsTest$TestException";
+
@Test
public void nestedThrowables() {
// This test confirms that throwables' details are recorded: their messages, types, stack
@@ -40,7 +43,11 @@
CrashFailureDetails.forThrowable(
functionForStackFrameTests_A(functionForStackFrameTests_B()));
- assertThat(failureDetail.getMessage()).isEqualTo("Crashed: myMessage_A, myMessage_B");
+ assertThat(failureDetail.getMessage())
+ .isEqualTo(
+ String.format(
+ "Crashed: (%s) myMessage_A, (%s) myMessage_B",
+ TEST_EXCEPTION_NAME, TEST_EXCEPTION_NAME));
assertThat(failureDetail.hasCrash()).isTrue();
Crash crash = failureDetail.getCrash();
assertThat(crash.getCode()).isEqualTo(Code.CRASH_UNKNOWN);
@@ -49,8 +56,7 @@
FailureDetails.Throwable outerCause = crash.getCauses(0);
assertThat(outerCause.getMessage()).isEqualTo("myMessage_A");
- assertThat(outerCause.getThrowableClass())
- .isEqualTo("com.google.devtools.build.lib.util.CrashFailureDetailsTest$TestException");
+ assertThat(outerCause.getThrowableClass()).isEqualTo(TEST_EXCEPTION_NAME);
assertThat(outerCause.getStackTraceCount()).isAtLeast(2);
assertThat(outerCause.getStackTrace(0))
.contains(
@@ -61,8 +67,7 @@
FailureDetails.Throwable innerCause = crash.getCauses(1);
assertThat(innerCause.getMessage()).isEqualTo("myMessage_B");
- assertThat(innerCause.getThrowableClass())
- .isEqualTo("com.google.devtools.build.lib.util.CrashFailureDetailsTest$TestException");
+ assertThat(innerCause.getThrowableClass()).isEqualTo(TEST_EXCEPTION_NAME);
assertThat(innerCause.getStackTraceCount()).isAtLeast(2);
assertThat(innerCause.getStackTrace(0))
.contains(