Engage SDK 叢集發布指南

本指南提供一套發布叢集的規範,供開發人員整合 Engage SDK 時使用。

推薦叢集

叢集標題

建議您提供獨特的相關叢集標題,讓使用者深入瞭解叢集內容。

以下是根據內容提供的叢集標題範例:

  • 購物相關叢集
    • 限時優惠
    • 每週必買
    • 與購買的 Pixel Buds 相關
    • 女用雨靴
  • 健康類書籍叢集
    • 身心健康
    • 為您推薦的健康書籍
    • 健身類暢銷書

叢集內容

發布推薦叢集時,開發人員必須考量使用者是否已登入其應用程式。

使用者已登入的情況

如果使用者已登入開發人員應用程式,則建議發布個人化或使用者產生的內容叢集。個人化及使用者產生的內容更符合使用者需求,因此他們會更願意透過 Google 途徑造訪開發人員應用程式。

  • 可發布個人化推薦內容。
    • 以下列舉一些個人化推薦內容範例:
      • 根據使用者觀看記錄推薦的熱門影片。
      • 與使用者閱讀記錄所列書籍類似的書籍。
      • 使用者喜愛藝人的歌曲。
  • 可發布使用者產生的內容資料庫。
    • 以下列舉一些使用者產生的內容資料庫範例:
      • 開發人員應用程式提供的使用者待觀看影劇清單。
      • 開發人員應用程式自行彙整的使用者最愛藝人名單。
推薦類型 內容更新策略 內容更新指南
個人化推薦內容

寬鬆

建議您每天更新一次推薦內容,讓使用者能夠每天看到新的推薦內容。

由於使用者對推薦內容沒有確切的期望,內容更新策略可以十分寬鬆。
使用者產生的內容資料庫

嚴格

建議您在使用者退出開發人員應用程式時更新內容資料庫。

這類內容必須和 Google 途徑上顯示的資料保持同步。這是因為使用者會期待一組確切的內容,這一點與個人化推薦內容不同。任何延遲發布的情況都會混淆使用者,因此必須嚴格執行內容更新策略。

使用者未登入的情況

如果使用者尚未登入開發人員應用程式,我們仍建議您發布叢集,鼓勵使用者透過 Google 途徑造訪開發人員應用程式。

  • 應發布非個人化推薦叢集。
    • 以下列舉一些非個人化推薦內容範例:
      • 今年最暢銷的 10 本書。
      • 新上映的電影。
      • 發燒 Podcast。
  • 發布登入資訊卡。
    • 為鼓勵使用者登入開發人員應用程式,開發人員可以選擇一併發布登入資訊卡和非個人化推薦叢集。如要進一步瞭解如何發布登入資訊卡,請參閱以下章節。
推薦類型 內容更新策略 內容更新指南
非個人化推薦內容

寬鬆

建議您每天更新一次推薦內容。

由於使用者對推薦內容沒有確切的期望,內容更新策略可以十分寬鬆。
推薦內容中的登入資訊卡

嚴格

建議您在使用者退出開發人員應用程式時更新登入資訊卡狀態。

使用者登入後,開發人員必須呼叫 deleteUserManagementCluster() API 才能刪除資訊卡。

登入狀態必須與 Google 途徑保持同步。如果使用者已登入帳戶,卻在 Google 途徑上看到登入資訊卡,會因而感到困惑。因此必須嚴格執行內容更新策略。

接續叢集

發布接續叢集時,開發人員必須考量使用者是否已登入其應用程式。

使用者已登入的情況

  • 應發布使用者產生的接續叢集。
    • 以下列舉一些使用者產生的接續叢集範例:
      • 從使用者停下來的地方繼續觀看。
      • 從使用者停下來的地方繼續閱讀。
接續類型 內容更新策略 內容更新指南
使用者產生的接續叢集

嚴格

建議您在使用者退出開發人員應用程式時更新內容資料庫。

這類內容必須和 Google 途徑上顯示的資料保持同步。這是因為使用者會期待一組確切的內容,這一點與個人化推薦內容不同。任何延遲發布的情況都會混淆使用者,因此必須嚴格執行內容更新策略。

使用者未登入的情況

接續歷程主要適用於已登入的使用者,但如果應用程式支援訪客工作階段,您也可以為登出的使用者發布接續叢集。

