home · contact · privacy
Minor test improvements/expansions/refactorings. master
authorChristian Heller <c.heller@plomlompom.de>
Sun, 18 Aug 2024 13:46:13 +0000 (15:46 +0200)
committerChristian Heller <c.heller@plomlompom.de>
Sun, 18 Aug 2024 13:46:13 +0000 (15:46 +0200)
tests/conditions.py
tests/todos.py
tests/utils.py

index c071e65a2765d4182b4573e7744d7123b5f6509a..b35dc6e7bc51d3e417eeb4dbf55ed3724f58dd4f 100644 (file)
@@ -3,9 +3,6 @@ from typing import Any
 from tests.utils import (TestCaseSansDB, TestCaseWithDB, TestCaseWithServer,
                          Expected)
 from plomtask.conditions import Condition
 from tests.utils import (TestCaseSansDB, TestCaseWithDB, TestCaseWithServer,
                          Expected)
 from plomtask.conditions import Condition
-from plomtask.processes import Process
-from plomtask.todos import Todo
-from plomtask.exceptions import HandledException
 
 
 class TestsSansDB(TestCaseSansDB):
 
 
 class TestsSansDB(TestCaseSansDB):
@@ -18,26 +15,6 @@ class TestsWithDB(TestCaseWithDB):
     checked_class = Condition
     default_init_kwargs = {'is_active': 0}
 
     checked_class = Condition
     default_init_kwargs = {'is_active': 0}
 
-    def test_remove(self) -> None:
-        """Test .remove() effects on DB and cache."""
-        super().test_remove()
-        proc = Process(None)
-        proc.save(self.db_conn)
-        todo = Todo(None, proc, False, '2024-01-01')
-        todo.save(self.db_conn)
-        # check condition can only be deleted if not depended upon
-        for depender in (proc, todo):
-            c = Condition(None)
-            c.save(self.db_conn)
-            assert isinstance(c.id_, int)
-            depender.set_condition_relations(self.db_conn, [c.id_], [], [], [])
-            depender.save(self.db_conn)
-            with self.assertRaises(HandledException):
-                c.remove(self.db_conn)
-            depender.set_condition_relations(self.db_conn, [], [], [], [])
-            depender.save(self.db_conn)
-            c.remove(self.db_conn)
-
 
 class ExpectedGetConditions(Expected):
     """Builder of expectations for GET /conditions."""
 
 class ExpectedGetConditions(Expected):
     """Builder of expectations for GET /conditions."""
@@ -81,6 +58,16 @@ class TestsWithServer(TestCaseWithServer):
         self.check_minimal_inputs('/condition', valid_payload)
         # check valid POST payload on bad paths
         self.check_post(valid_payload, '/condition?id=foo', 400)
         self.check_minimal_inputs('/condition', valid_payload)
         # check valid POST payload on bad paths
         self.check_post(valid_payload, '/condition?id=foo', 400)
+        # check cannot delete depended-upon Condition
+        self.post_exp_cond([], {})
+        for key in ('conditions', 'blockers', 'enables', 'disables'):
+            self.post_exp_process([], {key: [1]}, 1)
+            self.check_post({'delete': ''}, '/condition?id=1', 500)
+        self.post_exp_process([], {}, 1)
+        self.post_exp_day([], {'new_todo': '1'})
+        for key in ('conditions', 'blockers', 'enables', 'disables'):
+            self.post_exp_todo([], {key: [1]}, 1)
+            self.check_post({'delete': ''}, '/condition?id=1', 500)
 
     def test_POST_condition(self) -> None:
         """Test (valid) POST /condition and its effect on GET /condition[s]."""
 
     def test_POST_condition(self) -> None:
         """Test (valid) POST /condition and its effect on GET /condition[s]."""
@@ -88,24 +75,22 @@ class TestsWithServer(TestCaseWithServer):
         exp_single, exp_all = ExpectedGetCondition(1), ExpectedGetConditions()
         all_exps = [exp_single, exp_all]
         # test valid POST's effect on single /condition and full /conditions
         exp_single, exp_all = ExpectedGetCondition(1), ExpectedGetConditions()
         all_exps = [exp_single, exp_all]
         # test valid POST's effect on single /condition and full /conditions
