用 account.profile.updated 同步 WhatsApp 帳戶本身的名稱
要在應用程式同步已連接 WhatsApp 帳戶本身的名稱,應處理 UnifyPort 的 account.profile.updated 事件,讀取 data.profile.display_name。此名稱優先採用商家名稱,再回落至推送名稱。更新的是帳戶資料顯示,不是客戶聯絡人、內部帳戶標籤或連線狀態。文件描述的觸發來源是 WhatsApp 名稱事件,不能視為所有渠道通用的個人資料通知。
重點
- 用工作空間、provider 及
account_id識別帳戶,不要用顯示名稱作識別碼。 - 帳戶設定的
name與渠道公開名稱分開保存。 full_sync說明資料來源,不代表訊息記錄已恢復完成。- 收到資料通知不等於授權有效或連線正在運作。
先分清畫面顯示哪個名稱
客服系統的帳戶選單可以同時展示團隊內部標籤與渠道公開名稱。更名不應自動改變負責人、路由或權限。
| 值或事件 | 代表甚麼 | 建議位置 |
|---|---|---|
帳戶設定 name | 透過帳戶設定維護的標籤 | 內部帳戶選單 |
data.profile.display_name | 根據渠道資料產生的公開名稱 | 獨立的渠道名稱欄 |
data.profile.business_name / push_name | 事件文件列出的名稱組成 | 可選的資料詳情 |
contact.updated | 聯絡人通訊錄名稱 | 客戶聯絡人檢視 |
account.status.updated | 授權或執行狀態 | 連線健康檢視 |
聯絡人名稱同步教學處理的是客戶資料,不能直接套用於自身帳戶。客戶訊息內的發送者名稱,也不能當作本身帳戶改名的證據。
取得帳戶文件分別傳回帳戶設定及 provider_profile,可作畫面的初始讀取。公開名稱缺失時應顯示未有資料,不要把內部標籤當作已觀測到的公開名稱。
account.profile.updated 的實際範圍
以下採用事件參考的示例結構。名稱和識別碼均是文件示例,並非真實客戶記錄:
{
"id": "evt_profile_7e91d2c4",
"type": "account.profile.updated",
"provider": "whatsapp",
"account_id": "acc_8c21d0",
"occurred_at": "2026-08-28T09:51:51Z",
"data": {
"account": { "provider_account_ref": "provider_account_example" },
"profile": {
"display_name": "Example Business",
"business_name": "Example Business",
"push_name": "Example Account"
},
"event": {
"kind": "account_profile_updated",
"source": "self_rename"
}
}
}
直接使用提供的 display_name,不要另建一套衝突的名稱優先規則。商家名稱優先時,即使 push_name 改變,畫面的名稱亦可能不變。
data.event.source 的文件值分為:
self_rename:已連接帳戶更改了自己的名稱。full_sync:資料來自完整同步快照。
兩者都不能指出是哪位人員操作,切勿據此建立虛構的操作人審計記錄。full_sync 亦不表示全部訊息、聯絡人、頭像或其他帳戶資料已同步。
獨立建立帳戶資料檢視
建議實作流程:
- 先訂閱,再依賴更新。 將
account.profile.updated加入所需事件集合,保留現有訂閱與簽署設定。事件篩選指南說明明確列表與萬用字元的分別。 - 驗證簽署並持久儲存。 按投遞規格,使用
signing_secret驗證X-Device-Timestamp、句點及原始請求內容的十六進制 HMAC-SHA256,並檢查時間戳是否過舊。可靠保存已驗證事件後才回覆 2xx。 - 定位現有帳戶。 使用接收端的工作空間脈絡,以及信封內的 provider 和
account_id。新名稱不能建立第二個帳戶或把對話移到另一帳戶。 - 只更新資料顯示。 保留內部標籤、客戶名稱、授權及執行狀態。名稱應以文字而非 HTML 顯示。
- 在本地記錄來源。 為檢視保存事件 ID、發生時間和來源。這是應用程式的記錄設計,不是新增 API 欄位。
以下 JavaScript 只從已驗證事件擷取名稱,不包含儲存、排序或完整接收服務:
function profileNameCandidate(event) {
if (event.type !== 'account.profile.updated' ||
event.provider !== 'whatsapp') return null;
if (typeof event.account_id !== 'string' || !event.account_id) {
throw new Error('Missing account identity');
}
const name = event.data?.profile?.display_name;
if (typeof name !== 'string') {
throw new Error('Profile display name needs review');
}
return { accountId: event.account_id, displayName: name };
}
回傳物件的鍵是應用變數。名稱缺失或類型不正確時,保留事件供檢查,不要用預設值取代整份資料。空字串應按明確的本地政策顯示為「名稱暫不可用」;不要直接沿用聯絡人事件的清除規則。
處理舊事件及初始讀取
一般事件重試以事件 ID 去重。投遞順序沒有保證:套用資料事件時按 occurred_at 排序,同時間以事件 ID 決定順序,並把去重記錄與檢視更新一併提交。
此處沒有文件保證 REST 讀取與 Webhook 共用資料版本號。若初始讀取尚未完成時已套用新事件,不要讓遲到的讀取結果覆蓋它。可將初始化與事件處理串行協調,或將讀取作為基準,再套用暫存事件。觀測有衝突時標記為待核對,不要宣稱已重建上游完整的因果順序。
UnifyPort 提供非官方接口。此事件不是更改原生資料的指令、完整資料檔案或保證重播機制。LINE、Zalo、Telegram 或 whatsapp-protocol 共用信封格式,不等於它們會發出此事件。
常見問題
為何 push_name 改了,display_name 卻沒變?
文件規則優先使用 BusinessName,再回落至 PushName。先查看提供的名稱組成,不要直接判定更新失敗。
full_sync 是否表示訊息記錄已完整同步?
不是。它只標識此資料事件的來源,不能證明訊息記錄完整或恢復成功。
收到事件後應用 PATCH 更新帳戶 name 嗎?
不應自動執行。這會更改帳戶設定,而不只是顯示渠道名稱。內部標籤修改應保持獨立並由明確操作觸發。
下一步及參考資料
按帳戶資料事件參考建立帳戶卡片。建議測試兩種來源、不同商家與推送名稱、重複及舊事件、缺失或空名稱,以及遲到的初始讀取;確認聯絡人、內部標籤及連線狀態未被更改。這些是待執行檢查,不是已完成的測試結果。
資料核對日期:2026-11-05。
令訊息接入變成一條穩定嘅產品管線。
先用統一嘅 API 跑通發送,再用標準事件將所有入站訊息接返去業務系統。