Browse Source

Patched AL execution

Yentl Van Tendeloo 5 years ago
parent
commit
e333bcae9e

+ 1 - 0
bootstrap/core_algorithm.alc

@@ -1445,6 +1445,7 @@ Void function spawn_activity(returnvalue : Element, transformation_id : String,
 				model_overwrite(result[key], get_entry_id(outputs[key]), get_entry_id(output_map[key]))
 
 		set_add(returnvalue, "Success")
+		output("Success")
 
 	while (other_has_output(get_taskname())):
 		sleep(1)

+ 26 - 3
unit/test_all.py

@@ -4357,7 +4357,7 @@ class TestModelverse(unittest.TestCase):
         assert len(lst) == 1
         assert lst[0]["__type"] == "A"
         assert lst[0]["name"] == None
-        assert lst[0]["__id"].startswith("__")
+        assert lst[0]["__id"] == "a"
 
         # Execute activity with non-existing model (input)
         try:
@@ -4442,10 +4442,33 @@ class TestModelverse(unittest.TestCase):
         assert len(element_list_nice("users/user/test/a")) == len(element_list_nice("users/user/test/aaa"))
 
         # Make sure that models are not written when returning False
-        transformation_add_AL({"MODEL_A": "users/user/test/A"}, {"MODEL_B": "users/user/test/B"}, "users/user/test/g", default_code_false)
-        transformation_execute_AL("users/user/test/g", {"MODEL_A": "users/user/test/a"}, {"MODEL_B": "users/user/test/bb"})
+        transformation_add_AL({"MODEL_A": "users/user/test/A"}, {"MODEL_B": "users/user/test/B"}, "users/user/test/h", default_code_false)
+        transformation_execute_AL("users/user/test/h", {"MODEL_A": "users/user/test/a"}, {"MODEL_B": "users/user/test/bb"})
         assert "bb" not in model_list("users/user/test")
 
+        # Try out SC communication: requires back and forth computation
+        code_SC = """
+            include "io.alh"
+            include "primitives.alh"
+
+            Boolean function main(model : Element):
+                output("init")
+                log("Init OK")
+                output(cast_integer(input()) + cast_integer(input()))
+                log("Sent out value")
+                return True!
+        """
+        import exec_AL
+        ctrl = exec_AL.Controller(keep_running=False)
+        thrd = threading.Thread(target=ctrl.start)
+        thrd.daemon = True
+        transformation_add_AL({"MODEL_A": "users/user/test/A"}, {"MODEL_B": "users/user/test/B"}, "users/user/test/i", code_SC)
+        thrd.start()
+        print("STart exec")
+        transformation_execute_AL("users/user/test/i", {"MODEL_A": "users/user/test/a"}, {"MODEL_B": "users/user/test/bb"}, statechart=(ctrl, "inp", "outp"))
+        print("EXEC OK")
+        thrd.join()
+
     """
     def test_op_model_render(self):
     def test_op_transformation_execute_MT(self):

+ 29 - 10
wrappers/classes/modelverse.xml

@@ -1664,22 +1664,41 @@
                             </onentry>
 
                             <state id="forwarding">
+                                <onentry>
+                                    <script>
+                                        print("FORWARDING...")
+                                    </script>
+                                </onentry>
+                                <onexit>
+                                    <script>
+                                        print("STOP FORWARDING...")
+                                    </script>
+                                </onexit>
                                 <transition cond="self.expect_response('Success', pop=False) or self.expect_response('Failure', pop=False)" target="../../../history">
                                     <raise event="result">
                                         <parameter expr="True if self.responses.pop(0) == 'Success' else False"/>
                                     </raise>
+                                    <script>
+                                        print("SUCC OR FAIL")
+                                    </script>
                                 </transition>
 
-                                <transition cond="not (self.expect_response('Success', pop=False) or self.expect_response('Failure', pop=False)) and self.expect_response_partial('', pop=False)" target=".">
+                                <transition cond="self.responses and not (self.expect_response('Success', pop=False) or self.expect_response('Failure', pop=False))" target=".">
                                     <raise event="data_output">
                                         <parameter expr="self.responses.pop(0)"/>
                                     </raise>
+                                    <script>
+                                        print("DATA")
+                                    </script>
                                 </transition>
 
                                 <transition cond="self.expect_input('data_input')" target=".">
                                     <raise event="request">
                                         <parameter expr="self.inputs.pop(0)['parameters']"/>
                                     </raise>
+                                    <script>
+                                        print("DINPUT")
+                                    </script>
                                 </transition>
                             </state>
                         </state>
@@ -1698,28 +1717,28 @@
                                     <raise event="result">
                                         <parameter expr="self.responses.pop(0).split(': ')[1]"/>
                                     </raise>
+                                    <script>
+                                        print("EDITING")
+                                    </script>
                                 </transition>
 
                                 <transition cond="self.expect_response_partial('Nothing to modify', pop=True)" target=".">
                                     <raise event="result">
                                         <parameter expr="None"/>
                                     </raise>
+                                    <script>
+                                        print("NOTHING")
+                                    </script>
                                 </transition>
 
                                 <transition cond="self.inputs" target="../../../history">
+                                    <script>
+                                        print("INPUTS")
+                                    </script>
                                     <raise event="request">
                                         <parameter expr="0"/>
                                     </raise>
                                 </transition>
-
-                                <!--
-                                <transition cond="self.expect_response_partial('', pop=False)" target=".">
-                                    <script>
-                                        print("ERROR: " + str(self.responses))
-                                        self.responses.pop(0)
-                                    </script>
-                                </transition>
-                                -->
                             </state>
                         </state>
                     </state>

+ 6 - 2
wrappers/modelverse.py

@@ -182,8 +182,8 @@ def __run_new_modelverse_activity(address, username, password, taskname, pipe, c
 
             # Fetch output from the MV
             response = responses.fetch(0)
-            print("Got response: " + str(response))
             if response is not None:
+                print("Got response: " + str(response))
                 if response.name == "data_output":
                     # Got output of MV, so forward to SCCD
                     if pipe is not None:
@@ -192,6 +192,7 @@ def __run_new_modelverse_activity(address, username, password, taskname, pipe, c
                     print("Got result: " + str(response))
                     # Finished execution, so continue and return result
                     if pipe is not None:
+                        print("SEND TERMINATE")
                         pipe.send(("terminate", []))
                         pipe.close()
                     return
@@ -202,8 +203,10 @@ def __run_new_modelverse_activity(address, username, password, taskname, pipe, c
             # Fetch output from the SC
             if pipe is not None and pipe.poll():
                 response = pipe.recv()
+                print("Got data: " + str(response))
 
                 if response.name == "output":
+                    print("ADDED")
                     controller.addInput(Event("data_input", "action_in", [response.parameters]))
                 else:
                     raise Exception("Unknown data from SC to MV: " + str(response))
@@ -236,8 +239,8 @@ def _process_SC(statechart, port_sc, taskname):
             empty = False
 
         response = port_sc.fetch(0)
-        print("Got response in process: " + str(response))
         if response is not None:
+            print("Got response in process: " + str(response))
             p2c_pipe.send(response)
             empty = False
 
@@ -394,6 +397,7 @@ def transformation_add_MANUAL(source_metamodels, target_metamodels, operation_na
 def __transformation_execute(operation_name, input_models_dict, output_models_dict, statechart, tracability_model, fetch_output):
     if statechart is not None:
         port_sc = statechart[0].addOutputListener(statechart[2])
+        print("Added output listener to port " + str(statechart[2]))
 
     INPUT("transformation_execute", [operation_name, input_models_dict, output_models_dict, tracability_model, fetch_output])
     taskname = OUTPUT()

+ 15 - 1
wrappers/modelverse_SCCD.py

@@ -504,6 +504,8 @@ class Modelverse(RuntimeClassBase):
         
         # state /initialized/behaviour/wait_for_action/activity/SC/forwarding
         self.states["/initialized/behaviour/wait_for_action/activity/SC/forwarding"] = State(104, "/initialized/behaviour/wait_for_action/activity/SC/forwarding", self)
+        self.states["/initialized/behaviour/wait_for_action/activity/SC/forwarding"].setEnter(self._initialized_behaviour_wait_for_action_activity_SC_forwarding_enter)
+        self.states["/initialized/behaviour/wait_for_action/activity/SC/forwarding"].setExit(self._initialized_behaviour_wait_for_action_activity_SC_forwarding_exit)
         
         # state /initialized/behaviour/wait_for_action/activity/OP
         self.states["/initialized/behaviour/wait_for_action/activity/OP"] = State(105, "/initialized/behaviour/wait_for_action/activity/OP", self)
@@ -2287,6 +2289,12 @@ class Modelverse(RuntimeClassBase):
     def _initialized_behaviour_operations_service_stop_enter(self):
         self.raiseInternalEvent(Event("request", None, [['service_stop']]))
     
+    def _initialized_behaviour_wait_for_action_activity_SC_forwarding_enter(self):
+        print("FORWARDING...")
+    
+    def _initialized_behaviour_wait_for_action_activity_SC_forwarding_exit(self):
+        print("STOP FORWARDING...")
+    
     def _initialized_behaviour_going_manual_init_enter(self):
         self.current_model = self.actions[0]["parameters"][0]
     
@@ -3344,18 +3352,21 @@ class Modelverse(RuntimeClassBase):
     
     def _initialized_behaviour_wait_for_action_activity_SC_forwarding_0_exec(self, parameters):
         self.raiseInternalEvent(Event("result", None, [True if self.responses.pop(0) == 'Success' else False]))
+        print("SUCC OR FAIL")
     
     def _initialized_behaviour_wait_for_action_activity_SC_forwarding_0_guard(self, parameters):
         return self.expect_response('Success', pop=False) or self.expect_response('Failure', pop=False)
     
     def _initialized_behaviour_wait_for_action_activity_SC_forwarding_1_exec(self, parameters):
         self.raiseInternalEvent(Event("data_output", None, [self.responses.pop(0)]))
+        print("DATA")
     
     def _initialized_behaviour_wait_for_action_activity_SC_forwarding_1_guard(self, parameters):
-        return not (self.expect_response('Success', pop=False) or self.expect_response('Failure', pop=False)) and self.expect_response_partial('', pop=False)
+        return self.responses and not (self.expect_response('Success', pop=False) or self.expect_response('Failure', pop=False))
     
     def _initialized_behaviour_wait_for_action_activity_SC_forwarding_2_exec(self, parameters):
         self.raiseInternalEvent(Event("request", None, [self.inputs.pop(0)['parameters']]))
+        print("DINPUT")
     
     def _initialized_behaviour_wait_for_action_activity_SC_forwarding_2_guard(self, parameters):
         return self.expect_input('data_input')
@@ -3365,17 +3376,20 @@ class Modelverse(RuntimeClassBase):
     
     def _initialized_behaviour_wait_for_action_activity_OP_forwarding_1_exec(self, parameters):
         self.raiseInternalEvent(Event("result", None, [self.responses.pop(0).split(': ')[1]]))
+        print("EDITING")
     
     def _initialized_behaviour_wait_for_action_activity_OP_forwarding_1_guard(self, parameters):
         return self.expect_response_partial('Please edit this model before sending next input: ', pop=False)
     
     def _initialized_behaviour_wait_for_action_activity_OP_forwarding_2_exec(self, parameters):
         self.raiseInternalEvent(Event("result", None, [None]))
+        print("NOTHING")
     
     def _initialized_behaviour_wait_for_action_activity_OP_forwarding_2_guard(self, parameters):
         return self.expect_response_partial('Nothing to modify', pop=True)
     
     def _initialized_behaviour_wait_for_action_activity_OP_forwarding_3_exec(self, parameters):
+        print("INPUTS")
         self.raiseInternalEvent(Event("request", None, [0]))
     
     def _initialized_behaviour_wait_for_action_activity_OP_forwarding_3_guard(self, parameters):