A Trac ticket must be referenced in the ticket section. For PRs with fewer than threshold lines changed, "N/A" is also accepted (e.g. for typo fixes). Larger PRs must reference a ticket.
(pr_body, total_changes, threshold=LARGE_PR_THRESHOLD)
| 209 | |
| 210 | |
| 211 | def check_trac_ticket(pr_body, total_changes, threshold=LARGE_PR_THRESHOLD): |
| 212 | """A Trac ticket must be referenced in the ticket section. |
| 213 | |
| 214 | For PRs with fewer than threshold lines changed, "N/A" is also accepted |
| 215 | (e.g. for typo fixes). Larger PRs must reference a ticket. |
| 216 | """ |
| 217 | # Look for the ticket reference inside the Trac ticket number section. |
| 218 | section_match = re.search( |
| 219 | r"#### Trac ticket number[^\n]*\n(.*?)(?=\r?\n####|\Z)", |
| 220 | pr_body, |
| 221 | re.DOTALL, |
| 222 | ) |
| 223 | section = section_match.group(1) if section_match else pr_body |
| 224 | |
| 225 | # Strip HTML comments before checking -- the template itself contains "N/A" |
| 226 | # inside a comment, which would otherwise trigger the N/A exemption below. |
| 227 | section = strip_html_comments(section) |
| 228 | |
| 229 | if re.search(r"\bticket-\d+\b", section, re.IGNORECASE): # valid ticket found |
| 230 | return None |
| 231 | |
| 232 | # N/A is accepted for trivial PRs that don't warrant a ticket. |
| 233 | if total_changes < threshold and re.search( |
| 234 | r"(?:^|\s)N/A\b", section, re.IGNORECASE | re.MULTILINE |
| 235 | ): |
| 236 | return None |
| 237 | |
| 238 | return Message(*MISSING_TRAC_TICKET, threshold=threshold) |
| 239 | |
| 240 | |
| 241 | def check_trac_status(ticket_id, ticket_data): |
no test coverage detected