home · contact · privacy
Nest Todo creation by adopting and making children as needed.
[plomtask] / plomtask / todos.py
index a7af99faa3a298e27548e7a7234699c1cf8038fc..bffa23ae8c46ae02004344e7c206a4e7104050a0 100644 (file)
@@ -58,6 +58,27 @@ class Todo(BaseModel[int], ConditionsRelations):
             self.enables = self.process.enables[:]
             self.disables = self.process.disables[:]
 
+    @classmethod
+    def create_with_children(cls, db_conn: DatabaseConnection, date: str,
+                             process_ids: list[int]) -> list[Todo]:
+        """Create Todos of process_ids for date, ensure children."""
+        new_todos = []
+        for process_id in process_ids:
+            process = Process.by_id(db_conn, process_id)
+            todo = Todo(None, process, False, date)
+            todo.save(db_conn)
+            new_todos += [todo]
+        nothing_to_adopt = False
+        while not nothing_to_adopt:
+            nothing_to_adopt = True
+            existing_todos = Todo.by_date(db_conn, date)
+            for todo in new_todos:
+                if todo.adopt_from(existing_todos):
+                    nothing_to_adopt = False
+                todo.make_missing_children(db_conn)
+                todo.save(db_conn)
+        return new_todos
+
     @classmethod
     def from_table_row(cls, db_conn: DatabaseConnection,
                        row: Row | list[Any]) -> Todo:
@@ -167,10 +188,9 @@ class Todo(BaseModel[int], ConditionsRelations):
 
     def make_missing_children(self, db_conn: DatabaseConnection) -> None:
         """Fill unsatisfied dependencies with new Todos."""
-        for process_id in self.unsatisfied_dependencies:
-            process = Process.by_id(db_conn, process_id)
-            todo = self.__class__(None, process, False, self.date)
-            todo.save(db_conn)
+        new_todos = self.__class__.create_with_children(
+                db_conn, self.date, self.unsatisfied_dependencies)
+        for todo in new_todos:
             self.add_child(todo)
 
     def get_step_tree(self, seen_todos: set[int]) -> TodoNode: