瞭解訊息傳送方式

如要排解持續發生的訊息傳送失敗問題,請使用 FCM 疑難排解工具,並參閱這篇網誌文章,瞭解訊息未顯示的各種原因。您也可以前往 FCM 狀態資訊主頁,確認是否有任何服務中斷情形影響 FCM。

FCM 也提供三組工具,協助您深入瞭解訊息傳送成效和策略的廣泛評估:

  • Firebase 控制台訊息傳送報告
  • Firebase Cloud Messaging Data API 匯總的 Android SDK 傳送指標
  • 將完整資料匯出至 Google BigQuery

如要將資料匯出至 BigQuery,以及使用 Firebase 控制台的「 報表」分頁,都 必須啟用 Google Analytics。如要啟用 Google Analytics,請前往 Firebase 控制台的「」設定 >「整合」分頁。匯總廣告放送資料不需要 Google Analytics 即可運作。

請注意,由於分析資料會批次處理,因此本頁面上的許多統計資料最多可能會有 24 小時的延遲。

訊息傳送報告

在 Firebase 控制台中,前往「DevOps & Engagement」 >「Messaging」 >「Reports」分頁,即可查看傳送至 Android 或 Apple 平台 FCM SDK 的訊息相關資料,包括使用通知編寫器和 FCM API 傳送的訊息:

  • 傳送:資料訊息或通知訊息已排入傳送佇列,或已成功傳遞至 APN 等第三方服務進行傳送。請注意,傳送統計資料可能會延遲幾小時。 詳情請參閱訊息生命週期。
  • 已接收 (僅適用於 Android 裝置):應用程式已收到資料訊息或通知訊息。如果接收訊息的 Android 裝置已安裝 FCM SDK 18.0.1 以上版本,系統就會提供這項資料。
  • 曝光次數 (僅適用於 Android 裝置上的通知訊息):應用程式在背景執行時,裝置上顯示通知的次數。
  • 開啟:使用者開啟通知訊息。僅在應用程式於背景運作期間收到通知時回報。

這項資料適用於所有包含通知酬載的訊息,以及所有加上標籤的資料訊息。如要進一步瞭解標籤,請參閱「在訊息中加入數據分析標籤」。

查看郵件報告時,您可以設定顯示資料的日期範圍,並選擇匯出為 CSV 檔案。您也可以依下列條件篩選:

  • 平台 (iOS 或 Android)
  • 應用程式
  • 自訂數據分析標籤

為訊息新增數據分析標籤

為郵件加上標籤有助於自訂分析,您可以依標籤或標籤組合篩選傳送統計資料。如要為透過 HTTP v1 API 傳送的訊息新增標籤,請在訊息物件中設定 fcmOptions.analyticsLabel 欄位,或在平台專屬的 AndroidFcmOptions 或 ApnsFcmOptions 欄位中設定。

Analytics 標籤是格式為 ^[a-zA-Z0-9-_.~%]{1,50}$ 的文字字串。標籤可包含大小寫英文字母、數字和下列符號:

  • -
  • ~
  • %

長度上限為 50 個半形字元。每天最多可指定 100 個不重複標籤;如果郵件新增的標籤超過這個上限,就不會列入報表。

在 Firebase 控制台訊息的「Reports」(報表) 分頁中,您可以搜尋所有現有標籤的清單,並單獨或合併套用這些標籤,篩選顯示的統計資料。

使用 FCM Data API 匯總的放送資料

Firebase 雲端通訊 Data API 可讓您擷取資訊,瞭解指定 Android 應用程式的訊息要求結果。這個 API 會提供專案中所有已啟用資料收集功能的 Android 裝置匯總資料。包括未延遲傳送的訊息百分比,以及 Android 傳輸層中延遲或捨棄的訊息數量。評估這項資料可看出訊息傳送的大致趨勢,並協助您找出有效方法,提升傳送要求的成效。如要瞭解報表中的日期範圍可用性,請參閱「匯總資料時間軸」。

API 會提供特定應用程式的所有可用資料。請參閱 API 參考文件。

資料如何細分?

