taskai-cli 1.1.4__tar.gz → 1.2.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (25) hide show
  1. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/PKG-INFO +1 -1
  2. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/pyproject.toml +1 -1
  3. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/cli.py +12 -3
  4. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/models.py +5 -0
  5. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/views.py +54 -4
  6. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/.github/workflows/publish-to-pypi.yml +0 -0
  7. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/.gitignore +0 -0
  8. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/DEVLOG.md +0 -0
  9. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/README.md +0 -0
  10. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/docs/index.md +0 -0
  11. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/migrations/_001_removing_lists.py +0 -0
  12. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/migrations/convert_title_to_name.py +0 -0
  13. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/mkdocs.yml +0 -0
  14. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/scripts/bump_version.py +0 -0
  15. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/config.py +0 -0
  16. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/help_menu.py +0 -0
  17. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/json_dir_database.py +0 -0
  18. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/services/ai.py +0 -0
  19. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/services/pomodoro.py +0 -0
  20. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/services/repair_database.py +0 -0
  21. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/taskai/services/user_setup.py +0 -0
  22. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/test/test_cli.py +0 -0
  23. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/test/test_execution.py +0 -0
  24. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/test/test_json_dir_database.py +0 -0
  25. {taskai_cli-1.1.4 → taskai_cli-1.2.0}/test/test_view.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: taskai-cli
3
- Version: 1.1.4
3
+ Version: 1.2.0
4
4
  Author-email: Alex Paskal <alexcpaskal@gmail.com>
5
5
  Requires-Python: >=3.12
6
6
  Requires-Dist: google-genai>=2.8
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "taskai-cli"
3
- version = "1.1.4"
3
+ version = "1.2.0"
4
4
  description = ""
5
5
  authors = [{name = "Alex Paskal", email = "alexcpaskal@gmail.com"}]
6
6
  readme = "README.md"
@@ -112,11 +112,17 @@ class Controller:
112
112
  print(f"Added comment {comment_id} to item {item_id} - '{content}'")
113
113
  db.commit()
114
114
 
115
- def update_item(item_id: int|str, **kwargs):
115
+ def update_item(item_id: int|str, recursive=False, **kwargs):
116
116
  if not _is_int(item_id):
117
117
  item_id = Controller._find_model_by_stringmatch("name", item_id)
118
118
  db.update_item(item_id, **kwargs)
119
119
  print(f"Updated item {item_id}")
120
+
121
+ if recursive:
122
+ children = db.get_item_attr(item_id, "child_ids")
123
+ for child_id in children:
124
+ Controller.update_item(child_id, recursive=True, **kwargs)
125
+
120
126
  db.commit()
121
127
 
122
128
  def delete_item(id_: int|str):
@@ -134,7 +140,10 @@ class Controller:
134
140
 
135
141
  def delete_completed():
136
142
  for item_id in db.get_item_ids():
137
- item: TodoItem = db.get_item(item_id)
143
+ try:
144
+ item: TodoItem = db.get_item(item_id)
145
+ except:
146
+ continue
138
147
  if item.completed:
139
148
  db.delete_item(item_id)
140
149
  db.commit()
@@ -370,7 +379,7 @@ def execute_commands(*args, **kwargs) -> int:
370
379
 
371
380
  case "complete" | "done":
372
381
  match args[1]:
373
- case _ if _is_int(args[1]): Controller.update_item(args[1], completed=True)
382
+ case _ if _is_int(args[1]): Controller.update_item(args[1], completed=True, recursive=True)
374
383
  case _: Controller.throw_error("unrecognized complete command", *args, **kwargs)
375
384
 
376
385
  case "examples":
@@ -61,5 +61,10 @@ class CLIConfig(Base):
61
61
  GEMINI_MODEL: str = None
62
62
  GEMINI_API_KEY: str = None
63
63
 
64
+ # VIEW
65
+ DISPLAY_STRING: str = "id name status due_by"
66
+ DISPLAY_COLORS: str = "_ white dark_orange _"
67
+
68
+
64
69
  class LLMConfig(Base):
65
70
  pass
@@ -1,6 +1,7 @@
1
1
  # local
2
2
  from taskai.json_dir_database import JsonDirectoryDatabase
3
3
  from taskai.models import TodoItem, Comment
4
+ from taskai.config import config
4
5
 
5
6
  # external
6
7
  from rich import print
@@ -8,19 +9,68 @@ from rich.console import Console
8
9
  import rich
9
10
 
10
11
 
12
+ """
13
+ Lets give the lists a display string
14
+
15
+
16
+ set of valid attributes
17
+ - id
18
+ - name
19
+ - status
20
+ -
21
+
22
+
23
+ """
24
+
25
+
26
+ VALID_ATTRS = {
27
+ "id",
28
+ "name",
29
+ "created_on",
30
+ "due_by",
31
+ "priority",
32
+ "status"
33
+ }
34
+
35
+
36
+ @config("DISPLAY_STRING", "display_str")
37
+ @config("DISPLAY_COLORS", "display_colors")
11
38
  def view_lists(
12
39
  db: JsonDirectoryDatabase,
13
40
  roots: list[int],
14
- show_done=True,
41
+ show_done=True,
42
+ display_str: str = "id name status",
43
+ display_colors: str = None
15
44
  ):
16
45
  """Shows all the lists"""
17
46
 
47
+ attrs = display_str.lower().split(" ")
48
+
49
+ if display_colors:
50
+ colors = display_colors.lower().split(" ")
51
+ assert len(colors) == len(attrs), "must have a color for every attr"
52
+
53
+ for attr in attrs:
54
+ assert attr in VALID_ATTRS, "invalid attribute in display string {}".format(attr)
55
+
56
+ def _render_display_string(item: TodoItem):
57
+ display_string = ""
58
+ for i, attr in enumerate(attrs):
59
+ part = getattr(item, attr)
60
+ if not part:
61
+ continue
62
+ part = str(part)
63
+ if display_colors and colors[i] != "_":
64
+ part = _wrap_string(part, f"[{colors[i]}]", f"[/{colors[i]}]")
65
+ display_string += f" {part}"
66
+ display_string = _wrap_string(display_string, "[strike]", "[/strike]", condition=item.completed)
67
+ return display_string
18
68
 
19
69
  def _print_item(item: TodoItem, level: int):
20
70
  if not show_done and item.completed:
21
71
  return
22
- display_string = f"{item.id} {item.name}"
23
- display_string = _wrap_string(display_string, "[strike]", "[/strike]", condition=item.completed)
72
+
73
+ display_string = _render_display_string(item)
24
74
  indent = "\t" * level
25
75
  print(indent + display_string)
26
76
 
@@ -101,4 +151,4 @@ def _wrap_string(string_, before, after=None, condition=True):
101
151
  if condition:
102
152
  return f"{before}{string_}{after}"
103
153
  else:
104
- return string_
154
+ return string_
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes