rust-lang / rust-lang/rustfmt

`match_arm_blocks = false` interacts poorly on some lines that are exactly `max_width + 2` long.

Open
#6,136 1 comment 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

A-matches I-max-width only-with-option
Dominant language
Rust
Stars
7k
Forks
1.1k
Avg merge
2d 13h
Merged PRs (30d)
24

Description

I believe this to be a somewhat pathological off-by-one error.

I set up a reproduction repository, which I expect will also be the clearest description of this issue that I can give.

Attempting to summarize; given a max_width of 60, match_arm_blocks = false, and something like line 4 below, running cargo +nightly fmt will result in a line that is 61 characters wide. (NB. The specific max_width is unimportant; I'm using 60 here only to make the example slightly more concise.)

// Input
fn foo(i: i32) {
    match i {
        // This line is 62 characters wide
        _ => println!("1st argument: {}", "2nd argument ___"),
    }
}

// Output
fn foo(i: i32) {
    match i {
        _ =>
            // This line is 61 characters wide
            println!("1st argument: {}", "2nd argument ___"),
    }
}

This could be avoided if the arguments in the println! invocation were moved into the vertical style. Interestingly, if you add one more _ to line 4 (making that line 63 characters wide), those arguments will be moved into a vertical form, and max_width won't be exceeded. Also, if you set match_arm_blocks = true, there will be no trailing comma after the println!(..) (the comma will be moved to a }, on the line below), and max_width won't be exceeded.

I only noticed this edge case because the repository I'm working in also has error_on_line_overflow = true and error_on_unformatted = true set, which causes rustfmt to yield an error when run against a line like the one above. Which we somehow managed to already have in our repo when I started experimenting with match_arm_blocks = false.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with the linked reproduction repository and run cargo +nightly fmt using max_width = 60 and match_arm_blocks = false. Trace the formatting decision for the shown match arm and println! call, then verify that the formatted output does not exceed max_width and remains compatible with error_on_line_overflow = true and error_on_unformatted = true.

Written by the indexing model from the issue text.

Assessment

Tech stack
rust
Domain
tooling
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.