Returns a tuple (reverse string, group count) for a url. For example: Given the url pattern /([0-9]{4})/([a-z-]+)/, this method would return ('/%s/%s/', 2).
(self)
| 606 | return self._path % tuple(converted_args) |
| 607 | |
| 608 | def _find_groups(self) -> Tuple[Optional[str], Optional[int]]: |
| 609 | """Returns a tuple (reverse string, group count) for a url. |
| 610 | |
| 611 | For example: Given the url pattern /([0-9]{4})/([a-z-]+)/, this method |
| 612 | would return ('/%s/%s/', 2). |
| 613 | """ |
| 614 | pattern = self.regex.pattern |
| 615 | if pattern.startswith("^"): |
| 616 | pattern = pattern[1:] |
| 617 | if pattern.endswith("$"): |
| 618 | pattern = pattern[:-1] |
| 619 | |
| 620 | if self.regex.groups != pattern.count("("): |
| 621 | # The pattern is too complicated for our simplistic matching, |
| 622 | # so we can't support reversing it. |
| 623 | return None, None |
| 624 | |
| 625 | pieces = [] |
| 626 | for fragment in pattern.split("("): |
| 627 | if ")" in fragment: |
| 628 | paren_loc = fragment.index(")") |
| 629 | if paren_loc >= 0: |
| 630 | try: |
| 631 | unescaped_fragment = re_unescape(fragment[paren_loc + 1 :]) |
| 632 | except ValueError: |
| 633 | # If we can't unescape part of it, we can't |
| 634 | # reverse this url. |
| 635 | return (None, None) |
| 636 | pieces.append("%s" + unescaped_fragment) |
| 637 | else: |
| 638 | try: |
| 639 | unescaped_fragment = re_unescape(fragment) |
| 640 | except ValueError: |
| 641 | # If we can't unescape part of it, we can't |
| 642 | # reverse this url. |
| 643 | return (None, None) |
| 644 | pieces.append(unescaped_fragment) |
| 645 | |
| 646 | return "".join(pieces), self.regex.groups |
| 647 | |
| 648 | |
| 649 | class URLSpec(Rule): |