使用者管理叢集

使用者管理叢集的主要目標,是提醒使用者在提供者應用程式中執行特定動作。登入動作會將使用者導向應用程式的登入頁面,方便應用程式發布內容,或提供更個人化的內容。

登入資訊卡

屬性 必要性 說明
動作 URI 必要 導向動作的深層連結,也就是前往應用程式登入頁面
圖片 選用 - 如未提供,則必須提供標題

資訊卡上顯示的圖片

解析度 1264x712、顯示比例 16x9 的圖片

標題 選用 - 如未提供,則必須提供圖片 資訊卡上的標題
動作文字 選用 行動號召中顯示的文字,也就是「登入」
副標題 選用 資訊卡上的選用副標題

Kotlin


var SIGN_IN_CARD_ENTITY =
      SignInCardEntity.Builder()
          .addPosterImage(
              Image.Builder()
                  .setImageUri(Uri.parse("http://www.x.com/image.png"))
                  .setImageHeightInPixel(500)
                  .setImageWidthInPixel(500)
                  .build())
          .setActionText("Sign In")
          .setActionUri(Uri.parse("http://xx.com/signin"))
          .build()

appEngagePublishClient.publishUserAccountManagementRequest(
            PublishUserAccountManagementRequest.Builder()
                .setSignInCardEntity(SIGN_IN_CARD_ENTITY)
                .build());

Java


SignInCardEntity SIGN_IN_CARD_ENTITY =
      new SignInCardEntity.Builder()
          .addPosterImage(
              new Image.Builder()
                  .setImageUri(Uri.parse("http://www.x.com/image.png"))
                  .setImageHeightInPixel(500)
                  .setImageWidthInPixel(500)
                  .build())
          .setActionText("Sign In")
          .setActionUri(Uri.parse("http://xx.com/signin"))
          .build();

appEngagePublishClient.publishUserAccountManagementRequest(
            new PublishUserAccountManagementRequest.Builder()
                .setSignInCardEntity(SIGN_IN_CARD_ENTITY)
                .build());

使用者登入後,開發人員必須呼叫 deleteUserManagementCluster() API 才能刪除資訊卡。

更新發布狀態

如因內部業務原因,導致無法發布任何叢集,我們強烈建議使用 updatePublishStatus API 更新發布狀態。這麼做很重要,因為:

  • 在所有情況下,提供狀態都至關重要,即使內容已發布 (STATUS == PUBLISHED) 也一樣。如此一來,才能為資訊主頁填入資料,並以明確的狀態表示整合項目的健康度和其他指標。
  • 如未發布內容,但整合狀態未遭中斷 (STATUS == NOT_PUBLISHED),Google 便可避免在應用程式健康資訊主頁中觸發快訊。這可從提供者的角度確認內容是因預期的情況而未發布。
  • 這有助開發人員深入瞭解資料何時已發布或未發布。
  • Google 可能會使用狀態碼,提醒使用者在應用程式中執行特定動作,以便查看或解決應用程式內容。

以下為符合資格的發布狀態碼清單:

// Content is published
AppEngagePublishStatusCode.PUBLISHED,

// Content is not published as user is not signed in
AppEngagePublishStatusCode.NOT_PUBLISHED_REQUIRES_SIGN_IN,

// Content is not published as user is not subscribed
AppEngagePublishStatusCode.NOT_PUBLISHED_REQUIRES_SUBSCRIPTION,

// Content is not published as user location is ineligible
AppEngagePublishStatusCode.NOT_PUBLISHED_INELIGIBLE_LOCATION,

// Content is not published as there is no eligible content
AppEngagePublishStatusCode.NOT_PUBLISHED_NO_ELIGIBLE_CONTENT,

// Content is not published as the feature is disabled by the client
// Available in v1.3.1
AppEngagePublishStatusCode.NOT_PUBLISHED_FEATURE_DISABLED_BY_CLIENT,

// Content is not published as the feature due to a client error
// Available in v1.3.1
AppEngagePublishStatusCode.NOT_PUBLISHED_CLIENT_ERROR,

// Content is not published as the feature due to a service error
// Available in v1.3.1
AppEngagePublishStatusCode.NOT_PUBLISHED_SERVICE_ERROR,