-        self.post_exp_cond(all_exps, {'title': 'foo', 'description': 'oof'},
-                           post_to_id=False)
+        self.post_exp_cond(all_exps, {}, post_to_id=False)
         self.check_json_get(url_single, exp_single)
         self.check_json_get(url_all, exp_all)
         # test (no) effect of invalid POST to existing Condition on /condition
         self.check_post({}, url_single, 400)
         self.check_json_get(url_single, exp_single)
         self.check_json_get(url_single, exp_single)
         self.check_json_get(url_all, exp_all)
         # test (no) effect of invalid POST to existing Condition on /condition
         self.check_post({}, url_single, 400)
         self.check_json_get(url_single, exp_single)
-        # test effect of POST changing title and activeness
+        # test effect of POST changing title, description, and activeness
         self.post_exp_cond(all_exps, {'title': 'bar', 'description': 'oof',
                                       'is_active': 1})
         self.check_json_get(url_single, exp_single)
         self.post_exp_cond(all_exps, {'title': 'bar', 'description': 'oof',
                                       'is_active': 1})
         self.check_json_get(url_single, exp_single)
-        self.check_json_get(url_all, exp_all)
         # test POST sans 'is_active' setting it negative
         # test POST sans 'is_active' setting it negative
-        self.post_exp_cond(all_exps, {'title': 'bar', 'description': 'oof'})
+        self.post_exp_cond(all_exps, {})
         self.check_json_get(url_single, exp_single)
         self.check_json_get(url_single, exp_single)
-        self.check_json_get(url_all, exp_all)
         # test deletion POST's effect, both to return id=1 into empty single,
         # full /conditions into empty list
         # test deletion POST's effect, both to return id=1 into empty single,
         # full /conditions into empty list
+        self.check_json_get(url_single, exp_single)
         self.post_exp_cond(all_exps, {'delete': ''}, redir_to_id=False)
         exp_single.set('is_new', True)
         self.check_json_get(url_single, exp_single)
         self.post_exp_cond(all_exps, {'delete': ''}, redir_to_id=False)
         exp_single.set('is_new', True)
         self.check_json_get(url_single, exp_single)
@@ -125,8 +110,7 @@ class TestsWithServer(TestCaseWithServer):
         # make Condition and two Processes that among them establish all
         # possible ConditionsRelations to it, check /condition displays all
         exp = ExpectedGetCondition(1)
         # make Condition and two Processes that among them establish all
         # possible ConditionsRelations to it, check /condition displays all
         exp = ExpectedGetCondition(1)
-        self.post_exp_cond([exp], {'title': 'foo', 'description': 'oof'},
-                           post_to_id=False)
+        self.post_exp_cond([exp], {}, post_to_id=False)
         for i, p in enumerate([('conditions', 'disables'),
                                ('enables', 'blockers')]):
             self.post_exp_process([exp], {k: [1] for k in p}, i+1)
         for i, p in enumerate([('conditions', 'disables'),
                                ('enables', 'blockers')]):
             self.post_exp_process([exp], {k: [1] for k in p}, i+1)
index ea61a3306eb1ccd893217d1e845a8f502035e1ac..834330b2d0eb924ba12708b0a39390e44b8553d6 100644 (file)
@@ -232,11 +232,6 @@ class TestsWithServer(TestCaseWithServer):
     """Tests against our HTTP server/handler (and database)."""
     checked_class = Todo
 
     """Tests against our HTTP server/handler (and database)."""
     checked_class = Todo
 
-    def _post_exp_todo(
-            self, id_: int, payload: dict[str, Any], exp: Expected) -> None:
-        self.check_post(payload, f'/todo?id={id_}')
-        exp.set_todo_from_post(id_, payload)
-
     def test_basic_fail_POST_todo(self) -> None:
         """Test basic malformed/illegal POST /todo requests."""
         self.post_exp_process([], {}, 1)
     def test_basic_fail_POST_todo(self) -> None:
         """Test basic malformed/illegal POST /todo requests."""
         self.post_exp_process([], {}, 1)
@@ -270,10 +265,10 @@ class TestsWithServer(TestCaseWithServer):
         # test posting doneness, comment, calendarization, effort
         todo_post = {'is_done': 1, 'calendarize': 1,
                      'comment': 'foo', 'effort': 2.3}
         # test posting doneness, comment, calendarization, effort
         todo_post = {'is_done': 1, 'calendarize': 1,
                      'comment': 'foo', 'effort': 2.3}
