Extract plausible author names from a byline.
(line: str)
| 360 | |
| 361 | |
| 362 | def split_author_names(line: str) -> List[str]: |
| 363 | """Extract plausible author names from a byline.""" |
| 364 | normalized = (line or "").strip() |
| 365 | if not normalized: |
| 366 | return [] |
| 367 | if re.match(r"^\d+[\.\)]", normalized): |
| 368 | return [] |
| 369 | if "http" in normalized.lower(): |
| 370 | return [] |
| 371 | if is_section_heading(normalized): |
| 372 | return [] |
| 373 | |
| 374 | parts = re.split(r",|;|\band\b", normalized, flags=re.IGNORECASE) |
| 375 | authors: List[str] = [] |
| 376 | for part in parts: |
| 377 | candidate = re.sub(r"[\d*†‡]+", "", part).strip(" -|") |
| 378 | if not candidate: |
| 379 | continue |
| 380 | if "@" in candidate: |
| 381 | continue |
| 382 | words = [word for word in candidate.split() if word] |
| 383 | if not 1 <= len(words) <= 5: |
| 384 | continue |
| 385 | if not all(re.match(r"^[A-Z][A-Za-z.'\-]*$", word) for word in words): |
| 386 | continue |
| 387 | authors.append(candidate) |
| 388 | return authors |
| 389 | |
| 390 | |
| 391 | def extract_title_and_authors(lines: List[str]) -> Dict[str, Any]: |
no test coverage detected