Skip to content
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

Support default literals #368

Open
dtolnay opened this Issue Jun 10, 2016 · 13 comments

Comments

@dtolnay
Copy link
Member

dtolnay commented Jun 10, 2016

#[serde(default="0.1")]
pub n: f32

There is an ambiguity when the field is of function type so we need to figure that out.

@dtolnay

This comment has been minimized.

Copy link
Member Author

dtolnay commented Jun 13, 2016

This needs to be fleshed out a lot more before it can be implemented so please chime in if you have ideas for how this should work.

I am glad we implemented #[serde(default="...")] and it has been widely useful but backward compatibility is going to be tricky. To start brainstorming, here are a few possible alternatives:

  • Another level of nesting
    • #[serde(default(expr="0.1"))] - we insert the expression verbatim into the generated code
    • This is flexible but clunky.
  • Look for parentheses to denote an expression
    • #[serde(default="(0.1)")]
    • This is hacky and doesn't provide a path forward for deprecating the current syntax.
  • Use a different attribute name
    • #[serde(missing="0.1")], #[serde(default_expr="0.1")]
    • But default is such a perfect fit.
  • Treat as an expression if it fails to parse as a path
    • #[serde(default="0.1")]
    • This is ambiguous in many cases, for example enums: #[serde(default="Color::Yellow")]

@dtolnay dtolnay self-assigned this Jun 13, 2016

@sfackler

This comment has been minimized.

Copy link
Contributor

sfackler commented Aug 12, 2016

Seems like an easy route would be #[serde(default_value = "0.1")]. It's a bit more wordy but would allow us to get the functionality out there, and we can always deprecate default_value if a better approach comes around.

@dtolnay dtolnay removed their assignment Jan 24, 2017

@rekka

This comment has been minimized.

Copy link

rekka commented Feb 3, 2017

Would it be possible to support closures? Something like:

#[serde(default="||{ 0.1 }")]
pub n: f32
@skorokithakis

This comment has been minimized.

Copy link

skorokithakis commented Jul 28, 2017

The closure route would be the most logical for me (and the first thing I tried when exploring how to do what I wanted). However, I think default_expr would be by far the clearest.

I would have preferred default=3 to be the literal mode and default_func the function-based approach, but eh, can't do much about that now.

@dtolnay

This comment has been minimized.

Copy link
Member Author

dtolnay commented Sep 3, 2017

As reported in #1031, unit variants would be nice to support as well. Rust no longer enforces that the value in an attribute is a literal.

@Fiedzia

This comment has been minimized.

Copy link

Fiedzia commented Apr 20, 2018

Any progress on that? Right now I am forced to write functions like
fn one() -> u32 { 1 }
and it really looks silly

@alexbool

This comment has been minimized.

Copy link

alexbool commented May 20, 2018

I agree with @sfackler and think #[serde(default_value = "0.1")] is a way to go

@richardwhiuk

This comment has been minimized.

Copy link

richardwhiuk commented Jan 24, 2019

Surely #[serde(default_value = 0.1)] is better - and then any expression can be provided?

In fact, that can replace any of the current usage right?

@jhpratt

This comment has been minimized.

Copy link

jhpratt commented Jan 30, 2019

@dtolnay Would a PR be accepted for this? Using proc macros, it shouldn't be terribly difficult to generate a function (which can have an #[inline] hint) and do something along the lines of #[serde(default = #fn_name)] in the expansion.

I can certainly work on this if it's a feature you and the other maintainers are interested in.

@norru

This comment has been minimized.

Copy link

norru commented Feb 20, 2019

Just being bitten by this, currently writing a lot of
fn one() -> u32 { 1 }
which is very clunky.

@jplatte

This comment has been minimized.

Copy link

jplatte commented Feb 20, 2019

I don't know how to drive this forward, but I think a very small change to the compiler (or some other trick I have yet to find) could enable the existing attribute to work with values too: https://internals.rust-lang.org/t/implementing-traits-for-function-types/5888
(the playground code linked in that thread uses specialization but IIRC there was a way around that)

@jhpratt

This comment has been minimized.

Copy link

jhpratt commented Feb 20, 2019

@dtolnay Would a PR be accepted that resolves this? I asked a few weeks ago and received no answer. I don't think there's any question people want this.

@est31

This comment has been minimized.

Copy link

est31 commented Feb 23, 2019

This crate could also give inspiration: https://github.com/idanarye/rust-smart-default

It allows specifying literals as well as code for the default value.

@bossmc bossmc referenced a pull request that will close this issue Feb 25, 2019

Open

Add `default_expr` and `default_fn` #1490

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.