comate-cli 0.3.7__tar.gz → 0.3.9__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 (106) hide show
  1. {comate_cli-0.3.7 → comate_cli-0.3.9}/PKG-INFO +1 -2
  2. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/app.py +1 -1
  3. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/event_renderer.py +23 -3
  4. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/preflight.py +2 -2
  5. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui.py +7 -7
  6. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/render_panels.py +11 -4
  7. {comate_cli-0.3.7 → comate_cli-0.3.9}/pyproject.toml +1 -2
  8. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_completion_status_panel.py +2 -2
  9. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_event_renderer.py +12 -0
  10. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_task_panel_format.py +3 -3
  11. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_task_panel_rendering.py +1 -0
  12. {comate_cli-0.3.7 → comate_cli-0.3.9}/uv.lock +2 -4
  13. {comate_cli-0.3.7 → comate_cli-0.3.9}/.gitignore +0 -0
  14. {comate_cli-0.3.7 → comate_cli-0.3.9}/README.md +0 -0
  15. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/__init__.py +0 -0
  16. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/__main__.py +0 -0
  17. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/main.py +0 -0
  18. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/mcp_cli.py +0 -0
  19. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/__init__.py +0 -0
  20. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/animations.py +0 -0
  21. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/assistant_render.py +0 -0
  22. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/codenames.py +0 -0
  23. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/custom_slash_commands.py +0 -0
  24. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/env_utils.py +0 -0
  25. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/error_display.py +0 -0
  26. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/fragment_utils.py +0 -0
  27. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/history_printer.py +0 -0
  28. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/input_geometry.py +0 -0
  29. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/layout_coordinator.py +0 -0
  30. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/logging_adapter.py +0 -0
  31. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/logo.py +0 -0
  32. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/markdown_render.py +0 -0
  33. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/mention_completer.py +0 -0
  34. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/message_style.py +0 -0
  35. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/models.py +0 -0
  36. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/path_context_hint.py +0 -0
  37. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/question_view.py +0 -0
  38. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/resume_selector.py +0 -0
  39. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/rewind_store.py +0 -0
  40. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/rpc_protocol.py +0 -0
  41. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/rpc_stdio.py +0 -0
  42. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/selection_menu.py +0 -0
  43. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/session_view.py +0 -0
  44. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/slash_commands.py +0 -0
  45. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/startup.py +0 -0
  46. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/status_bar.py +0 -0
  47. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/text_effects.py +0 -0
  48. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tips.py +0 -0
  49. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tool_view.py +0 -0
  50. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/__init__.py +0 -0
  51. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/commands.py +0 -0
  52. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/history_sync.py +0 -0
  53. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/input_behavior.py +0 -0
  54. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/key_bindings.py +0 -0
  55. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/slash_command_registry.py +0 -0
  56. {comate_cli-0.3.7 → comate_cli-0.3.9}/comate_cli/terminal_agent/tui_parts/ui_mode.py +0 -0
  57. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/conftest.py +0 -0
  58. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_app_mcp_preload.py +0 -0
  59. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_app_preflight_gate.py +0 -0
  60. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_app_print_mode.py +0 -0
  61. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_app_shutdown.py +0 -0
  62. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_app_usage_line.py +0 -0
  63. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_cli_project_root.py +0 -0
  64. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_compact_command_semantics.py +0 -0
  65. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_completion_context_activation.py +0 -0
  66. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_context_command.py +0 -0
  67. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_custom_slash_commands.py +0 -0
  68. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_format_error.py +0 -0
  69. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_handle_error.py +0 -0
  70. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_history_printer.py +0 -0
  71. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_history_sync.py +0 -0
  72. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_input_behavior.py +0 -0
  73. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_input_history.py +0 -0
  74. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_interrupt_exit_semantics.py +0 -0
  75. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_layout_coordinator.py +0 -0
  76. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_logging_adapter.py +0 -0
  77. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_logo.py +0 -0
  78. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_main_args.py +0 -0
  79. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_mcp_cli.py +0 -0
  80. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_mcp_slash_command.py +0 -0
  81. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_mention_completer.py +0 -0
  82. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_path_context_hint.py +0 -0
  83. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_preflight.py +0 -0
  84. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_preflight_copilot.py +0 -0
  85. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_question_key_bindings.py +0 -0
  86. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_question_view.py +0 -0
  87. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_resume_selector.py +0 -0
  88. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_rewind_command_semantics.py +0 -0
  89. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_rewind_store.py +0 -0
  90. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_rpc_protocol.py +0 -0
  91. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_rpc_stdio_bridge.py +0 -0
  92. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_selection_menu.py +0 -0
  93. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_skills_slash_command.py +0 -0
  94. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_slash_argument_hint.py +0 -0
  95. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_slash_completer.py +0 -0
  96. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_slash_registry.py +0 -0
  97. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_status_bar.py +0 -0
  98. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_status_bar_transient.py +0 -0
  99. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_task_panel_key_bindings.py +0 -0
  100. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_task_poll.py +0 -0
  101. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_tool_view.py +0 -0
  102. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_tui_elapsed_status.py +0 -0
  103. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_tui_mcp_init_gate.py +0 -0
  104. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_tui_paste_placeholder.py +0 -0
  105. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_tui_split_invariance.py +0 -0
  106. {comate_cli-0.3.7 → comate_cli-0.3.9}/tests/test_update_check.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: comate-cli
