function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
安倍安倍 

例外発生時のロールバックについて

例外が発生したときにのロールバックの仕様について教えてください。

以下のように2つinsertが動くとき、accountの方は登録されています。
Account account = new Account(Name = 'aaa');
Account accountB = new Account(Name = 'bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb');
try {
    insert account;
    insert accountB;
} catch (Exception e) {
    System.debug('Excep');
    System.debug(e.getMessage());
}
List<Account> accounts = [select name from Account where name like 'aaa%' LIMIT 1];
System.debug(accounts);

解決方法はsavepointとrollbackを実装すればいいのはわかるのですが、
Exceptionが発生したらロールバックしますが、accountの方もロールバックされないのはなぜでしょうか。
 
Taiki YoshikawaTaiki Yoshikawa
savepointとrollbackを宣言しないとExceptionが発生するまでに実行された処理は実行されたままになります。
(トリガとバッチは除く)

複数の登録処理を実行してエラー発生時になかったことにしたい場合はsavepointとrollbackを宣言するのが安全です。
安倍安倍
ありがとうございます。

トリガとバッチなどコンテキストに応じて、
Exceptionの動作が異なるとは意外でした。

パット見たかぎりでは、そのような記載がドキュメントから見つからなかったのですが、
どこかにそのような記載があるのでしたら教えていただけましたら助かります。
 
安倍安倍
ありがとうございます。お勉強させていただきました。

トリガに関してはリンク貼っていただいた以下になるのですね。

>1 つのエラーはすべての処理のロールバックを引き起こします。

試してはいませんが、savepointとrollback指定せずとも、全てロールバックするということですね。


一方で、バッチについては、一括DMLを指しているのかなと思いました。
ドキュメントがパットしなかったので、実際試してみたところ、
以下のように指定した一括DMLについては、いずれも全ロールバックにはならず、
Exceptionが発生する前までの処理はcommitされておりました。

■検証1 Database.insertの第2引数をfalseに指定した場合
List<Account> accountsA = new List<Account> {
        new Account(Name = 'aaa1'),
        new Account(Name = 'aaa2')
};
List<Account> accountsB = new List<Account> {
        new Account(Name = 'bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb1'),
        new Account(Name = 'bbb2')
};

try {
    Database.insert(accountsA, false);
    Database.insert(accountsB, false);
} catch (Exception e) {
    System.debug('exception');
    System.debug(e.getMessage());
}
for(Account a1 : [select name from Account where name like 'aaa%' LIMIT 1]) {
    System.debug(a1);
}
for(Account b1 : [select name from Account where name like 'bbb%' LIMIT 1]) {
    System.debug(b1);
}
■検証1の結果
11:52:24.12 (111734322)|USER_DEBUG|[18]|DEBUG|Account:{Name=aaa1, Id=001O000001IhoWHIAZ}
11:52:24.12 (116749020)|USER_DEBUG|[21]|DEBUG|Account:{Name=bbb2, Id=001O000001IhoWJIAZ}



■検証2 Database.insertの第2引数をtrueに指定した場合
List<Account> accountsA = new List<Account> {
        new Account(Name = 'aaa!1'),
        new Account(Name = 'aaa!2')
};
List<Account> accountsB = new List<Account> {
        new Account(Name = 'bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb1'),
        new Account(Name = 'bbb!2')
};

try {
    Database.insert(accountsA, true);
    Database.insert(accountsB, true);
} catch (Exception e) {
    System.debug('exception');
    System.debug(e.getMessage());
}
for(Account a1 : [select name from Account where name like 'aaa!%' LIMIT 1]) {
    System.debug(a1);
}
for(Account b1 : [select name from Account where name like 'bbb!%' LIMIT 1]) {
    System.debug(b1);
}


■検証2の結果
11:46:20.21 (115219773)|USER_DEBUG|[14]|DEBUG|exception
11:46:20.21 (115270826)|USER_DEBUG|[15]|DEBUG|Insert failed. First exception on row 0; first error: STRING_TOO_LONG, 法人名: データ値が大きすぎる: bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb1 (max length=255): [Name]
11:46:20.21 (123122482)|USER_DEBUG|[18]|DEBUG|Account:{Name=aaa!1, Id=001O000001IhoVnIAJ}