@tishlang/tish-format 3.10.2 → 3.10.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bin/tish-format CHANGED
Binary file
@@ -1,6 +1,6 @@
1
1
  [package]
2
2
  name = "tishlang_fmt"
3
- version = "3.10.2"
3
+ version = "3.10.3"
4
4
  edition = "2021"
5
5
  description = "Opinionated formatter for Tish source (parse → pretty-print)"
6
6
  license-file = { workspace = true }
@@ -905,6 +905,9 @@ impl Printer {
905
905
  if lead_indent {
906
906
  self.indent(level);
907
907
  }
908
+ if self.try_inline_block(statements, span, level) {
909
+ return;
910
+ }
908
911
  self.buf.push_str("{\n");
909
912
  // Fresh sequence: suppress any blank line immediately after `{`.
910
913
  self.emitted = 0;
@@ -920,6 +923,80 @@ impl Printer {
920
923
  self.emitted = span.start.0;
921
924
  }
922
925
 
926
+ /// True when the source wrote this whole block on one line (`{ … }` with its
927
+ /// matching brace on the same line). The codebase uses `if (c) { return x }`
928
+ /// and `while (c) { a; b }` as a deliberate idiom; exploding those into
929
+ /// multi-line blocks was by far the largest source of reformat churn, so a
930
+ /// block that arrived on one line is kept on one line when it still fits.
931
+ fn source_one_liner(&self, span: Span) -> bool {
932
+ match self.braces.get(&span.start) {
933
+ Some(&(close_line, _)) => close_line == span.start.0,
934
+ None => false,
935
+ }
936
+ }
937
+
938
+ /// Statements simple enough to sit inside a preserved one-liner block. Anything
939
+ /// carrying a block of its own is excluded — nesting one-liners reads worse than
940
+ /// breaking, and the inline printer here emits no newlines or indentation.
941
+ fn inlinable_stmt(s: &Statement) -> bool {
942
+ matches!(
943
+ s,
944
+ Statement::ExprStmt { .. }
945
+ | Statement::Return { .. }
946
+ | Statement::Break { .. }
947
+ | Statement::Continue { .. }
948
+ | Statement::VarDecl { .. }
949
+ | Statement::VarDeclDestructure { .. }
950
+ | Statement::Throw { .. }
951
+ )
952
+ }
953
+
954
+ /// Re-emit a source one-liner block as `{ a; b }`. Returns false (leaving `buf`
955
+ /// untouched) when the block does not qualify or the flat form would overflow
956
+ /// [`WIDTH`], in which case the caller falls through to the normal broken form.
957
+ fn try_inline_block(&mut self, statements: &[Statement], span: Span, _level: usize) -> bool {
958
+ if self.src.is_empty() || statements.is_empty() {
959
+ return false;
960
+ }
961
+ if !self.source_one_liner(span) {
962
+ return false;
963
+ }
964
+ if !statements.iter().all(Self::inlinable_stmt) {
965
+ return false;
966
+ }
967
+ // A comment anywhere inside would be dropped by the inline path, which emits
968
+ // no comments at all. Bail out and let the broken form place it properly.
969
+ let close = self.braces.get(&span.start).copied().unwrap_or(span.start);
970
+ if self
971
+ .comments
972
+ .get(self.ci)
973
+ .is_some_and(|c| c.start >= span.start && c.start < close)
974
+ {
975
+ return false;
976
+ }
977
+
978
+ let mark = self.buf.len();
979
+ let col = self.col();
980
+ let was_flat = self.force_flat;
981
+ self.force_flat = true;
982
+ self.buf.push_str("{ ");
983
+ for (i, st) in statements.iter().enumerate() {
984
+ if i > 0 {
985
+ self.buf.push_str("; ");
986
+ }
987
+ self.stmt(st, 0);
988
+ }
989
+ self.buf.push_str(" }");
990
+ self.force_flat = was_flat;
991
+
992
+ if col + (self.buf.len() - mark) <= WIDTH && !self.buf[mark..].contains('\n') {
993
+ self.emitted = span.start.0;
994
+ return true;
995
+ }
996
+ self.buf.truncate(mark);
997
+ false
998
+ }
999
+
923
1000
  fn stmt_inline_or_block(&mut self, s: &Statement, level: usize) {
924
1001
  if let Statement::Block { statements, span } = s {
925
1002
  self.block(statements, *span, level, false);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@tishlang/tish-format",
3
- "version": "3.10.2",
3
+ "version": "3.10.3",
4
4
  "description": "Tish code formatter",
5
5
  "license": "PIF",
6
6
  "repository": {
Binary file
Binary file
Binary file
Binary file
Binary file