傳送資料會依應用程式、日期和數據分析標籤細分。呼叫 API 時,系統會傳回日期、應用程式和數據分析標籤的各種組合資料。舉例來說,單一 androidDeliveryData JSON 物件會像這樣:

 {
  "appId": "1:23456789:android:a93a5mb1234efe56",
  "date": {
    "year": 2021,
    "month": 1,
    "day": 1
  },
  "analyticsLabel": "foo",
  "data": {
    "countMessagesAccepted": "314159",
    "messageOutcomePercents": {
      "delivered": 71,
      "pending": 15
    },
   "deliveryPerformancePercents": {
      "deliveredNoDelay": 45,
      "delayedDeviceOffline": 11
    }
  }

如何解讀指標

傳送資料會列出符合下列各項指標的郵件百分比。一則訊息可能符合多項指標。由於資料收集方式和指標匯總精細程度的限制,部分訊息結果完全不會顯示在指標中,因此下列百分比總和不會達到 100%。

接受的訊息數量

資料集只會納入 FCM 接受並傳送至 Android 裝置的訊息數量。所有百分比都以這個值做為分母。請注意,如果使用者已停用裝置上的使用狀況與診斷資訊收集功能,系統就不會將傳送給他們的訊息計入。

訊息結果百分比

MessageOutcomePercents 物件包含的欄位會提供訊息要求結果的相關資訊。所有類別皆互斥。可回答「我的訊息是否已傳送?」和「是什麼原因導致訊息遭到捨棄?」等問題。

舉例來說,如果 droppedTooManyPendingMessages 欄位的值偏高,可能表示應用程式執行個體收到的不可收合訊息數量超過 FCM 的待處理訊息上限 (100 則)。為降低這類情況,請確保應用程式會處理對 onDeletedMessages 的呼叫,並考慮傳送可收合的訊息。同樣地,如果 droppedDeviceInactive 的百分比偏高,可能代表需要更新伺服器上的註冊權杖、移除過時權杖,並取消訂閱主題。請參閱「管理 FCM 註冊權杖」,瞭解這方面的最佳做法。

推送成效百分比

DeliveryPerformancePercents 物件中的欄位會提供成功傳送的訊息相關資訊。這項工具可以回答「我的訊息是否延遲?」和「為什麼訊息會延遲?」等問題。舉例來說,如果 delayedMessageThrottled 的值偏高,就表示您已超過每部裝置的上限,應調整傳送訊息的頻率。

訊息洞察百分比

這個物件提供所有訊息傳送作業的額外資訊。priorityLowered 欄位表示優先順序從 HIGH 降至 NORMAL 的已接受郵件百分比。如果這個值偏高,請嘗試減少傳送高優先順序訊息,或確保在傳送高優先順序訊息時一律顯示通知。詳情請參閱訊息優先順序說明文件

這項資料與匯出至 BigQuery 的資料有何不同?

BigQuery Export 提供個別訊息記錄,記錄 FCM 後端接受訊息和裝置 SDK 傳送訊息的情況 (FCM 架構的步驟 2 和 4)。這項資料有助於確保個別郵件已接受並傳送。如要進一步瞭解 BigQuery 資料匯出功能,請參閱下一節。

相較之下,Firebase 雲端通訊 Data API 則提供匯總詳細資料,說明 Android 傳輸層 (或 FCM 架構的步驟 3) 中發生的具體情況。這項資料可讓您深入分析訊息從 FCM 後端傳送至 Android SDK 的情況。這項功能特別適合用來顯示郵件在傳輸期間延遲或遭捨棄的趨勢。

在某些情況下,這兩個資料集可能不完全一致,原因如下:

  • 匯總指標只會對所有訊息的一部分進行取樣
  • 匯總指標會四捨五入
  • 我們不會顯示低於隱私權門檻的指標
  • 由於我們對大量流量的管理方式進行了最佳化,因此缺少部分訊息結果。

API 限制

匯總資料時間軸

API 會傳回 7 天的歷來資料,但資料最多會延遲 5 天。舉例來說,1 月 20 日可以查看 1 月 9 日至 15 日的資料,但無法查看 1 月 16 日之後的資料。此外,我們會盡力提供資料,如果發生資料中斷,FCM 會努力修正問題,但不會在問題修正後回填資料。如果服務中斷時間較長,資料可能一週或更久都無法使用。

資料涵蓋率

Firebase 雲端通訊 Data API 提供的指標,旨在協助您瞭解訊息傳遞的大致趨勢。不過,這些範本無法涵蓋所有訊息情境。下列情況是已知結果,但不會反映在指標中。

過期的訊息

如果存留時間 (TTL) 在指定記錄日期結束後到期,系統就不會將郵件計為當天的droppedTtlExpired。

傳送訊息至閒置裝置

傳送至閒置裝置的訊息可能會顯示在資料集中,也可能不會,具體取決於訊息採用的資料路徑。這可能會導致 droppedDeviceInactive 和 pending 欄位中的計數不準確。

傳送訊息給具有特定使用者偏好設定的裝置

如果使用者已停用裝置上的使用狀況與診斷資訊收集功能,系統就不會將他們的訊息納入計算,以符合他們的偏好設定。

四捨五入和最低限制

FCM 會刻意四捨五入,並排除數量不夠大的計數。

BigQuery 資料匯出

您可以將訊息資料匯出至 BigQuery,以便進一步分析。BigQuery 可讓您使用 BigQuery SQL 分析資料、將資料匯出至其他雲端服務供應商,或將資料用於自訂機器學習模型。匯出至 BigQuery 的資料包含所有可用的訊息資料,無論訊息類型為何,或訊息是否透過 API 或通知編輯器傳送,皆會包含在內。

如果訊息傳送至搭載下列 FCM SDK 最低版本的裝置,您還可以選擇啟用應用程式的訊息傳送資料匯出功能:

  • Android 20.1.0 以上版本。
  • iOS 8.6.0 以上版本
  • Firebase Web SDK 12.14.0 以上版本

如要開始使用,請透過 Firebase 控制台將專案連結至 BigQuery:

  1. 選擇下列其中一種做法:

    • 依序前往「DevOps & Engagement」 >「Messaging」 >「Notifications composer」,然後點選頁面底部的「Access BigQuery」。

    • 依序前往「 Settings」>「 Integrations分頁」。 然後在BigQuery中,按一下「連結」。

      這個頁面會顯示專案中所有已啟用 FCM 的應用程式,並列出 FCM 匯出選項。

  2. 按照畫面上的指示啟用 BigQuery。

詳情請參閱「將 Firebase 連結至 BigQuery」。

為Cloud Messaging啟用BigQuery匯出功能後:

  • Firebase 會將資料匯出至 BigQuery。請注意,匯出資料的初始傳播作業最多可能需要 48 小時才能完成。

  • 資料集建立後,位置就無法變更,不過您可以將資料集複製到其他位置,或手動將資料集移動 (重新建立) 至其他位置。詳情請參閱「變更資料集位置」。

  • Firebase 會定期將 Firebase 專案中的資料同步至BigQuery。每日匯出作業會在太平洋時間凌晨 4:00 開始,通常會在 24 小時內完成。

  • 根據預設,專案中的所有應用程式都會連結至 BigQuery,之後新增至專案的任何應用程式也會自動連結至 BigQuery。此外,您可以控管該讓哪些應用程式傳送資料。

如要停用 BigQuery 匯出功能,請在 Firebase 控制台中取消連結專案。

啟用訊息傳送資料匯出功能

iOS+

搭載 FCM SDK 8.6.0 以上版本的 iOS 裝置,可以啟用應用程式的訊息傳遞資料匯出功能。FCM 支援快訊和背景通知的資料匯出功能。根據預設,應用程式層級會停用資料匯出功能。在應用程式執行個體層級透過程式輔助方式啟用,可讓您要求使用者授權分析訊息傳送資料 (建議做法)。如果兩者都設定,應用程式執行個體層級的值會覆寫應用程式層級的值。

啟用這些選項前,請先按照「BigQuery 資料匯出」一文所述,為專案建立 FCM-BigQuery 連結。

啟用快訊通知的傳送資料匯出功能

由於只有快訊通知可以觸發通知服務應用程式擴充功能,因此您必須在應用程式中新增通知服務擴充功能,並在服務擴充功能中呼叫這個 API,才能啟用顯示訊息追蹤功能。請參閱 Apple 說明文件,瞭解如何修改新傳送通知中的內容

每收到一則通知,就必須發出下列呼叫:

Swift

// For alert notifications, call the API inside the service extension:
class NotificationService: UNNotificationServiceExtension {
  override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) {
    Messaging.serviceExtension().exportDeliveryMetrics(withMessageInfo:request.content.userInfo)
  }
}

