本記事では、「Apexトリガ」をテーマに基本知識から実装方法までをお届けします。トリガはクラスと合わせて、Salesforceのカスタマイズ・開発を行ううえで、非常に重要な仕組みのため、ぜひともシステム管理者・開発者の方は押さえておかれることをお薦めします。
Apexトリガとは?
Apexは、Salesforceのカスタマイズを目的としたプログラミング言語です。開発者コンソールを使用してコードを書くことができます。変数や式の構文など、Javaによく似ているので、Javaを習得している方には扱いやすい言語と言えます。
Apexトリガは、オブジェクトのレコードに対して何らかのイベント(作成、更新、削除など)が発生した際に、そのイベントをトリガ(引き金)としてアクションを実行できるApexを利用した仕組みです。
一般的な「データベーストリガ」と同様に、Apexにおいてもレコードを管理する目的でトリガがサポートされています。
トリガを使用するケースは、
- 特定の条件に基づいて操作を実行する場合
- 関連レコードを変更する場合
- 特定の操作の実行を制限する場合
などです。SOQLおよびDML※操作の実行や、Apexクラスのコールなど、Apexで行えることはすべてトリガを使って実行できます。
※DMLとは…データベースにおいてデータの検索・新規登録・更新・削除を行うための言語です。ApexにおいてもDMLを使い、レコードの挿入や更新、削除を可能にしています。
たとえば、オブジェクトのレコードがデータベースに挿入される前、レコードが削除された後、またはレコードがごみ箱から復元された後に実行されるといったトリガがあります。
具体的には、以下の表にあげられるDML操作が対象です。
操作 | 説明 | |
insert | 挿入 | 個別の取引先、取引先責任者など、1つ以上のsObject※を組織のデータに追加します。 |
update | 更新 | 個別の取引先、取引先責任者、請求書の明細などの、組織のデータ内にある1つ以上の既存のsObjectレコードを更新します。 |
delete | 削除 | 個別の取引先や取引先責任者など、1つ以上の既存のsObject レコードを組織のデータから削除します。 |
merge | マージ | 同じsObject データ型の最大3つのレコードを1つのレコードにマージし、他のレコードを削除してから、関連レコードを再ペアレント化します。 |
upsert | アップサート | 既存のオブジェクトが存在するかどうかを判別するために、指定された項目を使用するか、項目が指定されていない場合は ID 項目を使用して、1つのステートメント内で新規レコードの作成やsObjectレコードの更新を行います。 |
undelete | 復元 | 個別の取引先や取引先責任者など、1つ以上の既存のsObject レコードを組織のごみ箱から復元します。 |
参照:Salesforce Developers | Apex 開発者ガイド「Apex DML 操作」
※sObjectとは…組織の標準オブジェクト・カスタムオブジェクトに対応するApexのデータ型
Apexクラスとトリガの違い
Javaと同じように、Apexではクラスを作成できます。Apexにおけるクラスとはデータ構造を作る仕組みであり、クラスを使うと新たなデータ型を作ることができます。わかりやすく言えば、「クラスはオブジェクトを作成するための設計図」と説明できます。
対するトリガは、前述のようにレコードがデータベースに挿入される前や、レコードが削除された後など、特定のDML操作が発生する前後に実行されるApexコードです。標準オブジェクトまたはカスタムオブジェクトに関連付けられており、Apexクラスのメソッドを呼び出すことができます。
Apexトリガの実装手順と構文について
実際にトリガを実装する手順を見ていきましょう。
画面右上の[設定]アイコンから、[開発者コンソール]をクリックして専用のウインドウを開きます。
そして、開発者コンソールの左上メニューから、[File(ファイル)]→[New(新規)]→[Apex Trigger(Apex トリガ)]と順番にクリックします。
[Name(トリガ名)]には任意のトリガ名を入力し、その下の[sObject]をドロップダウンから指定します。
開発者コンソールのソースコードエディタ上にコードを入力し、保存するとトリガは完成します。
指定したオブジェクトに関連付けられて保存されるので、[オブジェクトマネージャ]→[各オブジェクト]→[トリガ]から以下のように、一覧表示されたトリガを確認できます。
トリガを関連付けできるのは、Account(取引先)やContact(取引先責任者)のような最上位の標準オブジェクト、カスタムオブジェクトおよび一部の子標準オブジェクトです。
またトリガは、作成時にデフォルトで有効になります。指定したイベントが発生したときに有効になっているトリガが自動的に実行されます。
トリガの構文
続いてトリガの構文について詳しく見ていきましょう。
トリガの構文は、クラスの構文とは異なります。triggerキーワードで始まり、その後にトリガの名前(TriggerName)→トリガが関連付けられているSalesforceオブジェクト(ObjectName)→トリガを実行するイベント(trigger_events)が続きます。
実際のベーシックな構文は以下のとおりです。
trigger TriggerName on ObjectName (trigger_events) { code_block } |
オブジェクトに対するレコードの挿入、更新、削除、復元操作の前または後にトリガを実行する場合、カンマ区切りのリスト形式で以下のトリガイベント(trigger_events)を指定します。
- before insert
- before update
- before delete
- after insert
- after update
- after delete
- after undelete
beforeトリガとafterトリガ
トリガは、「beforeトリガ」と「afterトリガ」の2つの種別に分かれます。
種別 | 説明 |
beforeトリガ | レコードがデータベースに保存される前にレコードの値を更新または検証する場合に使用します。 |
afterトリガ | システムによって設定された項目値
にアクセスする場合や、他のレコードの変更に影響を与える場合に使用します。afterトリガを実行するレコードは参照のみです。 |
参照:Salesforce Developers | Apex 開発者ガイド「トリガ」
この2つは、レコードがデータベースに保存される「前に起動するか」か「後に起動するか」どうかで異なります。
beforeトリガ・afterトリガ・標準機能の必須チェック・入力規則のチェックは、以下の順番で実行されます。
- beforeトリガ
- 標準機能の必須チェック
- 入力規則によるチェック
- afterトリガ
もし各処理のステージでエラーが発生した場合、そこで処理は中断され、エラーが通知される仕組みとなっています。
トリガコンテキスト変数
たとえば、レコード挿入をフックに特定の処理を実行したいといった場合に使用されるのが「コンテキスト変数」です。
「Trigger.〇〇」という形式で、〇〇の部分に変数があてられます。
trigger ExampleTrigger on Account (before insert, after insert) { if (Trigger.isInsert) { if (Trigger.isBefore) { // Process before insert } else if (Trigger.isAfter) { // Process after insert } } } |
トリガに使用できるコンテキスト変数を全て以下の表にまとめています。これらの変数は、大元のSystem.Triggerクラスに内包されています。
変数 | 使用方法 |
isExecuting | Apexコードの現在のコンテキストが Visualforceページ、Web サービス、またはexecuteanonymous() APIコールではなく、トリガである場合、TRUEを返します。 |
isInsert | 挿入操作により、Salesforce ユーザインターフェース、Apex、または API からこのトリガが実行された場合に、TRUEを返します。 |
isUpdate | 更新操作により、Salesforce ユーザインターフェース、Apex、または API からこのトリガが実行された場合に、TRUEを返します。 |
isDelete | 削除操作により、Salesforce ユーザインターフェース、Apex、または APIからこのトリガが実行された場合に、TRUEを返します。 |
isBefore | レコードが保存される前にこのトリガが実行された場合に、TRUEを返します。 |
isAfter | すべてのレコードが保存された後にこのトリガが実行された場合に、TRUEを返します。 |
isUndelete | レコードがごみ箱から復元された後にこのトリガが実行された場合に、TRUEを返します。この復元は、Salesforceユーザインターフェース、Apex、または APIからの復元操作の後にのみ行われます。 |
new | 新しいバージョンのsObjectレコードのリストを返します。
このsObjectリストはinsertトリガ、updateトリガおよびundeleteトリガでのみ使用でき、レコードはbeforeトリガでのみ変更できます。 |
newMap | 新しいバージョンの sObject レコードへの ID の対応付けです。
この対応付けは before updateトリガ、after insertトリガ、after update トリガおよびafter undeleteトリガでのみ使用できます。 |
old | 古いバージョンの sObjectレコードのリストを返します。
この sObjectリストはupdateトリガとdeleteトリガでのみ使用できます。 |
oldMap | 古いバージョンのsObjectレコードへのIDの対応付けです。
この対応付けはupdateトリガとdeleteトリガでのみ使用できます。 |
operationType | 現在の操作に対応する System.TriggerOperation種別の列挙値を返します。
System.TriggerOperation列挙の有効な値は次のとおりです。
トリガの種類に基づいて、異なるプログラミングロジックを使用する場合は、switchステートメントを使用して、一意のトリガ実行列挙状態の異なる順列を指定することを検討します。 |
size | 古いバージョンと新しいバージョンの両方を含む、トリガ呼び出しのレコードの合計数。 |
参照:Salesforce Developers | Apex 開発者ガイド「トリガコンテキスト変数」
トリガハンドラーを作る
前項で解説したようなシンプルな条件分岐であれば問題ないですが、分岐が重なってくるとトリガのソースコードが複雑になってしまいます。
そのような際は、Handler(ハンドラー)クラスを作って、処理をHandlerクラスで行うように分割すると、コードが綺麗で見やすくなりスッキリします。
トリガから分割されたクラスのメソッドをコールすることで、処理を再利用でき、かつトリガのサイズが縮小、コードのメンテナンス性も良くなります。
クラス作成はトリガ作成と同様に、開発者コンソールの左上メニューから[File(ファイル)]→[New (新規)]→[Apex Class(Apexクラス)]を順番にクリックします。
そして、クラス名に「TriggerHandler」と入力して、[OK]をクリックします。
続いてソースコードエディタ上に、以下のようなコードを入力して保存します。
public class TriggerHandler {
public static void TriggerBeforeInsert(List accounts) { public static void TriggerAfterUpdate(List accounts) { } |
これで、先ほどのトリガからコールするためのクラスが完成します。
Apexトリガまとめ
いかがでしたでしょうか。今回はApexトリガに関して基本知識から実装方法までを解説しました。Apexトリガはカスタマイズ性が高く、実装できると非常に便利な機能です。
一方で、複雑なシステムを構築する場合には、緻密な設計が求められ、開発の経験値も必要になってきます。まずは、Apexトリガの基本をしっかり習得し、簡単な業務の効率化・最適化から始めてみてはいかがでしょうか。
本記事が少しでもトリガ実装のヒントになれば幸いです。
Salesforceの開発・カスタマイズを検討中の方はサンブリッジにご相談ください
サンブリッジは、長年Salesforceの導入や開発に取り組み、貴社の業務に合わせたクラウドサービスを提供するSalesforceコンサルティングパートナーです。Salesforce導入時の設計・設定から導入後の定着化支援まで、安定した運用を実現できるよう、幅広く支援しています。
Salesforceの開発・カスタマイズを検討中の方は、ぜひ一度、サンブリッジまでご相談ください。
【ホワイトペーパー】
~Salesforceユーザーのための~
名刺管理ツール選定6つのポイント

名刺管理ツールを導入するにあたり、Salesforceを使っているユーザーならここをチェックしたいというポイントを6つの軸で解説した資料です。