-        self._post_exp_todo(1, todo_post, exp)
+        self.post_exp_todo([exp], todo_post, 1)
         self.check_json_get('/todo?id=1', exp)
         # test implicitly un-setting comment/calendarize/is_done by empty post
         self.check_json_get('/todo?id=1', exp)
         # test implicitly un-setting comment/calendarize/is_done by empty post
-        self._post_exp_todo(1, {}, exp)
+        self.post_exp_todo([exp], {}, 1)
         self.check_json_get('/todo?id=1', exp)
         # test effort post can be explicitly unset by "effort":"" post
         self.check_post({'effort': ''}, '/todo?id=1')
         self.check_json_get('/todo?id=1', exp)
         # test effort post can be explicitly unset by "effort":"" post
         self.check_post({'effort': ''}, '/todo?id=1')
@@ -287,7 +282,7 @@ class TestsWithServer(TestCaseWithServer):
         self.check_json_get('/todo?id=1', exp)
         todo_post = {'conditions': [1], 'disables': [1],
                      'blockers': [2], 'enables': [2]}
         self.check_json_get('/todo?id=1', exp)
         todo_post = {'conditions': [1], 'disables': [1],
                      'blockers': [2], 'enables': [2]}
-        self._post_exp_todo(1, todo_post, exp)
+        self.post_exp_todo([exp], todo_post, 1)
         self.check_json_get('/todo?id=1', exp)
 
     def test_POST_todo_deletion(self) -> None:
         self.check_json_get('/todo?id=1', exp)
 
     def test_POST_todo_deletion(self) -> None:
@@ -333,12 +328,12 @@ class TestsWithServer(TestCaseWithServer):
         self.post_exp_process([exp], {}, 1)
         self.post_exp_day([exp], {'new_todo': [1]})
         self.post_exp_day([exp], {'new_todo': [1]})
         self.post_exp_process([exp], {}, 1)
         self.post_exp_day([exp], {'new_todo': [1]})
         self.post_exp_day([exp], {'new_todo': [1]})
-        self._post_exp_todo(1, {'adopt': 2}, exp)
+        self.post_exp_todo([exp], {'adopt': 2}, 1)
         exp.set('steps_todo_to_process', [
             exp.step_as_dict(node_id=1, process=None, todo=2)])
         self.check_json_get('/todo?id=1', exp)
         # test Todo un-adopting by just not sending an adopt
         exp.set('steps_todo_to_process', [
             exp.step_as_dict(node_id=1, process=None, todo=2)])
         self.check_json_get('/todo?id=1', exp)
         # test Todo un-adopting by just not sending an adopt
-        self._post_exp_todo(1, {}, exp)
+        self.post_exp_todo([exp], {}, 1)
         exp.set('steps_todo_to_process', [])
         self.check_json_get('/todo?id=1', exp)
         # test fail on trying to adopt non-existing Todo
         exp.set('steps_todo_to_process', [])
         self.check_json_get('/todo?id=1', exp)
         # test fail on trying to adopt non-existing Todo
@@ -346,11 +341,11 @@ class TestsWithServer(TestCaseWithServer):
         # test cannot self-adopt
         self.check_post({'adopt': 1}, '/todo?id=1', 400)
         # test cannot do 1-step circular adoption
         # test cannot self-adopt
         self.check_post({'adopt': 1}, '/todo?id=1', 400)
         # test cannot do 1-step circular adoption
-        self._post_exp_todo(2, {'adopt': 1}, exp)
+        self.post_exp_todo([exp], {'adopt': 1}, 2)
         self.check_post({'adopt': 2}, '/todo?id=1', 400)
         # test cannot do 2-step circular adoption
         self.post_exp_day([exp], {'new_todo': [1]})
         self.check_post({'adopt': 2}, '/todo?id=1', 400)
         # test cannot do 2-step circular adoption
         self.post_exp_day([exp], {'new_todo': [1]})
-        self._post_exp_todo(3, {'adopt': 2}, exp)
+        self.post_exp_todo([exp], {'adopt': 2}, 3)
         self.check_post({'adopt': 3}, '/todo?id=1', 400)
         # test can adopt Todo into ProcessStep chain via its Process (with key
         # 'step_filler' equivalent to single-element 'adopt' if intable)
         self.check_post({'adopt': 3}, '/todo?id=1', 400)
         # test can adopt Todo into ProcessStep chain via its Process (with key
         # 'step_filler' equivalent to single-element 'adopt' if intable)
