Skip to main content

ゴール

このチュートリアルでは、kameleoon_to_airtable.py スクリプトの動作をステップごとに説明します。Kameleoon の実験 ID、Airtable のベース ID、Airtable のテーブル ID を指定すると、スクリプトは実験のメタデータと統計結果を取得し、最も成果の良いバリエーションを判断して、データを Airtable の Experiments スキーマにマッピングし、レコードを Airtable に書き戻します。同じ実験に対してスクリプトを再実行すると、重複を作成する代わりに既存の行を更新します。 本チュートリアルは、Automation API を使用して実験結果を取得する チュートリアルに続くものであり、同じリクエストとポーリングのフローを再利用します。

要件

  • Kameleoon API の認証情報。 Automation API にはアクセストークンが必要です。スクリプトは client_credentials グラントを使用して、client_idclient_secret からプログラムでアクセストークンを取得します。アクセストークンを取得する を参照してください。
  • 対象のベースに対して data.records:write スコープを持つ Airtable の個人アクセストークン。
  • Airtable のベース ID とテーブル ID。 どちらもテーブルの URL、またはベースの API ドキュメントに表示されます。ベース ID は app で始まり、テーブル ID は tbl で始まります。
  • Experiments スキーマがすでに構築された Airtable テーブル。 スクリプトは次のフィールドに書き込みます: Experiment NameStatusStart dateEnd dateNotesActualProbabilityResult。また、手動入力用のフィールド AssigneeCategoryPredictionMkt EstEng EstAttachments が存在することを前提としていますが、スクリプトがこれらの値を設定することはありません。Airtable はテーブルにまだ存在しないフィールド名への書き込みを拒否し、typecast は既存のフィールドに対して値の型を変換するだけです(不足しているフィールドや選択肢を作成することはありません)。スクリプトを実行する前に、これらのフィールドと対応する Status の選択肢を持つテーブルを作成してください。各フィールドに設定される値については、ステップ 6 を参照してください。
  • Python 3.9 以上requests ライブラリを含む(pip install requests)。
すべての認証情報は環境変数に保存してください。スクリプトにシークレットをハードコードしないでください。
このチュートリアルでは、例として実験 Product Page Redesign(ID 188308)を使用します。オリジナルバリエーションに加えて、Redesign 1(ID 828220)と Redesign 2(ID 828221)の 2 つのバリエーションがあります。

1. Automation API で認証する

エンドポイント: トークンエンドポイントに POST リクエストを送信して、アクセストークンを取得します。
例:
レスポンス:
以降のすべての Automation API リクエストで、返された access_tokenBearer トークンとして送信してください。アクセストークンはデフォルトで 2 時間有効です。

2. 実験を取得する

エンドポイント: Get an experiment エンドポイントに GET リクエストを送信して、実験のメタデータを取得します。
例:
レスポンス(一部省略):
スクリプトは、Airtable レコード用に namestatusdateStarteddateEndeddescription を読み取り、次のステップで結果リクエストの範囲を絞り込むために mainGoalId を読み取ります。
API はデフォルトで mainGoalId を返すため、これを読み取るために optionalFields パラメータは必要ありません。Automation API は status フィールドの固定された列挙値を公開していませんが、API 全体の他のステータス系フィールドは一貫して大文字のトークン(たとえば STOPPEDACTIVEDRAFT)を使用します。ステップ 6 では、この前提のもとで status フィールドをマッピングします。マッピングに依存する前に、実際のリクエストでアカウントが返す正確なトークンを確認してください。

3. 実験の結果をリクエストする

エンドポイント: Request experiment’s results エンドポイントに POST リクエストを送信して、結果レポートの生成をトリガーします。
例:
レスポンス:
Kameleoon はレポートを非同期で生成します。エンドポイントは dataCode を返し、ステップ 4 ではこれを使用して結果をポーリングします。
このスクリプトには bayesian: true が必要です。ベイズ推定を有効にすると、レポートの reliability の値にベイズ成功確率(あるバリエーションが参照バリエーションに勝る確率)が反映され、スクリプトはこの値を Probability フィールドにマッピングします。アカウントが別のデフォルトの統計手法を使用している場合は、Kameleoon アプリ内の同じレポートと照らして値を確認してください。Automation API の仕様では dateIntervals は必須と記載されていますが、上記の例ではこれを省略しても有効なレポートが返されます。仕様には、dateIntervals を省略した場合のデフォルト動作は記載されていません。本チュートリアルでは、実験の全期間をカバーすると仮定しているため、この動作に依存する前に、自分のアカウントで確認してください。特定の期間にレポートを限定するには、代わりに dateIntervals 配列を渡します。

4. 結果をポーリングする

エンドポイント: Poll results エンドポイントに GET リクエストを送信し、レポートが準備できるまで取得を繰り返します。
レスポンスの status は、Kameleoon がレポートを計算している間は WAITING、データが利用可能になると READY、失敗時は ERROR または TIMEOUT になります。ステータスが ERROR または TIMEOUT の場合、レスポンスにはトップレベルの errorDescription が含まれます。スクリプトは、ステータスが READY になるまで一定の間隔でポーリングします。 例:
レスポンス(一部省略):

