export_out_of_province_port_data.py 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. class ExportOutOfProvincePortDataTool:
  2. name = 'export_out_of_province_port_data'
  3. route_path = '/mcp/tools/exportOutOfProvincePortData'
  4. def __init__(self, api_client=None):
  5. self.api_client = api_client
  6. def metadata(self):
  7. return {
  8. 'name': self.name,
  9. 'description': (
  10. '导出后台排舱单列表中的省外进港资料,并返回可下载文件 URL。'
  11. '只能在用户明确要求导出省外进港资料,并明确提供排舱单号和'
  12. '宁波、上海或美森资料类型时调用。排舱单号不是系统订单号、'
  13. '客户参考号、快递单号、柜号、SO 号或 Shipment ID;不得根据'
  14. '号码格式猜测。号码类型或资料类型不明确时先询问用户。'
  15. '一次只能选择一种资料类型;用户要求多个类型时应分别调用。'
  16. '参数名仅用于工具调用;向用户回答时只能使用中文业务名称,'
  17. '不得展示内部参数名。'
  18. ),
  19. 'input_schema': {
  20. 'type': 'object',
  21. 'properties': {
  22. 'outbound_numbers': {
  23. 'type': 'array',
  24. 'items': {
  25. 'type': 'string',
  26. 'minLength': 1,
  27. 'maxLength': 100,
  28. },
  29. 'minItems': 1,
  30. 'maxItems': 100,
  31. 'uniqueItems': True,
  32. 'description': (
  33. '要导出的排舱单号数组。排舱单号是后台排舱单列表中的'
  34. '业务单号,不是系统订单号、客户参考号、快递单号、柜号、'
  35. 'SO号或Shipment ID。只能使用用户明确提供并确认类型为'
  36. '排舱单号的值,不得根据号码格式猜测。'
  37. ),
  38. 'examples': [[
  39. 'PC202607140001',
  40. 'PC202607140002',
  41. ]],
  42. },
  43. 'file_type': {
  44. 'type': 'string',
  45. 'enum': ['NB', 'SH', 'MS'],
  46. 'description': (
  47. '进港资料类型:NB=宁波进港资料,SH=上海进港资料,'
  48. 'MS=美森进港资料。必须根据用户明确选择传值;'
  49. '用户未说明时先询问,不得默认选择。'
  50. ),
  51. 'examples': ['NB'],
  52. },
  53. },
  54. 'required': ['outbound_numbers', 'file_type'],
  55. 'additionalProperties': False,
  56. },
  57. }
  58. def call(
  59. self,
  60. outbound_numbers,
  61. file_type,
  62. request_id='rq_export_out_of_province_port_data',
  63. ):
  64. if self.api_client is None:
  65. raise RuntimeError(
  66. 'api client is required for export_out_of_province_port_data'
  67. )
  68. numbers = self._normalize_outbound_numbers(outbound_numbers)
  69. normalized_type = str(file_type or '').strip().upper()
  70. if normalized_type not in ('NB', 'SH', 'MS'):
  71. raise ValueError('file_type must be NB, SH, or MS')
  72. return self.api_client.call_tool(
  73. self.name,
  74. self.route_path,
  75. {
  76. 'outbound_numbers': numbers,
  77. 'file_type': normalized_type,
  78. },
  79. request_id,
  80. )
  81. @staticmethod
  82. def _normalize_outbound_numbers(values):
  83. if not isinstance(values, list):
  84. raise ValueError('outbound_numbers must be an array')
  85. numbers = []
  86. for value in values:
  87. if not isinstance(value, str):
  88. raise ValueError('outbound_numbers must contain strings')
  89. value = value.strip()
  90. if not value:
  91. continue
  92. if len(value) > 100:
  93. raise ValueError('outbound number is too long')
  94. if value not in numbers:
  95. numbers.append(value)
  96. if not numbers or len(numbers) > 100:
  97. raise ValueError('outbound_numbers must contain 1 to 100 values')
  98. return numbers