Objective-C

// For alert notifications, call the API inside the service extension:
@implementation NotificationService
- (void)didReceiveNotificationRequest:(UNNotificationRequest *)request
                   withContentHandler:(void (^)(UNNotificationContent *_Nonnull))contentHandler {
  [[FIRMessaging extensionHelper] exportDeliveryMetricsToBigQueryWithMessageInfo:request.content.userInfo];
}
@end

如果您使用 HTTP v1 API 建構傳送要求,請務必在酬載物件中指定 `mutable-content = 1`。

啟用背景通知的傳送資料匯出功能

如果應用程式在前景或背景運作時收到背景訊息,您可以在主要應用程式的資料訊息處理常式中,呼叫資料匯出 API。每收到一則通知,就必須發出這項呼叫:

Swift

// For background notifications, call the API inside the
// UIApplicationDelegate or NSApplicationDelegate method:
func application(_ application: UIApplication,
didReceiveRemoteNotification userInfo: [AnyHashable : Any]) {
  Messaging.serviceExtension().exportDeliveryMetricsToBigQuery(withMessageInfo:userInfo)
}

Objective-C

// For background notifications, call the API inside the
// UIApplicationDelegate or NSApplicationDelegate method:
@implementation AppDelegate
- (void)application:(UIApplication *)application
    didReceiveRemoteNotification:(NSDictionary *)userInfo
          fetchCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler {
  [[FIRMessaging extensionHelper] exportDeliveryMetricsToBigQueryWithMessageInfo:userInfo];
}
@end

Android

搭載 FCM SDK 20.1.0 以上版本的 Android 裝置,可啟用應用程式的訊息傳遞資料匯出功能。應用程式層級預設會停用資料匯出功能。在應用程式執行個體層級透過程式輔助方式啟用,可讓您要求使用者授權分析其訊息傳送資料 (建議做法)。如果兩者都設定,應用程式執行個體層級的值會覆寫應用程式層級的值。

啟用這些選項前,請先按照「BigQuery 資料匯出」一文所述,為專案建立 FCM-BiqQuery 連結。

啟用應用程式執行個體的傳送資料匯出功能

在大多數情況下,建議您只在應用程式執行個體層級啟用訊息傳送資料匯出功能,並在應用程式層級停用。

FirebaseMessaging.getInstance().setDeliveryMetricsExportToBigQuery(true);

啟用應用程式的傳送資料匯出功能

如果您想在應用程式層級啟用匯出功能,請務必「不要」呼叫 setDeliveryMetricsExportToBigQuery 方法,並在應用程式資訊清單中,將下列屬性新增至應用程式物件:

<application>
  <meta-data android:name="delivery_metrics_exported_to_big_query_enabled"
      android:value="true" />
</application>

網頁

FCM SDK for Web 12.14.0 以上版本支援匯出放送資料。根據預設,應用程式層級會停用資料匯出功能。在應用程式執行個體層級透過程式輔助方式啟用,可讓您要求使用者授權分析訊息傳送資料 (建議做法)。如果兩者都設定,應用程式執行個體層級的值會覆寫應用程式層級的值。 當使用者同意或拒絕資料收集時,應用程式應為每個應用程式例項設定實驗性啟用或停用標記,如下所示:

// userConsent holds the decision of the user to give big query export consent.
const userConsent = ...;

const messaging = getMessagingInSw(app);

experimentalSetDeliveryMetricsExportedToBigQueryEnabled(messaging, userConsent);

哪些資料會匯出至 BigQuery?

請注意,指定過時權杖或無效註冊可能會導致部分統計資料膨脹。

