Skip to content

Commit 0b6872d

Browse files
authored
fix(fmt): don't break var assignments when callee fits (#12323)
* fix(fmt): don't break var assignments when callee fits * fix: deindent calls (exception)
1 parent f1ca3d6 commit 0b6872d

File tree

4 files changed

+79
-17
lines changed

4 files changed

+79
-17
lines changed

crates/fmt/src/state/sol.rs

Lines changed: 39 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -835,24 +835,48 @@ impl<'ast> State<'_, 'ast> {
835835
self.s.offset(self.ind);
836836
self.print_expr(rhs);
837837
}
838-
ast::ExprKind::Binary(_, op, _) => {
839-
// Binary expressions: check if we need to break and indent
840-
if force_break || self.estimate_lhs_size(rhs, op) + lhs_size > space_left {
841-
if !self.is_bol_or_only_ind() {
838+
ast::ExprKind::Binary(lhs, op, _) => {
839+
let print_inline = |this: &mut Self| {
840+
this.print_sep(Separator::Nbsp);
841+
this.neverbreak();
842+
this.print_expr(rhs);
843+
};
844+
let print_with_break = |this: &mut Self, force_break: bool| {
845+
if !this.is_bol_or_only_ind() {
842846
if force_break {
843-
self.print_sep(Separator::Hardbreak);
847+
this.print_sep(Separator::Hardbreak);
844848
} else {
845-
self.print_sep(Separator::Space);
849+
this.print_sep(Separator::Space);
846850
}
847851
}
848-
self.s.offset(self.ind);
849-
self.s.ibox(self.ind);
850-
self.print_expr(rhs);
851-
self.end();
852-
} else {
853-
self.print_sep(Separator::Nbsp);
854-
self.neverbreak();
855-
self.print_expr(rhs);
852+
this.s.offset(this.ind);
853+
this.s.ibox(this.ind);
854+
this.print_expr(rhs);
855+
this.end();
856+
};
857+
858+
// Binary expressions: check if we need to break and indent
859+
if force_break {
860+
print_with_break(self, true);
861+
} else if self.estimate_lhs_size(rhs, op) + lhs_size > space_left {
862+
if has_complex_successor(&rhs.kind, true)
863+
&& get_callee_head_size(lhs) + lhs_size <= space_left
864+
{
865+
// Keep complex exprs (where callee fits) inline, as they will have breaks
866+
if matches!(lhs.kind, ast::ExprKind::Call(..)) {
867+
self.s.ibox(-self.ind);
868+
print_inline(self);
869+
self.end();
870+
} else {
871+
print_inline(self);
872+
}
873+
} else {
874+
print_with_break(self, false);
875+
}
876+
}
877+
// Otherwise, if expr fits, ensure no breaks
878+
else {
879+
print_inline(self);
856880
}
857881
}
858882
_ => {
@@ -2926,6 +2950,7 @@ pub(super) fn get_callee_head_size(callee: &ast::Expr<'_>) -> usize {
29262950
_ => member_ident.as_str().len(),
29272951
}
29282952
}
2953+
ast::ExprKind::Binary(lhs, _, _) => get_callee_head_size(lhs),
29292954

29302955
// If the callee is not an identifier or member access, it has no "head"
29312956
_ => 0,

crates/fmt/testdata/VariableAssignment/bracket-spacing.fmt.sol

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,8 +39,8 @@ contract TestContract {
3939
"0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF";
4040
}
4141

42+
// https://github.com/foundry-rs/foundry/issues/12254
4243
function test_longIndexedCall() {
43-
// https://github.com/foundry-rs/foundry/issues/12254
4444
bytes memory message = mailboxes[destinationDomain].buildMessage(
4545
originDomain,
4646
bytes32(0),
@@ -55,4 +55,18 @@ contract TestContract {
5555
abi.encode(orderId, bytes32(0), address(0))
5656
);
5757
}
58+
59+
// https://github.com/foundry-rs/foundry/issues/12322
60+
function test_longComplexBinExpr() {
61+
vars.previousTotalDebt = getDescaledAmount(
62+
flow.getSnapshotDebtScaled(streamId),
63+
flow.getTokenDecimals(streamId)
64+
) + vars.previousOngoingDebtScaled;
65+
66+
vars.previousTotalDebt = vars.reallyLongVarThatCausesALineBreak
67+
+ vars.previousOngoingDebtScaled;
68+
69+
vars.previousTotalDebt = vars.reallyLongVarThatCausesALineBreak()
70+
.previousOngoingDebtScaled();
71+
}
5872
}

crates/fmt/testdata/VariableAssignment/fmt.sol

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,8 +38,8 @@ contract TestContract {
3838
"0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF";
3939
}
4040

41+
// https://github.com/foundry-rs/foundry/issues/12254
4142
function test_longIndexedCall() {
42-
// https://github.com/foundry-rs/foundry/issues/12254
4343
bytes memory message = mailboxes[destinationDomain].buildMessage(
4444
originDomain,
4545
bytes32(0),
@@ -54,4 +54,18 @@ contract TestContract {
5454
abi.encode(orderId, bytes32(0), address(0))
5555
);
5656
}
57+
58+
// https://github.com/foundry-rs/foundry/issues/12322
59+
function test_longComplexBinExpr() {
60+
vars.previousTotalDebt = getDescaledAmount(
61+
flow.getSnapshotDebtScaled(streamId),
62+
flow.getTokenDecimals(streamId)
63+
) + vars.previousOngoingDebtScaled;
64+
65+
vars.previousTotalDebt = vars.reallyLongVarThatCausesALineBreak
66+
+ vars.previousOngoingDebtScaled;
67+
68+
vars.previousTotalDebt = vars.reallyLongVarThatCausesALineBreak()
69+
.previousOngoingDebtScaled();
70+
}
5771
}

crates/fmt/testdata/VariableAssignment/original.sol

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,10 +37,19 @@ contract TestContract {
3737
"0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF";
3838
}
3939

40+
// https://github.com/foundry-rs/foundry/issues/12254
4041
function test_longIndexedCall() {
41-
// https://github.com/foundry-rs/foundry/issues/12254
4242
bytes memory message = mailboxes[destinationDomain].buildMessage(originDomain, bytes32(0), address(inbox).toBytes32(), abi.encode(orderId, bytes32(0), address(0)));
4343
// should have identicall behavior when call of the same size without indexing
4444
bytes memory message = mailboxes_destinationDomains.buildMessage(originDomain, bytes32(0), address(inbox).toBytes32(), abi.encode(orderId, bytes32(0), address(0)));
4545
}
46+
47+
// https://github.com/foundry-rs/foundry/issues/12322
48+
function test_longComplexBinExpr() {
49+
vars.previousTotalDebt = getDescaledAmount(flow.getSnapshotDebtScaled(streamId), flow.getTokenDecimals(streamId)) + vars.previousOngoingDebtScaled;
50+
51+
vars.previousTotalDebt = vars.reallyLongVarThatCausesALineBreak + vars.previousOngoingDebtScaled;
52+
53+
vars.previousTotalDebt = vars.reallyLongVarThatCausesALineBreak() .previousOngoingDebtScaled();
54+
}
4655
}

0 commit comments

Comments
 (0)