diff --git a/force_bdss/mco/events.py b/force_bdss/core_driver_events.py similarity index 57% rename from force_bdss/mco/events.py rename to force_bdss/core_driver_events.py index 216e1effa30d7b1e81e0a8f82312310bb3fae583..b656bde49b803ea1f46f59aa0930422ba61c1270 100644 --- a/force_bdss/mco/events.py +++ b/force_bdss/core_driver_events.py @@ -1,19 +1,21 @@ -from traits.api import HasStrictTraits, Tuple +from traits.api import HasStrictTraits, Tuple, Str -class BaseMCOEvent(HasStrictTraits): - """Base event for the MCO""" +class BaseDriverEvent(HasStrictTraits): + """Base event for the Driver""" -class MCOStartEvent(BaseMCOEvent): +class MCOStartEvent(BaseDriverEvent): """MCO should emit this event when the evaluation starts.""" + input_names = Str() + output_names = Str() -class MCOFinishEvent(BaseMCOEvent): +class MCOFinishEvent(BaseDriverEvent): """MCO should emit this event when the evaluation ends.""" -class MCOProgressEvent(BaseMCOEvent): +class MCOProgressEvent(BaseDriverEvent): """MCO should emit this event for every new evaluation that has been completed. It carries data about the evaluation, specifically the input data (MCO parameter values) and the resulting output (KPIs).""" diff --git a/force_bdss/core_mco_driver.py b/force_bdss/core_mco_driver.py index e2678daee1837df4cf8595ee4618008a988c47d3..3048172608c7308c5527dcf8308d94ea4cce0fba 100644 --- a/force_bdss/core_mco_driver.py +++ b/force_bdss/core_mco_driver.py @@ -14,6 +14,7 @@ from .io.workflow_reader import ( InvalidVersionException, InvalidFileException ) +from .core_driver_events import MCOStartEvent, MCOFinishEvent, MCOProgressEvent log = logging.getLogger(__name__) CORE_MCO_DRIVER_ID = plugin_id("core", "CoreMCODriver") @@ -31,7 +32,9 @@ class CoreMCODriver(BaseCoreDriver): @on_trait_change("application:started") def application_started(self): + self._deliver_start_event() self.mco.run(self.workflow.mco) + self._deliver_event(MCOFinishEvent()) @on_trait_change("application:stopping") def application_stopping(self): @@ -50,8 +53,25 @@ class CoreMCODriver(BaseCoreDriver): mco_factory = mco_model.factory return mco_factory.create_optimizer() - @on_trait_change("mco:event") - def _handle_mco_event(self, event): + def _deliver_start_event(self): + output_names = [] + for kpi in self.workflow.kpi_calculators: + output_names.extend(kpi.output_slot_names) + + self._deliver_event(MCOStartEvent( + input_names=[p.name for p in self.workflow.mco.parameters], + output_names=output_names + )) + + @on_trait_change("mco:new_data") + def _deliver_progress_event(self, event): + self._deliver_event(MCOProgressEvent( + input=event['input'], + output=event['output'] + )) + + def _deliver_event(self, event): + """ Delivers an event to the listeners """ for listener in self.listeners[:]: try: listener.deliver(event) diff --git a/force_bdss/core_plugins/dummy/dummy_dakota/dakota_optimizer.py b/force_bdss/core_plugins/dummy/dummy_dakota/dakota_optimizer.py index 9f9de5d87192fa818b1bd4e9ae49a510b3489827..8ceddba8282f9ca32a0c3ceae0ab460c26b4c026 100644 --- a/force_bdss/core_plugins/dummy/dummy_dakota/dakota_optimizer.py +++ b/force_bdss/core_plugins/dummy/dummy_dakota/dakota_optimizer.py @@ -4,8 +4,6 @@ import itertools import collections from force_bdss.api import BaseMCO -from force_bdss.mco.events import MCOStartEvent, MCOFinishEvent, \ - MCOProgressEvent def rotated_range(start, stop, starting_value): @@ -18,8 +16,6 @@ def rotated_range(start, stop, starting_value): class DummyDakotaOptimizer(BaseMCO): def run(self, model): - self.notify_event(MCOStartEvent()) - parameters = model.parameters values = [] @@ -45,9 +41,7 @@ class DummyDakotaOptimizer(BaseMCO): out = ps.communicate( " ".join([str(v) for v in value]).encode("utf-8")) out_data = out[0].decode("utf-8").split() - self.notify_event(MCOProgressEvent( - input=tuple(value), - output=tuple(out_data), - )) - - self.notify_event(MCOFinishEvent()) + self.new_data = { + 'input': tuple(value), + 'output': tuple(out_data) + } diff --git a/force_bdss/mco/base_mco.py b/force_bdss/mco/base_mco.py index ae9d89b72092c962ebc7f6415d3fa8166613711e..2c576d26d295a8a128d672662a9b1930aba6d9b1 100644 --- a/force_bdss/mco/base_mco.py +++ b/force_bdss/mco/base_mco.py @@ -17,6 +17,9 @@ class BaseMCO(ABCHasStrictTraits): #: Triggered when an event occurs. event = Event(BaseMCOEvent) + # Event triggered when the mco wants to send new data to listeners + new_data = Event() + def __init__(self, factory, *args, **kwargs): """Initializes the MCO. @@ -39,18 +42,3 @@ class BaseMCO(ABCHasStrictTraits): An instance of the model information, as created from create_model() """ - - def notify_event(self, event): - """Method based interface to deliver an event, instead of - assignment to traits. - - Sends the event, synchronously. When the routine returns, - listeners have been fully informed (they might, however, handle - the event asynchronously at their convenience) - - Parameters - ---------- - event: BaseMCOEvent - The event to deliver. - """ - self.event = event