匯出資料表的結構定義如下:

_PARTITIONTIME TIMESTAMP 這個虛擬資料欄含有載入資料當天開始的時間戳記 (採用世界標準時間)。對於 YYYYMMDD 分區,這個虛擬資料欄包含 TIMESTAMP('YYYY-MM-DD') 值。
event_timestamp TIMESTAMP 伺服器記錄的事件時間戳記
project_number INTEGER 專案編號可識別傳送訊息的專案
message_id STRING 郵件 ID 可用來識別郵件。訊息 ID 是根據應用程式 ID 和時間戳記產生,在某些情況下可能不是全域不重複。
instance_id STRING 訊息傳送目標應用程式的專屬 ID (如有)。可以是執行個體 ID 或 Firebase 安裝 ID。
message_type STRING 訊息類型。可以是通知訊息或資料訊息。主題用於識別主題或廣告活動傳送的原始訊息;後續訊息則為通知或資料訊息。
sdk_platform STRING 接收端應用程式的平台
app_name STRING Android 應用程式的套件名稱或 iOS 應用程式的軟體包 ID
collapse_key STRING 收合鍵可識別一組可收合的訊息。如果裝置未連線,系統只會將含有指定摺疊鍵的最後一則訊息排入佇列,以便最終傳送
優先順序 INTEGER 訊息的優先順序。5 代表「一般」優先順序,10 代表「高」優先順序。
ttl INTEGER 這項參數指定如果裝置離線,訊息應在 FCM 儲存空間中保留多久 (以秒為單位)
主題 STRING 訊息傳送到的主題名稱 (如適用)
bulk_id INTEGER 大量 ID 可識別一組相關訊息,例如傳送至某個主題的特定訊息
事件 STRING 事件類型。可能的值包括:
  • MESSAGE_ACCEPTED:FCM 伺服器已收到訊息,且要求有效。
  • MESSAGE_DELIVERED:訊息已傳送至裝置上的應用程式 FCM SDK。根據預設,這個欄位不會傳播。如要啟用,請按照 setDeliveryMetricsExportToBigQuery(boolean) 中的指示操作。
  • MISSING_REGISTRATIONS:要求因缺少註冊資訊而遭拒。
  • UNAUTHORIZED_REGISTRATION:訊息遭到拒絕,因為寄件者未獲授權傳送至註冊;
  • MESSAGE_RECEIVED_INTERNAL_ERROR:處理訊息要求時發生不明錯誤。
  • MISMATCH_SENDER_ID:傳送訊息的要求遭到拒絕,因為傳送訊息的寄件者 ID 與為端點宣告的 ID 不符。
  • QUOTA_EXCEEDED:配額不足,因此傳送訊息的要求遭拒。
  • INVALID_REGISTRATION:傳送訊息的要求因註冊無效而遭拒。
  • INVALID_PACKAGE_NAME:套件名稱無效,因此傳送訊息的要求遭拒。
  • INVALID_APNS_CREDENTIAL:由於 APNS 憑證無效,傳送訊息的要求遭到拒絕。
  • INVALID_PARAMETERS:傳送訊息的要求因參數無效而遭拒。
  • PAYLOAD_TOO_LARGE:傳送訊息的要求遭拒,因為酬載超過限制。
  • AUTHENTICATION_ERROR:由於驗證錯誤,傳送訊息的要求遭到拒絕 (請檢查用於傳送訊息的 API 金鑰);
  • INVALID_TTL:傳送訊息的要求因存留時間無效而遭拒。
analytics_label STRING 使用 HTTP v1 API 時,您可以在傳送訊息時設定數據分析標籤,以便標記訊息用於數據分析

匯出資料後可以做什麼?

下列各節提供查詢範例,說明如何在 BigQuery 中對匯出的 FCM 資料執行查詢。

依應用程式計算傳送的訊息數

SELECT app_name, COUNT(1)
FROM `project ID.firebase_messaging.data`
WHERE
  _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
  AND event = 'MESSAGE_ACCEPTED'
  AND message_id != ''
GROUP BY 1;

計算訊息指定的專屬應用程式執行個體數量

