diff --git a/crc/scripts/get_study_status.py b/crc/scripts/get_study_status.py new file mode 100644 index 00000000..8bc34fcb --- /dev/null +++ b/crc/scripts/get_study_status.py @@ -0,0 +1,18 @@ +from crc import session +from crc.models.study import StudyModel +from crc.scripts.script import Script + + +class GetStudyStatus(Script): + + def get_description(self): + return """Get the status of the current study. + Status can be one of `in_progress`, `hold`, `open_for_enrollment`, or `abandoned`.""" + + def do_task_validate_only(self, task, study_id, workflow_id, *args, **kwargs): + return self.do_task(task, study_id, workflow_id, *args, **kwargs) + + def do_task(self, task, study_id, workflow_id, *args, **kwargs): + study_status = session.query(StudyModel.status).filter(StudyModel.id == study_id).scalar() + if study_status: + return study_status.value diff --git a/crc/scripts/set_study_status.py b/crc/scripts/set_study_status.py new file mode 100644 index 00000000..32397d0c --- /dev/null +++ b/crc/scripts/set_study_status.py @@ -0,0 +1,69 @@ +from crc import session +from crc.api.common import ApiError +from crc.models.study import StudyModel, StudyStatus +from crc.scripts.script import Script + + +class SetStudyStatus(Script): + + def get_description(self): + return """Set the status of the current study. + Status can be one of `in_progress`, `hold`, `open_for_enrollment`, or `abandoned`.""" + + def do_task_validate_only(self, task, study_id, workflow_id, *args, **kwargs): + + if 'new_status' in kwargs.keys() or len(args) > 0: + if 'new_status' in kwargs.keys(): + new_status = kwargs['new_status'] + else: + new_status = args[0] + + try: + study_status = getattr(StudyStatus, new_status) + + except AttributeError as ae: + raise ApiError.from_task(code='invalid_argument', + message=f"We could not find a status matching `{new_status}`. Original message: {ae}", + task=task) + return study_status.value + + else: + raise ApiError.from_task(code='missing_argument', + message='You must include the new status when calling `set_study_status` script. ' + 'The new status must be one of `in_progress`, `hold`, `open_for_enrollment`, or `abandoned`.', + task=task) + + def do_task(self, task, study_id, workflow_id, *args, **kwargs): + + # Get new status + if 'new_status' in kwargs.keys() or len(args) > 0: + if 'new_status' in kwargs.keys(): + new_status = kwargs['new_status'] + else: + new_status = args[0] + + # Get StudyStatus object for new_status + try: + study_status = getattr(StudyStatus, new_status) + + # Invalid argument + except AttributeError as ae: + raise ApiError.from_task(code='invalid_argument', + message=f"We could not find a status matching `{new_status}`. Original message: {ae}" + 'The new status must be one of `in_progress`, `hold`, `open_for_enrollment`, or `abandoned`.', + task=task) + + # Set new status + study_model = session.query(StudyModel).filter(StudyModel.id == study_id).first() + study_model.status = study_status + session.commit() + + return study_model.status.value + + # Missing argument + else: + raise ApiError.from_task(code='missing_argument', + message='You must include the new status when calling `set_study_status` script. ' + 'The new status must be one of `in_progress`, `hold`, `open_for_enrollment`, or `abandoned`.', + task=task) + diff --git a/tests/data/get_study_status/get_study_status.bpmn b/tests/data/get_study_status/get_study_status.bpmn new file mode 100644 index 00000000..760814db --- /dev/null +++ b/tests/data/get_study_status/get_study_status.bpmn @@ -0,0 +1,47 @@ + + + + + Flow_1iqprcz + + + + Flow_1iqprcz + Flow_0npc38l + study_status = get_study_status() + + + # Study Status +{{ study_status }} + Flow_0npc38l + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/tests/data/set_study_status/set_study_status.bpmn b/tests/data/set_study_status/set_study_status.bpmn new file mode 100644 index 00000000..af1027d3 --- /dev/null +++ b/tests/data/set_study_status/set_study_status.bpmn @@ -0,0 +1,114 @@ + + + + + Flow_0c77bdh + + + + + + + + + + + + + + Flow_1e9oiuw + Flow_0q0rtvj + + + + Flow_0q0rtvj + Flow_0ana8xt + returned_status = set_study_status(selected_status) + + + + # Study Status + +## Original Status +{{ original_status }} + +## Selected Status +{{ selected_status }} + +## Returned Status +{{ returned_status }} + + +## New Status +{{ new_status }} + Flow_0nckhhn + Flow_14s6jnt + + + Flow_14s6jnt + + + + + + Flow_0c77bdh + Flow_1e9oiuw + original_status = get_study_status() + + + + Flow_0ana8xt + Flow_0nckhhn + new_status = get_study_status() + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/tests/scripts/test_get_study_status.py b/tests/scripts/test_get_study_status.py new file mode 100644 index 00000000..8012ddb7 --- /dev/null +++ b/tests/scripts/test_get_study_status.py @@ -0,0 +1,11 @@ +from tests.base_test import BaseTest + + +class TestGetStudyStatus(BaseTest): + + def test_get_study_status(self): + workflow = self.create_workflow('get_study_status') + workflow_api = self.get_workflow_api(workflow) + task = workflow_api.next_task + + self.assertEqual(task.data['study_status'], workflow.study.status.value) diff --git a/tests/scripts/test_set_study_status.py b/tests/scripts/test_set_study_status.py new file mode 100644 index 00000000..ece8c30c --- /dev/null +++ b/tests/scripts/test_set_study_status.py @@ -0,0 +1,35 @@ +from tests.base_test import BaseTest + + +class TestSetStudyStatus(BaseTest): + + def test_set_study_status_validation(self): + self.load_example_data() + spec_model = self.load_test_spec('set_study_status') + rv = self.app.get('/v1.0/workflow-specification/%s/validate' % spec_model.id, headers=self.logged_in_headers()) + self.assertEqual([], rv.json) + + def test_set_study_status(self): + workflow = self.create_workflow('set_study_status') + workflow_api = self.get_workflow_api(workflow) + task = workflow_api.next_task + + original_status = task.data['original_status'] + self.assertEqual('in_progress', original_status) + + workflow_api = self.complete_form(workflow, task, {'selected_status': 'hold'}) + task = workflow_api.next_task + + self.assertEqual('Activity_DisplayStatus', task.name) + self.assertEqual('hold', task.data['selected_status']) + self.assertEqual('hold', task.data['new_status']) + + def test_set_study_status_fail(self): + + self.load_example_data() + workflow = self.create_workflow('set_study_status') + workflow_api = self.get_workflow_api(workflow) + task = workflow_api.next_task + + with self.assertRaises(AssertionError): + self.complete_form(workflow, task, {'selected_status': 'asdf'})