ParthKulshreshtha's picture
Deploy personalized ad environment
526cf2e verified
Raw
History Blame Contribute Delete
2.8 kB
"""The answer key, derived from persona features. ONE rule, any persona.
96 personas today; 10k real Expedia rows later — same function, zero authoring cost.
Verified total and single-valued over all 96 combos (test_rules.py).
"""
from __future__ import annotations
from .personas import Persona
from .scenarios import ScenarioTruth
_ALLOWED_OFFERS: dict[str, frozenset[str]] = {
"low": frozenset({"15% off", "10% off"}),
"mid": frozenset({"15% off", "free breakfast"}),
"high": frozenset({"free breakfast", "free night"}),
}
def _intent(p: Persona) -> str:
if p.trip_type == "conference" and p.near_event:
return "book_hotel_near_event"
if p.trip_type in ("conference", "business"):
return "business_trip" # a conference with no nearby event is still a business trip
if p.trip_type == "family":
return "family_vacation"
return "generic_leisure"
def _background(p: Persona) -> str:
if p.trip_type in ("conference", "business"):
return "hotel_exterior"
if p.trip_type == "family":
return "room_interior"
return "city_skyline"
def _headline(p: Persona) -> str:
# FIRST MATCH WINS — the order is load-bearing. 'proximity' is gated on trip_type as well as
# near_event, which is what guarantees it is only ever CORRECT when an event actually exists.
if p.near_event and p.trip_type in ("conference", "business"):
return "proximity"
if p.budget_tier == "high":
return "boutique"
if p.trip_type == "leisure":
return "destination"
return "generic"
def _cta(p: Persona) -> str:
return "Book now" if p.device == "mobile" else "Learn more"
def truth_for(persona: Persona) -> ScenarioTruth:
return ScenarioTruth(
correct_intent=_intent(persona),
correct_background=_background(persona),
correct_headline_strategy=_headline(persona),
correct_cta=_cta(persona),
allowed_offers=_ALLOWED_OFFERS[persona.budget_tier],
)
def oracle_action(persona: Persona) -> list[int]:
"""The perfect action for a persona. Used by tests, the demo, and (later) as the agent's
upper-bound baseline. Scores exactly 1.0 by construction.
sorted(allowed_offers)[0] — NEVER next(iter(frozenset)), whose order varies with
PYTHONHASHSEED and would make the oracle non-deterministic across processes.
"""
from .brief import MENUS # local import: brief imports personas, rules imports personas
t = truth_for(persona)
return [
MENUS["intent"].index(t.correct_intent),
MENUS["headline"].index(t.correct_headline_strategy),
MENUS["offer"].index(sorted(t.allowed_offers)[0]),
MENUS["cta"].index(t.correct_cta),
MENUS["background"].index(t.correct_background),
]