2012-05-02 21 views
0

バッチ頂点クラスを使用してウェブサイトや電子メールのコレクションを作成しています。これらのコレクションを使用して他のクエリをフィルタリングしてコレクションにすることができます。すべてのコレクションが設定されているので、私はビジネスプロセスを実行するためにスコープの最終ループを実行したいと思う。SalesforceバッチApexクラス - 大規模データセットに対するクエリ

モックアップ:

for(Object o : scope) 
{ 
listEmails.add(o.Email); 
listWebsites.add(o.Websites); 
} 

Map<String, Account> accounts = Gather all accounts where website not in :listWebsties; //Website is key 
List<String, Contact> contacts = Gather all contacts where email not in :listEmails; //Email is key 

for(Object o : scope) 
{ 
    Account = accounts.get(o.website); 
    Contact = contacts.get(o.Email); 

    Perform business logic here 
} 

問題は、私はこのバッチを実行すると、それは時間の処理のままです。かなり小さなデータベースで作業する場合、これは正常に動作します。しかし、大規模な環境で作業する場合、おそらくこれは最善の解決策ではありません。

もっと効果的なアプローチでバッチ処理のスピードアップに役立つ人はいますか?

+0

バッチを実行するとき、あなたが供給するバッチサイズは何ですか? 'ID BatchId = Database.executeBatch(バッチ、[何番ですか?])'また、バッチのデバッグログの要約を投稿できますか? 'SOQLクエリの数:0のうち0クエリの行数:50000のうち0など..これらのデータは、どのように高速化できるかを判断するのに役立ちます。 –

+0

私はバッチサイズを指定しません。最初のプロセスの実行範囲はわずか300レコードでした。そのため、300個のリストアイテムの集合が、照会された他のオブジェクト、すなわちアカウントと連絡先をフィルタリングするために使用されます。それは、プロセスを劇的に遅くしている他のオブジェクトです。 –

+0

デフォルトのバッチサイズは200です。つまり、start()メソッドでクエリを取得したものは200個のリストに分割され、一度に200個のアイテムがスコープに渡されます。一度にメインクエリのすべてを処理することはできないので、これを考慮に入れてロジックを書き直す必要があるかもしれません。 –

答えて

0

バッチ頂点クラス全体を投稿するにはどうしますか?または、データをもっと理解するのを助けますか? あなたのアカウントのすべてのアカウント(理論上は)がユニークなウェブサイトを持ち、あなたのすべての連絡先にユニークなメールがあるようです。 私はそれらのマップを手作業で構築すると仮定しますか?つまり、アカウントをループして、 map.put(account.website、account)を実行しますか?

地図のサイズを確認するためのシステムデバッグステートメントがありますか? accounts.get()を呼び出すときにアカウントがない場合や連絡がない場合はどうなりますか?

ビジネスロジック - それ以上のループですか?

静的にバッチ変数を使用しています。つまり、処理されたレコードの総数をカウントするカウンタを持つことができます。もしそうなら、あなたの変数はリストですか?もちろんそれは危険なことがあります。

スコープオブジェクトはどのオブジェクトですか?それは重要なことではありませんが、私は自分のスコープをアカウント自身や連絡先にしたいと思っています。

私は、バッチにsystem.debugステートメントを追加して実行中であることを確認し、無限ループが発生している場所を確認します。

関連する問題