50 lines
1.7 KiB
Python
50 lines
1.7 KiB
Python
from __future__ import annotations
|
|
|
|
import re
|
|
from collections.abc import Iterable
|
|
|
|
from gitea_codex_bot.types import ParsedCommand
|
|
|
|
PREFIX_RE = re.compile(r"^@([^\s]+)\s+(.+)$", re.IGNORECASE | re.DOTALL)
|
|
HELP_ALIASES = {"-h", "--help", "help"}
|
|
SUPPORTED_COMMANDS = {"review", "explain", "fix", "ignore", "rerun"}
|
|
|
|
|
|
def parse_command(body: str, aliases: Iterable[str] | None = None) -> ParsedCommand | None:
|
|
stripped = body.strip()
|
|
match = PREFIX_RE.match(stripped)
|
|
if not match:
|
|
return None
|
|
command_alias = match.group(1).lstrip("@").lower()
|
|
allowed_aliases = {alias.lstrip("@").lower() for alias in (aliases or {"codex"})}
|
|
if command_alias not in allowed_aliases:
|
|
return None
|
|
|
|
remainder = match.group(2).strip()
|
|
if not remainder:
|
|
return None
|
|
parts = remainder.split(maxsplit=1)
|
|
raw_name = parts[0].lower()
|
|
rest = parts[1].strip() if len(parts) > 1 else ""
|
|
if raw_name in HELP_ALIASES:
|
|
return ParsedCommand(name="help", raw=stripped, arguments=[token for token in rest.split() if token])
|
|
if raw_name not in SUPPORTED_COMMANDS:
|
|
return None
|
|
name = raw_name
|
|
tokens = [token for token in rest.split() if token]
|
|
|
|
parsed = ParsedCommand(name=name, raw=stripped, arguments=tokens)
|
|
if name == "review":
|
|
if "--full" in tokens:
|
|
parsed.full = True
|
|
parsed.mode = "full"
|
|
parsed.mode_explicit = True
|
|
for mode in ("security", "performance", "tests"):
|
|
if mode in tokens:
|
|
parsed.mode = mode
|
|
parsed.mode_explicit = True
|
|
break
|
|
elif name == "fix":
|
|
parsed.branch_fix = "--branch" in tokens
|
|
return parsed
|