@blxzer/cursor-trellis 0.2.9 → 0.3.2

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 (234) hide show
  1. package/CHANGELOG.md +94 -0
  2. package/README.md +85 -19
  3. package/README.zh-CN.md +60 -21
  4. package/bin/smart-search.js +1 -1
  5. package/dist/cli/index.d.ts.map +1 -1
  6. package/dist/cli/index.js +46 -18
  7. package/dist/cli/index.js.map +1 -1
  8. package/dist/commands/capability-smoke.d.ts +24 -0
  9. package/dist/commands/capability-smoke.d.ts.map +1 -0
  10. package/dist/commands/capability-smoke.js +83 -0
  11. package/dist/commands/capability-smoke.js.map +1 -0
  12. package/dist/commands/channel/agent-loader.d.ts +1 -1
  13. package/dist/commands/channel/agent-loader.js +4 -4
  14. package/dist/commands/channel/agent-loader.js.map +1 -1
  15. package/dist/commands/channel/guard.d.ts +2 -2
  16. package/dist/commands/channel/guard.js +3 -3
  17. package/dist/commands/channel/guard.js.map +1 -1
  18. package/dist/commands/channel/index.js +3 -3
  19. package/dist/commands/channel/index.js.map +1 -1
  20. package/dist/commands/channel/list.d.ts +1 -1
  21. package/dist/commands/channel/list.js +1 -1
  22. package/dist/commands/channel/rm.d.ts +1 -1
  23. package/dist/commands/channel/rm.js +1 -1
  24. package/dist/commands/channel/store/lock.d.ts +1 -1
  25. package/dist/commands/channel/store/lock.js +1 -1
  26. package/dist/commands/channel/store/paths.js +1 -1
  27. package/dist/commands/channel/store/paths.js.map +1 -1
  28. package/dist/commands/init.d.ts.map +1 -1
  29. package/dist/commands/init.js +197 -91
  30. package/dist/commands/init.js.map +1 -1
  31. package/dist/commands/uninstall.d.ts +4 -4
  32. package/dist/commands/uninstall.js +12 -12
  33. package/dist/commands/uninstall.js.map +1 -1
  34. package/dist/commands/update.d.ts +7 -2
  35. package/dist/commands/update.d.ts.map +1 -1
  36. package/dist/commands/update.js +161 -61
  37. package/dist/commands/update.js.map +1 -1
  38. package/dist/commands/upgrade.js +2 -2
  39. package/dist/commands/upgrade.js.map +1 -1
  40. package/dist/commands/workflow.d.ts +4 -4
  41. package/dist/commands/workflow.d.ts.map +1 -1
  42. package/dist/commands/workflow.js +10 -9
  43. package/dist/commands/workflow.js.map +1 -1
  44. package/dist/configurators/cursor.d.ts +2 -2
  45. package/dist/configurators/cursor.js +4 -4
  46. package/dist/configurators/cursor.js.map +1 -1
  47. package/dist/configurators/index.d.ts.map +1 -1
  48. package/dist/configurators/index.js +4 -4
  49. package/dist/configurators/index.js.map +1 -1
  50. package/dist/configurators/shared.d.ts +10 -10
  51. package/dist/configurators/shared.d.ts.map +1 -1
  52. package/dist/configurators/shared.js +32 -32
  53. package/dist/configurators/shared.js.map +1 -1
  54. package/dist/configurators/workflow.d.ts +6 -6
  55. package/dist/configurators/workflow.js +1 -1
  56. package/dist/constants/paths.d.ts +24 -24
  57. package/dist/constants/paths.d.ts.map +1 -1
  58. package/dist/constants/paths.js +16 -16
  59. package/dist/constants/paths.js.map +1 -1
  60. package/dist/migrations/manifests/0.2.10.json +374 -0
  61. package/dist/migrations/manifests/0.3.0.json +89 -0
  62. package/dist/migrations/manifests/0.3.1.json +32 -0
  63. package/dist/templates/common/bundled-skills/{trellis-cursor2plus-setup → cstl-cursor2plus-setup}/SKILL.md +15 -14
  64. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/SKILL.md +75 -75
  65. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/add-project-local-conventions.md +19 -19
  66. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-agents.md +8 -8
  67. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-context-loading.md +26 -26
  68. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-hooks.md +9 -9
  69. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-skills-or-commands.md +8 -8
  70. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-spec-structure.md +17 -17
  71. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-task-lifecycle.md +46 -46
  72. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/change-workflow.md +18 -18
  73. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/customize-local/overview.md +55 -55
  74. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/local-architecture/context-injection.md +20 -20
  75. package/dist/templates/common/bundled-skills/cstl-meta/references/local-architecture/generated-files.md +83 -0
  76. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/local-architecture/overview.md +15 -15
  77. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/local-architecture/spec-system.md +12 -12
  78. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/local-architecture/task-system.md +34 -34
  79. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/local-architecture/workflow.md +8 -8
  80. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/local-architecture/workspace-memory.md +19 -19
  81. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/platform-files/agents.md +12 -12
  82. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/platform-files/hooks-and-settings.md +7 -7
  83. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/platform-files/overview.md +9 -9
  84. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/platform-files/platform-map.md +7 -7
  85. package/dist/templates/common/bundled-skills/{trellis-meta → cstl-meta}/references/platform-files/skills-and-commands.md +19 -19
  86. package/dist/templates/common/bundled-skills/{trellis-micro-grill → cstl-micro-grill}/SKILL.md +62 -47
  87. package/dist/templates/common/bundled-skills/{trellis-skill-creator → cstl-skill-creator}/SKILL.md +44 -44
  88. package/dist/templates/common/bundled-skills/{trellis-skill-creator → cstl-skill-creator}/references/authoring-rules.md +97 -97
  89. package/dist/templates/common/bundled-skills/{trellis-skill-creator/references/trellis-skill-locations.md → cstl-skill-creator/references/cstl-skill-locations.md} +52 -52
  90. package/dist/templates/common/bundled-skills/{trellis-skill-creator → cstl-skill-creator}/references/review-checklist.md +47 -47
  91. package/dist/templates/common/bundled-skills/{trellis-spec-bootstrap → cstl-spec-bootstrap}/SKILL.md +6 -6
  92. package/dist/templates/common/bundled-skills/{trellis-spec-bootstrap → cstl-spec-bootstrap}/references/repository-analysis.md +1 -1
  93. package/dist/templates/common/bundled-skills/{trellis-spec-bootstrap → cstl-spec-bootstrap}/references/spec-task-planning.md +3 -3
  94. package/dist/templates/common/bundled-skills/{trellis-spec-bootstrap → cstl-spec-bootstrap}/references/spec-writing.md +1 -1
  95. package/dist/templates/common/commands/continue.md +24 -24
  96. package/dist/templates/common/commands/finish-work.md +5 -5
  97. package/dist/templates/common/commands/start.md +20 -20
  98. package/dist/templates/common/index.d.ts +1 -1
  99. package/dist/templates/common/index.d.ts.map +1 -1
  100. package/dist/templates/common/skills/before-dev.md +4 -4
  101. package/dist/templates/common/skills/brainstorm.md +188 -164
  102. package/dist/templates/common/skills/break-loop.md +3 -3
  103. package/dist/templates/common/skills/check.md +5 -5
  104. package/dist/templates/common/skills/update-spec.md +4 -4
  105. package/dist/templates/cursor/agents/{trellis-check.md → cstl-check.md} +14 -14
  106. package/dist/templates/cursor/agents/{trellis-implement.md → cstl-implement.md} +14 -14
  107. package/dist/templates/cursor/agents/{trellis-research.md → cstl-research.md} +11 -11
  108. package/dist/templates/cursor/commands/cursor2plus-setup.md +15 -15
  109. package/dist/templates/cursor/fixtures/expected-rules.d.ts +1 -1
  110. package/dist/templates/cursor/fixtures/expected-rules.d.ts.map +1 -1
  111. package/dist/templates/cursor/fixtures/expected-rules.js +2 -2
  112. package/dist/templates/cursor/fixtures/expected-rules.js.map +1 -1
  113. package/dist/templates/cursor/rules/{trellis-subagent-dispatch.mdc → cstl-subagent-dispatch.mdc} +4 -4
  114. package/dist/templates/cursor/rules/{trellis-triage.mdc → cstl-triage.mdc} +3 -3
  115. package/dist/templates/cursor/rules/retrieval-routing.mdc +4 -4
  116. package/dist/templates/extract.d.ts +1 -1
  117. package/dist/templates/extract.js +1 -1
  118. package/dist/templates/markdown/agents.md +13 -13
  119. package/dist/templates/markdown/prompts/run-semantic-slice-12.md.txt +1 -1
  120. package/dist/templates/markdown/spec/guides/cross-platform-thinking-guide.md.txt +634 -634
  121. package/dist/templates/markdown/spec/guides/cursor-context-injection-guide.md.txt +5 -5
  122. package/dist/templates/markdown/spec/guides/cursor-semantic-compliance.md.txt +7 -1
  123. package/dist/templates/markdown/spec/guides/cursor-subagent-policy.md.txt +393 -391
  124. package/dist/templates/markdown/spec/guides/durable-learning-decision-guide.md.txt +14 -14
  125. package/dist/templates/markdown/spec/guides/execution-strategy.md.txt +5 -5
  126. package/dist/templates/markdown/spec/guides/index.md.txt +3 -2
  127. package/dist/templates/markdown/spec/guides/retrieval-daily-guide.md.txt +10 -10
  128. package/dist/templates/markdown/workspace-index.md +3 -3
  129. package/dist/templates/markdown/worktree.yaml.txt +1 -1
  130. package/dist/templates/shared-hooks/index.d.ts +2 -2
  131. package/dist/templates/shared-hooks/index.js +2 -2
  132. package/dist/templates/shared-hooks/inject-retrieval-plan.py +3 -3
  133. package/dist/templates/shared-hooks/inject-shell-session-context.py +7 -7
  134. package/dist/templates/shared-hooks/inject-subagent-context.py +4 -4
  135. package/dist/templates/shared-hooks/inject-workflow-state.py +37 -37
  136. package/dist/templates/shared-hooks/research-end-retrieval-pack.py +2 -2
  137. package/dist/templates/shared-hooks/session-start.py +16 -16
  138. package/dist/templates/trellis/config/execution-strategy-rules.json +1 -1
  139. package/dist/templates/trellis/config.yaml +5 -25
  140. package/dist/templates/trellis/index.d.ts +2 -2
  141. package/dist/templates/trellis/index.js +2 -2
  142. package/dist/templates/trellis/local/README.md +15 -13
  143. package/dist/templates/trellis/local/patch_wpelc8.py +7 -7
  144. package/dist/templates/trellis/local/subagent-models.json.example +1 -1
  145. package/dist/templates/trellis/local/trellis-task-models.json.example +3 -3
  146. package/dist/templates/trellis/local/trellis-task-models.json5.example +5 -5
  147. package/dist/templates/trellis/local/trellis_task_models_config.py +6 -6
  148. package/dist/templates/trellis/scripts/add_session.py +20 -20
  149. package/dist/templates/trellis/scripts/common/active_task.py +2 -2
  150. package/dist/templates/trellis/scripts/common/artifact_search.py +587 -587
  151. package/dist/templates/trellis/scripts/common/cli_adapter.py +3 -3
  152. package/dist/templates/trellis/scripts/common/codebase_retrieval_router.py +6 -6
  153. package/dist/templates/trellis/scripts/common/config.py +3 -3
  154. package/dist/templates/trellis/scripts/common/developer.py +2 -2
  155. package/dist/templates/trellis/scripts/common/execution_strategy.py +1 -1
  156. package/dist/templates/trellis/scripts/common/packages_context.py +23 -23
  157. package/dist/templates/trellis/scripts/common/parent_orchestration.py +702 -702
  158. package/dist/templates/trellis/scripts/common/paths.py +107 -107
  159. package/dist/templates/trellis/scripts/common/project_file_stats.py +1 -1
  160. package/dist/templates/trellis/scripts/common/retrieval_agent_instructions.py +1 -1
  161. package/dist/templates/trellis/scripts/common/safe_commit.py +31 -31
  162. package/dist/templates/trellis/scripts/common/session_context.py +1159 -1159
  163. package/dist/templates/trellis/scripts/common/session_memory.py +360 -360
  164. package/dist/templates/trellis/scripts/common/smart_search_evidence.py +514 -514
  165. package/dist/templates/trellis/scripts/common/smart_search_resolve.py +1 -1
  166. package/dist/templates/trellis/scripts/common/subagent_dispatch.py +7 -7
  167. package/dist/templates/trellis/scripts/common/task_context.py +1 -1
  168. package/dist/templates/trellis/scripts/common/task_dashboard.py +140 -140
  169. package/dist/templates/trellis/scripts/common/task_gates.py +2056 -2034
  170. package/dist/templates/trellis/scripts/common/task_store.py +1594 -1594
  171. package/dist/templates/trellis/scripts/common/task_utils.py +3 -3
  172. package/dist/templates/trellis/scripts/common/tasks.py +1 -1
  173. package/dist/templates/trellis/scripts/common/trellis_config.py +3 -3
  174. package/dist/templates/trellis/scripts/common/workflow_phase.py +1 -1
  175. package/dist/templates/trellis/scripts/cursor_retrieval_probe.py +3 -3
  176. package/dist/templates/trellis/scripts/cursor_retrieval_probe_prompt.md +11 -11
  177. package/dist/templates/trellis/scripts/hooks/linear_sync.py +8 -8
  178. package/dist/templates/trellis/scripts/init_developer.py +2 -2
  179. package/dist/templates/trellis/scripts/retrieval_probe_matrix_template.json +4 -4
  180. package/dist/templates/trellis/scripts/route_codebase_retrieval.py +1 -1
  181. package/dist/templates/trellis/scripts/task.py +918 -918
  182. package/dist/templates/trellis/tasks/templates/release-readiness/implement.md +2 -2
  183. package/dist/templates/trellis/workflow.md +805 -805
  184. package/dist/types/ai-tools.d.ts +1 -1
  185. package/dist/types/ai-tools.d.ts.map +1 -1
  186. package/dist/types/ai-tools.js +1 -1
  187. package/dist/types/ai-tools.js.map +1 -1
  188. package/dist/types/migration.d.ts +1 -1
  189. package/dist/types/migration.d.ts.map +1 -1
  190. package/dist/utils/agents-md.d.ts +37 -0
  191. package/dist/utils/agents-md.d.ts.map +1 -0
  192. package/dist/utils/agents-md.js +82 -0
  193. package/dist/utils/agents-md.js.map +1 -0
  194. package/dist/utils/codebase-retrieval-router.js +5 -5
  195. package/dist/utils/codebase-retrieval-router.js.map +1 -1
  196. package/dist/utils/manifest-prune.d.ts +2 -2
  197. package/dist/utils/manifest-prune.js +4 -4
  198. package/dist/utils/manifest-prune.js.map +1 -1
  199. package/dist/utils/mirror-check.d.ts +3 -1
  200. package/dist/utils/mirror-check.d.ts.map +1 -1
  201. package/dist/utils/mirror-check.js +22 -11
  202. package/dist/utils/mirror-check.js.map +1 -1
  203. package/dist/utils/project-capabilities.d.ts +14 -3
  204. package/dist/utils/project-capabilities.d.ts.map +1 -1
  205. package/dist/utils/project-capabilities.js +127 -17
  206. package/dist/utils/project-capabilities.js.map +1 -1
  207. package/dist/utils/readiness.d.ts +10 -0
  208. package/dist/utils/readiness.d.ts.map +1 -1
  209. package/dist/utils/readiness.js +6 -3
  210. package/dist/utils/readiness.js.map +1 -1
  211. package/dist/utils/retrieval-agent-instructions.js +1 -1
  212. package/dist/utils/retrieval-agent-instructions.js.map +1 -1
  213. package/dist/utils/retrieval-execution-telemetry.js +1 -1
  214. package/dist/utils/retrieval-execution-telemetry.js.map +1 -1
  215. package/dist/utils/template-fetcher.js +1 -1
  216. package/dist/utils/template-fetcher.js.map +1 -1
  217. package/dist/utils/template-hash.d.ts +2 -2
  218. package/dist/utils/template-hash.d.ts.map +1 -1
  219. package/dist/utils/template-hash.js +12 -10
  220. package/dist/utils/template-hash.js.map +1 -1
  221. package/dist/utils/workflow-dir.d.ts +13 -0
  222. package/dist/utils/workflow-dir.d.ts.map +1 -0
  223. package/dist/utils/workflow-dir.js +35 -0
  224. package/dist/utils/workflow-dir.js.map +1 -0
  225. package/dist/utils/workflow-ownership.d.ts +36 -0
  226. package/dist/utils/workflow-ownership.d.ts.map +1 -0
  227. package/dist/utils/workflow-ownership.js +137 -0
  228. package/dist/utils/workflow-ownership.js.map +1 -0
  229. package/dist/utils/workflow-resolver.d.ts +1 -1
  230. package/dist/utils/workflow-resolver.js +1 -1
  231. package/package.json +3 -4
  232. package/dist/templates/common/bundled-skills/trellis-meta/references/local-architecture/generated-files.md +0 -83
  233. /package/bin/{trellis.js → cstl.js} +0 -0
  234. /package/dist/templates/common/bundled-skills/{trellis-spec-bootstrap → cstl-spec-bootstrap}/references/mcp-setup.md +0 -0
