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

Keep prev spaces #607

Merged
merged 1 commit into from
Jun 30, 2023
Merged

Keep prev spaces #607

merged 1 commit into from
Jun 30, 2023

Conversation

tompng
Copy link
Member

@tompng tompng commented Jun 15, 2023

Re-imlement prev_space feature #605 (temporarily dropped in #500)

Code pasted to irb sometimes have base indent. This pull request make IRB indent correctly with base indent

# no base indent
irb(main):001:1* if 1
irb(main):002:1*   2
irb(main):003:0> end
# base indent = 4
irb(main):001:1*     if 1
irb(main):002:1*       2
irb(main):003:0>     end

Example of base indent and heredoc

irb(main):001:1*         if 1
irb(main):002:0"           <<A
irb(main):003:0" hello
irb(main):004:1* A
irb(main):005:2"           <<~A
irb(main):006:2"             world
irb(main):007:1*           A
irb(main):008:0>         end

TODO: wait for #515, #608, write tests for heredoc done

Basic algorithm

I defined base_indent to satisfy actual_indent == base_indent + 2 * indent_level. base_indent can differ on line.

Pasted code

      if 1 # base_indent is 6, indent_level is 0
          if 2 # base_indent is 8, indent_level is 1
            3
            4.tap do # base_indent is 8, indent_level is 2, indent is 12 spaces
              5

Reference code

if 1
  if 2
    3
    4.tap do # indent is 4 spaces (= 2 * indent_level)
      5

Line 5 is just inside token do on line 4. We need to calculate base_indent of line 4 where do is located.
base_indent of line 4 can be calculated by 12 - 2 * indent_level.
12 is the indent of pasted code on line 4 and indent_level is 2

Exceptional case

      if 1
          if 2
            "helloworld
helloworld".tap do
              5

If the beginning of line 4 is inside string literal, we cannot calculate base_indent of line 4.
In that case, base_indent of line 3 is used instead.

Exceptional case 2

      :"ruby
ruby
ruby" + "helloworld
helloworld".tap do
        5

Cannot calculate line 4, fallback to line 3 (beginning of tstring_beg)
Cannot calculate line 3, fallback to line 1 (beginning of symbeg)
base_indent of line 1 is 6

@@ -370,7 +370,7 @@ def calc_nesting_depth(opens)
indent_level = 0
end
end
when :on_tstring_beg, :on_regexp_beg, :on_symbeg
when :on_tstring_beg, :on_regexp_beg, :on_symbeg, :on_backtick
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I forgot to add :on_backtick and the test test_pasted_code_keep_base_indent_spaces failed

          ]+[["a
b" + `c
d` + /e ← failed here
f/ + :"g
h".tap do

@tompng tompng marked this pull request as ready for review June 20, 2023 18:13
@tompng tompng force-pushed the keep_prev_spaces branch from 57e2a7d to 6c761c2 Compare June 25, 2023 05:14
# irb(main):002:1* if b # base_indent is 6, indent calculated from tokens is 2
# irb(main):003:0> c # base_indent is 6, indent calculated from tokens is 4
if prev_open_token
base_indent = [0, indent_difference(lines, line_results, prev_open_token.pos[0] - 1)].max
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this imply the result of indent_difference(lines, line_results, prev_open_token.pos[0] - 1) could be negative?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. It could be negative.

if 1 # diff = 0
  if 2 # diff = 0
  end
end
    if 1 # diff = 4
      if 2 # diff = 4
      end
    end
    if 1 # diff = 4
    if 2 # diff = 2
    end
    end
if 1 # diff = 0
if 2 # diff = -2 ← negative
end
end

@st0012 st0012 added the bug Something isn't working label Jun 29, 2023
@st0012 st0012 merged commit 9d97a19 into ruby:master Jun 30, 2023
@tompng tompng deleted the keep_prev_spaces branch June 30, 2023 17:41
@st0012 st0012 mentioned this pull request Jul 4, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Development

Successfully merging this pull request may close these issues.

None yet

2 participants