SELECT COUNT(DISTINCT instance_id)
FROM `project ID.firebase_messaging.data`
WHERE
  _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
  AND event = 'MESSAGE_ACCEPTED';

計算傳送的通知訊息

SELECT COUNT(1)
FROM `project ID.firebase_messaging.data`
WHERE
  _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
  AND event = 'MESSAGE_ACCEPTED'
  AND message_type = 'DISPLAY_NOTIFICATION';

計算傳送的資料訊息

SELECT COUNT(1)
FROM `project ID.firebase_messaging.data`
WHERE
  _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
  AND event = 'MESSAGE_ACCEPTED'
  AND message_type = 'DATA_MESSAGE';

計算傳送至主題或廣告活動的訊息數量

SELECT COUNT(1)
FROM `project ID.firebase_messaging.data`
WHERE
  _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
  AND event = 'MESSAGE_ACCEPTED'
  AND bulk_id = your bulk id AND message_id != '';

如要追蹤傳送至特定主題的訊息事件,請修改這項查詢,將 AND message_id != '' 替換為 AND message_id = <your message id>;。

計算特定主題或廣告活動的展開時間長度

展開開始時間是收到原始要求的時間,結束時間則是建立最後一則指定單一執行個體的個別訊息的時間。

SELECT
  TIMESTAMP_DIFF(
    end_timestamp, start_timestamp, MILLISECOND
  ) AS fanout_duration_ms,
  end_timestamp,
  start_timestamp
FROM (
    SELECT MAX(event_timestamp) AS end_timestamp
    FROM `project ID.firebase_messaging.data`
    WHERE
      _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
      AND event = 'MESSAGE_ACCEPTED'
      AND bulk_id = your bulk id
  ) sent
  CROSS JOIN (
    SELECT event_timestamp AS start_timestamp
    FROM `project ID.firebase_messaging.data`
    WHERE
      _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
      AND event = 'MESSAGE_ACCEPTED'
      AND bulk_id = your bulk id
      AND message_type = 'TOPIC'
  ) initial_message;

已送達訊息的數量百分比

SELECT
  messages_sent,
  messages_delivered,
  messages_delivered / messages_sent * 100 AS percent_delivered
FROM (
    SELECT COUNT(DISTINCT CONCAT(message_id, instance_id)) AS messages_sent
    FROM `project ID.firebase_messaging.data`
    WHERE
      _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
      AND event = 'MESSAGE_ACCEPTED'
  ) sent
  CROSS JOIN (
    SELECT COUNT(DISTINCT CONCAT(message_id, instance_id)) AS messages_delivered
    FROM `project ID.firebase_messaging.data`
    WHERE
      _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
      AND (event = 'MESSAGE_DELIVERED'
      AND message_id
      IN (
        SELECT message_id FROM `project ID.firebase_messaging.data`
        WHERE
          _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
          AND event = 'MESSAGE_ACCEPTED'
        GROUP BY 1
      )
  ) delivered;

追蹤指定訊息 ID 和執行個體 ID 的所有事件

SELECT *
FROM `project ID.firebase_messaging.data`
WHERE
    _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
    AND message_id = 'your message id'
    AND instance_id = 'your instance id'
ORDER BY event_timestamp;

計算指定訊息 ID 和執行個體 ID 的延遲時間

SELECT
  TIMESTAMP_DIFF(
    MAX(delivered_time), MIN(accepted_time), MILLISECOND
  ) AS latency_ms
FROM (
    SELECT event_timestamp AS accepted_time
    FROM `project ID.firebase_messaging.data`
    WHERE
      _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD')
      AND message_id = 'your message id'
      AND instance_id = 'your instance id'
      AND event = 'MESSAGE_ACCEPTED'
  ) sent
  CROSS JOIN (
    SELECT event_timestamp AS delivered_time
    FROM `project ID.firebase_messaging.data`
    WHERE
      _PARTITIONTIME = TIMESTAMP('date as YYYY-MM-DD') AND
      message_id = 'your message id' AND instance_id = 'your instance id'
      AND (event = 'MESSAGE_DELIVERED'
  ) delivered;