Skip to content

Commit ef798af

Browse files
committed
remove some SM hooks from context and move code to actions
1 parent 1d93649 commit ef798af

6 files changed

Lines changed: 68 additions & 70 deletions

File tree

render_machine/actions/fix_conformance_test.py

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,19 +9,41 @@
99
from render_machine.actions.base_action import BaseAction
1010
from render_machine.implementation_code_helpers import ImplementationCodeHelpers
1111
from render_machine.render_context import RenderContext
12-
from render_machine.render_types import TestExecutionPhase
12+
from render_machine.render_types import RenderError, TestExecutionPhase
13+
14+
MAX_CONFORMANCE_TEST_FIX_ATTEMPTS = 20
15+
MAX_CONFORMANCE_TEST_RERENDER_ATTEMPTS = 1
1316

1417

1518
class FixConformanceTest(BaseAction):
1619
IMPLEMENTATION_CODE_NOT_UPDATED = "implementation_code_not_updated"
1720
IMPLEMENTATION_CODE_UPDATED = "implementation_code_updated"
21+
LIMIT_EXCEEDED_OUTCOME = "conformance_test_fix_limit_exceeded"
22+
REGENERATE_CONFORMANCE_TESTS_OUTCOME = "regenerate_conformance_tests"
1823

1924
ISSUE_REASON_CODE_CONFORMANCE_TESTS = 0
2025
ISSUE_REASON_CODE_IMPLEMENTATION_CODE = 1
2126
ISSUE_REASON_CODE_CONFLICTING_REQUIREMENTS = 2
2227
ISSUE_REASON_CODE_CONFLICTING_ACCEPTANCE_TESTS = 3
2328

2429
def execute(self, render_context: RenderContext, previous_action_payload: Any | None):
30+
ctx = render_context.conformance_tests_running_context
31+
ctx.fix_attempts += 1
32+
33+
if ctx.fix_attempts >= MAX_CONFORMANCE_TEST_FIX_ATTEMPTS:
34+
if ctx.conformance_tests_render_attempts >= MAX_CONFORMANCE_TEST_RERENDER_ATTEMPTS:
35+
error_msg = f"The renderer was unable to produce an implementation that passes conformance tests for functionality '{render_context.frid_context.frid}' after many attempts. Please review and rewrite the specification. (Render ID: {render_context.run_state.render_id})"
36+
render_context.last_error_message = error_msg
37+
return (
38+
self.LIMIT_EXCEEDED_OUTCOME,
39+
RenderError.encode(message=error_msg).to_payload(),
40+
)
41+
else:
42+
ctx.regenerating_conformance_tests = True
43+
return self.REGENERATE_CONFORMANCE_TESTS_OUTCOME, None
44+
45+
console.info(f"Running conformance tests attempt {ctx.fix_attempts + 1}.")
46+
2547
console.info(
2648
f"Fixing conformance test for functionality {render_context.conformance_tests_running_context.current_testing_frid} in module {render_context.conformance_tests_running_context.current_testing_module_name}."
2749
)

render_machine/actions/prepare_testing_environment.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,12 @@ class PrepareTestingEnvironment(BaseAction):
1212
FAILED_OUTCOME = "testing_environment_preparation_failed"
1313

1414
def execute(self, render_context: RenderContext, _previous_action_payload: Any | None):
15+
if (
16+
render_context.prepare_environment_script is None
17+
or not render_context.conformance_tests_running_context.should_prepare_testing_environment
18+
):
19+
return self.SUCCESSFUL_OUTCOME, None
20+
1521
console.info(
1622
f"Running testing environment preparation script {render_context.prepare_environment_script} for build folder {render_context.build_folder}."
1723
)

render_machine/actions/refactor_code.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,13 +5,31 @@
55
from render_machine.actions.base_action import BaseAction
66
from render_machine.implementation_code_helpers import ImplementationCodeHelpers
77
from render_machine.render_context import RenderContext
8+
from render_machine.render_types import RenderError
9+
10+
MAX_REFACTORING_ITERATIONS = 5
811

912

1013
class RefactorCode(BaseAction):
1114
SUCCESSFUL_OUTCOME = "refactoring_successful"
1215
NO_FILES_REFACTORED_OUTCOME = "no_files_refactored"
16+
ITERATION_LIMIT_EXCEEDED_OUTCOME = "refactoring_iteration_limit_exceeded"
1317

