Skip to content

Commit be762c5

Browse files
committed
Add test_dont_indent_already_indented
1 parent 7a332a4 commit be762c5

File tree

2 files changed

+32
-13
lines changed

2 files changed

+32
-13
lines changed

Lib/_pyrepl/readline.py

Lines changed: 10 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -256,12 +256,11 @@ def _should_auto_indent(buffer: list[str], pos: int) -> bool:
256256
# check if last character before "pos" is a colon, ignoring
257257
# whitespaces and comments.
258258
last_char = None
259-
# A stack to keep track of string delimiters (quotes). Push a quote when
260-
# entering a string, and pop it when the string ends. When the stack is
261-
# empty, we're not inside a string. If encounter a '#' while not inside a
262-
# string, it's a comment start; otherwise, it's just a '#' character within
263-
# a string.
264-
in_string: list[str] = []
259+
# A stack to keep track of string delimiters. Push a quote when entering a
260+
# string, pop it when the string ends. If the stack is empty, we're not
261+
# inside a string. When see a '#', it's a comment start if we're not inside
262+
# a string; otherwise, it's just a '#' character within a string.
263+
str_delims: list[str] = []
265264
in_comment = False
266265
char_line_indent_start = None
267266
char_line_indent = 0
@@ -275,7 +274,7 @@ def _should_auto_indent(buffer: list[str], pos: int) -> bool:
275274

276275
# update last_char
277276
if char == "#":
278-
if in_string:
277+
if str_delims:
279278
last_char = char # '#' inside a string is just a character
280279
else:
281280
in_comment = True
@@ -290,17 +289,17 @@ def _should_auto_indent(buffer: list[str], pos: int) -> bool:
290289
elif char not in " \t":
291290
if char_line_indent_start is not None:
292291
char_line_indent = i - char_line_indent_start
293-
if not in_comment and not in_string:
292+
if not in_comment and not str_delims:
294293
# update last_char with non-whitespace chars outside comments and strings
295294
last_char = char
296295
lastchar_line_indent = char_line_indent
297296

298297
# update stack
299298
if char in "\"'" and (i == 0 or buffer[i - 1] != "\\"):
300-
if in_string and in_string[-1] == char:
301-
in_string.pop()
299+
if str_delims and str_delims[-1] == char:
300+
str_delims.pop()
302301
else:
303-
in_string.append(char)
302+
str_delims.append(char)
304303
cursor_line_indent = char_line_indent
305304
return last_char == ":" and cursor_line_indent <= lastchar_line_indent
306305

Lib/test/test_pyrepl/test_pyrepl.py

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -666,7 +666,7 @@ def test_auto_indent_ignore_comments(self):
666666
output = multiline_input(reader)
667667
self.assertEqual(output, output_code)
668668

669-
def test_auto_indent_hashtag(self):
669+
def test_dont_indent_hashtag(self):
670670
# fmt: off
671671
events = code_to_events(
672672
"if ' ' == '#':\n"
@@ -684,7 +684,7 @@ def test_auto_indent_hashtag(self):
684684
output = multiline_input(reader)
685685
self.assertEqual(output, output_code)
686686

687-
def test_auto_indent_multiline_string(self):
687+
def test_dont_indent_in_multiline_string(self):
688688
# fmt: off
689689
events = code_to_events(
690690
"s = '''\n"
@@ -703,6 +703,26 @@ def test_auto_indent_multiline_string(self):
703703
output = multiline_input(reader)
704704
self.assertEqual(output, output_code)
705705

706+
def test_dont_indent_already_indented(self):
707+
# fmt: off
708+
events = code_to_events(
709+
"def f():\n"
710+
"# foo\n"
711+
"pass\n\n"
712+
)
713+
714+
output_code = (
715+
"def f():\n"
716+
" # foo\n"
717+
" pass\n"
718+
" "
719+
)
720+
# fmt: on
721+
722+
reader = self.prepare_reader(events)
723+
output = multiline_input(reader)
724+
self.assertEqual(output, output_code)
725+
706726

707727
class TestPyReplOutput(ScreenEqualMixin, TestCase):
708728
def prepare_reader(self, events):

0 commit comments

Comments
 (0)