调价后的新价格写入报价单;多段段前的货物带到各段,协同群不再把体积里的星号吃掉。海运字段齐了先核对再查价。

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-10-03 22:39:54 +08:00
co-authored by Cursor
parent 0a14b4cc15
commit 7c77e45e03
32 changed files with 1384 additions and 75 deletions
@@ -184,7 +184,8 @@ def handle_air_group(
return "handoff_ignore"
from agent.policy.system_exception import reply_paused_ticket, ticket_is_paused
if ticket_is_paused(ticket):
# 锁舱失败留下的暂停只拦还要打 TMS 的操作。成交、未成交和补原因不调用 TMS。
if ticket_is_paused(ticket) and not _deal_ignores_tms_pause(ticket, intent):
reply_paused_ticket(
ticket=ticket,
reply=lambda text: send_group_text(group_client_of(engine), chat_id, text),
@@ -281,6 +282,21 @@ def _handle_cabin(
)
def _deal_ignores_tms_pause(ticket: object, intent: str) -> bool:
"""
成交跟进不因 TMS 暂停而改口。
上午锁舱失败会把工单标成暂停。之后群里确认未成交、或补未成交原因,
不能再回「TMS接口异常」。锁舱、释放仍走各自的重试。
"""
if intent in {INTENT_DEAL, INTENT_LOST, INTENT_NEGOTIATE}:
return True
view = ticket_view(ticket)
status = str(view.get("status") or "").strip()
reason = str(view.get("lost_reason") or "").strip()
return status == "未成交" and not reason
def _handle_bound(
engine,
message: InboundMessage,
@@ -452,6 +452,32 @@ def finish_attach_wave(
or get_land_text_flow().session_of(sender_id)
)
wo = (sess.work_order_no if sess else "") or ""
if (
not wo
and sess
and wave
and (sess.business_line or "").upper() == "SEA"
):
# 海运先出核对卡,工单要等确定。附件键先留在书签上。
files = []
for row in wave.materials:
key = row.object_key
if not key:
continue
name = row.filename or ("image.jpg" if row.kind == "image" else "attachment.bin")
ctype = "image/jpeg" if row.kind == "image" else "application/octet-stream"
files.append(
{
"file_name": name,
"object_key": key,
"content_type": ctype,
}
)
for engine in (get_sea_text_flow(), get_air_text_flow(), get_land_text_flow()):
hit = engine.session_of(sender_id)
if hit is sess:
engine.remember_pending_files(sender_id, files)
break
if wo and wave:
ledger = None
for engine in (get_sea_text_flow(), get_air_text_flow(), get_land_text_flow()):
@@ -385,6 +385,31 @@ def finish_wave(
or get_land_text_flow().session_of(sender_id)
)
wo = (sess.work_order_no if sess else "") or ""
if (
not wo
and sess
and wave
and (sess.business_line or "").upper() == "SEA"
and wave.object_keys
):
# 海运先出核对卡,工单要等确定。图片键先留在书签上。
files = []
for i, key in enumerate(wave.object_keys):
name = wave.filenames[i] if i < len(wave.filenames) else "image.jpg"
if not key:
continue
files.append(
{
"file_name": name or "image.jpg",
"object_key": key,
"content_type": "image/jpeg",
}
)
for engine in (get_sea_text_flow(), get_air_text_flow(), get_land_text_flow()):
hit = engine.session_of(sender_id)
if hit is sess:
engine.remember_pending_files(sender_id, files)
break
if wo and wave:
ledger = None
for engine in (get_sea_text_flow(), get_air_text_flow(), get_land_text_flow()):