1418
def execute(self, render_context: RenderContext, _previous_action_payload: Any | None):
19+
if render_context.frid_context.refactoring_iteration == 0:
20+
console.info("Refactoring the generated code...")
21+
22+
render_context.frid_context.refactoring_iteration += 1
23+
24+
if render_context.frid_context.refactoring_iteration >= MAX_REFACTORING_ITERATIONS:
25+
error_message = "Refactoring iterations limit of {MAX_REFACTORING_ITERATIONS} reached for functionality {render_context.frid_context.frid}."
26+
render_context.last_error_message = error_message
27+
28+
return (
29+
self.ITERATION_LIMIT_EXCEEDED_OUTCOME,
30+
RenderError.encode(message=error_message).to_payload(),
31+
)
32+
1533
existing_files, existing_files_content = ImplementationCodeHelpers.fetch_existing_files(
1634
render_context.build_folder
1735
)

render_machine/actions/render_functional_requirement.py

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,22 @@
1616
class RenderFunctionalRequirement(BaseAction):
1717
SUCCESSFUL_OUTCOME = "code_and_unit_tests_generated"
1818
FUNCTIONAL_REQUIREMENT_TOO_COMPLEX_OUTCOME = "functional_requirement_too_complex"
19+
ITERATION_LIMIT_EXCEEDED_OUTCOME = "frid_iteration_limit_exceeded"
1920

2021
def execute(self, render_context: RenderContext, _previous_action_payload: Any | None):
22+
if render_context.frid_context.functional_requirement_render_attempts >= MAX_CODE_GENERATION_RETRIES:
23+
error_msg = f"Unittests could not be fixed after rendering the functionality {render_context.frid_context.frid} for the {MAX_CODE_GENERATION_RETRIES} times."
24+
render_context.last_error_message = error_msg
25+
return self.ITERATION_LIMIT_EXCEEDED_OUTCOME, None
26+
27+
render_context.frid_context.functional_requirement_render_attempts += 1
28+
29+
if render_context.frid_context.functional_requirement_render_attempts > 1:
30+
console.info(
31+
f"Unittests could not be fixed after rendering the functionality. "
32+
f"Restarting rendering functionality {render_context.frid_context.frid} from scratch."
33+
)
34+
2135
render_utils.revert_changes_for_frid(render_context)
2236
existing_files, existing_files_content = ImplementationCodeHelpers.fetch_existing_files(
2337
render_context.build_folder

render_machine/render_context.py

Lines changed: 0 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,6 @@
2323
)
2424

2525
MAX_UNITTEST_FIX_ATTEMPTS = 20
26-
MAX_CODE_GENERATION_RETRIES = 2
27-
MAX_CONFORMANCE_TEST_RERENDER_ATTEMPTS = 1
28-
MAX_REFACTORING_ITERATIONS = 5
29-
MAX_CONFORMANCE_TEST_FIX_ATTEMPTS = 20
3026
MAX_FUNCTIONAL_REQUIREMENT_RENDER_ATTEMPTS_FAILED_UNIT_DURING_CONFORMANCE_TESTS = 2
3127

3228

@@ -165,20 +161,6 @@ def start_implementing_frid(self):
165161
self.run_state.current_frid = frid
166162
return
167163

168-
def check_frid_iteration_limit(self):
169-
if self.frid_context.functional_requirement_render_attempts >= MAX_CODE_GENERATION_RETRIES:
170-
error_msg = f"Unittests could not be fixed after rendering the functionality {self.frid_context.frid} for the {MAX_CODE_GENERATION_RETRIES} times."
171-
self.dispatch_error(error_msg)
172-
173-
self.frid_context.functional_requirement_render_attempts += 1
174-
175-
if self.frid_context.functional_requirement_render_attempts > 1:
176-
# this if is intended just for logging
177-
console.info(
178-
f"Unittests could not be fixed after rendering the functionality. "
179-
f"Restarting rendering the functionality {self.frid_context.frid} from scratch."
180-
)
181-
182164
def has_next_frid(self) -> bool:
183165
next_frid = plain_spec.get_next_frid(self.plain_source_tree, self.frid_context.frid)
184166
if self.render_range is None or len(self.render_range) == 0:
@@ -310,26 +292,6 @@ def _on_unit_test_limit_exceeded_in_refactoring(self):
310292
git_utils.revert_changes(self.build_folder)
311293
self.machine.dispatch(triggers.START_NEW_REFACTORING_ITERATION)
312294

