The RMS MCP Server exposes 26 tools for ocean freight rate management with significant quality gaps. While tool names follow the verb_noun convention (price_enquiry, search_rates, create_freight_rate, etc.), descriptions are present but often lack depth and context. Most critically, input schemas are visible in the provided source but are incomplete: many parameters lack descriptions, and output schemas are entirely undocumented. The server shows poor composition discipline, tools like price_enquiry, search_rates, and create_freight_rate operate on overlapping domains (pricing/rates) but lack clear differentiation guidance. Error handling is not evident in the provided code. Parameter validation rules are not specified (e.g., what makes a valid UN/LOCODE format? What are valid container types beyond the examples given?). The tools are READ_ONLY or WRITE-classified correctly, but no security patterns (permission gates, audit logging) are visible. Overall, this is a domain-specific tool collection that is functional but lacks the rigor expected of production-grade agent toolkits.
Output schemas entirely undocumented. Not a single tool explicitly documents what fields it returns, what types those fields have, or what the LLM should expect. This violates the pattern:tool requirement that tools document their output schema.
Add explicit output schema documentation to every tool. For each tool, document: what object is returned, what fields it has (name, type, description), and what those fields mean. Example: 'Returns {rate_id: number, buy_amount: number, vendor_id: number, valid_from: ISO8601_date, is_preferred: boolean, status: "active"|"expired"}'.
Expand descriptions for all parameters lacking them. For example, update_margin_rule's 'updates' parameter should describe: 'Object with fields to update: margin_percentage (number, 0-100), margin_fixed (number, currency units), valid_from/valid_to (ISO 8601 dates), rule_name (string 1-100 chars).'
Add parameter constraints and validation rules to descriptions. Example: 'pol_code: UN/LOCODE, 5 uppercase alphanumeric chars (e.g., CNSHA, USLAX)' and 'container_type: one of 20GP, 20HC, 40GP, 40HC, 45HC' rather than just 'Container type'.
Document error cases and recovery guidance for each write/delete tool. Example for create_freight_rate: 'Error: Invalid vendor_id (vendor does not exist). Call list_vendors() to find valid IDs.' and 'Error: Rate already exists for this route/container/vendor combination. Call search_rates() to find existing rates and update them instead.'
Add pagination support (limit, offset, total_count) to all list and search tools. Example: search_rates should accept 'limit' (1-100, default 20) and 'offset' (0 by default) parameters and return {results: [], total: 1250, limit: 20, offset: 0} so agents can iterate through large result sets.
Parameter descriptions are missing or generic for many tools. Examples: get_surcharges lacks description for container_type parameter; update_surcharge updates field lacks details on what can be updated; list_vendors filters are undocumented. LLMs cannot infer valid inputs without explicit parameter descriptions.
No error handling guidance visible. Tools have no documented error cases, recovery steps, or actionable error messages. An LLM encountering a failed call (invalid port code, duplicate surcharge, etc.) has no guidance on how to proceed or self-correct.
No security patterns enforced or documented. No visible permission gates, audit logging, or secret injection mechanisms. Tools that modify freight rates and surcharges (write operations) lack any documented authorization checks or audit trails.
Tool composition discipline is weak. Multiple tools operate on closely related domains (rates, surcharges, margins, pricing) without clear differentiation. Tools like price_enquiry (compound operation) and create_freight_rate (atomic operation) are adjacent concerns but lack guidance on when to use each.
No pagination support visible for list tools. list_vendors, list_carriers, list_services, list_margin_rules, list_charge_codes do not accept limit/offset parameters or document result limits. An LLM cannot handle large result sets efficiently.
Input validation rules not specified. Parameters like container_type, pol_code, pod_code, and charge_code accept enums or constrained values but lack format constraints or validation guidance in descriptions. LLMs will guess at valid values.
Destructive operations (delete_margin_rule) lack confirmation or dry-run support. The tool description does not warn about irreversibility or offer a way to preview the delete before execution, increasing agent error risk.
delete_margin_rule
Implement permission gates and audit logging for all write/destructive operations. Document required permissions (e.g., 'Requires scope: write:rates') and ensure all calls are logged with user_id, tool_name, parameters, timestamp, and result.
Clarify tool selection guidance for overlapping domains. Add a note to price_enquiry explaining it is a high-level composite operation (find best rates, apply margins, return final pricing), while search_rates returns raw vendor rates and create_freight_rate creates individual rate records. Help agents understand when to use each.
Add confirmation step or dry-run support to delete_margin_rule. Either require a second parameter (confirmed: true) or offer a separate preview_delete_margin_rule tool that shows what will be deleted before execution.
Add UOM (unit of measure) and natural language output support. For numeric results (pricing, transit times), return both machine values and human-readable summaries (e.g., 'USD 1,500 per 40HC' instead of just 1500).
Document chaining IDs: ensure that tools that search (search_rates, search_locations) return IDs that downstream create/update tools accept. Verify that search_rates returns vendor_id (used by create_freight_rate) and pol_code/pod_code (used by create_location).