|
| 1 | +from nameparser import HumanName |
| 2 | +from nameparser.config import Constants |
| 3 | +from nameparser.config.regexes import REGEXES |
| 4 | + |
| 5 | +from tests.base import HumanNameTestBase |
| 6 | + |
| 7 | + |
| 8 | +class HumanNameCommaVariantsTests(HumanNameTestBase): |
| 9 | + """Non-ASCII comma characters should split "Last, First" the same as ',' (#265).""" |
| 10 | + |
| 11 | + def test_arabic_comma_splits_lastname_format(self) -> None: |
| 12 | + hn = HumanName("سلمان، محمد") |
| 13 | + self.m(hn.first, "محمد", hn) |
| 14 | + self.m(hn.last, "سلمان", hn) |
| 15 | + |
| 16 | + def test_fullwidth_comma_splits_lastname_format(self) -> None: |
| 17 | + hn = HumanName("Smith,John") |
| 18 | + self.m(hn.first, "John", hn) |
| 19 | + self.m(hn.last, "Smith", hn) |
| 20 | + |
| 21 | + def test_arabic_comma_does_not_pollute_output(self) -> None: |
| 22 | + hn = HumanName("سلمان، محمد") |
| 23 | + self.assertNotIn("،", hn.last) |
| 24 | + self.assertNotIn("،", str(hn)) |
| 25 | + |
| 26 | + def test_trailing_arabic_comma_stripped(self) -> None: |
| 27 | + # matches ASCII behavior: a single word with a trailing comma has |
| 28 | + # nothing after the comma, so it's a bare name, not "Last," |
| 29 | + hn = HumanName("سلمان،") |
| 30 | + self.m(hn.first, "سلمان", hn) |
| 31 | + |
| 32 | + def test_custom_regexes_without_commas_key_does_not_shatter_name(self) -> None: |
| 33 | + # A custom regexes dict that omits "commas" entirely must not fall |
| 34 | + # back to RegexTupleManager's EMPTY_REGEX default for splitting -- |
| 35 | + # re.compile('').split(...) matches between every character, which |
| 36 | + # explodes any name into single-char pieces instead of leaving it |
| 37 | + # unsplit (the EMPTY_REGEX convention elsewhere in this codebase |
| 38 | + # means "feature disabled", not "split on every character"). |
| 39 | + # With comma splitting disabled, "Smith, John" is tokenized like any |
| 40 | + # other no-comma input (word tokenizing drops the punctuation), |
| 41 | + # yielding a plain first/last pair -- not the inverted "Last, First" |
| 42 | + # reading, and definitely not single-character pieces. |
| 43 | + custom = {k: v for k, v in REGEXES.items() if k != 'commas'} |
| 44 | + c = Constants(regexes=custom) |
| 45 | + hn = HumanName("Smith, John", constants=c) |
| 46 | + self.m(hn.first, "Smith", hn) |
| 47 | + self.m(hn.last, "John", hn) |
0 commit comments