rustfmt icon indicating copy to clipboard operation
rustfmt copied to clipboard

rustfmt fails to format long strings

Open xscd opened this issue 3 years ago • 8 comments

Describe the bug

rustfmt fails to format long strings in variable declarations.

To Reproduce

  1. Go to the playground link: https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=934f95c1ee7c244bd171e2f8b211fb54

  2. From Tools section run rustfmt

  3. See that when the strings are short there are no issues but if they are long they are not formatted.

Expected behavior

I expected that rustfmt can format long strings too.

Meta

  • rustfmt version: rustfmt 1.4.36-stable (7de6968 2021-02-07)
  • From where did you install rustfmt?: rustup
  • How do you run rustfmt: directly from commandline "rustfmt" and/or inside vscode

xscd avatar Apr 14 '21 23:04 xscd

Thanks for reaching out. This is fixed in source (apparently) but hasn't been pulled into a release branch.

For anyone interested in working on this please note that the fix would need to be versioned gated to avoid violating the formatting stability guarantee. It was an intentional decision early on in rustfmt to bail in cases like this when it's completely impossible to format an element within the max_width constraint, so even though it's preferable now to format anyway (and let users turn on config options like error_on_line_overflow) we still have to gate that change

calebcartwright avatar Apr 16 '21 02:04 calebcartwright

I've hit this too when writing unit tests with structs that have fields with longs strings. I was going to make a new issue but I found this one thankfully.

Here is my example:

https://play.rust-lang.org/?version=nightly&mode=debug&edition=2018&gist=c1da9e431970417426af1bd25ab458c3

And here is a workaround I found by using a block and declaring the string inside.

https://play.rust-lang.org/?version=nightly&mode=debug&edition=2018&gist=22e7e3c4eab0a90046dcf1148e59bb8a

This way at least the rest of the file seems to keep formatting.

joakin avatar Jun 09 '21 11:06 joakin

For another piece of code where I was having issues with another long string, I ended up splitting it with \ and that also made rustfmt happier and formatted the body of my function. Different tricks for different parts of the code I guess. Very disruptive :(

joakin avatar Jun 09 '21 12:06 joakin

same as https://github.com/rust-lang/rustfmt/issues/4797

I can't format the first for_each() , string too long (no problem with the second one)

here it seems to happen if the string in the println!("") is longer than 85 characters (remove 1 letter in my example and it will indent the code correctly)

fn main() {
    println!("Hello, world!");

    vec![""].into_iter().for_each(|_| {
            println!("indent ind qqsde indent me indent me indent me indent me indent me indent me indent me ");
        println!("2");
    });

    vec![""].into_iter().for_each(|_| {
        println!("indent me");
        println!("2");
    });
}

i'm using Rust 1.54.0

ValHeimer avatar Jul 30 '21 09:07 ValHeimer

@ValHeimer - that's a duplicate of #3863 which is separate from this issue

calebcartwright avatar Jul 30 '21 22:07 calebcartwright

Any update on this? My string is around 100 chars long and rustfmt does not format it nor the surrounding code (other fields in the struct besides the one with the long string).

benma avatar Oct 02 '21 01:10 benma

So currently the only way is to manually split long string?

tkkcc avatar Sep 02 '22 07:09 tkkcc

So currently the only way is to manually split long string?

@tkkcc If you're using a nightly rustfmt you can set format_strings=true to allow rustfmt to break long strings for you.

ytmimi avatar Sep 02 '22 14:09 ytmimi

Super minimal repro: https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=2688750fd027bda1b762fda5fa7e1998

nsunderland1 avatar Oct 28 '22 18:10 nsunderland1

Still no fix? This is a major issue, especially when generating Rust code with TokenStreams which need to be formatted, but this causes otherwise rather large sections to remain in one line.

let request = client . request (reqwest :: Method :: GET , reqwest :: Url :: parse_with_params (format ! ("https://apis.website.com/xy-api-abc/apis/api-stuff-url-things/v2/more-things/{stuff}") . as_str () , & [("" , "")] ,) . unwrap () ,) . headers (headers) ;

Obviously this is completely unreadable

Fabus1184 avatar Sep 20 '23 20:09 Fabus1184

This is fixed but gated behind the version=Two flag as required per the stability guarantee.

As noted above the other comments relative to chains are unrelated to this issue and are duplicates of #3863

calebcartwright avatar Sep 20 '23 20:09 calebcartwright