-
Notifications
You must be signed in to change notification settings - Fork 12.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Implement DebugStruct::non_exhaustive
.
#66716
Conversation
r? @kennytm (rust_highfive has picked a reviewer for you, use r? to override) |
r? @scottmcm since they saw the internals post. |
src/libcore/fmt/builders.rs
Outdated
/// # #![feature(debug_non_exhaustive)] | ||
/// use std::fmt; | ||
/// | ||
/// struct Foo; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd add a field foo
to this structure, just for clarity's sake.
Probably Box<dyn (pick your favorite object safe trait that isn't `Debug`)>
.
Would it be simpler to print e.g. smth like pub fn non_exhaustive(&mut self) -> &mut DebugStruct<'a, 'b> {
self.result = self.result.and_then(|_| {
if self.is_pretty() {
if !self.has_fields {
self.fmt.write_str(" {\n")?;
}
let mut slot = None;
let mut state = Default::default();
let mut writer = PadAdapter::wrap(&mut self.fmt, &mut slot, &mut state);
writer.write_str("..\n")
} else {
let prefix = if self.has_fields { ", " } else { " { " };
self.fmt.write_str(prefix)?;
self.fmt.write_str("..")
}
});
self.has_fields = true;
self
}
pub fn finish_non_exhaustive(&mut self) -> fmt::Result {
self.non_exhaustive().finish()
} |
That is certainly another possibility, I'd be interested to hear other people's opinions. |
src/libcore/fmt/builders.rs
Outdated
@@ -190,7 +195,7 @@ impl<'a, 'b: 'a> DebugStruct<'a, 'b> { | |||
/// } | |||
/// | |||
/// assert_eq!( | |||
/// format!("{:?}", Foo), | |||
/// format!("{:?}", Foo { foo: Box::new([1, 2].into_iter().copied()) }), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🚩🚩🚩🚩🚩🚩
You do not want to use .into_iter().copied()
here. This takes an autoref to &[_]
and will break when we eventually add impl IntoIterator for [_]
. Use .iter()
instead.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
okies thanks!
Ping from triage: @scottmcm - all checks pass, can you please review this PR? |
Pinging again from triage: |
r? @dtolnay |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks! I would be on board with supporting ..
in DebugStruct.
-
I think opaque_field should be removed from this PR. It is easy enough to get the same behavior with
field("field", &format_args!("_"))
. But the representationStruct { field: _ }
is not one that I find intuitive or would want to encourage. Almost anything would be better, for examplefield("field", &format_args!("<some Iterator>"))
. I would prefer to leave this up to the caller rather than dictating a default representation for opaque fields. This way the caller can write an impl that is as useful as possible within their constraints. -
The bool argument of non_exhaustive doesn't seem useful. The caller would pretty much always need to pass true which is just noisy. In the rare case that a struct may or may not print as nonexhaustive depending on a runtime decision, the Debug impl can use an
if
around the non_exhaustive call. -
I would lean toward making this an alternative to
finish
to sidestep the ambiguity about what it should do if you print more fields after calling non_exhaustive.f.debug_struct("Struct").field("field", &self.field).finish_non_exhaustive()
The job Click to expand the log.
I'm a bot! I can only do what humans tell me to, so if this was not helpful or you have suggestions for improvements, please ping or otherwise contact |
Thanks @derekdreery! This looks good to me. Could you please file a tracking issue and put the issue number into the #[unstable(...)] attribute in the PR? After that I'm happy to merge this. |
DebugStruct::non_exhaustive
and DebugStruct::opaque_field
.DebugStruct::non_exhaustive
.
Tracking issue added :) |
Could you also squash the commits down into just one? Thanks! It would also be good to update the PR description to be slightly more commit-y -- e.g., removing open questions, etc. -- since it'll go into the bors merge commit, so is preserved for all history. This is more of a personal pet peeve of mine though :) |
Off topic question: bors-ng has a setting where you can ignore any part of the PR description after some special line, which I often set to e.g. Is this something that the rust-lang bors is capable of doing? If not, should we add it? If so, should we enable it and teach people to use it? |
6303a13
to
985127c
Compare
Done and done. |
📌 Commit 985127c has been approved by |
🌲 The tree is currently closed for pull requests below priority 100, this pull request will be tested once the tree is reopened |
…=dtolnay Implement `DebugStruct::non_exhaustive`. This patch adds a function (finish_non_exhaustive) to add ellipsis before the closing brace when formatting using `DebugStruct`. ## Example ```rust #![feature(debug_non_exhaustive)] use std::fmt; struct Bar { bar: i32, hidden: f32, } impl fmt::Debug for Bar { fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { fmt.debug_struct("Bar") .field("bar", &self.bar) .non_exhaustive(true) // Show that some other field(s) exist. .finish() } } assert_eq!( format!("{:?}", Bar { bar: 10, hidden: 1.0 }), "Bar { bar: 10, .. }", ); ```
The job Click to expand the log.
I'm a bot! I can only do what humans tell me to, so if this was not helpful or you have suggestions for improvements, please ping or otherwise contact |
💔 Test failed - checks-azure |
☔ The latest upstream changes (presumably #67540) made this pull request unmergeable. Please resolve the merge conflicts. |
This needs a rebase but is otherwise ready to land. |
The job Click to expand the log.
I'm a bot! I can only do what humans tell me to, so if this was not helpful or you have suggestions for improvements, please ping or otherwise contact |
dd04a56
to
9864ec4
Compare
Should be up-to-date now. |
The job Click to expand the log.
I'm a bot! I can only do what humans tell me to, so if this was not helpful or you have suggestions for improvements, please ping or otherwise contact |
https://dev.azure.com/rust-lang/e71b0ddf-dd27-435a-873c-e30f86eea377/_apis/build/builds/18417/logs/66 looks like it wants a rustfmt of these files. |
ready for review |
Thanks! @bors r+ |
📌 Commit 73124df has been approved by |
Implement `DebugStruct::non_exhaustive`. This patch adds a function (finish_non_exhaustive) to add ellipsis before the closing brace when formatting using `DebugStruct`. ## Example ```rust #![feature(debug_non_exhaustive)] use std::fmt; struct Bar { bar: i32, hidden: f32, } impl fmt::Debug for Bar { fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { fmt.debug_struct("Bar") .field("bar", &self.bar) .non_exhaustive(true) // Show that some other field(s) exist. .finish() } } assert_eq!( format!("{:?}", Bar { bar: 10, hidden: 1.0 }), "Bar { bar: 10, .. }", ); ```
☀️ Test successful - checks-azure |
This patch adds a function (finish_non_exhaustive) to add ellipsis before the closing brace when formatting using
DebugStruct
.Example