313-
def start_refactoring_code(self):
314-
315-
if self.frid_context.refactoring_iteration == 0:
316-
console.info("Refactoring the generated code...")
317-
318-
self.frid_context.refactoring_iteration += 1
319-
320-
if self.frid_context.refactoring_iteration >= MAX_REFACTORING_ITERATIONS:
321-
console.info(
322-
f"Refactoring iterations limit of {MAX_REFACTORING_ITERATIONS} reached for functionality {self.frid_context.frid}."
323-
)
324-
self.machine.dispatch(triggers.PROCEED_FRID_PROCESSING)
325-
326-
def start_testing_environment_preparation(self):
327-
if (
328-
self.prepare_environment_script is None
329-
or not self.conformance_tests_running_context.should_prepare_testing_environment
330-
):
331-
self.machine.dispatch(triggers.MARK_TESTING_ENVIRONMENT_PREPARED)
332-
333295
def start_conformance_tests_processing(self):
334296
console.info("Implementing conformance tests...")
335297
current_frid_specifications, _ = plain_spec.get_specifications_for_frid(
@@ -589,23 +551,6 @@ def start_conformance_tests_for_frid(self):
589551
# Should never reach here
590552
raise RuntimeError(f"Unexpected execution phase: {ctx.execution_phase}")
591553

592-
def start_fixing_conformance_tests(self):
593-
self.conformance_tests_running_context.fix_attempts += 1
594-
595-
if self.conformance_tests_running_context.fix_attempts >= MAX_CONFORMANCE_TEST_FIX_ATTEMPTS:
596-
if (
597-
self.conformance_tests_running_context.conformance_tests_render_attempts
598-
>= MAX_CONFORMANCE_TEST_RERENDER_ATTEMPTS
599-
):
600-
error_msg = f"The renderer was unable to produce an implementation that passes conformance tests for functionality '{self.frid_context.frid}' after many attempts. Please review and rewrite the specification. (Render ID: {self.run_state.render_id})"
601-
self.dispatch_error(error_msg)
602-
else:
603-
self.conformance_tests_running_context.regenerating_conformance_tests = True
604-
self.machine.dispatch(triggers.MARK_REGENERATION_OF_CONFORMANCE_TESTS)
605-
606-
def finish_fixing_conformance_tests(self):
607-
console.info(f"Running conformance tests attempt {self.conformance_tests_running_context.fix_attempts + 1}.")
608-
609554
def start_render_completed(self):
610555
self.run_state.set_render_succeeded(True)
611556

render_machine/state_machine_config.py

Lines changed: 7 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -73,12 +73,14 @@ def get_action_result_triggers_map(self) -> Dict[str, str]:
7373
PrepareRepositories.SUCCESSFUL_OUTCOME: triggers.START_RENDER,
7474
RenderFunctionalRequirement.SUCCESSFUL_OUTCOME: triggers.RENDER_FUNCTIONAL_REQUIREMENT,
7575
RenderFunctionalRequirement.FUNCTIONAL_REQUIREMENT_TOO_COMPLEX_OUTCOME: triggers.HANDLE_ERROR,
76+
RenderFunctionalRequirement.ITERATION_LIMIT_EXCEEDED_OUTCOME: triggers.HANDLE_ERROR,
7677
RunUnitTests.SUCCESSFUL_OUTCOME: triggers.MARK_UNIT_TESTS_PASSED,
7778
RunUnitTests.FAILED_OUTCOME: triggers.MARK_UNIT_TESTS_FAILED,
7879
RunUnitTests.UNRECOVERABLE_ERROR_OUTCOME: triggers.HANDLE_ERROR,
7980
FixUnitTests.SUCCESSFUL_OUTCOME: triggers.MARK_UNIT_TESTS_READY,
8081
RefactorCode.SUCCESSFUL_OUTCOME: triggers.REFACTOR_CODE,
8182
RefactorCode.NO_FILES_REFACTORED_OUTCOME: triggers.PROCEED_FRID_PROCESSING,
83+
RefactorCode.ITERATION_LIMIT_EXCEEDED_OUTCOME: triggers.PROCEED_FRID_PROCESSING,
8284
CommitImplementationCodeChanges.SUCCESSFUL_OUTCOME: triggers.PROCEED_FRID_PROCESSING,
8385
FinishFunctionalRequirement.SUCCESSFUL_OUTCOME: triggers.PROCEED_FRID_PROCESSING,
8486
CreateDist.SUCCESSFUL_OUTCOME: triggers.FINISH_RENDER,
@@ -90,6 +92,8 @@ def get_action_result_triggers_map(self) -> Dict[str, str]:
9092
RunConformanceTests.UNRECOVERABLE_ERROR_OUTCOME: triggers.HANDLE_ERROR,
9193
FixConformanceTest.IMPLEMENTATION_CODE_NOT_UPDATED: triggers.MARK_CONFORMANCE_TESTS_READY,
9294
FixConformanceTest.IMPLEMENTATION_CODE_UPDATED: triggers.MARK_UNIT_TESTS_READY,
95+
FixConformanceTest.LIMIT_EXCEEDED_OUTCOME: triggers.HANDLE_ERROR,
96+
FixConformanceTest.REGENERATE_CONFORMANCE_TESTS_OUTCOME: triggers.MARK_REGENERATION_OF_CONFORMANCE_TESTS,
9397
CommitConformanceTestsChanges.SUCCESSFUL_OUTCOME_IMPLEMENTATION_UPDATED: triggers.MARK_NEXT_CONFORMANCE_TESTS_POSTPROCESSING_STEP,
9498
CommitConformanceTestsChanges.SUCCESSFUL_OUTCOME_IMPLEMENTATION_NOT_UPDATED: triggers.PROCEED_FRID_PROCESSING,
9599
SummarizeConformanceTests.SUCCESSFUL_OUTCOME: triggers.MARK_NEXT_CONFORMANCE_TESTS_POSTPROCESSING_STEP,
@@ -135,16 +139,9 @@ def get_processing_conformance_tests_states(self, render_context: RenderContext)
135139
"name": States.CONFORMANCE_TESTING_INITIALISED.value,
136140
"on_enter": render_context.start_conformance_tests_for_frid,
137141
},
138-
{
139-
"name": States.CONFORMANCE_TEST_GENERATED.value,
140-
"on_enter": render_context.start_testing_environment_preparation,
141-
},
142+
States.CONFORMANCE_TEST_GENERATED.value,
142143
States.CONFORMANCE_TEST_ENV_PREPARED.value,
143-
{
144-
"name": States.CONFORMANCE_TEST_FAILED.value,
145-
"on_enter": render_context.start_fixing_conformance_tests,
146-
"on_exit": render_context.finish_fixing_conformance_tests,
147-
},
144+
States.CONFORMANCE_TEST_FAILED.value,
148145
self.get_processing_unit_tests_states(
149146
render_context, render_context._on_unit_test_limit_exceeded_in_conformance_tests
150147
),
@@ -164,7 +161,6 @@ def get_states(self, render_context: RenderContext) -> List[Any]:
164161
refactoring_code_states = {
165162
"name": States.REFACTORING_CODE.value,
166163
"initial": States.READY_FOR_REFACTORING.value,
167-
"on_enter": render_context.start_refactoring_code,
168164
"children": [
169165
States.READY_FOR_REFACTORING.value,
170166
self.get_processing_unit_tests_states(
@@ -183,10 +179,7 @@ def get_states(self, render_context: RenderContext) -> List[Any]:
183179
"on_exit": render_context.finish_implementing_frid,
184180
"children": [
185181
{"name": States.STEP_COMPLETED.value},
186-
{
187-
"name": States.READY_FOR_FRID_IMPLEMENTATION.value,
188-
"on_enter": render_context.check_frid_iteration_limit,
189-
},
182+
States.READY_FOR_FRID_IMPLEMENTATION.value,
190183
self.get_processing_unit_tests_states(
191184
render_context, render_context._on_unit_test_limit_exceeded_in_implementation
192185
),

0 commit comments

Comments
 (0)