3
- Version: 0.3.7
3
+ Version: 0.3.9
4
4
  Summary: Comate terminal CLI built on comate-agent-sdk
5
5
  Project-URL: Homepage, https://github.com/AndyLee1024/agent-sdk
6
6
  Project-URL: Repository, https://github.com/AndyLee1024/agent-sdk
@@ -15,7 +15,6 @@ Classifier: Programming Language :: Python :: 3.12
15
15
  Classifier: Programming Language :: Python :: 3.13
16
16
  Requires-Python: >=3.11
17
17
  Requires-Dist: comate-agent-sdk<1.0.0,>=0.0.2
18
- Requires-Dist: packaging>=25.0
19
18
  Requires-Dist: prompt-toolkit>=3.0
20
19
  Requires-Dist: rich>=14.0
21
20
  Description-Content-Type: text/markdown
@@ -370,7 +370,7 @@ async def run(
370
370
  if mgr and mgr.failed_servers:
371
371
  aliases = [alias for alias, _ in mgr.failed_servers]
372
372
  status_bar.show_transient(
373
- f"MCP: {', '.join(aliases)} unavailable",
373
+ f"MCP: {', '.join(aliases)} unavailable",
374
374
  duration_s=5.0,
375
375
  )
376
376
 
@@ -112,6 +112,18 @@ def _task_sort_key(task: dict[str, Any]) -> tuple[int, int]:
112
112
  return rank, numeric_id
113
113
 
114
114
 
115
+ def _task_stats_header(tasks: list[dict[str, Any]]) -> str:
116
+ """生成 task 统计标题,如 '3 tasks (1 done, 2 open)'。"""
117
+ total = len(tasks)
118
+ done = sum(
119
+ 1 for t in tasks
120
+ if str(t.get("status", "")).strip().lower() == "completed"
121
+ )
122
+ open_count = total - done
123
+ noun = "task" if total == 1 else "tasks"
124
+ return f"{total} {noun} ({done} done, {open_count} open)"
125
+
126
+
115
127
  def _format_task_row(task: dict[str, Any]) -> str:
116
128
  """格式化单条 task 行。
117
129
 
@@ -295,6 +307,12 @@ class EventRenderer:
295
307
  def has_active_todos(self) -> bool:
296
308
  return self.has_active_tasks()
297
309
 
310
+ def has_in_progress_tasks(self) -> bool:
311
+ return any(
312
+ str(t.get("status", "")).strip().lower() == "in_progress"
313
+ for t in self._current_tasks
314
+ )
315
+
298
316
  def compute_required_tool_panel_lines(self) -> int:
299
317
  """计算显示所有 running tools 所需的最小行数。"""
300
318
  if not self._running_tools:
@@ -518,7 +536,9 @@ class EventRenderer:
518
536
  if not tasks:
519
537
  return []
520
538
 
521
- header = str(self._current_task_title or "").strip() or "Tasks"
539
+ header = str(self._current_task_title or "").strip()
540
+ if not header:
541
+ header = _task_stats_header(tasks)
522
542
  lines: list[str] = [header]
523
543
  for task in sorted(tasks, key=_task_sort_key):
524
544
  lines.append(_format_task_row(task))
@@ -849,7 +869,7 @@ class EventRenderer:
849
869
  return
850
870
 
851
871
  all_completed = all(str(item.get("status", "")).strip().lower() == "completed" for item in normalized)
852
- # 标题:显示 ID 最小的 in_progress task 的 subject,否则 "Tasks"
872
+ # 标题:显示 ID 最小的 in_progress task 的 subject,否则统计摘要
853
873
  in_progress_tasks = [
854
874
  t for t in normalized
855
875
  if str(t.get("status", "")).strip().lower() == "in_progress"
@@ -858,7 +878,7 @@ class EventRenderer:
858
878
  in_progress_tasks.sort(key=lambda t: int(t.get("id", 0)))
859
879
  header = str(in_progress_tasks[0].get("subject", "")).strip() or "Tasks"
860
880
  else:
861
- header = "Tasks"
881
+ header = _task_stats_header(normalized)
862
882
  if not all_completed:
863
883
  if not self._current_tasks:
864
884
  self._task_started_at_monotonic = time.monotonic()
@@ -188,7 +188,7 @@ PROVIDER_PRESETS: tuple[ProviderPreset, ...] = (
188
188
  models={
189
189
  "LOW": "glm-4.7",
190
190
  "MID": "glm-4.7",
191
- "HIGH": "glm-5",
191
+ "HIGH": "glm-5.1",
192
192
  },
193
193
  ),
194
194
  ProviderPreset(
@@ -200,7 +200,7 @@ PROVIDER_PRESETS: tuple[ProviderPreset, ...] = (
200
200
  models={
201
201
  "LOW": "glm-4.7",
202
202
  "MID": "glm-4.7",
203
- "HIGH": "glm-5",
203
+ "HIGH": "glm-5.1",
204
204
  },
205
205
  ),
206
206
  ProviderPreset(
@@ -1305,16 +1305,16 @@ class TerminalAgentTUI(
1305
1305
  except asyncio.TimeoutError:
1306
1306
  logger.debug(
1307
1307
  "MCP init timed out after "
1308
- f"{self._mcp_init_gate_timeout_s:.1f}s; degrade and continue",
1308
+ f"{self._mcp_init_gate_timeout_s:.1f}s; continuing in background",
1309
1309
  )
1310
1310
  self._status_bar.show_transient(
1311
- "MCP: init timed out", duration_s=5.0,
1312
- )
1313
- await self._cancel_task_with_timeout(
1314
- init_task,
1315
- timeout_s=self._mcp_init_cancel_timeout_s,
1316
- task_name="terminal-mcp-init-worker",
1311
+ "MCP: init timed out, continuing in background…",
1312
+ duration_s=5.0,
1317
1313
  )
1314
+ # Don't cancel init_task — let it complete in background.
1315
+ # asyncio.shield above already protects it from wait_for's
1316
+ # auto-cancellation. When it finishes, runtime._mcp_manager
1317
+ # will be set and tools become available for the next turn.
1318
1318
  except asyncio.CancelledError:
1319
1319
  await self._cancel_task_with_timeout(
1320
1320
  init_task,
@@ -243,9 +243,8 @@ class RenderPanelsMixin:
243
243
  return max_lines
244
244
 
245
245
  def _should_hide_loading_panel(self) -> bool:
246
- """统一 loading 显隐逻辑:仅当 Todo 面板出现且无工具运行时隐藏 loading 区域。"""
247
- if self._renderer.has_running_tools():
248
- return False
246
+ """统一 loading 显隐逻辑:当 Task 面板存在时始终隐藏 loading 区域,
247
+ loading 语义由 task title 的呼吸圆点承载。"""
249
248
  return self._renderer.has_active_todos()
250
249
 
251
250
  def _sync_todo_panel_state(self) -> None:
@@ -593,7 +592,15 @@ class RenderPanelsMixin:
593
592
  title_elapsed_suffix = (
594
593
  f" ({self._format_run_elapsed(elapsed)} • ctrl+c to interrupt)"
595
594
  )
596
- title_budget = width - 1 - get_cwidth(title_elapsed_suffix)
595
+ # busy 时在 title 前加呼吸圆点,承载 loading 语义
596
+ dot_prefix_width = 0
597
+ if self._busy:
598
+ dot_color = breathing_dot_color(self._loading_frame)
599
+ dot_glyph = breathing_dot_glyph(time.monotonic())
600
+ dot_style = f"fg:{dot_color} bold"
601
+ fragments.append((dot_style, f"{dot_glyph} "))
602
+ dot_prefix_width = 2 # glyph(1) + space(1)
603
+ title_budget = width - 1 - dot_prefix_width - get_cwidth(title_elapsed_suffix)
597
604
  clipped_title = fit_single_line(line, max(title_budget, 8))
598
605
  fragments.extend(self._todo_title_shimmer_fragments(clipped_title))
599
606
  if title_elapsed_suffix:
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "comate-cli"
7
- version = "0.3.7"
7
+ version = "0.3.9"
8
8
  description = "Comate terminal CLI built on comate-agent-sdk"
9
9
  readme = "README.md"
10
10
  requires-python = ">=3.11"
@@ -25,7 +25,6 @@ dependencies = [
25
25
  "comate-agent-sdk>=0.0.2,<1.0.0",
26
26
  "rich>=14.0",
27
27
  "prompt-toolkit>=3.0",
28
- "packaging>=25.0",
29
28
  ]
30
29
 
31
30
  [project.urls]
@@ -248,10 +248,10 @@ class TestCompletionStatusPanel(unittest.TestCase):
248
248
  self.assertTrue(tui._should_hide_loading_panel())
249
249
  self.assertEqual(tui._loading_text(), [("", " ")])
250
250
 
251
- # 有 todo 且有工具运行(subagent 执行中)→ 不隐藏,loading 面板优先
251
+ # 有 todo 且有工具运行(subagent 执行中)→ 也隐藏,loading 语义由 task title 承载
252
252
  tui._renderer.active_todos = True
253
253
  tui._renderer.running_tools = True
254
- self.assertFalse(tui._should_hide_loading_panel())
254
+ self.assertTrue(tui._should_hide_loading_panel())
255
255
 
256
256
  # 无 todo,有工具运行 → 不隐藏
257
257
  tui._renderer.active_todos = False
@@ -396,6 +396,18 @@ class TestEventRenderer(unittest.TestCase):
396
396
  def test_task_completed_appends_summary_and_hides_panel(self) -> None:
397
397
  renderer = EventRenderer()
398
398
  renderer.start_turn()
399
+ # 先创建 pending tasks,使 _current_tasks 非空
400
+ renderer.handle_event(
401
+ TaskUpdatedEvent(
402
+ list_id="default",
403
+ tasks=[
404
+ {"id": "1", "subject": "a", "status": "pending", "open_blocked_by": []},
405
+ {"id": "2", "subject": "b", "status": "pending", "open_blocked_by": []},
406
+ ],
407
+ )
408
+ )
409
+ self.assertTrue(renderer.has_active_todos())
410
+ # 全部完成后应写入 summary 并隐藏面板
399
411
  renderer.handle_event(
400
412
  TaskUpdatedEvent(
401
413
  list_id="default",
@@ -76,14 +76,14 @@ def test_title_shows_smallest_id_in_progress():
76
76
  assert renderer._current_task_title == "Task A"
77
77
 
78
78
 
79
- def test_title_falls_back_to_tasks_when_no_in_progress():
79
+ def test_title_falls_back_to_stats_when_no_in_progress():
80
80
  renderer = _make_renderer_for_title_test()
81
81
  tasks = [
82
82
  {"id": "1", "subject": "Set up project", "status": "pending", "open_blocked_by": []},
83
83
  {"id": "2", "subject": "Write tests", "status": "pending", "open_blocked_by": []},
84
84
  ]
85
85
  renderer._update_tasks(tasks, list_id="default")
86
- assert renderer._current_task_title == "Tasks"
86
+ assert renderer._current_task_title == "2 tasks (0 done, 2 open)"
87
87
 
88
88
 
89
89
  def test_title_ignores_list_id():
@@ -92,5 +92,5 @@ def test_title_ignores_list_id():
92
92
  {"id": "1", "subject": "Task A", "status": "pending", "open_blocked_by": []},
93
93
  ]
94
94
  renderer._update_tasks(tasks, list_id="team-alpha")
95
- assert renderer._current_task_title == "Tasks"
95
+ assert renderer._current_task_title == "1 task (0 done, 1 open)"
96
96
  assert "team-alpha" not in (renderer._current_task_title or "")
@@ -38,6 +38,7 @@ class _StubMixin(RenderPanelsMixin):
38
38
  self._todo_panel_expanded_max_lines = 12
39
39
  self._run_start_time = None
40
40
  self._tool_result_flash_active = False
41
+ self._busy = False
41
42
 
42
43
  def _terminal_width(self) -> int:
43
44
  return 80
@@ -364,7 +364,7 @@ wheels = [
364
364
 
365
365
  [[package]]
366
366
  name = "comate-agent-sdk"
367
- version = "0.3.4"
367
+ version = "0.3.8"
368
368
  source = { editable = "../../" }
369
369
  dependencies = [
370
370
  { name = "aiohttp" },
@@ -429,11 +429,10 @@ dev = [
429
429
 
430
430
  [[package]]
431
431
  name = "comate-cli"
432
- version = "0.3.4"
432
+ version = "0.3.8"
433
433
  source = { editable = "." }
434
434
  dependencies = [
435
435
  { name = "comate-agent-sdk" },
436
- { name = "packaging" },
437
436
  { name = "prompt-toolkit" },
438
437
  { name = "rich" },
439
438
  ]
@@ -446,7 +445,6 @@ dev = [
446
445
  [package.metadata]
447
446
  requires-dist = [
448
447
  { name = "comate-agent-sdk", editable = "../../" },
449
- { name = "packaging", specifier = ">=25.0" },
450
448
  { name = "prompt-toolkit", specifier = ">=3.0" },
451
449
  { name = "rich", specifier = ">=14.0" },
452
450
  ]
File without changes
File without changes
File without changes