Skip to content

Commit 28af653

Browse files
CodeMeisterneilvcarvalho
authored andcommitted
Improve sequence handling with better context support
- Refactored :increment_sequence to remove the URI requirement. - Updated sequence specs for both direct and implicit strategy use. - FactoryBot.build(:user) - build(:user)
1 parent 343824f commit 28af653

File tree

3 files changed

+26
-15
lines changed

3 files changed

+26
-15
lines changed

lib/factory_bot/evaluator.rb

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -51,8 +51,15 @@ def __override_names__
5151
@overrides.keys
5252
end
5353

54-
def increment_sequence(sequence)
55-
sequence.next(self)
54+
def increment_sequence(sequence, scope: self)
55+
value = sequence.next(scope)
56+
57+
raise if value.respond_to?(:start_with?) && value.start_with?("#<FactoryBot::Declaration")
58+
59+
value
60+
rescue
61+
raise ArgumentError, "Sequence '#{sequence.uri_manager.first}' failed to " \
62+
"return a value. Perhaps it needs a scope to operate? (scope: <object>)"
5663
end
5764

5865
def self.attribute_list

lib/factory_bot/syntax/methods.rb

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ def generate(*uri_parts, scope: nil)
123123
raise(KeyError,
124124
"Sequence not registered: #{FactoryBot::UriManager.build_uri(uri_parts)}")
125125

126-
increment_sequence(uri, sequence, scope: scope)
126+
increment_sequence(sequence, scope: scope)
127127
end
128128

129129
# Generates and returns the list of values in a global or factory sequence.
@@ -147,7 +147,7 @@ def generate_list(*uri_parts, count, scope: nil)
147147
raise(KeyError, "Sequence not registered: '#{uri}'")
148148

149149
(1..count).map do
150-
increment_sequence(uri, sequence, scope: scope)
150+
increment_sequence(sequence, scope: scope)
151151
end
152152
end
153153

@@ -161,21 +161,19 @@ def generate_list(*uri_parts, count, scope: nil)
161161
# Increments the given sequence and returns the value.
162162
#
163163
# Arguments:
164-
# uri: (Symbol)
165-
# The URI for the sequence
166164
# sequence:
167165
# The sequence instance
168166
# scope: (object)(optional)
169167
# The object the sequence should be evaluated within
170168
#
171-
def increment_sequence(uri, sequence, scope: nil)
169+
def increment_sequence(sequence, scope: nil)
172170
value = sequence.next(scope)
173171

174172
raise if value.respond_to?(:start_with?) && value.start_with?("#<FactoryBot::Declaration")
175173

176174
value
177175
rescue
178-
raise ArgumentError, "Sequence '#{uri}' failed to " \
176+
raise ArgumentError, "Sequence '#{sequence.uri_manager.first}' failed to " \
179177
"return a value. Perhaps it needs a scope to operate? (scope: <object>)"
180178
end
181179
end

spec/acceptance/sequence_context_spec.rb

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
describe "sequences are evaluated in the correct context" do
1+
describe "sequences are evaluated in the correct context, directly & implicitly" do
2+
include FactoryBot::Syntax::Methods
3+
24
before do
35
define_class("User") do
46
attr_accessor :id, :name
@@ -17,6 +19,7 @@ def awesome
1719
end
1820

1921
expect(FactoryBot.build(:sequence_with_sprintf).id).to eq "foo1"
22+
expect(build(:sequence_with_sprintf).id).to eq "foo2"
2023
end
2124

2225
it "invokes the correct method on the instance" do
@@ -27,6 +30,7 @@ def awesome
2730
end
2831

2932
expect(FactoryBot.build(:sequence_with_public_method).id).to eq "aw yeah"
33+
expect(build(:sequence_with_public_method).id).to eq "aw yeah"
3034
end
3135

3236
it "invokes a method with no arguments on the instance" do
@@ -37,6 +41,7 @@ def awesome
3741
end
3842

3943
expect(FactoryBot.build(:sequence_with_frozen).id).to be false
44+
expect(build(:sequence_with_frozen).id).to be false
4045
end
4146

4247
it "allows direct reference of a method in a sequence" do
@@ -46,6 +51,7 @@ def awesome
4651
end
4752
end
4853
expect(FactoryBot.build(:sequence_referencing_attribute_directly).id).to eq "aw yeah1"
54+
expect(build(:sequence_referencing_attribute_directly).id).to eq "aw yeah2"
4955
end
5056

5157
context "with inherited factories" do
@@ -62,7 +68,7 @@ def awesome
6268
expect(parents[1].id).to eq "id_2"
6369
expect(parents[2].id).to eq "id_3"
6470

65-
children = FactoryBot.build_list(:child, 3)
71+
children = build_list(:child, 3)
6672
expect(children[0].id).to eq "id_4"
6773
expect(children[1].id).to eq "id_5"
6874
expect(children[2].id).to eq "id_6"
@@ -83,7 +89,7 @@ def awesome
8389
parent_ids = FactoryBot.build_list(:parent, 3, :with_sequenced_id).map(&:id)
8490
expect(parent_ids).to eq ["id_1", "id_2", "id_3"]
8591

86-
child_ids = FactoryBot.build_list(:child, 3, :with_sequenced_id).map(&:id)
92+
child_ids = build_list(:child, 3, :with_sequenced_id).map(&:id)
8793
expect(child_ids).to eq ["id_4", "id_5", "id_6"]
8894
end
8995

@@ -109,7 +115,7 @@ def awesome
109115
expect(parents[1].id).to eq "id_2"
110116
expect(parents[2].id).to eq "id_3"
111117

112-
children = FactoryBot.build_list(:child, 3)
118+
children = build_list(:child, 3)
113119
expect(children[0].id).to eq "id_1"
114120
expect(children[1].id).to eq "id_2"
115121
expect(children[2].id).to eq "id_3"
@@ -136,7 +142,7 @@ def awesome
136142
expect(parents[1].id).to eq "parent_2"
137143
expect(parents[2].id).to eq "parent_3"
138144

139-
children = FactoryBot.build_list(:child, 3)
145+
children = build_list(:child, 3)
140146
expect(children[0].id).to eq "child_1"
141147
expect(children[1].id).to eq "child_2"
142148
expect(children[2].id).to eq "child_3"
@@ -164,7 +170,7 @@ def awesome
164170
expect(globals[1]).to eq "global_2"
165171
expect(globals[2]).to eq "global_3"
166172

167-
parents = FactoryBot.build_list(:parent, 3)
173+
parents = build_list(:parent, 3)
168174
expect(parents[0].id).to eq "parent_1"
169175
expect(parents[1].id).to eq "parent_2"
170176
expect(parents[2].id).to eq "parent_3"
@@ -174,7 +180,7 @@ def awesome
174180
expect(children[1].id).to eq "child_2"
175181
expect(children[2].id).to eq "child_3"
176182

177-
siblings = FactoryBot.build_list(:sibling, 3)
183+
siblings = build_list(:sibling, 3)
178184
expect(siblings[0].id).to eq "sibling_1"
179185
expect(siblings[1].id).to eq "sibling_2"
180186
expect(siblings[2].id).to eq "sibling_3"

0 commit comments

Comments
 (0)