Apexでクエリを実行して大量のレコードを取得する場合、他の組織に影響が出ないようにガバナ制限で取得上限が制御されていますが、Apexを利用せずにJavaScriptからSalesforce APIを使用してクエリを実行した場合は、ガバナ制限の影響を受けません。
今回はJavaScriptからSalesforce APIを簡単に実行できるJSforceを使ってApexと比べて取得上限数がどのように違うか確認してみました。
Apex Query
まずは、Apexでクエリを実行した場合です。通常Apexを使用した場合、画面に表示できる件数は1000件までとなっています。
Apex Class
Debug Log
確認画面
確認画面(最終行)
画面に表示できる件数は1000件までですが、Apexクラス内だけなら50000件まで扱うことができます。この画面に表示するというのはapex:pageBlockTableやapex:repeatなどでリストを表示した場合です。
Debug Log
1000件を超えて画面に表示しようとした場合
もし、クエリ実行時にLIMITを指定せず、取得結果が50000件を超えてしまった場合は『too many query rows』というエラーになってしまいます。
Debug Log
画面表示
このように通常のApexで扱える件数は、画面が1000件、クラス内では50000件となります。
Apex Query Read Only
上で通常のApexで扱える件数を確認しましたが、例外として『readOnly="true"』を宣言して取得件数を増やす方法があります。これを宣言するとDMLが実行できなくなる代わりに1000件を超えて画面に表示することが可能になります。
Visualforce
Apex Class
Debug Log
確認画面
確認画面(最終行)
このように『readOnly="true"』を宣言すると通常1000件までしか表示できなかったのが、10000件まで表示できるようになります。readOnlyを使っても10000件を超えるとエラーとなります。
ただし、Apexクラス内だけなら10000件を超えて取得できます。先程のクエリからLIMITを除外して実行した結果です。
Debug Log
画面表示
これ以上の件数は用意できなかったので検証はしていませんが、最大1,000,000件まで検索できるみたいです。DMLが実行できないという制限はありますが、Apexで大量件数を取得したい場合は『readOnly="true"』を宣言することで対応できるかもしれません。
JSforce Search
Apexの取得条件を確認したところでJSforceでSalesforce APIを実行した場合を確認してみます。
Visualforce
JavaScript
Debug Log
画面表示
画面表示 (最終行)
この方法でクエリを実行したところ2000件まで表示されました。Apexのときと違い、LIMITで上限を指定しなかった場合でもシステムエラーにならずに上限件数で止めてくれるみたいです。
ひとまず2000件まで表示されることを確認できましたが、もしかすると件数のみを取得した場合は結果が異なるかもと思い、Command Lineから『SELECT COUNT(Id)』を実行して取得件数を確認してみました。
結果は2000件を大きく超えて取得できました。CommandLineで実行した場合はVisualforceから実行した場合と取得できる件数が違う可能性もあるのでVisualforce側で確認用に使用したクエリを実行してみました。
レコードは全件取得するができました。ただし、処理で使用できるレコードは2000件までとなりました。先程のVisulaforce側で確認した2000件はこの2000件となるみたいです。
JSforceで取得できる最大件数は確認できていませんが、大量データの件数を表示したい場合はJSforceが便利そうです。1つ注意する点としてはJSforceはAPI使用数を消費するので頻繁に使用される箇所で利用する場合はAPI使用制限が問題ないか気をつける必要があります。
ちなみにJSforceで処理したときはサーバ側で処理する必要がなくなるので、Apexのときよりも短時間で処理を行うことができました。Apexの方がデータ型など扱えるのでシンプルに実装できると思うのですが、処理件数や処理時間などの制約がある場合はJSforceが便利そうです。