Generate all leaves that should be ignored by the `# fmt: skip` from `leaf`.
(
leaf: Leaf, comment: ProtoComment, mode: Mode
)
| 651 | |
| 652 | |
| 653 | def _generate_ignored_nodes_from_fmt_skip( |
| 654 | leaf: Leaf, comment: ProtoComment, mode: Mode |
| 655 | ) -> Iterator[LN]: |
| 656 | """Generate all leaves that should be ignored by the `# fmt: skip` from `leaf`.""" |
| 657 | prev_sibling = leaf.prev_sibling |
| 658 | parent = leaf.parent |
| 659 | ignored_nodes: list[LN] = [] |
| 660 | # Need to properly format the leaf prefix to compare it to comment.value, |
| 661 | # which is also formatted |
| 662 | comments = list_comments(leaf.prefix, is_endmarker=False, mode=mode) |
| 663 | if not comments or comment.value != comments[0].value: |
| 664 | return |
| 665 | |
| 666 | if prev_sibling is None and parent is not None: |
| 667 | prev_sibling = parent.prev_sibling |
| 668 | |
| 669 | if prev_sibling is None and comment.type == token.COMMENT: |
| 670 | prev_sibling = _find_closest_previous_sibling(leaf) |
| 671 | |
| 672 | if parent is not None and parent.type == syms.suite and leaf.type == token.NEWLINE: |
| 673 | # The `# fmt: skip` is on the colon line of the if/while/def/class/... |
| 674 | # statements. The ignored nodes should be previous siblings of the |
| 675 | # parent suite node. Do this before the generic "same physical line" |
| 676 | # logic so multiline headers are preserved as a whole. |
| 677 | leaf.prefix = "" |
| 678 | parent_sibling = parent.prev_sibling |
| 679 | while parent_sibling is not None and parent_sibling.type != syms.suite: |
| 680 | ignored_nodes.insert(0, parent_sibling) |
| 681 | parent_sibling = parent_sibling.prev_sibling |
| 682 | # Special case for `async_stmt` where the ASYNC token is on the |
| 683 | # grandparent node. |
| 684 | grandparent = parent.parent |
| 685 | if ( |
| 686 | grandparent is not None |
| 687 | and grandparent.prev_sibling is not None |
| 688 | and grandparent.prev_sibling.type == token.ASYNC |
| 689 | ): |
| 690 | ignored_nodes.insert(0, grandparent.prev_sibling) |
| 691 | yield from iter(ignored_nodes) |
| 692 | elif prev_sibling is not None: |
| 693 | # Generates the nodes to be ignored by `fmt: skip`. |
| 694 | |
| 695 | # Nodes to ignore are the ones on the same line as the |
| 696 | # `# fmt: skip` comment, excluding the `# fmt: skip` |
| 697 | # node itself. |
| 698 | |
| 699 | # Traversal process (starting at the `# fmt: skip` node): |
| 700 | # 1. Move to the `prev_sibling` of the current node. |
| 701 | # 2. If `prev_sibling` has children, go to its rightmost leaf. |
| 702 | # 3. If there's no `prev_sibling`, move up to the parent |
| 703 | # node and repeat. |
| 704 | # 4. Continue until: |
| 705 | # a. You encounter an `INDENT` or `NEWLINE` node (indicates |
| 706 | # start of the line). |
| 707 | # b. You reach the root node. |
| 708 | |
| 709 | # Include all visited LEAVES in the ignored list, except INDENT |
| 710 | # or NEWLINE leaves. |
no test coverage detected