lacommedia's picture
Publish v2.8 classifier specification and audit
63bc467 verified
Raw History Blame Contribute Delete
2.91 kB
"""Coin source-item classifier v2.8. Proposals require human review."""
import re
LABELS=["shadowboxing","bag_work","partner_work","footwork","strength","conditioning","mobility","recovery","unknown"]
LETTER_TO_LABEL={"A":"shadowboxing","B":"footwork","C":"conditioning","D":"unknown","E":"bag_work","F":"partner_work"}
SYSTEM_PROMPT=("Classify one boxing workout source item using its immutable parent section only as context. " "A = solo boxing practice, punches, or defense without a partner. " "B = footwork, steps, or agility without punches. " "C = physical conditioning or strength. D = unclear, a heading, or a prescription. " "E = heavy-bag work. F = partner work or sparring. Return one letter only.")
def explicit_activity(text, kind="boxing", allow_kind_fallback=True):
if re.search(r"\bpush[ -]?ups?\b",text,re.I) and re.search(r"\b(?:jumps?|squats?)\b",text,re.I): return "strength",re.search(r"\bpush[ -]?ups?\b",text,re.I).group(0)
if re.search(r"\b(?:frontal|fighting) stance\b",text,re.I) and re.search(r"\battack\b",text,re.I): return "shadowboxing",re.search(r"\battack\b",text,re.I).group(0)
patterns=[("recovery",r"\b(?:rest day|active recovery|recovery day)\b"),("conditioning",r"\b(?:conditioning|running|sprints?|jump rope)\b"),("shadowboxing",r"\b(?:virtual|virual) sparring\b"),("partner_work",r"\b(?:partner work|sparring|partner drill)\b"),("bag_work",r"\bbag work\b"),("shadowboxing",r"\b(?:shadowboxing|shadow boxing|virtual pad work|punch(?:es)?|jab|hooks?|uppercuts?|combos?|combinations?|defen[cs]e|slips?|rolls?)\b"),("strength",r"\b(?:squats?|push[ -]?ups?|pull[ -]?ups?|burpees?|mountain climbers?|leg raises?|tucks?|medicine ball|med ball|dumbbell|kettlebell|deadlift|bench press|snatch|inverted row)\b"),("mobility",r"\b(?:stretches|stretching|stretch|mobility)\b")]
for activity,pattern in patterns:
match=re.search(pattern,text,re.I)
if match:return activity,match.group(0)
if allow_kind_fallback and kind=="recovery":return "recovery",text.splitlines()[0][:200]
return None
def explicit_parent_activity(text):
lines=[line.strip() for line in text.splitlines() if line.strip()]
heading=" ".join(lines[:2])
for activity,pattern in (("bag_work",r"\bBAG WORK\b"),("partner_work",r"\b(?:PARTNER WORK|(?<!VIRTUAL )(?<!VIRUAL )SPARRING)\b")):
match=re.search(pattern,heading,re.I)
if match:return activity,match.group(0).strip()
return None
def model_request(source_text,parent_section):
return {"messages":[{"role":"system","content":SYSTEM_PROMPT},{"role":"user","content":__import__("json").dumps({"item":source_text,"parent_section":parent_section},sort_keys=True,separators=(",",":"))}],"max_tokens":1,"temperature":0,"logprobs":True,"top_logprobs":10,"chat_template_kwargs":{"enable_thinking":False}}
def decode_choice(choice):
return LETTER_TO_LABEL.get(choice.strip(),"unknown")