0

サブスクリプション注文のメールを追跡する Rails 3.2 アプリケーションがあります。

基本的なモデル構造は次のとおりです。

has_many サブスクリプションの注文 has_many SubscriptionMailings

毎月、各サブスクリプション メールのレコードが生成され、これらのレコードから csv ファイルがエクスポートされます。

郵送先住所は注文レベルで保存されます。

基本的には、その月の郵送に有効な購読をすべて選択し、それらをループ処理して、注文オブジェクトから郵送先住所を取得します。次に、それぞれに対して新しいサブスクリプション メーリング レコードを作成します。

サブスクリプションが多くないため、今のところ問題なく動作しますが、かなり遅いです。

このプロセスをスピードアップするにはどうすればよいですか?

4

3 に答える 3

0

最適化するには、ここで Ruby レベルから SQL レベルにステップダウンする必要があります。

N+1選択 (1すべてのサブスクリプションをフェッチし、各サブスクリプションのすべての注文をフェッチするため)を行う代わりに、結合による選択Nのみを実行できる場合があります。1

SubscriptionMailing.
  joins(:subscrtiption).
  joins(:order).
  where(Order.table_name => { valid: true })
于 2012-05-26T06:11:34.850 に答える
0

いくつかの調査の後、他の変更を加えずにコードをトランザクションにラップすることになりました。

それは物事をかなりスピードアップしました。

トランザクションを追加する前は、コードの実行に 1 分以上かかっていましたが、今では約 10 秒に短縮されました。これは私のニーズに対して十分に高速であるため、これ以上最適化することはしませんでした。

ActiveRecord::Base.transaction do
   # my db stuff here
end
于 2012-06-10T02:32:40.337 に答える
0

インクルードを使用して注文を積極的にロードしたいようです。多分このようなもの:

# Subscription.rb
scope :valid_for_month lambda {|month| where(month: month)}

# Elsewhere
valid_subscriptions = Subscription.valid_for_month(Time.now.month).includes(:order)
valid_subscriptions.each do |subscription|
  subscription.generate_subscription_mailing
end

インクルードの詳細: http://api.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.html

于 2012-05-26T07:37:29.160 に答える