PiperOrigin-RevId: 665539414pull/17878/head
parent
8bb789e462
commit
737803eec4
6 changed files with 182 additions and 9 deletions
@ -0,0 +1,52 @@ |
|||||||
|
package com.google.protobuf; |
||||||
|
|
||||||
|
/** |
||||||
|
* ProtobufToStringOutput controls the output format of {@link Message#toString()}. Specifically, for |
||||||
|
* the Runnable object passed to `callWithDebugFormat` and `callWithTextFormat`, Message.toString() |
||||||
|
* will always output the specified format unless ProtobufToStringOutput is used again to change the |
||||||
|
* output format. |
||||||
|
*/ |
||||||
|
public final class ProtobufToStringOutput { |
||||||
|
private enum OutputMode { |
||||||
|
DEBUG_FORMAT, |
||||||
|
TEXT_FORMAT |
||||||
|
} |
||||||
|
|
||||||
|
private static final ThreadLocal<OutputMode> outputMode = |
||||||
|
new ThreadLocal<OutputMode>() { |
||||||
|
@Override |
||||||
|
protected OutputMode initialValue() { |
||||||
|
return OutputMode.TEXT_FORMAT; |
||||||
|
} |
||||||
|
}; |
||||||
|
|
||||||
|
private ProtobufToStringOutput() {} |
||||||
|
|
||||||
|
@CanIgnoreReturnValue |
||||||
|
private static OutputMode setOutputMode(OutputMode newMode) { |
||||||
|
OutputMode oldMode = outputMode.get(); |
||||||
|
outputMode.set(newMode); |
||||||
|
return oldMode; |
||||||
|
} |
||||||
|
|
||||||
|
private static void callWithSpecificFormat(Runnable impl, OutputMode mode) { |
||||||
|
OutputMode oldMode = setOutputMode(mode); |
||||||
|
try { |
||||||
|
impl.run(); |
||||||
|
} finally { |
||||||
|
OutputMode unused = setOutputMode(oldMode); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
public static void callWithDebugFormat(Runnable impl) { |
||||||
|
callWithSpecificFormat(impl, OutputMode.DEBUG_FORMAT); |
||||||
|
} |
||||||
|
|
||||||
|
public static void callWithTextFormat(Runnable impl) { |
||||||
|
callWithSpecificFormat(impl, OutputMode.TEXT_FORMAT); |
||||||
|
} |
||||||
|
|
||||||
|
public static boolean shouldOutputDebugFormat() { |
||||||
|
return outputMode.get() == OutputMode.DEBUG_FORMAT; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,103 @@ |
|||||||
|
package com.google.protobuf; |
||||||
|
|
||||||
|
import static com.google.common.truth.Truth.assertThat; |
||||||
|
|
||||||
|
import protobuf_unittest.UnittestProto.RedactedFields; |
||||||
|
import protobuf_unittest.UnittestProto.TestNestedMessageRedaction; |
||||||
|
import java.util.ArrayList; |
||||||
|
import org.junit.Before; |
||||||
|
import org.junit.Test; |
||||||
|
import org.junit.runner.RunWith; |
||||||
|
import org.junit.runners.JUnit4; |
||||||
|
|
||||||
|
@RunWith(JUnit4.class) |
||||||
|
public final class ProtobufToStringOutputTest extends DebugFormatTest { |
||||||
|
RedactedFields message; |
||||||
|
|
||||||
|
@Before |
||||||
|
public void setupTest() { |
||||||
|
message = |
||||||
|
RedactedFields.newBuilder() |
||||||
|
.setOptionalUnredactedString("foo") |
||||||
|
.setOptionalRedactedString("bar") |
||||||
|
.setOptionalRedactedMessage( |
||||||
|
TestNestedMessageRedaction.newBuilder().setOptionalUnredactedNestedString("foobar")) |
||||||
|
.build(); |
||||||
|
} |
||||||
|
|
||||||
|
@Test |
||||||
|
public void toStringFormat_defaultFormat() { |
||||||
|
assertThat(message.toString()) |
||||||
|
.matches( |
||||||
|
"optional_redacted_string: \"bar\"\n" |
||||||
|
+ "optional_unredacted_string: \"foo\"\n" |
||||||
|
+ "optional_redacted_message \\{\n" |
||||||
|
+ " optional_unredacted_nested_string: \"foobar\"\n" |
||||||
|
+ "\\}\n"); |
||||||
|
} |
||||||
|
|
||||||
|
@Test |
||||||
|
public void toStringFormat_testDebugFormat() { |
||||||
|
ProtobufToStringOutput.callWithDebugFormat( |
||||||
|
() -> |
||||||
|
assertThat(message.toString()) |
||||||
|
.matches( |
||||||
|
String.format( |
||||||
|
"%soptional_redacted_string: %s\n" |
||||||
|
+ "optional_unredacted_string: \"foo\"\n" |
||||||
|
+ "optional_redacted_message \\{\n" |
||||||
|
+ " %s\n" |
||||||
|
+ "\\}\n", |
||||||
|
UNSTABLE_PREFIX_MULTILINE, REDACTED_REGEX, REDACTED_REGEX))); |
||||||
|
} |
||||||
|
|
||||||
|
@Test |
||||||
|
public void toStringFormat_testTextFormat() { |
||||||
|
ProtobufToStringOutput.callWithTextFormat( |
||||||
|
() -> { |
||||||
|
assertThat(message.toString()) |
||||||
|
.matches( |
||||||
|
"optional_redacted_string: \"bar\"\n" |
||||||
|
+ "optional_unredacted_string: \"foo\"\n" |
||||||
|
+ "optional_redacted_message \\{\n" |
||||||
|
+ " optional_unredacted_nested_string: \"foobar\"\n" |
||||||
|
+ "\\}\n"); |
||||||
|
}); |
||||||
|
} |
||||||
|
|
||||||
|
@Test |
||||||
|
public void toStringFormat_testProtoWrapperWithDebugFormat() { |
||||||
|
ProtobufToStringOutput.callWithDebugFormat( |
||||||
|
() -> { |
||||||
|
ArrayList<RedactedFields> list = new ArrayList<>(); |
||||||
|
list.add(message); |
||||||
|
assertThat(list.toString()) |
||||||
|
.matches( |
||||||
|
String.format( |
||||||
|
"\\[%soptional_redacted_string: %s\n" |
||||||
|
+ "optional_unredacted_string: \"foo\"\n" |
||||||
|
+ "optional_redacted_message \\{\n" |
||||||
|
+ " %s\n" |
||||||
|
+ "\\}\n" |
||||||
|
+ "\\]", |
||||||
|
UNSTABLE_PREFIX_MULTILINE, REDACTED_REGEX, REDACTED_REGEX)); |
||||||
|
}); |
||||||
|
} |
||||||
|
|
||||||
|
@Test |
||||||
|
public void toStringFormat_testProtoWrapperWithTextFormat() { |
||||||
|
ProtobufToStringOutput.callWithTextFormat( |
||||||
|
() -> { |
||||||
|
ArrayList<RedactedFields> list = new ArrayList<>(); |
||||||
|
list.add(message); |
||||||
|
assertThat(list.toString()) |
||||||
|
.matches( |
||||||
|
"\\[optional_redacted_string: \"bar\"\n" |
||||||
|
+ "optional_unredacted_string: \"foo\"\n" |
||||||
|
+ "optional_redacted_message \\{\n" |
||||||
|
+ " optional_unredacted_nested_string: \"foobar\"\n" |
||||||
|
+ "\\}\n" |
||||||
|
+ "\\]"); |
||||||
|
}); |
||||||
|
} |
||||||
|
} |
Loading…
Reference in new issue