在 test/fixtures/performance/orders.yml 使用 ERB 迴圈產生 100 筆訂單:
<% for i in 1..100 %>
order_<%= i %>:
id: <%= i %>
name: Fred
email: fred@flintstones.com
address: 123 Rockpile Circle
pay_type: check
<% end %>
執行 ruby test/unit/order_test.rb 即可載入資料庫驗證。
在 test/performance/order_test.rb:
require File.dirname(__FILE__) + '/../test_helper'
require 'store_controller'
class OrderTest < Test::Unit::TestCase
fixtures :products
HOW_MANY = 100
def setup
@controller = StoreController.new
@request = ActionController::TestRequest.new
@response = ActionController::TestResponse.new
get :add_to_cart, :id => 1 # 確保購物車有商品
end
def teardown
Order.delete_all
end
def test_save_bulk_orders
elapsed = Benchmark::realtime do
# 載入大量測試資料
Fixtures.create_fixtures(File.dirname(__FILE__) + "/../fixtures/performance", "orders")
assert_equal HOW_MANY, Order.find(:all).size
# 逐筆下單並驗證
1.upto(HOW_MANY) do |id|
order = Order.find(id)
get :save_order, :order => order.attributes
assert_redirected_to :action => 'index'
assert_equal "Thank you for your order.", flash[:notice]
end
end
# 斷言:100 筆訂單處理需在 3 秒內完成
assert elapsed < 3.0, "Actually took #{elapsed} seconds"
end
end
Benchmark::realtime 精確測量執行時間Fixtures.create_fixtures 動態載入指定目錄 fixturesteardown 清理資料,避免測試間相互干擾class OrderTest < Test::Unit::TestCase
self.use_transactional_fixtures = true # 使用交易回滾,加速測試
fixtures :products
# ...
end
開啟後,每個測試方法在交易中執行,結束自動回滾,無需手動 delete_all。
ruby script/performance/profiler "Product.salable_items"
輸出各方法呼叫次數、耗時、佔比,快速找出熱點方法。
ruby script/performance/benchmarker 10 "Product.salable_items" "Order.count_pending"
執行 10 次迴圈,比較兩方法平均耗時:
user system total real
#1 0.078000 0.000000 0.078000 ( 0.078000)
#2 0.000000 0.000000 0.000000 ( 0.016000)
參數順序:迴圈次數 "方法1" "方法2" ...,方法間以空格分隔。