diff --git a/aiida/backends/sqlalchemy/models/workflow.py b/aiida/backends/sqlalchemy/models/workflow.py index 1068623af0..7421bdcd5b 100644 --- a/aiida/backends/sqlalchemy/models/workflow.py +++ b/aiida/backends/sqlalchemy/models/workflow.py @@ -88,18 +88,14 @@ def set_script_md5(self, md5): self.script_md5 = md5 self.save() - # def add_data(self, dict, d_type): - # for k in dict.keys(): - # p, create = self.data.get_or_create(name=k, data_type=d_type) - # p.set_value(dict[k]) - def add_data(self, dict, d_type): for k in dict.keys(): p, create = self._get_or_create_data(name=k, data_type=d_type) p.set_value(dict[k]) def _get_or_create_data(self, name, data_type): - match_data = {name: _ for _ in self.data if _.name == name} + match_data = {name: _ for _ in self.data if _.name == name + and _.data_type == data_type} if not match_data: # create case dbdata = DbWorkflowData(parent_id=self.id, name=name, data_type=data_type) @@ -250,7 +246,8 @@ def set_value(self, arg): try: if isinstance(arg, Node) or issubclass(arg.__class__, Node): if arg.pk is None: - raise ValueError("Cannot add an unstored node as an attribute of a Workflow!") + raise ValueError("Cannot add an unstored node as an " + "attribute of a Workflow!") sess = get_scoped_session() self.aiida_obj = sess.merge(arg.dbnode, load=True) self.value_type = wf_data_value_types.AIIDA diff --git a/aiida/backends/tests/workflows.py b/aiida/backends/tests/workflows.py index 9caa7d9d26..ce8b193893 100644 --- a/aiida/backends/tests/workflows.py +++ b/aiida/backends/tests/workflows.py @@ -241,6 +241,37 @@ def test_failing_calc_in_wf(self): if handler: handler.setLevel(original_level) + def test_result_parameter_name_colision(self): + """ + This test checks that the the workflow parameters and results do not + collide. This was a problem in SQLA (Issue #960) but a test for both + backends is added (for completeness). + """ + # Creating a simple workflow & storing it + wf = WFTestEmpty() + wf.store() + + # Set some parameters + params = {'band_calculation_set': 2, + 'codename': 'pw-5.2.0', + 'pseudo_family': 'SSSP_v0.7_eff_PBE'} + wf.set_params(params) + + # Add some results that their names collide with the parameter names + wf.add_result('structure', 'test_string_1') + wf.add_result('codename', 'test_string_2') + + # Check that we have the correct results + self.assertDictEqual( + {'structure': 'test_string_1', 'codename': 'test_string_2'}, + wf.get_results(), "The workflow results are not the expected " + "ones.") + + # Check that we have the correct parameters + self.assertDictEqual(params, wf.get_parameters(), + "The workflow parameters are not the expected " + "ones.") + def tearDown(self): """ Cleaning the database after each test. Since I don't