はじめにこんにちは!Masaです。普段はTableauを使ったダッシュボード開発や、中途採用のお手伝いをしています。今回の社内勉強会では、Salesforceの「変更履歴の管理」をテーマに、標準の「項目履歴管理」だけではカバーしきれない要件の時、カスタムオブジェクトとフローでどう実現するかを取り上げました。Salesforceには、特定の項目の変更履歴を自動で保存してくれる「項目履歴管理」という標準機能があります。ただ、以下のようなケースでは、標準機能だけでは足りないことがあります。・変更履歴を長期間保管したい・20より多くの項目を柔軟に変更管理したい・履歴情報を独自のレイアウトで表示したいそこで今回は、取引先責任者(Contact)を主オブジェクトとし、その変更履歴を保持する「一般情報履歴」というカスタムオブジェクトを新たに定義。さらに、レコードトリガーフローを使って、変更があったときだけ履歴レコードを自動生成する仕組みを実装しました。この記事では、勉強会の内容をベースに、・項目履歴管理とは?・勉強会の目的/ユースケースと要件・具体的な実装手順を順番に紹介していきます。項目履歴管理とは?「項目履歴管理」は、Salesforceの標準機能のひとつで、特定の項目について「誰が・いつ・どの値からどの値に変更したか」を自動で保存してくれる仕組みです。変更があった時の履歴情報は、該当レコードの詳細ページで関連リストとして確認することができます。例えば、誤った内容で保存してしまったときに元の値を振り返って修正に活かせるなど、ミス防止やデータの信頼性確保にとても役立ちます。一方で、標準の項目履歴管理には、以下のような制約もあります。UI上での保持:最大18か月/API経由での保持:最大24か月1オブジェクトにつき最大20項目まで数式、自動採番、ロングテキストエリア、複数選択ピックリストなど一部項目は対象外履歴データのスキーマ変更は不可能※Salesforceには項目履歴管理の制約を拡張する有償のセキュリティ製品アドオンとしてField Audit Trail(項目監査履歴)があります。これを利用すると標準の保持期間や追跡可能な項目数の制限を大幅に拡張し、より長期・大量の変更履歴データを管理できるようになります(ただし別途ライセンスが必要です)。勉強会の目的今回の勉強会のゴールは、次の2つでした。Salesforceでの履歴管理の考え方(標準機能とカスタム設計の違い)を理解すること取引先責任者の変更履歴をカスタムオブジェクト + フローで実装できるようになること具体的には、以下のユースケースを想定し、それを実現するための要件を満たす仕組みを題材として取り上げました。ユースケース営業担当者が、取引先責任者の氏名・所属・役職・電話番号・メールアドレスなどを日常的に利用している名刺交換や移動・昇進・部署変更などにより、これらの情報は頻繁に変更される誰がいつ、どのように変更したのかを、取引先責任者の画面からすぐ確認し、永年保持したい要件取引先責任者のレコードで何らかの変更があったとき、変更があった項目ごとに「一般情報履歴」オブジェクトのレコードを自動作成する※今回はシンプルな実装をするため、変更対象の項目を「電話」項目のみとしています。履歴レコードには、以下の情報をセットする対象の取引先責任者変更日(いつ)変更者(誰が)項目名(何を)元の値(どの値から)新しい値(どの値へ)変更カテゴリ取引先責任者のレコードページを開いたとき、関連リストとして履歴が一覧表示されること実装手順今回の勉強会では、Developer Editionを使用しました。①一般情報履歴カスタムオブジェクトの作成設定→[オブジェクトマネージャー]から、カスタムオブジェクトを新規作成します。表示ラベル:一般情報履歴オブジェクト名:GeneralInfoHistory__cデータ型:自動採番②取引先責任者と一般情報履歴オブジェクトを主従関係で関連付け次に、一般情報履歴側に取引先責任者との主従関係項目を作成します。項目の表示ラベル:取引先責任者API参照名:Relationship_Contact__cデータ型:主従関係関連先:取引先責任者主従関係にすることで、取引先責任者が削除されたときに履歴も一緒に削除されます。また、取引先責任者レコードから「一般情報履歴」関連リストを表示できるようになります。③一般情報履歴オブジェクトに履歴情報の項目を作成する一般情報履歴オブジェクトに、履歴として保存したい情報を項目として定義します。変更日(データ型:日付または日付/時間)変更者(データ型:参照関係、関連先:ユーザー)項目名(データ型:テキスト)元の値(データ型:テキスト)新しい値(データ型:テキスト)変更カテゴリ(データ型:選択リスト、値:"一般情報"、"重要情報"、"その他")④変更があった場合に履歴レコードを作成するフローを実装するここが今回の勉強会のメインです。取引先責任者が更新されたときにフローを起動し、変更があった項目だけ履歴レコードを作成する、という仕組みを作ります。1. レコードトリガーフローの作成設定 → [フロー] → [新規フロー] → [レコードトリガーフロー]を選択します。[開始]要素にて次の設定にします。オブジェクト:取引先責任者フローをトリガーする条件:レコードが更新されたエントリ条件:すべての条件に一致 (AND) → 項目:電話、演算子:変更済み、値:True※今回は電話のみを対象とするためエントリ条件の項目も「電話」のみですが、複数項目を対象とする場合、OR条件で複数項目をセットすることで、トリガーするレコード数とフローの実行回数を減らし、組織のリソースを節約することができます。フローを実行するタイミング:レコードを更新し、条件の要件に一致するたびフローを最適化:アクションと関連レコード2. どの項目が変更されたかを判定する「決定」要素で、以下の条件を指定します。結果の表示ラベル:電話結果を実行する条件の要件:すべての条件に一致 (AND)リソース:トリガー Contact($Record) > 電話演算子:次の文字列と一致しない値:トリガー Contact の前の値($Record__Prior) > 電話結果を実行するタイミング:条件の要件を満たす場合フローでは、更新前と更新後の値を比較するために、$Record(更新後)と$Record__Prior(更新前)を使います。3. 履歴レコードを作成する決定の各出力ごとに、一般情報履歴のレコードを作成します。「レコードを作成」要素で、以下の条件を指定します。レコードの項目値の設定方法:手動オブジェクト:一般情報履歴項目:項目名 ← 値:電話項目:変更日 ← 値:実行中のフローのCurrentDate項目:変更者 ← 値:実行ユーザー > Id項目:元の値 ← 値:トリガー Contactの前の値 > 電話項目:新しい値 ← 値:トリガー Contact > 電話項目:取引先責任者 ← 値:トリガー Contact > 取引先責任者 ID項目:変更カテゴリ ← 値:一般情報メール、氏名など他の項目の履歴レコードを作成したい場合、2:項目判定と3:レコード作成の要素を順に追加していきます。⑤一般情報履歴の関連リストを取引先責任者のレコードページに配置する最後に、ユーザーが履歴を確認できるように取引先責任者レコードページに関連リストを配置します。設定 → [オブジェクトマネージャー] → [取引先責任者] → [ページレイアウト]から対象のページレイアウトを選択する[関連リスト]から「一般情報履歴」をドラッグ&ドロップでレイアウトに配置する[関連リストのプロパティ]にて選択済みの項目に「変更日」「変更者」「項目名」「元の値」「新しい値」「変更カテゴリ」を追加し、それ以外の項目を削除するページレイアウトを適用して保存する結果取引先責任者のレコードページから、「電話」項目の値を変更します。画面右下に一般情報履歴の関連リストが表示され、「すべてを表示」をクリックすると履歴レコードを確認することができました。まとめ今回は「変更履歴の管理」について取り上げると同時に、カスタムオブジェクトとフローを利用して変更履歴を永年保持する方法を整理しました。カスタムオブジェクトなので「変更カテゴリ」のような新規項目を追加しフローで値を更新することで、標準機能より柔軟な設計も可能です。みなさんもぜひ活用してみてはいかがでしょうか!参考リンク・資料Salesforce公式ドキュメントhttps://help.salesforce.com/s/articleView?id=xcloud.tracking_field_history.htm&type=5Trailheadモジュール(主従関係)https://trailhead.salesforce.com/ja/content/learn/modules/data_modeling/object_relationships