@@ -2,7 +2,7 @@
2
2
  """
3
3
  Resolve how to invoke the smart-search CLI (argv prefix for subprocess).
4
4
 
5
- No writes under .trellis/.runtime/. Optional per-machine override:
5
+ No writes under .cstl/.runtime/. Optional per-machine override:
6
6
  TRELLIS_SMART_SEARCH_COMMAND or smart_search.command in config.yaml.
7
7
  """
8
8
 
@@ -15,17 +15,17 @@ from typing import Literal
15
15
  from .io import read_json
16
16
  from .paths import FILE_TASK_JSON
17
17
 
18
- DIR_WORKFLOW = ".trellis"
18
+ DIR_WORKFLOW = ".cstl"
19
19
  DIR_SPEC = "spec"
20
20
 
21
- AGENT_IMPLEMENT = "trellis-implement"
22
- AGENT_CHECK = "trellis-check"
23
- AGENT_RESEARCH = "trellis-research"
21
+ AGENT_IMPLEMENT = "cstl-implement"
22
+ AGENT_CHECK = "cstl-check"
23
+ AGENT_RESEARCH = "cstl-research"
24
24
 
25
25
  AGENTS_ALL = (AGENT_IMPLEMENT, AGENT_CHECK, AGENT_RESEARCH)
