コンテキストデータの反復 personalization-contexts
Handlebars 反復構文を使用して、イベント、カスタムアクション応答、その他のコンテキストデータなど、メッセージ内の様々なソースのデータの動的リストを表示する方法を説明します。
概要 overview
Journey Optimizerでは、 メッセージのパーソナライゼーション の際に、複数のソースからのコンテキストデータにアクセスできます。 ネイティブチャネル(email、push、SMS)の Handlebars 構文を使用してこれらのソースの配列を反復し、製品リスト、レコメンデーション、その他の繰り返し要素などの動的コンテンツを表示できます。
使用可能なコンテキストソース:
- イベント:ジャーニーイベント(ビジネスイベント、単一イベント)からのデータ
- カスタムアクションの応答:カスタムアクションを介した外部 API 呼び出しから返されたデータ
- データセットルックアップ:Adobe Experience Platform データセットから取得したエンリッチメントされたデータ
- 技術プロパティ:ジャーニーメタデータ(ジャーニー ID や追加の識別情報など)
- ジャーニーコンテキスト:実行中にアクセス可能なその他のジャーニー関連データ
このガイドでは、メッセージ内のこれらの各ソースからの配列を繰り返し処理する方法と、ジャーニーアクティビティを設定する際に配列を操作する方法について説明します。 メッセージのパーソナライゼーションの基本を理解するには、 ハンドルバーの反復構文 から始めてください。または、ジャーニー式で配列を操作する に移動して、配列データをカスタムアクションやデータセット検索に渡す方法を学習してください。
ハンドルバーのイテレーション構文 syntax
Handlebars は、配列に対して繰り返し処理するための {{#each}} ヘルパー を提供します。 基本的な構文を次に示します。
ポイント:
arrayPathを配列データへのパスに置き換えます- 任意の変数名で
itemを置き換えます(例:product、response、element) {{item.propertyName}}を使用して各項目のプロパティにアクセスする- 複数レベルの配列に対して複数の
{{#each}}ブロックをネストできます
イベントデータの反復 event-data
イベントデータは、ジャーニーが イベント によってトリガーされた場合に使用できます。 これは、ジャーニーの開始時に取り込まれたデータ(買い物かごの内容、注文項目、フォーム送信など)を表示する場合に便利です。
イベントのコンテキストパス
<event_ID>:ジャーニーで設定したイベントの一意の ID<fieldPath>:イベントスキーマ内のフィールドまたは配列へのパス
例:イベントからの買い物かご項目
イベントスキーマ に productListItems 配列(標準 XDM 形式 )が含まれている場合は、以下のサンプルで説明されているように、買い物かごの中身を表示できます。
| code language-handlebars |
|---|
|
例:イベント内でネストされた配列
ネストされた構造には、ネストされた {{#each}} ブロックを使用します。
| code language-handlebars |
|---|
|
ネストについて詳しくは、 ベストプラクティス を参照してください。
カスタムアクション応答の反復 custom-action-responses
カスタムアクション 応答には、外部 API 呼び出しから返されたデータが含まれます。 これは、ロイヤルティポイント、製品レコメンデーション、在庫ステータス、パーソナライズされたオファーなど、システムからリアルタイムの情報を表示する場合に役立ちます。
カスタムアクションのコンテキストパス
<actionName>:ジャーニーで設定した カスタムアクション の名前<fieldPath>:応答ペイロード内のフィールドまたは配列へのパス
例:API からの製品レコメンデーション
カスタムアクションから返された製品レコメンデーションの配列を繰り返し処理し、メッセージに個々のカードとして表示するには、以下の例を参照してください。
API 応答:
| code language-json |
|---|
|
メッセージのパーソナライゼーション:
| code language-handlebars |
|---|
|
例:カスタムアクションからのネストされた配列
ネストされた配列(各オブジェクトに別の配列が含まれるオブジェクトの配列)を含んだカスタムアクション応答を繰り返し処理するには、以下の例を参照してください。 これは、ネストされた {{#each}} ループを使用して、複数レベルのデータにアクセスする方法を示しています。
API 応答:
| code language-json |
|---|
|
メッセージのパーソナライゼーション:
| code language-handlebars |
|---|
|
より複雑なネストパターンについては、 ベストプラクティス を参照してください。
例:ロイヤルティ層のメリット
ロイヤルティステータスに基づいて動的な特典を表示するには、次の例を参照してください。
API 応答:
| code language-json |
|---|
|
メッセージのパーソナライゼーション:
| code language-handlebars |
|---|
|
データセット検索結果の繰り返し dataset-lookup
データセットルックアップアクティビティ を使用すると、ジャーニーの実行時に Adobe Experience Platform データセット からデータを取得できます。 エンリッチメントされたデータは配列として保存され、メッセージ内で繰り返し処理できます。
データセットルックアップアクティビティの設定について詳しくは、 この節 を参照してください。 データセットルックアップは、イベントデータと組み合わせると特に強力です。実用的なユースケースについては、 例:データセットルックアップを使用して強化されたイベントデータ を参照してください。
データセット検索のコンテキストパス
<activityID>:データセットルックアップアクティビティの一意の IDentities:データセットから取得したエンリッチメントされたデータの配列
例:データセットからの製品詳細
データセットルックアップアクティビティを使用して、SKU に基づいて製品情報を取得する場合は、以下のサンプルを参照してください。
データセットルックアップ設定:
- 参照キー:
list(@event{purchase_event.products.sku}) - 返されるフィールド:
["SKU", "category", "price", "name"]
メッセージのパーソナライゼーション:
| code language-handlebars |
|---|
|
例:データセットデータを使用してイテレーションをフィルタリングする
イテレーション中にデータセットのルックアップ結果をフィルタリングして、特定の条件に一致する項目(特定のカテゴリの製品など)のみを表示するには、{{#if}} ループ内で条件付き {{#each}} ステートメントを使用します。 以下の例を参照してください。
| code language-handlebars |
|---|
|
条件付きフィルタリングについて詳しくは、 ベストプラクティス を参照してください。
例:データセットルックアップからの合計の計算
データセットのルックアップ結果を繰り返し処理しながら合計を計算して表示するには、以下の例を参照してください。
| code language-handlebars |
|---|
|
ジャーニーのテクニカルプロパティの使用 technical-properties
ジャーニーのテクニカルプロパティでは、ジャーニー ID や追加の識別子など、ジャーニーの実行に関するメタデータへのアクセスを提供します。 これらは、イテレーションパターンと組み合わせる場合に役立ちます。特に、特定のジャーニーインスタンスに基づいて配列をフィルタリングする場合に便利です。
利用可能な技術プロパティ
例:追加の識別子を使用した配列項目のフィルタリング
配列を使用したイベントトリガージャーニーで補足的な識別子を使用する場合は、フィルタリングして、現在のジャーニーインスタンスに関連する項目のみを表示できます。 追加の識別子について詳しくは、 このガイド を参照してください。
シナリオ:1 つのジャーニーが複数の予約でトリガーされますが、このジャーニーインスタンスをトリガーした特定の予約(追加の ID によって識別)の情報のみを表示したい場合。
| code language-handlebars |
|---|
|
例:トラッキングにジャーニー ID を含める
トラッキング目的でメッセージにジャーニー ID を含めるには、以下の例を参照してください。
| code language-handlebars |
|---|
|
複数のコンテキストソースの組み合わせ combine-sources
異なるソースのデータを同じメッセージ内で組み合わせて、パーソナライズされた豊富なエクスペリエンスを作成できます。 この節では、複数のコンテキストソースを組み合わせて使用する実践的な例を示します。
組み合わせることができるコンテキストソース:
例:リアルタイムの在庫を含む買い物かご項目
イベントデータ(買い物かごのコンテンツ)をカスタムアクションデータ(在庫ステータス)と組み合わせるには、以下のサンプルを表示します。
| code language-handlebars |
|---|
|
例:データセット参照を使用してエンリッチメントされたイベントデータ
イベント SKU を データセットルックアップ の詳細な製品情報と組み合わせるには、以下のサンプルを表示します。
| code language-handlebars |
|---|
|
例:複数のソースを技術的なプロパティと組み合わせる
複数のコンテキストソース(プロファイルデータ、イベントデータ、カスタムアクション、技術プロパティ)を 1 つのメッセージに組み合わせるには、以下のサンプルを表示します。
| code language-handlebars |
|---|
|
その他のコンテキストタイプ other-contexts
このガイドでは配列の反復に重点を置いていますが、通常は反復を必要としないパーソナライゼーションには、他のコンテキストタイプも使用できます。 これらは、ループ処理ではなく直接アクセスされます。
- プロファイル属性 (
profile.*):Adobe Experience Platformの個々のプロファイルフィールド - Audiences (
inAudience()):オーディエンスメンバーシップの確認 - オファーの決定:意思決定管理オファー
- ターゲット属性 (オーケストレートキャンペーンのみ):キャンペーンキャンバスで計算される属性
- トークン (
context.token):セッションまたは認証トークン
これらのソースを使用した完全なパーソナライゼーション構文と例については、以下を参照してください。
ジャーニー式での配列の操作 arrays-in-journeys
前の節では、Handlebars を使用したメッセージパーソナライゼーションにおける配列の反復に焦点を当てましたが、ジャーニーアクティビティを設定する際にも配列を操作します。 この節では、イベントの配列データをジャーニー式で使用する方法、特に、カスタムアクションにデータを渡す場合や、データセット検索で配列を使用する場合について説明します。
first、all、serializeList などの関数と共に使用します。 メッセージコンテンツでは、{{#each}} ループで Handlebars 構文を使用します。カスタムアクションパラメーターに配列値を渡す arrays-to-custom-actions
カスタムアクション を設定する場合、多くの場合、イベント配列から値を抽出し、パラメーターとして渡す必要があります。 ここでは、一般的なパターンについて説明します。
コレクションをカスタムアクションパラメーターに渡す でコレクションを渡す方法の詳細を説明します。
配列から 1 つの値を抽出します
ユースケース:イベント配列から特定のフィールドを取得し、GET リクエストのクエリパラメーターとして渡します。
サンプルシナリオ:価格が 0 を超える最初の SKU を製品リストから抽出します。
イベントスキーマの例:
| code language-json |
|---|
|
カスタムアクション設定:
- カスタムアクションで、タイプ
skuのクエリパラメーター(例:string)を設定します - 動的な値を許可する場合は「
Variable」とマークします
アクション パラメーターのジャーニー式:
| code language-javascript |
|---|
|
説明:
@event{YourEventName}:ジャーニーイベントを参照します.first(currentEventField.condition):条件に一致する最初の配列項目を返しますcurrentEventField:イベント配列内の各項目をループ処理するときに表します.SKU:一致した項目から SKU フィールドを抽出します- 結果:
"SKU-1"(アクションパラメーターに適した文字列)
first 関数について詳しくは、 コレクション管理関数 を参照してください。
配列から値のリストを作成
ユースケース:クエリパラメーターとして渡す ID のコンマ区切りリストを作成します(例:/products?ids=sku1,sku2,sku3)。
カスタムアクション設定:
- タイプ
idsのクエリパラメーター(例:string)を設定 Variableとしてマーク
ジャーニー式:
| code language-javascript |
|---|
|
説明:
-
.all(currentEventField.condition):条件に一致するすべての配列項目を返します(リストを返します) -
currentEventField:イベント配列内の各項目をループ処理するときに表します -
.SKU: SKU 値のみを含めるようにリストをプロジェクト化します -
serializeList(list, delimiter, addQuotes):リストを文字列に結合します",":区切り文字としてコンマを使用しますtrue:各文字列要素を引用符で囲みます
-
結果:
"SKU-1,SKU-3"(クエリパラメーターに適しています)
詳しくは、以下を参照してください。
カスタムアクションのコレクション処理については、 カスタムアクションパラメーターへのコレクションの受け渡し を参照してください。
オブジェクトの配列をカスタムアクションに渡す
ユースケース:リクエスト本文内のオブジェクトの完全な配列を送信します(本文を持つ POST またはGETの場合)。
リクエスト本文の例:
| code language-json |
|---|
|
カスタムアクション設定:
- リクエスト本文で、
productsをタイプlistObjectとして定義します。 Variableとしてマーク- オブジェクトフィールド
id、name、price、colorを定義します(それぞれがマッピング可能になります)。
ジャーニー キャンバスの構成:
-
詳細設定モードで、コレクション式を設定します。
code language-javascript @event{YourEventName.commerce.productListItems.all(currentEventField.priceTotal > 0)} -
コレクションマッピング UI で、次の操作を行います。
idの地図→productListItems.SKUnameの地図→productListItems.namepriceの地図→productListItems.priceTotalcolorの地図→productListItems.color
Journey Optimizerは、アクションペイロード構造に一致するオブジェクトの配列を作成します。
| note note |
|---|
| NOTE |
イベント配列を操作する場合は、currentEventField を使用して各項目を参照します。 データソースコレクション(Adobe Experience Platform)には、currentDataPackField を使用します。 カスタムアクションの応答コレクションには、currentActionField を使用します。 |
詳しくは、 コレクションをカスタムアクションパラメーターに渡す を参照してください。
データセット検索での配列の使用 arrays-with-dataset-lookup
データセットルックアップアクティビティ を使用する場合、値の配列をルックアップキーとして渡して、エンリッチメントされたデータを取得できます。
例:イベント配列内のすべての SKU の製品の詳細を検索します。
データセットルックアップ設定:
ルックアップキーフィールドで、list() を使用して配列パスをリストに変換します。
| code language-javascript |
|---|
|
これにより、データセットで検索するすべての SKU 値のリストが作成されます。 結果は、メッセージで繰り返し処理できる context.journey.datasetLookup.<activityID>.entities の配列として利用できます( データセットルックアップ結果の繰り返し を参照)。
制限事項とパターン array-limitations
ジャーニーで配列を使用する場合は、次の制限事項に注意してください。
ジャーニーフローで配列に動的なループはない
ジャーニーは、配列の各項目に対して 1 つのアクションノードが複数回実行される動的ループを作成できません。 これは、暴走パフォーマンスの問題を防ぐことを目的としています。
できないこと:
- カスタムアクションを配列項目ごとに 1 回動的に実行
- 配列の長さに基づいて複数のジャーニー分岐を作成します
推奨されるパターン:
-
すべての項目を一度に送信:配列全体またはシリアル化されたリストを、すべての項目を処理する単一のカスタムアクションに渡します。 配列から値のリストを作成する を参照してください。
-
外部集計の使用:外部 API で複数の ID を受け入れ、1 回の呼び出しで組み合わせた結果を返すようにします。
-
AEPで事前計算: 計算済み属性 を使用して、プロファイルレベルで配列から値を事前計算します。
-
単一値の抽出:1 つの値のみが必要な場合は、
firstまたはheadを使用して抽出します。 配列から 1 つの値を抽出 を参照してください。
詳しくは、 ガードレールと制限事項 を参照してください。
配列サイズに関する考慮事項
大規模な配列は、ジャーニーのパフォーマンスに影響を与える可能性があります。
- イベント配列:イベントペイロードの合計が 50 KB 未満に抑える
- カスタムアクション応答:応答ペイロードは 100 KB 未満にする必要があります
- データセットルックアップ結果:ルックアップキーと返されるエンティティの数を制限する
完全な例:カスタムアクションに対するイベント配列 complete-example
カスタムアクションでイベント配列を使用する方法を示す完全なワークフローを次に示します。
シナリオ:ユーザーが買い物かごを放棄すると、外部のレコメンデーション API に買い物かごデータを送信してパーソナライズされた提案を取得し、メールに表示します。
手順 1:カスタムアクションの設定
カスタムアクション「GetCartRecommendations」を作成します。
- メソッド: POST
- URL:
https://api.example.com/recommendations - リクエスト本文:
| code language-json |
|---|
|
cartItemsをタイプlistObjectおよびVariableとしてマーク- フィールドを定義:
sku(文字列)、price(数値)、quantity(整数)
詳しくは、 カスタムアクションの設定 を参照してください。
手順 2:応答ペイロードの設定
カスタムアクションで、応答を設定します。
| code language-json |
|---|
|
詳しくは、API 呼び出し応答の使用 を参照してください。
手順 3:ジャーニー内のアクションを関連付ける
-
買い物かご放棄イベントの後に、カスタムアクションを追加します
-
cartItemsコレクションの詳細設定モード:code language-javascript @event{cartAbandonment.commerce.productListItems.all(currentEventField.quantity > 0)} -
コレクションフィールドをマッピングします
sku→productListItems.SKUprice→productListItems.priceTotalquantity→productListItems.quantity
手順 4:メールでの応答の使用
メールコンテンツで、レコメンデーションを繰り返し処理します。
| code language-handlebars |
|---|
|
手順 5:設定をテストする
ライブジャーニーを実行する前に、アクション設定の「テストリクエストを送信」機能を使用してカスタムアクションをテストし、作成されたリクエストと値を確認します。
- ジャーニーテストモード を使用
productListItems配列を含むサンプルイベントデータを持つトリガー- カスタムアクションが正しい配列構造を受け取ることを確認します。
- アクションテストログ を確認します
- メールをプレビューして、両方の配列が正しく表示されていることを確認します
詳しくは、 カスタムアクションのトラブルシューティング を参照してください。
ベストプラクティス best-practices
コンテキストデータを繰り返し処理して、保守可能でパフォーマンスの高いパーソナライゼーションを作成する場合は、次のベストプラクティスに従ってください。
わかりやすい変数名を使用
反復している内容を明確に示す変数名を選択します。 これにより、コードがより読みやすく、メンテナンスが容易になります。 詳しくは、 パーソナライゼーション構文 を参照してください。
| code language-handlebars |
|---|
|
ループ内の式フラグメント
ループ内で 式フラグメント {{#each}} を使用する場合、ループスコープ変数をフラグメントパラメーターとして渡すことはできません。 ただし、フラグメントは、フラグメント外のメッセージコンテンツで定義されたグローバル変数にアクセスできます。
サポートされているパターン – グローバル変数を使用:
| code language-handlebars |
|---|
|
フラグメントは、メッセージ内でグローバルに定義されているので、globalDiscount を参照できます。
サポートされていません – ループ変数を渡しています:
| code language-handlebars |
|---|
|
回避策:フラグメントを使用する代わりに、パーソナライゼーションロジックをループに直接含めるか、ループの外でフラグメントを呼び出します。
詳細な例やその他の回避策など、 ループ内での式フラグメントの使用 について説明します。
空の配列を処理
配列が空の場合にフォールバックコンテンツを提供するには、{{else}} 句を使用します。 ヘルパー関数 の詳細:
| code language-handlebars |
|---|
|
条件付きヘルパーとの組み合わせ
条件付きコンテンツの場合は、{{#if}} within ループを使用します。 条件付きルール について詳しくは、 カスタムアクション応答 および データセットルックアップ の節の例を参照してください。
| code language-handlebars |
|---|
|
パフォーマンスのイテレーションを制限
大きな配列の場合は、繰り返し回数を制限することを検討してください。
| code language-handlebars |
|---|
|
配列メタデータへのアクセス
Handlebars には、高度な繰り返しパターンに役立つ特別な変数がループ内に用意されています。
@index:現在のイテレーションインデックス(0 から始まります)@first:最初のイテレーションでは True@last:最後のイテレーションでは True
| code language-handlebars |
|---|
|
@index、@first、@last)は、メッセージのパーソナライゼーションの {{#each}} ループ内でのみ使用できます。 ジャーニー式で配列を操作する場合(カスタムアクションに渡す前に配列から最初の項目を取得する場合など)は、head、first、all などの配列関数を使用します。 詳しくは、ジャーニー式での配列の操作 を参照してください。トラブルシューティング troubleshooting
反復に問題がありますか? この節では、一般的な問題と解決策について説明します。
アレイが表示されない
問題:配列の反復にコンテンツが表示されていません。
考えられる原因と解決策:
-
パスが正しくありません:コンテキストソースに基づいて、配列への正確なパスを確認してください。
- イベント の場合:
context.journey.events.<event_ID>.<fieldPath> - カスタムアクション の場合:
context.journey.actions.<actionName>.<fieldPath> - データセット検索 の場合:
context.journey.datasetLookup.<activityID>.entities
- イベント の場合:
-
配列が空です:
{{else}}句を追加して、配列にデータがないかどうかを確認します。 例については、 ベストプラクティス を参照してください。 -
まだデータを使用できません:ジャーニーフローのメッセージアクティビティの前に、カスタムアクション、イベントまたはデータセットのルックアップアクティビティが実行されていることを確認します。
構文エラー
問題:式の検証が失敗するか、メッセージがレンダリングされません。
よくある間違い:
- 終了タグがありません:すべての
{{#each}}には{{/each}}が必要です。 適切な構造を得るには、Handlebars 反復構文 を確認してください。 - 変数名が正しくありません:ブロック全体で変数名を一貫して使用してください。 命名規則については、 ベストプラクティス を参照してください。
- パスの区切り文字が正しくありません。スラッシュなどの文字を使用せずにドット(
.)を使用してください
ループで式フラグメントが機能しない
問題:式フラグメントが {{#each}} ループ内で使用された場合に期待されるコンテンツを表示しないか、空の出力または予期しない出力を表示します。
考えられる原因と解決策:
-
ループ変数をパラメーターとして渡そうとして:式フラグメントは、ループスコープ変数(現在の反復項目など)をパラメーターとして受け取ることができません。 これは既知の制限です。
解決策:次のいずれかの回避策を使用します。
- フラグメントがアクセスできるメッセージ内のグローバル変数を定義する
- フラグメントを使用する代わりに、パーソナライゼーションロジックをループに直接含めます
- ループ固有のデータが不要な場合は、ループの外部でフラグメントを呼び出します
-
フラグメントは、使用できないパラメーターを想定しています:フラグメントが特定の入力パラメーターを受け取るように設計されている場合、これらのパラメーターをループ内から渡すことができない限り、正しく機能しません。
解決策:フラグメントがアクセスできるグローバル変数を使用するように、アプローチを再構築します。 例については、 ベストプラクティス – ループ内の式フラグメント を参照してください。
-
変数スコープが正しくありません:フラグメントが、ループスコープ内にのみ存在する変数を参照しようとしている可能性があります。
解決策:フラグメントに必要な変数をメッセージレベル(ループの外側)で定義して、グローバルにアクセスできるようにします。
詳細な説明、例、推奨されるパターンなど、 ループ内での式フラグメントの使用 について説明します。
イテレーションのテスト
ジャーニーテストモード を使用して、イテレーションを検証します。 これは、 カスタムアクション または データセット検索 を使用する場合に特に重要です。
- ジャーニーを テストモード で開始します
- イベントまたはカスタムアクションとサンプルデータのトリガー
- メッセージプレビュー をチェックして、イテレーションが正しく表示されていることを確認します
- エラーのテストモードログを確認します( カスタムアクションテストモードログ を参照)
関連トピック related-topics
Personalizationの基本事項: パーソナライゼーションの概要 | パーソナライゼーションを追加 | Personalization構文 | ヘルパー関数 | 条件付きルールの作成
ジャーニー構成: イベントについて | カスタムアクションの設定 | コレクションをカスタムアクションパラメーターに渡す | カスタムアクションでの API 呼び出し応答の使用 | カスタムアクションのトラブルシューティング | ジャーニーでのAdobe Experience Platform データの使用 | ジャーニーで追加の識別子を使用 | ガードレールと制限 | ジャーニーのテスト
ジャーニー式関数: 高度な式エディター | コレクション管理関数 (first、all、last) | リスト関数 (serializeList、filter、sort) | 配列関数 (head、tail)
Personalizationのユースケース: 買い物かごの放棄に関するメール | 注文ステータスの通知
メッセージデザイン: メールデザインの概要 | プッシュ通知の作成 | SMS メッセージの作成 | コンテンツのプレビューとテスト