module FactoryGirl
module Strategy
class Stub
@@next_id = 1000
def association(runner)
runner.run(:build_stubbed)
end
def result(evaluation)
evaluation.object.tap do |instance|
stub_database_interaction_on_result(instance)
clear_changed_attributes_on_result(instance)
evaluation.notify(:after_stub, instance)
end
end
private
... # 省略
end
FactoryGirl.define do
factory :user do
name 'Bob'
age 31
height 172
weight 64
before(:stub_custom) do |user, evaluation|
user.bmi = (user.weight / ((user.height / 100.0) ** 2)).round(1)
end
before(:build_custom) do |user, evaluation|
user.bmi = (user.weight / ((user.height / 100.0) ** 2)).round(1)
end
end
end
# 作成したStrategyを使用することにより、id, delete_flag, created_at, updated_atを自動挿入したインスタンスを返す
user = FactoryGirl.stub_custom(:user)
# 各フィールドに抜けのないインスタンスが10生成される
users = FactoryGirl.stub_custom_list(:user, 10)
module FactoryGirl
class FactoryRunner
def initialize(name, strategy, traits_and_overrides)
@name = name
@strategy = strategy
@overrides = traits_and_overrides.extract_options!
@traits = traits_and_overrides
end
def run(runner_strategy = @strategy, &block)
factory = FactoryGirl.factory_by_name(@name)
factory.compile
if @traits.any?
factory = factory.with_traits(@traits)
end
instrumentation_payload = {
name: @name,
strategy: runner_strategy,
traits: @traits,
overrides: @overrides,
factory: factory
}
ActiveSupport::Notifications.instrument('factory_girl.run_factory', instrumentation_payload) do
factory.run(runner_strategy, @overrides, &block)
end
end
end
end
class CustomStub < FactoryGirl::Strategy::Stub
def association(runner)
runner.run(:build_stubbed)
end
def result(evaluation)
evaluation.object.tap do |instance|
evaluation.notify(:before_stub_custom, instance)
stub_database_interaction_on_result(instance)
evaluation.notify(:after_stub_custom, instance)
end
end
end
# ここで実際に作成したクラスを登録する
FactoryGirl.register_strategy(:stub_custom, CustomStub)
FactoryGirl.register_callback(:before_stub_custom)
FactoryGirl.register_callback(:after_stub_custom)
module FactoryGirl
module Strategy
class Create
def association(runner)
runner.run
end
def result(evaluation)
evaluation.object.tap do |instance|
evaluation.notify(:after_build, instance)
evaluation.notify(:before_create, instance)
evaluation.create(instance)
evaluation.notify(:after_create, instance)
end
end
end
end
end
module FactoryGirl
module Strategy
class Build
def association(runner)
runner.run
end
def result(evaluation)
evaluation.object.tap do |instance|
evaluation.notify(:after_build, instance)
end
end
end
end
end