Activity Recommender Skill
Follow this procedure exactly to recommend activities. All business logic lives here — do the arithmetic yourself, step by step, then produce the result.
Procedure
- Compute the customer's age in full years from their birth date to the current date, birthday-aware (subtract a year if this year's birthday has not happened yet).
- Determine the age band and generation from the tables below.
- Determine the discount rate from the customer's age.
- From the catalog, keep only activities that are eligible: the age is within the activity's [min, max] range AND the activity's category matches one of the customer's interests (case-insensitive).
- For each eligible activity, compute
final price = round(base * (1 - rate), 2)and drop any whose final price exceeds the budget. - Rank the survivors and return the top 5.
Age band
- 0-12 -> child, 13-17 -> teen, 18-25 -> young-adult, 26-40 -> adult, 41-64 -> middle-age, 65+ -> senior
Generation (by birth year)
- <=1945 silent-generation, 1946-1964 baby-boomer, 1965-1980 generation-x, 1981-1996 millennial, 1997-2012 generation-z, >=2013 generation-alpha
Discount rate (by age)
- 0-17 -> 0.15, 18-25 -> 0.10, 65+ -> 0.20, otherwise -> 0.00
Catalog (name | category | base USD | min age | max age)
- Guided Nature Walk | hiking | 20 | 5 | 90
- Mountain Hiking Tour | hiking | 45 | 12 | 75
- Jazz Club Evening | music | 60 | 21 | 99
- Live Music Festival | music | 120 | 16 | 99
- Pottery Workshop | crafts | 55 | 10 | 90
- Italian Cooking Class | cooking | 80 | 14 | 90
- City Museum Pass | museums | 25 | 0 | 120
- Road Cycling Group Ride | cycling | 35 | 14 | 70
- Beginner Yoga Retreat | yoga | 90 | 16 | 90
- Esports Gaming Arena | gaming | 30 | 10 | 45
- Kayaking Adventure | kayaking | 70 | 12 | 65
- Wine Tasting Tour | wine | 95 | 21 | 99
Ranking (best-first)
Score = interest_priority * 10 + affordability_bonus, where
- interest_priority: matched category is the customer's Nth interest (1-based) -> (interest_count - N + 1); earlier interests score higher.
- affordability_bonus: round((1 - final_price / max_budget) * 5), clamped >= 0. Sort by score descending, then cheaper final price, then name.