# 顺丰物流推送完整链路

## 架构

```
pull_orders.py → shipment_pipeline.py → sf_delivery_watchdog.py → 飞书卡片
(MCP拉订单)      (顺丰API查轨迹)         (状态diff+推送)            (内嵌浏览器)
```

## 关键文件

| 文件 | 位置 | 用途 |
|------|------|------|
| pull_orders.py | 数据/ | MCP销售订单拉取 |
| pull_customers.py | 数据/ | MCP客户数据拉取 |
| pull_complaints.py | 数据/ | MCP客诉数据拉取 |
| pull_contacts.py | 数据/ | 联系人聚合 |
| shipment_pipeline.py | 脚本/ | 顺丰API轨迹查询 |
| sf_delivery_watchdog.py | ~/.hermes/scripts/ | 定时推送主脚本 |
| cb_sync.sh | 脚本/ | CloudBase全量同步 |

## 顺丰API凭证

```python
SF_PARTNER_ID = "BRSWK5CQ08HV"
SF_SECRET = "V7JDT0azGX93pnIXRyZe9zvlzY6fk1rC"
```

## 飞书API凭证

```bash
FEISHU_APP_ID=cli_aac5af01fd625bdd
FEISHU_APP_SECRET=FxAZsdQWVRuPOIK8byWDccwNTan7AadN
```

已知open_id: 刘新元=`ou_fd1028935f5d87fac78bd6356cbe395e`

## 飞书卡片：内嵌浏览器打开方案

| 方式 | 桌面端 | 移动端 | 推荐 |
|------|:--:|:--:|:--:|
| 按钮 `url` | ❌ 外部浏览器 | ✅ 内嵌 | ✗ |
| AppLink `applink.feishu.cn` | ❌ 外部浏览器+重定向 | ❌ | ✗ |
| 内联markdown链接 `[文字](url)` | ✅ 内嵌 | ✅ 内嵌 | ✅ |

**结论**：飞书桌面端内嵌浏览器只能用卡片body中的markdown链接。按钮URL无论怎么配置都会被桌面端用外部浏览器打开。

```python
# ✅ 正确：内联markdown链接
body = f"**✅ 已签收**\n\n单号：{oid}\n金额：{amt}\n\n[📋 查看订单详情]({url})"
card_elements = [{'tag': 'div', 'text': {'tag': 'lark_md', 'content': body}}]

# ❌ 废弃方案
# 按钮 url → 桌面端外部浏览器
# applink.feishu.cn → 不生效
```

## URL跳转格式

卡片内链接格式：`WORKBENCH_URL?tracking=SFxxx#orders`

**为什么用 `?tracking=` 不用 `#orders:SFxxx`**：
飞书WebView会把hash中的 `?` 解析为search参数截断。用search参数+hash组合最可靠。

### 前端 `_pendingTracking` 模式

```javascript
// 在页面JS最开始立即捕获（在init()之前）
var _pendingTracking = (function() {
  var s = window.location.search;
  var m = s.match(/[?&]tracking=([^&]+)/);
  return m ? decodeURIComponent(m[1]) : '';
})();
```

然后在 `loadData` 的 Promise 回调中使用：
```javascript
var tracking = _pendingTracking || '';
// set orderState.filterText + _autoExpandTracking + switchTab('orders')
// renderOrders末尾 setTimeout toggleShipmentDetail + scrollIntoView
```

## 每条订单单独推送

一个卡片 = 一个订单，包含：单号、金额、快递号、收货人

```
📦 已签收
━━━━━━━━━━━━━
✅ 订单已签收

📋 单号：ZHBR260724027
💰 金额：¥371,396
📦 快递：SF5112860018518
📍 收货：蔡琦｜湖南省长沙市岳麓区

[📋 查看订单详情]  ← 内联链接，点击内嵌打开
```

## 顺丰API约束

- checkPhoneNo必传（收货人手机后4位），不传全部返回无数据
- 批量最多10单/次，需按手机号分组
- 成功率<50%=API异常，放弃写入（安全闸）

## 销售员匹配

MCP销售订单无销售员字段。需从客户owner反向查。当前大量客户owner非@biori.com邮箱，暂统一推送刘新元。后期需IT修正飞书客户owner。