26
26
  AGENTS_REQUIRE_TASK = (AGENT_IMPLEMENT, AGENT_CHECK)
27
27
 
28
- INJECTION_MARKER = "<!-- trellis-hook-injected -->"
28
+ INJECTION_MARKER = "<!-- cstl-hook-injected -->"
29
29
 
30
30
  DispatchRole = Literal["implement", "check", "research"]
31
31
 
@@ -341,7 +341,7 @@ Conversations get compacted; files do not. Every research topic MUST be written
341
341
  ## Dispatch contract
342
342
 
343
343
  - External facts: load `smart-search-cli` skill + Bash — default **not** Cursor `WebSearch`/`WebFetch`.
344
- - Do NOT spawn nested `trellis-implement` / `trellis-check` / `trellis-research` sub-agents.
344
+ - Do NOT spawn nested `cstl-implement` / `cstl-check` / `cstl-research` sub-agents.
345
345
 
346
346
  ## Project Info
347
347
 
@@ -369,7 +369,7 @@ Conversations get compacted; files do not. Every research topic MUST be written
369
369
 
370
370
  ## Write FORBIDDEN
371
371
 
372
- - Code, `.trellis/spec/`, platform config, git operations"""
372
+ - Code, `.cstl/spec/`, platform config, git operations"""
373
373
 
