summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--isort/output.py46
-rwxr-xr-xscripts/build_config_option_docs.py2
-rw-r--r--tests/test_isort.py19
-rw-r--r--tests/test_regressions.py30
4 files changed, 53 insertions, 44 deletions
diff --git a/isort/output.py b/isort/output.py
index ce687ff2..cf6e4968 100644
--- a/isort/output.py
+++ b/isort/output.py
@@ -1,7 +1,7 @@
import copy
import itertools
from functools import partial
-from typing import Iterable, List, Tuple
+from typing import Dict, Iterable, List, Tuple
from isort.format import format_simplified
@@ -57,9 +57,6 @@ def sorted_imports(
from_modules, key=lambda key: sorting.module_key(key, config, section_name=section)
)
- if config.force_sort_within_sections:
- copied_comments = copy.deepcopy(parsed.categorized_comments)
-
section_output: List[str] = []
if config.from_first:
section_output = _with_from_imports(
@@ -107,11 +104,20 @@ def sorted_imports(
)
if config.force_sort_within_sections:
- # Remove comments
- section_output = [line for line in section_output if not line.startswith("#")]
+ # collapse comments
+ comments_above = []
+ new_section_output: List[str] = []
+ for line in section_output:
+ if line.startswith("#"):
+ comments_above.append(line)
+ elif comments_above:
+ new_section_output.append(_LineWithComments(line, comments_above))
+ comments_above = []
+ else:
+ new_section_output.append(line)
- section_output = sorting.naturally(
- section_output,
+ new_section_output = sorting.naturally(
+ new_section_output,
key=partial(
sorting.section_key,
order_by_type=config.order_by_type,
@@ -121,19 +127,11 @@ def sorted_imports(
),
)
- # Add comments back
- all_comments = copied_comments["above"]["from"]
- all_comments.update(copied_comments["above"]["straight"])
- comment_indexes = {}
- for module, comment_list in all_comments.items():
- for idx, line in enumerate(section_output):
- if module in line:
- comment_indexes[idx] = comment_list
- added = 0
- for idx, comment_list in comment_indexes.items():
- for comment in comment_list:
- section_output.insert(idx + added, comment)
- added += 1
+ # uncollapse comments
+ section_output = []
+ for line in new_section_output:
+ section_output.extend(getattr(line, "comments", ()))
+ section_output.append(str(line))
section_name = section
no_lines_before = section_name in config.no_lines_before
@@ -535,3 +533,9 @@ def _normalize_empty_lines(lines: List[str]) -> List[str]:
lines.append("")
return lines
+
+
+class _LineWithComments(str):
+ def __new__(cls, value, comments):
+ cls.comments = comments
+ return super().__new__(cls, value) # type: ignore
diff --git a/scripts/build_config_option_docs.py b/scripts/build_config_option_docs.py
index a1d43f43..927c858b 100755
--- a/scripts/build_config_option_docs.py
+++ b/scripts/build_config_option_docs.py
@@ -170,7 +170,7 @@ def config_options() -> Generator[ConfigOption, None, None]:
extra_kwargs["description"] = cli.help
yield ConfigOption(
- name=name, default=cli.default, cli_options=cli.option_strings, **extra_kwargs,
+ name=name, default=cli.default, cli_options=cli.option_strings, **extra_kwargs
)
diff --git a/tests/test_isort.py b/tests/test_isort.py
index 4ef2a0a9..94fea3d7 100644
--- a/tests/test_isort.py
+++ b/tests/test_isort.py
@@ -4087,25 +4087,6 @@ def test_isort_ensures_blank_line_between_import_and_comment() -> None:
assert api.sort_code_string(test_input, **config) == expected_output
-def test_moving_comments_issue_726():
- config = {"force_sort_within_sections": 1} # type: Dict[str, Any]
- test_input = (
- "from Blue import models as BlueModels\n"
- "# comment for PlaidModel\n"
- "from Plaid.models import PlaidModel\n"
- )
- assert api.sort_code_string(test_input, **config) == test_input
-
- test_input = (
- "# comment for BlueModels\n"
- "from Blue import models as BlueModels\n"
- "# comment for PlaidModel\n"
- "# another comment for PlaidModel\n"
- "from Plaid.models import PlaidModel\n"
- )
- assert api.sort_code_string(test_input, **config) == test_input
-
-
def test_pyi_formatting_issue_942(tmpdir) -> None:
test_input = "import os\n\n\ndef my_method():\n"
expected_py_output = test_input.splitlines()
diff --git a/tests/test_regressions.py b/tests/test_regressions.py
index 5e9962d0..eb141663 100644
--- a/tests/test_regressions.py
+++ b/tests/test_regressions.py
@@ -6,9 +6,33 @@ def test_isort_duplicating_comments_issue_1264():
"""Ensure isort doesn't duplicate comments when force_sort_within_sections is set to `True`
as was the case in issue #1264: https://github.com/timothycrosley/isort/issues/1264
"""
- assert isort.code("""
+ assert (
+ isort.code(
+ """
from homeassistant.util.logging import catch_log_exception
-# Loading the config flow file will register...
+# Loading the config flow...
from . import config_flow
-""", force_sort_within_sections=True).count("# Loading the config flow file will register...") == 1
+""",
+ force_sort_within_sections=True,
+ ).count("# Loading the config flow...")
+ == 1
+ )
+
+
+def test_moving_comments_issue_726():
+ test_input = (
+ "from Blue import models as BlueModels\n"
+ "# comment for PlaidModel\n"
+ "from Plaid.models import PlaidModel\n"
+ )
+ assert isort.code(test_input, force_sort_within_sections=True) == test_input
+
+ test_input = (
+ "# comment for BlueModels\n"
+ "from Blue import models as BlueModels\n"
+ "# comment for PlaidModel\n"
+ "# another comment for PlaidModel\n"
+ "from Plaid.models import PlaidModel\n"
+ )
+ assert isort.code(test_input, force_sort_within_sections=True) == test_input