@@ -367,7 +362,7 @@ class TestsWithServer(TestCaseWithServer):
         self.post_exp_day([exp], {'new_todo': [2]})
         self.post_exp_day([exp], {'new_todo': [3]})
         self.check_json_get('/todo?id=1', exp)
         self.post_exp_day([exp], {'new_todo': [2]})
         self.post_exp_day([exp], {'new_todo': [3]})
         self.check_json_get('/todo?id=1', exp)
-        self._post_exp_todo(1, {'step_filler_to_1': 5, 'adopt': [4]}, exp)
+        self.post_exp_todo([exp], {'step_filler_to_1': 5, 'adopt': [4]}, 1)
         exp.lib_get('Todo', 1)['children'] += [5]
         slots[0]['todo'] = 4
         slots[1]['todo'] = 5
         exp.lib_get('Todo', 1)['children'] += [5]
         slots[0]['todo'] = 4
         slots[1]['todo'] = 5
@@ -386,7 +381,7 @@ class TestsWithServer(TestCaseWithServer):
         slots[1]['children'] = [exp.step_as_dict(
             node_id=3, process=4, todo=None, fillable=True)]
         self.post_exp_day([exp], {'new_todo': [4]})
         slots[1]['children'] = [exp.step_as_dict(
             node_id=3, process=4, todo=None, fillable=True)]
         self.post_exp_day([exp], {'new_todo': [4]})
-        self._post_exp_todo(1, {'adopt': [4, 5, 6]}, exp)
+        self.post_exp_todo([exp], {'adopt': [4, 5, 6]}, 1)
         slots += [exp.step_as_dict(
             node_id=4, process=None, todo=6, fillable=False)]
         self.check_json_get('/todo?id=1', exp)
         slots += [exp.step_as_dict(
             node_id=4, process=None, todo=6, fillable=False)]
         self.check_json_get('/todo?id=1', exp)
index 045194fb099785d897fcac0a556cc9a94dc993e3..b9db97e0610e87be5f83a821a9b2face47f4867d 100644 (file)
@@ -713,7 +713,7 @@ class Expected:
 
     def set_cond_from_post(self, id_: int, d: dict[str, Any]) -> None:
         """Set Condition of id_ in library based on POST dict d."""
 
     def set_cond_from_post(self, id_: int, d: dict[str, Any]) -> None:
         """Set Condition of id_ in library based on POST dict d."""
-        if d == {'delete': ''}:
+        if 'delete' in d:
             self.lib_del('Condition', id_)
             return
         cond = self.lib_get('Condition', id_)
             self.lib_del('Condition', id_)
             return
         cond = self.lib_get('Condition', id_)
@@ -892,6 +892,10 @@ class TestCaseWithServer(TestCaseWithDB):
         # pylint: disable=too-many-arguments
         target = f'/condition?id={id_}' if post_to_id else '/condition'
         redir = f'/condition?id={id_}' if redir_to_id else '/conditions'
         # pylint: disable=too-many-arguments
         target = f'/condition?id={id_}' if post_to_id else '/condition'
         redir = f'/condition?id={id_}' if redir_to_id else '/conditions'
+        if 'title' not in payload:
+            payload['title'] = 'foo'
+        if 'description' not in payload:
+            payload['description'] = 'foo'
         self.check_post(payload, target, redir=redir)
         for exp in exps:
             exp.set_cond_from_post(id_, payload)
         self.check_post(payload, target, redir=redir)
         for exp in exps:
             exp.set_cond_from_post(id_, payload)
@@ -930,6 +934,16 @@ class TestCaseWithServer(TestCaseWithDB):
             exp.set_proc_from_post(id_, payload)
         return payload
 
             exp.set_proc_from_post(id_, payload)
         return payload
 
+    def post_exp_todo(self,
+                      exps: list[Expected],
+                      payload: dict[str, Any],
+                      id_: int,
+                      ) -> None:
+        """POST /todo, appropriately updated Expecteds."""
+        self.check_post(payload, f'/todo?id={id_}')
+        for exp in exps:
+            exp.set_todo_from_post(id_, payload)
+
     def check_filter(self, exp: Expected, category: str, key: str,
                      val: str, list_ids: list[int]) -> None:
         """Check GET /{category}?{key}={val} sorts to list_ids."""
     def check_filter(self, exp: Expected, category: str, key: str,
                      val: str, list_ids: list[int]) -> None:
         """Check GET /{category}?{key}={val} sorts to list_ids."""