// Content is not published due to some other reason
// Reach out to engage-developers@ before using this enum.
AppEngagePublishStatusCode.NOT_PUBLISHED_OTHER

如果內容因使用者未登入而未發布,建議您發布登入資訊卡。如因任何原因導致提供者無法發布登入資訊卡,建議您呼叫 updatePublishStatus API,並使用狀態碼 NOT_PUBLISHED_REQUIRES_SIGN_IN

Kotlin


client.updatePublishStatus(
   PublishStatusRequest.Builder()
     .setStatusCode(AppEngagePublishStatusCode.NOT_PUBLISHED_REQUIRES_SIGN_IN)
     .build())

Java


client.updatePublishStatus(
    new PublishStatusRequest.Builder()
        .setStatusCode(AppEngagePublishStatusCode.NOT_PUBLISHED_REQUIRES_SIGN_IN)
        .build());

用於發布叢集的 WorkManager

建議您使用 WorkManager 發布叢集,因為在必須結合「機會式執行」和「保證執行」的背景工作上,這是建議的解決方案。

  • WorkManager 會盡快執行背景工作。
  • WorkManager 會透過邏輯確保在不同情況下都能開始工作,即便使用者離開應用程式也一樣。

當使用者離開應用程式時,建議您啟動背景工作,同時發布接續叢集和推薦叢集。您可以利用 Activity.onStop() 來處理這個邏輯,在使用者離開應用程式時呼叫此方法。

建議您使用 PeriodicWorkRequest 安排週期性工作,每 24 小時發布叢集一次。開發人員可使用 CANCEL_AND_REENQUEUE 政策觸發工作,確保在每次使用者離開應用程式時,WorkManager 都會傳送更新後的資料。這樣做可避免使用者看到過時的資料。

以下範例會示範這個做法:

// Define the PublishClusters Worker requiring input
public class PublishClusters extends Worker {

   public PublishClusters(Context appContext, WorkerParameters workerParams) {
       super(appContext, workerParams);
   }

   @NonNull
   @Override
   public Result doWork() {
       // publish clusters
   }
   ...
}

public static void schedulePublishClusters(Context appContext) {
// Create a PeriodicWorkRequest to schedule a recurring job to update
// clusters at a regular interval
PeriodicWorkRequest publishClustersEntertainmentSpace =
// Define the time for the periodic job
       new PeriodicWorkRequest.Builder(PublishClusters.class, 24, TimeUnit.HOURS)
// Set up a tag for the worker.
// Tags are Unique identifier, which can be used to identify that work
// later in order to cancel the work or observe its progress.
          .addTag("Publish Clusters to Entertainment Space")
          .build();

// Trigger Periodic Job, this will ensure that the periodic job is triggered
// only once since we have defined a uniqueWorkName
WorkManager.getInstance(appContext).enqueueUniquePeriodicWork(
// uniqueWorkName
     "publishClustersEntertainmentSpace",
// If a work with the uniqueWorkName is already running, it will cancel the
// existing running jobs and replace it with the new instance.
// ExistingPeriodicWorkPolicy#CANCEL_AND_REENQUEUE
     ExistingPeriodicWorkPolicy.CANCEL_AND_REENQUEUE,
// Recurring Work Request
publishClustersEntertainmentSpace);

}

處理廣播意圖

除了透過工作發出發布內容 API 呼叫,您還需要設定 BroadcastReceiver 來接收內容發布要求。

不過,開發人員必須謹慎小心,避免僅仰賴廣播功能,因為廣播只有在特定情況下才會觸發,主要是應用程式重新啟動及強制同步處理資料的情況。只有在 Engage Service 判定內容可能已過時的情況,系統才會觸發廣播。 這樣一來,即使應用程式長時間未開啟,使用者也能獲得最新的內容體驗。

BroadcastReceiver 必須透過下列兩種方式進行設定:

  • 使用 Context.registerReceiver() 以動態方式註冊 BroadcastReceiver 類別的例項。這樣就能接收仍在記憶體中的應用程式訊息。
  • AndroidManifest.xml 檔案中使用 <receiver> 標記,以靜態方式宣告實作項目。這可讓應用程式在未執行的情況下接收廣播意圖,也能讓應用程式發布內容。