55from src .stats .stats import Stats
66from src .ui .userInterface import UserInterface
77from src .world .timeService import TimeService
8- from unittest .mock import MagicMock
8+ from unittest .mock import MagicMock , patch
99
1010
1111def createDocks ():
@@ -127,23 +127,31 @@ def test_fish():
127127 docksInstance = createDocks ()
128128 docksInstance .userInterface .lotsOfSpace = MagicMock ()
129129 docksInstance .userInterface .divider = MagicMock ()
130- docks .print = MagicMock ()
131- docks .sys .stdout .flush = MagicMock ()
132- docks .time .sleep = MagicMock ()
133- docks .random .randint = MagicMock (return_value = 3 )
134- docksInstance .timeService .increaseTime = MagicMock ()
135-
136- # call
137- docksInstance .fish ()
138-
139- # check
140- docksInstance .userInterface .lotsOfSpace .assert_called_once ()
141- docksInstance .userInterface .divider .assert_called_once ()
142- assert docks .print .call_count == 4
143- assert docks .sys .stdout .flush .call_count == 4
144- assert docks .time .sleep .call_count == 4
145- assert docksInstance .player .fishCount == 3
146- assert docksInstance .stats .totalFishCaught == 3
130+
131+ # Create a side effect that alternates between 0 and 0.5 indefinitely
132+ def time_side_effect ():
133+ while True :
134+ yield 0
135+ yield 0.5
136+
137+ with patch ('src.location.docks.print' ), \
138+ patch ('src.location.docks.sys.stdout.flush' ), \
139+ patch ('src.location.docks.time.sleep' ), \
140+ patch ('src.location.docks.time.time' , side_effect = time_side_effect ()), \
141+ patch ('src.location.docks.input' , return_value = "" ), \
142+ patch ('src.location.docks.random.randint' , return_value = 3 ):
143+
144+ docksInstance .timeService .increaseTime = MagicMock ()
145+
146+ # call
147+ docksInstance .fish ()
148+
149+ # check
150+ docksInstance .userInterface .lotsOfSpace .assert_called_once ()
151+ docksInstance .userInterface .divider .assert_called_once ()
152+ # Player should catch fish based on success rate
153+ assert docksInstance .player .fishCount >= 1
154+ assert docksInstance .stats .totalFishCaught >= 1
147155
148156
149157def test_run_fish_action_low_energy ():
@@ -169,19 +177,29 @@ def test_fish_consumes_energy():
169177 docksInstance .player .energy = 100
170178 docksInstance .userInterface .lotsOfSpace = MagicMock ()
171179 docksInstance .userInterface .divider = MagicMock ()
172- docks .print = MagicMock ()
173- docks .sys .stdout .flush = MagicMock ()
174- docks .time .sleep = MagicMock ()
175- docks .random .randint = MagicMock (return_value = 3 ) # Fish for 3 hours, catch 3 fish
176- docksInstance .timeService .increaseTime = MagicMock ()
177-
178- # call
179- docksInstance .fish ()
180-
181- # check
182- assert docksInstance .player .energy == 100 - (
183- 3 * 10
184- ) # Should lose 30 energy (3 hours * 10 per hour)
180+
181+ # Create a side effect that alternates between 0 and 0.5 indefinitely
182+ def time_side_effect ():
183+ while True :
184+ yield 0
185+ yield 0.5
186+
187+ with patch ('src.location.docks.print' ), \
188+ patch ('src.location.docks.sys.stdout.flush' ), \
189+ patch ('src.location.docks.time.sleep' ), \
190+ patch ('src.location.docks.time.time' , side_effect = time_side_effect ()), \
191+ patch ('src.location.docks.input' , return_value = "" ), \
192+ patch ('src.location.docks.random.randint' , return_value = 3 ):
193+
194+ docksInstance .timeService .increaseTime = MagicMock ()
195+
196+ # call
197+ docksInstance .fish ()
198+
199+ # check
200+ assert docksInstance .player .energy == 100 - (
201+ 3 * 10
202+ ) # Should lose 30 energy (3 hours * 10 per hour)
185203
186204
187205def test_fish_with_limited_energy ():
@@ -190,19 +208,85 @@ def test_fish_with_limited_energy():
190208 docksInstance .player .energy = 25 # Only enough for 2 hours
191209 docksInstance .userInterface .lotsOfSpace = MagicMock ()
192210 docksInstance .userInterface .divider = MagicMock ()
193- docks .print = MagicMock ()
194- docks .sys .stdout .flush = MagicMock ()
195- docks .time .sleep = MagicMock ()
196- docks .random .randint = MagicMock (
197- return_value = 5
198- ) # Would normally fish for 5 hours, but energy limits to 2
199- docksInstance .timeService .increaseTime = MagicMock ()
200-
201- # call
202- docksInstance .fish ()
203-
204- # check
205- assert docksInstance .player .energy == 5 # Should be 25 - (2 * 10)
206- assert (
207- docksInstance .timeService .increaseTime .call_count == 2
208- ) # Only fished for 2 hours due to energy limit
211+
212+ # Create a side effect that alternates between 0 and 0.5 indefinitely
213+ def time_side_effect ():
214+ while True :
215+ yield 0
216+ yield 0.5
217+
218+ with patch ('src.location.docks.print' ), \
219+ patch ('src.location.docks.sys.stdout.flush' ), \
220+ patch ('src.location.docks.time.sleep' ), \
221+ patch ('src.location.docks.time.time' , side_effect = time_side_effect ()), \
222+ patch ('src.location.docks.input' , return_value = "" ), \
223+ patch ('src.location.docks.random.randint' , return_value = 5 ):
224+
225+ docksInstance .timeService .increaseTime = MagicMock ()
226+
227+ # call
228+ docksInstance .fish ()
229+
230+ # check
231+ assert docksInstance .player .energy == 5 # Should be 25 - (2 * 10)
232+ assert (
233+ docksInstance .timeService .increaseTime .call_count == 2
234+ ) # Only fished for 2 hours due to energy limit
235+
236+
237+ def test_fish_interactive_success ():
238+ # Test that quick reactions result in successful catches
239+ docksInstance = createDocks ()
240+ docksInstance .userInterface .lotsOfSpace = MagicMock ()
241+ docksInstance .userInterface .divider = MagicMock ()
242+
243+ # Create a side effect that alternates between 0 and 0.5 indefinitely (quick reactions)
244+ def time_side_effect ():
245+ while True :
246+ yield 0
247+ yield 0.5
248+
249+ with patch ('src.location.docks.print' ), \
250+ patch ('src.location.docks.sys.stdout.flush' ), \
251+ patch ('src.location.docks.time.sleep' ), \
252+ patch ('src.location.docks.time.time' , side_effect = time_side_effect ()), \
253+ patch ('src.location.docks.input' , return_value = "" ), \
254+ patch ('src.location.docks.random.randint' , side_effect = [3 , 6 ]):
255+
256+ docksInstance .timeService .increaseTime = MagicMock ()
257+
258+ # call
259+ docksInstance .fish ()
260+
261+ # check - with 100% success rate, should get full catch
262+ assert docksInstance .player .fishCount >= 3 # Should get good catch with all successes
263+ assert docksInstance .stats .totalFishCaught >= 3
264+
265+
266+ def test_fish_interactive_failure ():
267+ # Test that slow reactions result in fewer catches
268+ docksInstance = createDocks ()
269+ docksInstance .userInterface .lotsOfSpace = MagicMock ()
270+ docksInstance .userInterface .divider = MagicMock ()
271+
272+ # Create a side effect that alternates between 0 and 3.0 indefinitely (slow reactions)
273+ def time_side_effect ():
274+ while True :
275+ yield 0
276+ yield 3.0
277+
278+ with patch ('src.location.docks.print' ), \
279+ patch ('src.location.docks.sys.stdout.flush' ), \
280+ patch ('src.location.docks.time.sleep' ), \
281+ patch ('src.location.docks.time.time' , side_effect = time_side_effect ()), \
282+ patch ('src.location.docks.input' , return_value = "" ), \
283+ patch ('src.location.docks.random.randint' , side_effect = [3 , 10 ]):
284+
285+ docksInstance .timeService .increaseTime = MagicMock ()
286+
287+ # call
288+ docksInstance .fish ()
289+
290+ # check - with 0% success rate, should still get at least 1 fish minimum
291+ assert docksInstance .player .fishCount == 1 # Minimum 1 fish even with failures
292+ assert docksInstance .stats .totalFishCaught == 1
0 commit comments