Skip to content

Commit

Permalink
Merge pull request #66 from younesaassila/fix/line-breaker-variable-a…
Browse files Browse the repository at this point in the history
…ssignment

Line breaker: Fix variable assignation with cast
  • Loading branch information
cacharle committed Sep 3, 2023
2 parents efb5873 + 9a57436 commit 87676af
Show file tree
Hide file tree
Showing 2 changed files with 55 additions and 24 deletions.
57 changes: 37 additions & 20 deletions c_formatter_42/formatters/line_breaker.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,23 @@ def insert_break(line: str, column_limit: int) -> str:
return line


def get_paren_depth(s: str) -> int:
paren_depth = 0
is_surrounded_sq = False
is_surrounded_dq = False
for c in s:
if c == "'" and not is_surrounded_dq:
is_surrounded_sq = not is_surrounded_sq
elif c == '"' and not is_surrounded_sq:
is_surrounded_dq = not is_surrounded_dq
elif c == "(" and not is_surrounded_sq and not is_surrounded_dq:
paren_depth += 1
elif c == ")" and not is_surrounded_sq and not is_surrounded_dq:
paren_depth -= 1

return paren_depth


# The additional indent level increases in proportion to the corresponding parentheses depth
#
# Examples:
Expand All @@ -59,31 +76,31 @@ def insert_break(line: str, column_limit: int) -> str:
# > > * baz())) Next line should be indented with 2 tabs (paren depth is 2)
# -----------------------------------------------------------------------------------
def additional_indent_level(s: str, nest_indent_level: int = 0) -> int:
paren_depth = 0
is_surrounded_sq = False
is_surrounded_dq = False
for c in s:
if c == "'":
is_surrounded_sq = not is_surrounded_sq
elif c == '"':
is_surrounded_dq = not is_surrounded_dq
elif c == "(" and not is_surrounded_sq and not is_surrounded_dq:
paren_depth += 1
elif c == ")" and not is_surrounded_sq and not is_surrounded_dq:
paren_depth -= 1

if paren_depth > 0:
return nest_indent_level + paren_depth
else:
return 1 # 1 is the default additional indent level
paren_depth = get_paren_depth(s)
return nest_indent_level + paren_depth if paren_depth > 0 else 1


def additional_nest_indent_level(line: str) -> int:
# An exceptional rule for variable assignment
# https://github.com/42School/norminette/blob/921b5e22d991591f385e1920f7e7ee5dcf71f3d5/norminette/rules/check_assignation_indent.py#L59
align_pattern = r"^\s*({decl})((\.|->){decl})*\s+=\s+(.|\n)*?;$"
align_pattern = align_pattern.format(decl=helper.REGEX_DECL_NAME)
return 1 if re.match(align_pattern, line) is not None else 0
is_assignation = False
is_surrounded_sq = False
is_surrounded_dq = False
for index, c in enumerate(line):
if c == "'" and not is_surrounded_dq:
is_surrounded_sq = not is_surrounded_sq
elif c == '"' and not is_surrounded_sq:
is_surrounded_dq = not is_surrounded_dq
is_assignation = (
c == "="
and not is_surrounded_sq
and not is_surrounded_dq
and get_paren_depth(line[:index]) == 0
)
if is_assignation:
break

return 1 if is_assignation else 0


def line_length(line: str) -> int:
Expand Down
22 changes: 18 additions & 4 deletions tests/formatters/test_line_breaker.py
Original file line number Diff line number Diff line change
Expand Up @@ -224,13 +224,27 @@ def test_insert_line_break_basic_23():


def test_insert_line_break_basic_24():
output = "*foo = foooooo(bar\n\t\t* baz);"
assert output == line_breaker("*foo = foooooo(bar * baz);", 18)
output = "foo = foooooo(bar\n\t\t* baz);"
assert output == line_breaker("foo = foooooo(bar * baz);", 18)


def test_insert_line_break_basic_25():
output = "foo[0] = foooooo(bar\n\t\t* baz);"
assert output == line_breaker("foo[0] = foooooo(bar * baz);", 20)
output = "foo[i] = foooooo(bar\n\t\t* baz);"
assert output == line_breaker("foo[i] = foooooo(bar * baz);", 21)


def test_insert_line_break_basic_26():
output = '"EXT = TXT" + foooooo(bar\n\t* baz);'
assert output == line_breaker('"EXT = TXT" + foooooo(bar * baz);', 27)


def test_insert_line_break_basic_27():
input = (
'((t_cast *)it->content)->name = get_name((t_cast *)it->content, "EXT=TXT");'
)
output = """((t_cast *)it->content)->name = get_name((t_cast *)it->content,
\t\t\"EXT=TXT\");"""
assert output == line_breaker(input, 64)


def test_insert_line_break_long_function_declaration():
Expand Down

0 comments on commit 87676af

Please sign in to comment.