5. 最も成果の良いバリエーションを選択する

結果には、variationData の下にバリエーションごとに 1 つのエントリと、オリジナルページ用の _reference の行が含まれます。各バリエーションについて、リクエストしたゴールの指標は breakdownData._reference.generalData.goalsData[goalId] の下にあります。 スクリプトは _reference エントリをスキップし、各バリエーションの improvementRatereliability(ベイズ成功確率)を読み取り、改善率が最も高いバリエーションを最も成果の良いものとして選択します。次のステップでマッピングされる Result フィールドには、そのバリエーションが実際に勝利したかどうか、つまり十分に高い成功確率と正の上昇率を達成したかどうかが記録されます。 例:
この例では、両方のバリエーションが 100% のベイズ成功確率に達していますが、Redesign 1828220)は +211.48% の改善を示しているのに対し、Redesign 2 は -43.33% です。したがって、Redesign 1 が最も成果の良いバリエーションであり、95% を超える確率と正の上昇率を伴う正真正銘の勝者です。

6. データを Airtable フィールドにマッピングする

スクリプトは、実験のメタデータと最も成果の良いバリエーションの指標を、Airtable の Experiments スキーマに変換します。 スクリプトは、Kameleoon 側にソースがないフィールド(AssigneeCategoryPredictionMkt EstEng EstAttachments)を設定しません。これらのフィールドは、Airtable 内で手動入力用として利用できる状態のままです。また、スクリプトは空の値を省略するため、既存のセルを空欄で上書きすることはありません。 例:
Automation API は実験の status フィールドに固定された列挙値を公開しておらず、トークンは今後変わる可能性があります。map_status は大文字・小文字を区別せずにマッチングし、認識できないステータスに対しては None を返すため、誤った値を書き込む代わりに Status セルへの書き込みを省略します。1 回の GET /experiments/{experimentId} でアカウントが返すトークンを確認し、必要に応じて STATUS_MAP を拡張してください。

7. レコードを Airtable にアップサートする

Airtable の Update table エンドポイント(PATCH /v0/meta/bases/{baseId}/tables/{tableId})は、テーブルの名前と説明のみを変更するものであり、行にデータを書き込むことはできません。レコードにデータを入力するには、performUpsert オプションを指定して records エンドポイントを使用してください。
エンドポイント: records エンドポイントに PATCH リクエストを送信して、レコードを作成または更新します。
例:
レスポンス(一部省略):
レスポンスは、レコードごとに結果を報告します。createdRecords の下に ID が返される場合は Airtable が新しい行を作成したことを意味し、updatedRecords の下に ID がある場合は Airtable が既存の行を更新したことを意味します。

8. スクリプトを実行する

実験 ID と Airtable のベース ID、テーブル ID を引数として渡します:
スクリプトは、認証、取得した実験、最も成果の良いバリエーション、マッピングされたフィールド、そして Airtable レコードを作成したか更新したかという各ステップを出力します。

スクリプト全文

以下の完全なスクリプトは、kameleoon_to_airtable.py と関数単位で一致しています。そのままコピーするか、リンク先からファイルをダウンロードしてください。

カスタマイズに関する注意事項

  • ステータスマッピングSTATUS_MAP 定数にあり、API が返す大文字のステータストークンをキーとします。Status の選択肢が Running / Implementing / Completed / Defunct と異なる場合はターゲットの値を調整し、マッピングに依存する前に実際の GET /experiments/{experimentId} リクエストでアカウントが返すトークンを確認してください。
  • Probability は測定されたベイズ成功確率から取得され、結果リクエストで bayesian: true が必要です。Probability フィールドが実験前の見積もりを手動で入力するものである場合は、build_airtable_fields から Probability の行を削除してください。
  • ゴールの選択 には実験の mainGoalId を使用します。別のゴールについてレポートするには、そのゴール ID を request_resultspick_best_variation に渡してください。
  • アップサートキー。 Airtable はマージフィールドを厳密に一致させるため、Experiment Name の大文字・小文字や空白の違いは、既存の行を更新する代わりに新しい行を作成してしまいます。実験名を安定させるか、専用の安定した識別子フィールドでマージしてください。
  • Actual フィールドの形式。 スクリプトは、生の improvementRate の値(たとえば 211.48)を Actual に書き込みます。Actual が Airtable の Percent フィールドである場合は、分数ではなく通常の数値を受け取るように設定するか、分数ベースの Percent フィールドに合わせて build_airtable_fields 内でその値を 100 で割ってください。
  • レート制限。 Automation API は 10 秒あたり最大 50 リクエスト、1 時間あたり最大 1,000 リクエストまで許可していますが、Kameleoon はアカウントごとに 1 分あたり 12 コール未満に抑えることを推奨しており、高頻度のトラッキングに Automation API を使用しないよう推奨しています。多数の実験をまとめて処理する場合は、トークンをキャッシュし、リクエストをスロットリングし、大量のデータが必要な場合は Data API の使用を検討してください。