(self, parent: etree.Element, blocks: list[str])
| 464 | return bool(self.RE.search(block)) |
| 465 | |
| 466 | def run(self, parent: etree.Element, blocks: list[str]) -> None: |
| 467 | block = blocks.pop(0) |
| 468 | m = self.RE.search(block) |
| 469 | if m: |
| 470 | before = block[:m.start()] # All lines before header |
| 471 | after = block[m.end():] # All lines after header |
| 472 | if before: |
| 473 | # As the header was not the first line of the block and the |
| 474 | # lines before the header must be parsed first, |
| 475 | # recursively parse this lines as a block. |
| 476 | self.parser.parseBlocks(parent, [before]) |
| 477 | # Create header using named groups from RE |
| 478 | h = etree.SubElement(parent, 'h%d' % len(m.group('level'))) |
| 479 | h.text = m.group('header').strip() |
| 480 | if after: |
| 481 | # Insert remaining lines as first block for future parsing. |
| 482 | if self.parser.state.isstate('looselist'): |
| 483 | # This is a weird edge case where a header is a child of a loose list |
| 484 | # and there is no blank line after the header. To ensure proper |
| 485 | # parsing, the line(s) after need to be detabbed. See #1443. |
| 486 | after = self.looseDetab(after) |
| 487 | blocks.insert(0, after) |
| 488 | else: # pragma: no cover |
| 489 | # This should never happen, but just in case... |
| 490 | logger.warn("We've got a problem header: %r" % block) |
| 491 | |
| 492 | |
| 493 | class SetextHeaderProcessor(BlockProcessor): |
nothing calls this directly
no test coverage detected