Identify, score, and re-engage lapsed customers with personalized win-back campaigns.
Single tool 'run' with adequate schema and parameter documentation, but severely limited by generic naming, missing error handling guidance, and lack of LLM-specific optimizations. The tool name 'run' is a critical anti-pattern, it is generic and does not convey action. No input validation schema constraints (enums, ranges, patterns). Output schema is documented but response includes verbose fields that don't match upstream tool chainability. No destructive operation warnings. Server lacks pagination, error recovery guidance, and schema constraints that production agents require.
Run win-back analysis and campaign generation.
Tool name 'run' is generic and violates verb_noun naming convention. Does not convey 'win-back analysis' action. LLMs cannot infer intent from 'run' alone, should be 'analyze_lapsed_customers' or 'generate_winback_campaigns'.
Input schema lacks constraints. 'customers' parameter accepts unbounded list[dict] with no documented required fields, type validation, or validation error guidance. 'max_discount_pct' is a float with no bounds (0-100 expected); LLMs could pass negative or >100 values without error. 'brand_name' has no length constraints.
No error handling or recovery guidance in tool description. If invalid customer data is passed (missing 'id', malformed 'days_since_purchase'), the tool fails silently with a generic error. No actionable recovery hints (e.g. 'Ensure each customer dict has id, days_since_purchase, total_spend, total_orders, avg_order_value, preferred_category').
| Scored | Grade | Overall | Spec posture | Rubric |
|---|---|---|---|---|
| 2026-09-23 | F | 41 | 2026-07-28+ | v2 |
Output schema not formally documented for LLM consumption. Response includes verbose per-customer fields ('send_day', 'hook', nested 'email_sequence') that are implementation details. No pagination support, if 1000+ customers are analyzed, response explodes context. No limit stated in description.
Tool description (157 chars) is under the LLM-optimized range (180-250 chars). Missing key context: When to use this tool? What does 'win-back' mean? What are output guarantees (e.g. customers sorted by priority)? No indication that output is paginated or limited.
Parameter 'customers' description does not specify valid field names or consequences of missing fields. Code silently defaults missing values (e.g. 'name' defaults to f'Customer {id}', 'days_since_purchase' defaults to 180) without documenting these defaults in the schema. LLMs cannot know what will happen if fields are omitted.
No idempotency or state mutation warnings. Tool performs state-like analysis (scoring, segmentation) on input but no indication whether repeated calls with same input produce identical results or if there are side effects.