Custom MCP server that wraps a mock CRM (data/crm.json) and exposes deal data, risk assessment, and activity logging to a multi-agent sales assistant system. Implements security gates for write operations and PII redaction.
Four tools with complete schemas and descriptions, but significant gaps in parameter documentation and error handling. Tool names follow verb_noun convention (get_*, log_*, check_*). Descriptions range 80 - 180 chars, meeting the 10 - 1024 baseline. However, 2 of 4 tools lack parameter descriptions for critical inputs (deal object in check_email_grounding has no type/format guidance). No output schemas documented. Error handling is minimal, no recovery guidance, no categorization of retryable vs fatal errors. Security is well-intentioned (auth_token gating, PII redaction in logs) but token exposure in parameters violates pattern:secret-injection. Risk assessment logic is pure and testable, but tool composition could be tighter.
Check whether an email draft is grounded in deal data. Flags factual claims not supported by the deal's own data: dollar amounts, email addresses, percentages/discounts/promises.
Return the FULL record for one deal (including notes + contact) merged with its live risk assessment.
List pipeline deals as compact summaries with risk flags attached.
Record an outreach activity against a deal. THIS IS A WRITE -> auth-gated. Security gate: the call is rejected unless `auth_token` matches the server's CRM_API_TOKEN.
auth_token exposed as tool parameter violates secret-injection pattern. Credentials must use server-side injection via environment variables, not parameters. Agent traces log all parameters, secrets leak into logs and prompt history.
check_email_grounding's 'deal' parameter is typed as 'object' with no schema, format, or structure guidance. LLMs cannot infer what fields are required or how to construct the object. Needs explicit JSON Schema with required fields and type definitions.
No output schemas documented for any tool. LLMs cannot plan downstream calls or extract fields without knowing response structure. get_deals should document: returns list of {id, company, amount, stage, risk_flags}; get_deal_details should document full record structure.
Inferred effective spec: 2025-06-18+.
| Scored | Grade | Overall | Spec posture | Rubric |
|---|---|---|---|---|
| 2026-09-23 | D | 53 | 2025-06-18+ | v2 |
Error handling is absent. No recovery guidance, no error categorization (retryable vs fatal), no actionable error messages. If log_activity fails due to invalid auth_token, the LLM gets no guidance on what to do next.
get_deals and get_deal_details lack pagination parameters (limit, offset, page_size). If the pipeline grows to hundreds of deals, these tools will return unbounded results, exhausting context windows. Baseline: paginated tools accept limit (1 - 100) and offset/cursor.