374
374
 
375
375
  def _repo_relative(task_dir: Path, repo_root: Path) -> str:
@@ -11,7 +11,7 @@ Note:
11
11
  ``cmd_init_context`` was removed in v0.5.0-beta.12. JSONL context files
12
12
  are now seeded at ``task.py create`` time with a self-describing
13
13
  ``_example`` line; the AI agent curates real entries during planning when
14
- the task needs sub-agent/spec context. See ``.trellis/workflow.md`` for the
14
+ the task needs sub-agent/spec context. See ``.cstl/workflow.md`` for the
15
15
  current planning artifact contract.
16
16
  """
17
17
 
@@ -1,140 +1,140 @@
1
- #!/usr/bin/env python3
2
- """Task dashboard rendering for framework entry routing."""
3
-
4
- from __future__ import annotations
5
-
6
- from pathlib import Path
7
-
8
- from .active_task import resolve_selected_task
9
- from .paths import DIR_TASKS, DIR_WORKFLOW, get_developer, get_repo_root, get_tasks_dir
10
- from .task_map import get_child_state
11
- from .tasks import (
12
- children_progress,
13
- format_child_task_display,
14
- iter_active_tasks,
15
- load_parent_child_integration_states,
16
- )
17
-
18
-
19
- _STATUS_ORDER = ("planning", "in_progress", "review", "blocked")
20
-
21
-
22
- def _task_path(dir_name: str) -> str:
23
- return f"{DIR_WORKFLOW}/{DIR_TASKS}/{dir_name}"
24
-
25
-
26
- def _selected_line(
27
- repo_root: Path,
28
- platform_input: dict | None = None,
29
- platform: str | None = None,
30
- ) -> str:
31
- selected = resolve_selected_task(repo_root, platform_input, platform)
32
- if selected.task_path:
33
- suffix = f" ({selected.source})" if selected.source else ""
34
- return f"Selected task: {selected.task_path}{suffix}"
35
- return (
36
- "Selected task: none "
37
- "(no session pointer — use task.py select <task> or task.py list)"
38
- )
39
-
40
-
41
- def render_task_dashboard(
42
- repo_root: Path | None = None,
43
- platform_input: dict | None = None,
44
- platform: str | None = None,
45
- ) -> str:
46
- """Render a compact, non-mutating Task Dashboard."""
47
- if repo_root is None:
48
- repo_root = get_repo_root()
49
-
50
- tasks_dir = get_tasks_dir(repo_root)
51
- developer = get_developer(repo_root)
52
- all_tasks = {task.dir_name: task for task in iter_active_tasks(tasks_dir)}
53
- all_statuses = {name: task.status for name, task in all_tasks.items()}
54
-
55
- lines: list[str] = [
56
- "Task Dashboard",
57
- "Trellis framework: active",
58
- _selected_line(repo_root, platform_input, platform),
59
- "",
60
- ]
61
-
62
- if not all_tasks:
63
- lines.append("Tasks: none")
64
- else:
65
- printed: set[str] = set()
66
- for status in _STATUS_ORDER:
67
- names = [
68
- name
69
- for name, task in sorted(all_tasks.items())
70
- if task.status == status and not task.parent
71
- ]
72
- if not names:
73
- continue
74
- title = status.replace("_", " ").title()
75
- lines.append(f"{title}:")
76
- for name in names:
77
- _append_task(lines, name, all_tasks, all_statuses, printed)
78
- lines.append("")
79
-
80
- other_names = [
81
- name
82
- for name, task in sorted(all_tasks.items())
83
- if name not in printed and not task.parent
84
- ]
85
- if other_names:
86
- lines.append("Other:")
87
- for name in other_names:
88
- _append_task(lines, name, all_tasks, all_statuses, printed)
89
- lines.append("")
90
-
91
- lines.append("Suggested actions:")
92
- lines.append(" - Select a task: python ./.trellis/scripts/task.py select <task>")
93
- lines.append(" - Create a task: python ./.trellis/scripts/task.py create \"<title>\" --slug <slug>")
94
- lines.append(" - Inspect raw list: python ./.trellis/scripts/task.py list")
95
- lines.append(" - Continue without a task only for No Task or Micro-Grill work")
96
- if developer:
97
- lines.append(f"Developer: {developer}")
98
-
99
- return "\n".join(line.rstrip() for line in lines).rstrip()
100
-
101
-
102
- def _append_task(
103
- lines: list[str],
104
- name: str,
105
- all_tasks: dict,
106
- all_statuses: dict[str, str],
107
- printed: set[str],
108
- indent: int = 0,
109
- parent_dir: Path | None = None,
110
- ) -> None:
111
- task = all_tasks[name]
112
- printed.add(name)
113
- integration_states = None
114
- if task.children:
115
- integration_states = load_parent_child_integration_states(
116
- task.directory, task.children
117
- )
118
- progress = children_progress(
119
- task.children, all_statuses, integration_states
120
- )
121
- integration_state = None
122
- if parent_dir is not None:
123
- integration_state = get_child_state(parent_dir, name)
124
- status_display = format_child_task_display(task.status, integration_state)
125
- assignee = task.assignee or "-"
126
- prefix = " " * indent + " - "
127
- lines.append(
128
- f"{prefix}{_task_path(name)} ({status_display}){progress} [{assignee}]"
129
- )
130
- for child_name in task.children:
131
- if child_name in all_tasks:
132
- _append_task(
133
- lines,
134
- child_name,
135
- all_tasks,
136
- all_statuses,
137
- printed,
138
- indent + 1,
139
- parent_dir=task.directory,
140
- )
1
+ #!/usr/bin/env python3
2
+ """Task dashboard rendering for framework entry routing."""
3
+
4
+ from __future__ import annotations
5
+
6
+ from pathlib import Path
7
+
8
+ from .active_task import resolve_selected_task
9
+ from .paths import DIR_TASKS, DIR_WORKFLOW, get_developer, get_repo_root, get_tasks_dir
10
+ from .task_map import get_child_state
11
+ from .tasks import (
12
+ children_progress,
13
+ format_child_task_display,
14
+ iter_active_tasks,
15
+ load_parent_child_integration_states,
16
+ )
17
+
18
+
19
+ _STATUS_ORDER = ("planning", "in_progress", "review", "blocked")
20
+
21
+
22
+ def _task_path(dir_name: str) -> str:
23
+ return f"{DIR_WORKFLOW}/{DIR_TASKS}/{dir_name}"
24
+
25
+
26
+ def _selected_line(
27
+ repo_root: Path,
28
+ platform_input: dict | None = None,
29
+ platform: str | None = None,
30
+ ) -> str:
31
+ selected = resolve_selected_task(repo_root, platform_input, platform)
32
+ if selected.task_path:
33
+ suffix = f" ({selected.source})" if selected.source else ""
34
+ return f"Selected task: {selected.task_path}{suffix}"
35
+ return (
36
+ "Selected task: none "
37
+ "(no session pointer — use task.py select <task> or task.py list)"
38
+ )
39
+
40
+
41
+ def render_task_dashboard(
42
+ repo_root: Path | None = None,
43
+ platform_input: dict | None = None,
44
+ platform: str | None = None,
45
+ ) -> str:
46
+ """Render a compact, non-mutating Task Dashboard."""
47
+ if repo_root is None:
48
+ repo_root = get_repo_root()
49
+
50
+ tasks_dir = get_tasks_dir(repo_root)
51
+ developer = get_developer(repo_root)
52
+ all_tasks = {task.dir_name: task for task in iter_active_tasks(tasks_dir)}
53
+ all_statuses = {name: task.status for name, task in all_tasks.items()}
54
+
55
+ lines: list[str] = [
56
+ "Task Dashboard",
57
+ "Trellis framework: active",
58
+ _selected_line(repo_root, platform_input, platform),
59
+ "",
60
+ ]
61
+
62
+ if not all_tasks:
63
+ lines.append("Tasks: none")
64
+ else:
65
+ printed: set[str] = set()
66
+ for status in _STATUS_ORDER:
67
+ names = [
68
+ name
69
+ for name, task in sorted(all_tasks.items())
70
+ if task.status == status and not task.parent
71
+ ]
72
+ if not names:
73
+ continue
74
+ title = status.replace("_", " ").title()
75
+ lines.append(f"{title}:")
76
+ for name in names:
77
+ _append_task(lines, name, all_tasks, all_statuses, printed)
78
+ lines.append("")
79
+
80
+ other_names = [
81
+ name
82
+ for name, task in sorted(all_tasks.items())
83
+ if name not in printed and not task.parent
84
+ ]
85
+ if other_names:
86
+ lines.append("Other:")
87
+ for name in other_names:
88
+ _append_task(lines, name, all_tasks, all_statuses, printed)
89
+ lines.append("")
90
+
91
+ lines.append("Suggested actions:")
92
+ lines.append(" - Select a task: python ./.cstl/scripts/task.py select <task>")
93
+ lines.append(" - Create a task: python ./.cstl/scripts/task.py create \"<title>\" --slug <slug>")
94
+ lines.append(" - Inspect raw list: python ./.cstl/scripts/task.py list")
95
+ lines.append(" - Continue without a task only for No Task or Micro-Grill work")
96
+ if developer:
97
+ lines.append(f"Developer: {developer}")
98
+
99
+ return "\n".join(line.rstrip() for line in lines).rstrip()
100
+
101
+
102
+ def _append_task(
103
+ lines: list[str],
104
+ name: str,
105
+ all_tasks: dict,
106
+ all_statuses: dict[str, str],
107
+ printed: set[str],
108
+ indent: int = 0,
109
+ parent_dir: Path | None = None,
110
+ ) -> None:
111
+ task = all_tasks[name]
112
+ printed.add(name)
113
+ integration_states = None
114
+ if task.children:
115
+ integration_states = load_parent_child_integration_states(
116
+ task.directory, task.children
117
+ )
118
+ progress = children_progress(
119
+ task.children, all_statuses, integration_states
120
+ )
121
+ integration_state = None
122
+ if parent_dir is not None:
123
+ integration_state = get_child_state(parent_dir, name)
124
+ status_display = format_child_task_display(task.status, integration_state)
125
+ assignee = task.assignee or "-"
126
+ prefix = " " * indent + " - "
127
+ lines.append(
128
+ f"{prefix}{_task_path(name)} ({status_display}){progress} [{assignee}]"
129
+ )
130
+ for child_name in task.children:
131
+ if child_name in all_tasks:
132
+ _append_task(
133
+ lines,
134
+ child_name,
135
+ all_tasks,
136
+ all_statuses,
137
+ printed,
138
+ indent + 1,
139
+ parent_dir=task.directory,
140
+ )