@scemoon/cdh 1.0.6 → 1.0.8

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 (551) hide show
  1. package/package.json +2 -2
  2. package/run.js +2 -1
  3. package/ai-dlc-skill/SKILL.md +0 -77
  4. package/ai-dlc-skill/agents/deliver-agent.md +0 -24
  5. package/ai-dlc-skill/agents/master.md +0 -50
  6. package/ai-dlc-skill/agents/plan-agent.md +0 -23
  7. package/ai-dlc-skill/agents/understand-agent.md +0 -23
  8. package/ai-dlc-skill/agents/verify-agent.md +0 -27
  9. package/ai-dlc-skill/architecture/project-structure.md +0 -78
  10. package/ai-dlc-skill/brownfield/README.md +0 -30
  11. package/ai-dlc-skill/brownfield/generate-context.sh +0 -64
  12. package/ai-dlc-skill/brownfield/scripts/deps.sh +0 -27
  13. package/ai-dlc-skill/brownfield/scripts/discover.sh +0 -34
  14. package/ai-dlc-skill/brownfield/scripts/extract-api.sh +0 -45
  15. package/ai-dlc-skill/components/backend.md +0 -34
  16. package/ai-dlc-skill/components/desktop.md +0 -30
  17. package/ai-dlc-skill/components/mya.md +0 -29
  18. package/ai-dlc-skill/components/native.md +0 -30
  19. package/ai-dlc-skill/components/tta.md +0 -29
  20. package/ai-dlc-skill/components/web.md +0 -31
  21. package/ai-dlc-skill/components/wxa.md +0 -29
  22. package/ai-dlc-skill/contracts/README.md +0 -25
  23. package/ai-dlc-skill/core/adaptive-flow.md +0 -36
  24. package/ai-dlc-skill/core/security.md +0 -29
  25. package/ai-dlc-skill/cross-tool/cline/export.sh +0 -31
  26. package/ai-dlc-skill/cross-tool/copilot/export.sh +0 -47
  27. package/ai-dlc-skill/cross-tool/cursor/export.sh +0 -32
  28. package/ai-dlc-skill/cross-tool/export.sh +0 -22
  29. package/ai-dlc-skill/cross-tool/onecode/config.yaml.tpl +0 -17
  30. package/ai-dlc-skill/cross-tool/onecode/export-skills.sh +0 -35
  31. package/ai-dlc-skill/cross-tool/onecode/export.sh +0 -54
  32. package/ai-dlc-skill/phases/deliver/entry.md +0 -26
  33. package/ai-dlc-skill/phases/deliver/lifecycle.md +0 -185
  34. package/ai-dlc-skill/phases/deliver/prompt.md +0 -40
  35. package/ai-dlc-skill/phases/deliver/rules.md +0 -61
  36. package/ai-dlc-skill/phases/plan/entry.md +0 -25
  37. package/ai-dlc-skill/phases/plan/lifecycle.md +0 -204
  38. package/ai-dlc-skill/phases/plan/prompt.md +0 -38
  39. package/ai-dlc-skill/phases/plan/rules.md +0 -25
  40. package/ai-dlc-skill/phases/understand/entry.md +0 -26
  41. package/ai-dlc-skill/phases/understand/lifecycle.md +0 -184
  42. package/ai-dlc-skill/phases/understand/prompt.md +0 -41
  43. package/ai-dlc-skill/phases/understand/rules.md +0 -37
  44. package/ai-dlc-skill/phases/verify/entry.md +0 -26
  45. package/ai-dlc-skill/phases/verify/lifecycle.md +0 -192
  46. package/ai-dlc-skill/phases/verify/prompt.md +0 -43
  47. package/ai-dlc-skill/phases/verify/rules.md +0 -73
  48. package/ai-dlc-skill/practices/bdd.md +0 -91
  49. package/ai-dlc-skill/practices/sdd.md +0 -84
  50. package/ai-dlc-skill/practices/tdd.md +0 -95
  51. package/ai-dlc-skill/providers/README.md +0 -114
  52. package/ai-dlc-skill/providers/aliyun/deployment.yaml +0 -66
  53. package/ai-dlc-skill/providers/aliyun/preview.yaml +0 -84
  54. package/ai-dlc-skill/providers/aliyun/provider.yaml +0 -160
  55. package/ai-dlc-skill/providers/tcb/deployment.yaml +0 -69
  56. package/ai-dlc-skill/providers/tcb/preview.yaml +0 -83
  57. package/ai-dlc-skill/providers/tcb/provider.yaml +0 -172
  58. package/ai-dlc-skill/requirements.md +0 -140
  59. package/ai-dlc-skill/skill.yaml +0 -147
  60. package/ai-dlc-skill/templates/integration/CHANGELOG.md +0 -41
  61. package/ai-dlc-skill/templates/integration/asyncapi.yaml +0 -43
  62. package/ai-dlc-skill/templates/integration/contract-diff.md +0 -63
  63. package/ai-dlc-skill/templates/integration/contract-spec.md +0 -49
  64. package/ai-dlc-skill/templates/integration/openapi.yaml +0 -18
  65. package/ai-dlc-skill/templates/integration/runtime-contract.yaml +0 -36
  66. package/ai-dlc-skill/templates/plan/design.md +0 -49
  67. package/ai-dlc-skill/templates/plan/task-list.md +0 -32
  68. package/ai-dlc-skill/templates/project/README.md +0 -126
  69. package/ai-dlc-skill/templates/project/template.md +0 -119
  70. package/ai-dlc-skill/templates/understand/feature.feature +0 -23
  71. package/ai-dlc-skill/templates/understand/intent.md +0 -29
  72. package/ai-dlc-skill/templates/understand/spec-delta.md +0 -47
  73. package/ai-dlc-skill/templates/verify/test-unit.py +0 -27
  74. package/ai-dlc-skill/walkthrough/collect.sh +0 -50
  75. package/ai-dlc-skill/walkthrough/template.md +0 -54
  76. package/ai-dlc-skill/workflows/ai-dlc.yaml +0 -110
  77. package/ai-dlc-skill/workflows/deployment.yaml +0 -199
  78. package/cdh/__init__.py +0 -0
  79. package/cdh/__main__.py +0 -4
  80. package/cdh/__pycache__/__init__.cpython-314.pyc +0 -0
  81. package/cdh/__pycache__/cdh_mcp_injector.cpython-314.pyc +0 -0
  82. package/cdh/__pycache__/cdh_mcp_loader.cpython-314.pyc +0 -0
  83. package/cdh/__pycache__/cdh_mcp_manager.cpython-314.pyc +0 -0
  84. package/cdh/__pycache__/cdh_session_aggregator.cpython-314.pyc +0 -0
  85. package/cdh/__pycache__/cdh_skill_loader.cpython-314.pyc +0 -0
  86. package/cdh/__pycache__/cdh_skill_manager.cpython-314.pyc +0 -0
  87. package/cdh/__pycache__/cli.cpython-313.pyc +0 -0
  88. package/cdh/__pycache__/cli.cpython-314.pyc +0 -0
  89. package/cdh/__pycache__/scaffold.cpython-314.pyc +0 -0
  90. package/cdh/cdh_mcp_injector.py +0 -115
  91. package/cdh/cdh_mcp_loader.py +0 -67
  92. package/cdh/cdh_mcp_manager.py +0 -73
  93. package/cdh/cdh_session_aggregator.py +0 -258
  94. package/cdh/cdh_skill_manager.py +0 -105
  95. package/cdh/cli.py +0 -807
  96. package/cdh/scaffold.py +0 -728
  97. package/onecode/__init__.py +0 -1
  98. package/onecode/__main__.py +0 -4
  99. package/onecode/__pycache__/__init__.cpython-314.pyc +0 -0
  100. package/onecode/__pycache__/cli.cpython-314.pyc +0 -0
  101. package/onecode/__pycache__/commands.cpython-314.pyc +0 -0
  102. package/onecode/__pycache__/config.cpython-314.pyc +0 -0
  103. package/onecode/__pycache__/config_screen.cpython-314.pyc +0 -0
  104. package/onecode/__pycache__/migrate.cpython-314.pyc +0 -0
  105. package/onecode/agent/__init__.py +0 -0
  106. package/onecode/agent/__pycache__/__init__.cpython-314.pyc +0 -0
  107. package/onecode/agent/__pycache__/cdh_loader.cpython-314.pyc +0 -0
  108. package/onecode/agent/__pycache__/context.cpython-314.pyc +0 -0
  109. package/onecode/agent/__pycache__/engine.cpython-314.pyc +0 -0
  110. package/onecode/agent/__pycache__/hooks.cpython-314.pyc +0 -0
  111. package/onecode/agent/__pycache__/onecode_agent_acp.cpython-314.pyc +0 -0
  112. package/onecode/agent/__pycache__/permissions.cpython-314.pyc +0 -0
  113. package/onecode/agent/__pycache__/permissions_store.cpython-314.pyc +0 -0
  114. package/onecode/agent/__pycache__/project_doc.cpython-314.pyc +0 -0
  115. package/onecode/agent/__pycache__/session.cpython-314.pyc +0 -0
  116. package/onecode/agent/agents/__init__.py +0 -29
  117. package/onecode/agent/agents/__pycache__/__init__.cpython-314.pyc +0 -0
  118. package/onecode/agent/agents/__pycache__/types.cpython-314.pyc +0 -0
  119. package/onecode/agent/agents/types.py +0 -589
  120. package/onecode/agent/attachments.py +0 -112
  121. package/onecode/agent/cdh_loader.py +0 -267
  122. package/onecode/agent/context.py +0 -343
  123. package/onecode/agent/engine.py +0 -2700
  124. package/onecode/agent/hooks.py +0 -86
  125. package/onecode/agent/onecode_agent_acp.py +0 -2743
  126. package/onecode/agent/onecode_agent_acp.py.bak +0 -2447
  127. package/onecode/agent/permissions.py +0 -150
  128. package/onecode/agent/permissions_store.py +0 -62
  129. package/onecode/agent/project_doc.py +0 -19
  130. package/onecode/agent/session.py +0 -195
  131. package/onecode/agent/snapshot.py +0 -144
  132. package/onecode/agent/tools/__init__.py +0 -17
  133. package/onecode/agent/tools/__pycache__/__init__.cpython-314.pyc +0 -0
  134. package/onecode/agent/tools/__pycache__/agent_tools.cpython-314.pyc +0 -0
  135. package/onecode/agent/tools/__pycache__/apply_patch_tool.cpython-314.pyc +0 -0
  136. package/onecode/agent/tools/__pycache__/bash_tool.cpython-314.pyc +0 -0
  137. package/onecode/agent/tools/__pycache__/communication_tools.cpython-314.pyc +0 -0
  138. package/onecode/agent/tools/__pycache__/config_tool.cpython-314.pyc +0 -0
  139. package/onecode/agent/tools/__pycache__/cron_tools.cpython-314.pyc +0 -0
  140. package/onecode/agent/tools/__pycache__/errors.cpython-314.pyc +0 -0
  141. package/onecode/agent/tools/__pycache__/file_ops.cpython-314.pyc +0 -0
  142. package/onecode/agent/tools/__pycache__/file_tools.cpython-314.pyc +0 -0
  143. package/onecode/agent/tools/__pycache__/git_tools.cpython-314.pyc +0 -0
  144. package/onecode/agent/tools/__pycache__/lsp_tools.cpython-314.pyc +0 -0
  145. package/onecode/agent/tools/__pycache__/mcp_tools.cpython-314.pyc +0 -0
  146. package/onecode/agent/tools/__pycache__/permission_handler.cpython-314.pyc +0 -0
  147. package/onecode/agent/tools/__pycache__/permissions.cpython-314.pyc +0 -0
  148. package/onecode/agent/tools/__pycache__/protocol.cpython-314.pyc +0 -0
  149. package/onecode/agent/tools/__pycache__/registry.cpython-314.pyc +0 -0
  150. package/onecode/agent/tools/__pycache__/sandbox.cpython-314.pyc +0 -0
  151. package/onecode/agent/tools/__pycache__/schema_validation.cpython-314.pyc +0 -0
  152. package/onecode/agent/tools/__pycache__/skill_tools.cpython-314.pyc +0 -0
  153. package/onecode/agent/tools/__pycache__/todo_tools.cpython-314.pyc +0 -0
  154. package/onecode/agent/tools/__pycache__/web_tools.cpython-314.pyc +0 -0
  155. package/onecode/agent/tools/agent_tools.py +0 -132
  156. package/onecode/agent/tools/apply_patch_tool.py +0 -138
  157. package/onecode/agent/tools/bash_tool.py +0 -111
  158. package/onecode/agent/tools/communication_tools.py +0 -148
  159. package/onecode/agent/tools/config_tool.py +0 -130
  160. package/onecode/agent/tools/cron_tools.py +0 -178
  161. package/onecode/agent/tools/errors.py +0 -17
  162. package/onecode/agent/tools/file_ops.py +0 -221
  163. package/onecode/agent/tools/file_tools.py +0 -225
  164. package/onecode/agent/tools/git_tools.py +0 -88
  165. package/onecode/agent/tools/lsp_tools.py +0 -404
  166. package/onecode/agent/tools/mcp_tools.py +0 -127
  167. package/onecode/agent/tools/permission_handler.py +0 -46
  168. package/onecode/agent/tools/permissions.py +0 -77
  169. package/onecode/agent/tools/protocol.py +0 -20
  170. package/onecode/agent/tools/registry.py +0 -201
  171. package/onecode/agent/tools/sandbox.py +0 -358
  172. package/onecode/agent/tools/schema_validation.py +0 -100
  173. package/onecode/agent/tools/skill_tools.py +0 -52
  174. package/onecode/agent/tools/todo_tools.py +0 -207
  175. package/onecode/agent/tools/web_tools.py +0 -169
  176. package/onecode/builtin_skills/agent-browser/SKILL.md +0 -212
  177. package/onecode/builtin_skills/agent-browser/skill.yaml +0 -8
  178. package/onecode/builtin_skills/git/SKILL.md +0 -64
  179. package/onecode/builtin_skills/git/skill.yaml +0 -7
  180. package/onecode/builtin_skills/shell/SKILL.md +0 -58
  181. package/onecode/builtin_skills/shell/skill.yaml +0 -8
  182. package/onecode/builtin_skills/skill-creator/SKILL.md +0 -106
  183. package/onecode/builtin_skills/skill-creator/skill.yaml +0 -8
  184. package/onecode/cli.py +0 -935
  185. package/onecode/cloud/__init__.py +0 -0
  186. package/onecode/cloud/base.py +0 -20
  187. package/onecode/codebase/__init__.py +0 -69
  188. package/onecode/codebase/__pycache__/__init__.cpython-314.pyc +0 -0
  189. package/onecode/codebase/__pycache__/chunker.cpython-314.pyc +0 -0
  190. package/onecode/codebase/__pycache__/indexer.cpython-314.pyc +0 -0
  191. package/onecode/codebase/__pycache__/retriever.cpython-314.pyc +0 -0
  192. package/onecode/codebase/__pycache__/storage.cpython-314.pyc +0 -0
  193. package/onecode/codebase/__pycache__/tools.cpython-314.pyc +0 -0
  194. package/onecode/codebase/chunker.py +0 -125
  195. package/onecode/codebase/indexer.py +0 -149
  196. package/onecode/codebase/retriever.py +0 -203
  197. package/onecode/codebase/storage.py +0 -131
  198. package/onecode/codebase/tools.py +0 -59
  199. package/onecode/commands.py +0 -596
  200. package/onecode/config.py +0 -314
  201. package/onecode/config_screen.py +0 -600
  202. package/onecode/cron/__init__.py +0 -3
  203. package/onecode/lsp/__init__.py +0 -3
  204. package/onecode/mcp/__init__.py +0 -4
  205. package/onecode/mcp/__pycache__/__init__.cpython-314.pyc +0 -0
  206. package/onecode/mcp/__pycache__/client.cpython-314.pyc +0 -0
  207. package/onecode/mcp/__pycache__/manager.cpython-314.pyc +0 -0
  208. package/onecode/mcp/client.py +0 -193
  209. package/onecode/mcp/manager.py +0 -190
  210. package/onecode/memory/__init__.py +0 -49
  211. package/onecode/memory/__pycache__/__init__.cpython-314.pyc +0 -0
  212. package/onecode/memory/__pycache__/backend.cpython-314.pyc +0 -0
  213. package/onecode/memory/__pycache__/offload.cpython-314.pyc +0 -0
  214. package/onecode/memory/__pycache__/pyramid.cpython-314.pyc +0 -0
  215. package/onecode/memory/__pycache__/recall.cpython-314.pyc +0 -0
  216. package/onecode/memory/__pycache__/symbolic.cpython-314.pyc +0 -0
  217. package/onecode/memory/backend.py +0 -159
  218. package/onecode/memory/pyramid.py +0 -133
  219. package/onecode/memory/recall.py +0 -203
  220. package/onecode/migrate.py +0 -122
  221. package/onecode/models/__init__.py +0 -4
  222. package/onecode/models/__pycache__/__init__.cpython-314.pyc +0 -0
  223. package/onecode/models/__pycache__/errors.cpython-314.pyc +0 -0
  224. package/onecode/models/__pycache__/messages.cpython-314.pyc +0 -0
  225. package/onecode/models/__pycache__/provider.cpython-314.pyc +0 -0
  226. package/onecode/models/__pycache__/registry.cpython-314.pyc +0 -0
  227. package/onecode/models/errors.py +0 -104
  228. package/onecode/models/messages.py +0 -739
  229. package/onecode/models/provider.py +0 -699
  230. package/onecode/models/providers/__init__.py +0 -17
  231. package/onecode/models/providers/__pycache__/__init__.cpython-314.pyc +0 -0
  232. package/onecode/models/providers/__pycache__/anthropic_provider.cpython-314.pyc +0 -0
  233. package/onecode/models/providers/__pycache__/deepseek_provider.cpython-314.pyc +0 -0
  234. package/onecode/models/providers/__pycache__/glm_provider.cpython-314.pyc +0 -0
  235. package/onecode/models/providers/__pycache__/minimax_provider.cpython-314.pyc +0 -0
  236. package/onecode/models/providers/__pycache__/minimaxi_provider.cpython-314.pyc +0 -0
  237. package/onecode/models/providers/__pycache__/ollama_provider.cpython-314.pyc +0 -0
  238. package/onecode/models/providers/__pycache__/openai_provider.cpython-314.pyc +0 -0
  239. package/onecode/models/providers/anthropic_provider.py +0 -273
  240. package/onecode/models/providers/deepseek_provider.py +0 -212
  241. package/onecode/models/providers/glm_provider.py +0 -195
  242. package/onecode/models/providers/minimax_provider.py +0 -158
  243. package/onecode/models/providers/minimaxi_provider.py +0 -417
  244. package/onecode/models/providers/ollama_provider.py +0 -100
  245. package/onecode/models/providers/openai_provider.py +0 -237
  246. package/onecode/models/registry.py +0 -212
  247. package/onecode/server/__init__.py +0 -3
  248. package/onecode/server/app.py +0 -224
  249. package/onecode/skills/__init__.py +0 -11
  250. package/onecode/skills/__pycache__/__init__.cpython-314.pyc +0 -0
  251. package/onecode/skills/__pycache__/argument_substitution.cpython-314.pyc +0 -0
  252. package/onecode/skills/__pycache__/bootstrap.cpython-314.pyc +0 -0
  253. package/onecode/skills/__pycache__/create.cpython-314.pyc +0 -0
  254. package/onecode/skills/__pycache__/frontmatter.cpython-314.pyc +0 -0
  255. package/onecode/skills/__pycache__/loader.cpython-314.pyc +0 -0
  256. package/onecode/skills/__pycache__/manager.cpython-314.pyc +0 -0
  257. package/onecode/skills/__pycache__/model.cpython-314.pyc +0 -0
  258. package/onecode/skills/argument_substitution.py +0 -38
  259. package/onecode/skills/bootstrap.py +0 -124
  260. package/onecode/skills/create.py +0 -56
  261. package/onecode/skills/frontmatter.py +0 -33
  262. package/onecode/skills/loader.py +0 -139
  263. package/onecode/skills/manager.py +0 -75
  264. package/onecode/skills/model.py +0 -43
  265. package/onecode/storage/__init__.py +0 -0
  266. package/onecode/storage/activity.py +0 -63
  267. package/onecode/storage/project.py +0 -54
  268. package/onecode/storage/session.py +0 -112
  269. package/onecode/tasks/__init__.py +0 -26
  270. package/onecode/tasks/manager.py +0 -232
  271. package/onecode/tasks/models.py +0 -240
  272. package/onecode/trace/__init__.py +0 -0
  273. package/onecode/trace/tracer.py +0 -173
  274. package/onecode/utils/__init__.py +0 -0
  275. package/onecode/utils/helpers.py +0 -20
  276. package/pyproject.toml +0 -74
  277. package/tui/__init__.py +0 -46
  278. package/tui/__main__.py +0 -4
  279. package/tui/__pycache__/__init__.cpython-314.pyc +0 -0
  280. package/tui/__pycache__/_loop.cpython-314.pyc +0 -0
  281. package/tui/__pycache__/_path_fuzzy_search.cpython-314.pyc +0 -0
  282. package/tui/__pycache__/_path_match.cpython-314.pyc +0 -0
  283. package/tui/__pycache__/about.cpython-314.pyc +0 -0
  284. package/tui/__pycache__/agent.cpython-314.pyc +0 -0
  285. package/tui/__pycache__/agent_schema.cpython-314.pyc +0 -0
  286. package/tui/__pycache__/agents.cpython-314.pyc +0 -0
  287. package/tui/__pycache__/answer.cpython-314.pyc +0 -0
  288. package/tui/__pycache__/app.cpython-313.pyc +0 -0
  289. package/tui/__pycache__/app.cpython-314.pyc +0 -0
  290. package/tui/__pycache__/atomic.cpython-314.pyc +0 -0
  291. package/tui/__pycache__/complete.cpython-314.pyc +0 -0
  292. package/tui/__pycache__/constants.cpython-314.pyc +0 -0
  293. package/tui/__pycache__/conversation_markdown.cpython-314.pyc +0 -0
  294. package/tui/__pycache__/danger.cpython-314.pyc +0 -0
  295. package/tui/__pycache__/db.cpython-314.pyc +0 -0
  296. package/tui/__pycache__/dec.cpython-314.pyc +0 -0
  297. package/tui/__pycache__/directory.cpython-314.pyc +0 -0
  298. package/tui/__pycache__/directory_suggester.cpython-314.pyc +0 -0
  299. package/tui/__pycache__/directory_watcher.cpython-314.pyc +0 -0
  300. package/tui/__pycache__/format_path.cpython-314.pyc +0 -0
  301. package/tui/__pycache__/fuzzy.cpython-314.pyc +0 -0
  302. package/tui/__pycache__/fuzzy_index.cpython-314.pyc +0 -0
  303. package/tui/__pycache__/history.cpython-314.pyc +0 -0
  304. package/tui/__pycache__/jsonrpc.cpython-314.pyc +0 -0
  305. package/tui/__pycache__/menus.cpython-314.pyc +0 -0
  306. package/tui/__pycache__/message_log.cpython-314.pyc +0 -0
  307. package/tui/__pycache__/messages.cpython-314.pyc +0 -0
  308. package/tui/__pycache__/path_complete.cpython-314.pyc +0 -0
  309. package/tui/__pycache__/path_filter.cpython-314.pyc +0 -0
  310. package/tui/__pycache__/paths.cpython-314.pyc +0 -0
  311. package/tui/__pycache__/pill.cpython-314.pyc +0 -0
  312. package/tui/__pycache__/platform_commands.cpython-314.pyc +0 -0
  313. package/tui/__pycache__/protocol.cpython-314.pyc +0 -0
  314. package/tui/__pycache__/session_tracker.cpython-314.pyc +0 -0
  315. package/tui/__pycache__/settings.cpython-314.pyc +0 -0
  316. package/tui/__pycache__/settings_schema.cpython-314.pyc +0 -0
  317. package/tui/__pycache__/shell.cpython-314.pyc +0 -0
  318. package/tui/__pycache__/shell_read.cpython-314.pyc +0 -0
  319. package/tui/__pycache__/slash_command.cpython-314.pyc +0 -0
  320. package/tui/__pycache__/version.cpython-314.pyc +0 -0
  321. package/tui/_loop.py +0 -86
  322. package/tui/_path_fuzzy_search.py +0 -48
  323. package/tui/_path_match.py +0 -141
  324. package/tui/about.py +0 -95
  325. package/tui/acp/__pycache__/agent.cpython-314.pyc +0 -0
  326. package/tui/acp/__pycache__/api.cpython-314.pyc +0 -0
  327. package/tui/acp/__pycache__/encode_tool_call_id.cpython-314.pyc +0 -0
  328. package/tui/acp/__pycache__/messages.cpython-314.pyc +0 -0
  329. package/tui/acp/__pycache__/prompt.cpython-314.pyc +0 -0
  330. package/tui/acp/__pycache__/protocol.cpython-314.pyc +0 -0
  331. package/tui/acp/agent.py +0 -1002
  332. package/tui/acp/api.py +0 -73
  333. package/tui/acp/encode_tool_call_id.py +0 -12
  334. package/tui/acp/messages.py +0 -203
  335. package/tui/acp/prompt.py +0 -53
  336. package/tui/acp/protocol.py +0 -499
  337. package/tui/agent.py +0 -70
  338. package/tui/agent_schema.py +0 -76
  339. package/tui/agents.py +0 -46
  340. package/tui/ansi/__init__.py +0 -1
  341. package/tui/ansi/__pycache__/__init__.cpython-314.pyc +0 -0
  342. package/tui/ansi/__pycache__/_ansi.cpython-314.pyc +0 -0
  343. package/tui/ansi/__pycache__/_ansi_colors.cpython-314.pyc +0 -0
  344. package/tui/ansi/__pycache__/_control_codes.cpython-314.pyc +0 -0
  345. package/tui/ansi/__pycache__/_keys.cpython-314.pyc +0 -0
  346. package/tui/ansi/__pycache__/_sgr_styles.cpython-314.pyc +0 -0
  347. package/tui/ansi/__pycache__/_stream_parser.cpython-314.pyc +0 -0
  348. package/tui/ansi/_ansi.py +0 -1689
  349. package/tui/ansi/_ansi_colors.py +0 -264
  350. package/tui/ansi/_control_codes.py +0 -37
  351. package/tui/ansi/_keys.py +0 -251
  352. package/tui/ansi/_sgr_styles.py +0 -64
  353. package/tui/ansi/_stream_parser.py +0 -418
  354. package/tui/answer.py +0 -12
  355. package/tui/app.py +0 -1266
  356. package/tui/atomic.py +0 -37
  357. package/tui/cli.py +0 -313
  358. package/tui/code_analyze.py +0 -27
  359. package/tui/complete.py +0 -38
  360. package/tui/constants.py +0 -61
  361. package/tui/conversation_markdown.py +0 -30
  362. package/tui/danger.py +0 -372
  363. package/tui/data/agents/ampcode.com.toml +0 -52
  364. package/tui/data/agents/augmentcode.com.toml +0 -41
  365. package/tui/data/agents/cdh.cloud-dev-harness.toml +0 -23
  366. package/tui/data/agents/claude.com.toml +0 -41
  367. package/tui/data/agents/copilot.github.com.toml +0 -29
  368. package/tui/data/agents/crowai.dev.toml +0 -36
  369. package/tui/data/agents/cursor.com.toml +0 -38
  370. package/tui/data/agents/deepagents.langchain.com +0 -34
  371. package/tui/data/agents/docker.com.toml +0 -60
  372. package/tui/data/agents/geminicli.com.toml +0 -28
  373. package/tui/data/agents/goose.ai.toml +0 -52
  374. package/tui/data/agents/inference.huggingface.co.toml +0 -41
  375. package/tui/data/agents/kimi.com.toml +0 -35
  376. package/tui/data/agents/kiro.dev.toml +0 -43
  377. package/tui/data/agents/onecode.dev.toml +0 -22
  378. package/tui/data/agents/openai.com.toml +0 -53
  379. package/tui/data/agents/openclaw.ai.toml +0 -37
  380. package/tui/data/agents/opencode.ai.toml +0 -39
  381. package/tui/data/agents/openhands.dev.toml +0 -46
  382. package/tui/data/agents/stakpak.dev.toml +0 -62
  383. package/tui/data/agents/vibe.mistral.ai.toml +0 -31
  384. package/tui/data/agents/vtcode.dev.toml +0 -63
  385. package/tui/data/images/frog.png +0 -0
  386. package/tui/data/sounds/question.wav +0 -0
  387. package/tui/data/sounds/turn-over.wav +0 -0
  388. package/tui/db.py +0 -213
  389. package/tui/dec.py +0 -332
  390. package/tui/directory.py +0 -234
  391. package/tui/directory_suggester.py +0 -93
  392. package/tui/directory_watcher.py +0 -231
  393. package/tui/format_path.py +0 -25
  394. package/tui/fuzzy.py +0 -140
  395. package/tui/fuzzy_index.py +0 -275
  396. package/tui/gist.py +0 -33
  397. package/tui/history.py +0 -138
  398. package/tui/jsonrpc.py +0 -578
  399. package/tui/menus.py +0 -14
  400. package/tui/message_log.py +0 -69
  401. package/tui/messages.py +0 -144
  402. package/tui/option_content.py +0 -51
  403. package/tui/os.py +0 -0
  404. package/tui/path_complete.py +0 -217
  405. package/tui/path_filter.py +0 -124
  406. package/tui/paths.py +0 -87
  407. package/tui/pill.py +0 -23
  408. package/tui/platform_commands.py +0 -52
  409. package/tui/prompt/__pycache__/extract.cpython-314.pyc +0 -0
  410. package/tui/prompt/__pycache__/resource.cpython-314.pyc +0 -0
  411. package/tui/prompt/extract.py +0 -19
  412. package/tui/prompt/resource.py +0 -68
  413. package/tui/protocol.py +0 -28
  414. package/tui/screens/__init__.py +0 -0
  415. package/tui/screens/__pycache__/__init__.cpython-314.pyc +0 -0
  416. package/tui/screens/__pycache__/agent_modal.cpython-314.pyc +0 -0
  417. package/tui/screens/__pycache__/component_picker.cpython-314.pyc +0 -0
  418. package/tui/screens/__pycache__/diff_screen.cpython-314.pyc +0 -0
  419. package/tui/screens/__pycache__/log.cpython-314.pyc +0 -0
  420. package/tui/screens/__pycache__/main.cpython-313.pyc +0 -0
  421. package/tui/screens/__pycache__/main.cpython-314.pyc +0 -0
  422. package/tui/screens/__pycache__/permissions.cpython-314.pyc +0 -0
  423. package/tui/screens/__pycache__/projects_app.cpython-314.pyc +0 -0
  424. package/tui/screens/__pycache__/projects_screen.cpython-314.pyc +0 -0
  425. package/tui/screens/__pycache__/sessions.cpython-314.pyc +0 -0
  426. package/tui/screens/__pycache__/store.cpython-314.pyc +0 -0
  427. package/tui/screens/__pycache__/tool_content_screen.cpython-314.pyc +0 -0
  428. package/tui/screens/action_modal.py +0 -94
  429. package/tui/screens/agent_modal.py +0 -175
  430. package/tui/screens/command_edit_modal.py +0 -74
  431. package/tui/screens/component_picker.py +0 -168
  432. package/tui/screens/diff_screen.py +0 -84
  433. package/tui/screens/log.py +0 -553
  434. package/tui/screens/main.py +0 -385
  435. package/tui/screens/main.tcss +0 -655
  436. package/tui/screens/permissions.py +0 -404
  437. package/tui/screens/permissions.tcss +0 -72
  438. package/tui/screens/projects.tcss +0 -80
  439. package/tui/screens/projects_app.py +0 -347
  440. package/tui/screens/projects_screen.py +0 -284
  441. package/tui/screens/session_resume_modal.py +0 -172
  442. package/tui/screens/session_resume_modal.tcss +0 -35
  443. package/tui/screens/sessions.py +0 -164
  444. package/tui/screens/sessions.tcss +0 -119
  445. package/tui/screens/settings.py +0 -254
  446. package/tui/screens/settings.tcss +0 -101
  447. package/tui/screens/store.py +0 -500
  448. package/tui/screens/store.tcss +0 -274
  449. package/tui/screens/tool_content_screen.py +0 -59
  450. package/tui/session_tracker.py +0 -123
  451. package/tui/settings.py +0 -353
  452. package/tui/settings_schema.py +0 -431
  453. package/tui/shell.py +0 -304
  454. package/tui/shell_read.py +0 -42
  455. package/tui/slash_command.py +0 -34
  456. package/tui/tui.tcss +0 -246
  457. package/tui/twitter.py +0 -38
  458. package/tui/version.py +0 -80
  459. package/tui/visuals/__init__.py +0 -0
  460. package/tui/visuals/__pycache__/__init__.cpython-314.pyc +0 -0
  461. package/tui/visuals/__pycache__/columns.cpython-314.pyc +0 -0
  462. package/tui/visuals/columns.py +0 -272
  463. package/tui/widgets/__init__.py +0 -0
  464. package/tui/widgets/__pycache__/__init__.cpython-314.pyc +0 -0
  465. package/tui/widgets/__pycache__/acp_content.cpython-314.pyc +0 -0
  466. package/tui/widgets/__pycache__/agent_response.cpython-314.pyc +0 -0
  467. package/tui/widgets/__pycache__/agent_thought.cpython-314.pyc +0 -0
  468. package/tui/widgets/__pycache__/ask_user.cpython-314.pyc +0 -0
  469. package/tui/widgets/__pycache__/condensed_path.cpython-314.pyc +0 -0
  470. package/tui/widgets/__pycache__/context_stats.cpython-314.pyc +0 -0
  471. package/tui/widgets/__pycache__/conversation.cpython-314.pyc +0 -0
  472. package/tui/widgets/__pycache__/diff_view.cpython-314.pyc +0 -0
  473. package/tui/widgets/__pycache__/directory_input.cpython-314.pyc +0 -0
  474. package/tui/widgets/__pycache__/flash.cpython-314.pyc +0 -0
  475. package/tui/widgets/__pycache__/future_text.cpython-314.pyc +0 -0
  476. package/tui/widgets/__pycache__/grid_select.cpython-314.pyc +0 -0
  477. package/tui/widgets/__pycache__/highlighted_textarea.cpython-314.pyc +0 -0
  478. package/tui/widgets/__pycache__/load_more.cpython-314.pyc +0 -0
  479. package/tui/widgets/__pycache__/mandelbrot.cpython-314.pyc +0 -0
  480. package/tui/widgets/__pycache__/markdown_note.cpython-314.pyc +0 -0
  481. package/tui/widgets/__pycache__/menu.cpython-314.pyc +0 -0
  482. package/tui/widgets/__pycache__/modified_files.cpython-314.pyc +0 -0
  483. package/tui/widgets/__pycache__/non_selectable_label.cpython-314.pyc +0 -0
  484. package/tui/widgets/__pycache__/note.cpython-314.pyc +0 -0
  485. package/tui/widgets/__pycache__/path_search.cpython-314.pyc +0 -0
  486. package/tui/widgets/__pycache__/plan.cpython-314.pyc +0 -0
  487. package/tui/widgets/__pycache__/project_directory_tree.cpython-314.pyc +0 -0
  488. package/tui/widgets/__pycache__/project_grid_select.cpython-314.pyc +0 -0
  489. package/tui/widgets/__pycache__/project_summary.cpython-314.pyc +0 -0
  490. package/tui/widgets/__pycache__/prompt.cpython-314.pyc +0 -0
  491. package/tui/widgets/__pycache__/question.cpython-314.pyc +0 -0
  492. package/tui/widgets/__pycache__/session_grid_select.cpython-314.pyc +0 -0
  493. package/tui/widgets/__pycache__/session_summary.cpython-314.pyc +0 -0
  494. package/tui/widgets/__pycache__/session_tabs.cpython-314.pyc +0 -0
  495. package/tui/widgets/__pycache__/shell_result.cpython-314.pyc +0 -0
  496. package/tui/widgets/__pycache__/shell_terminal.cpython-314.pyc +0 -0
  497. package/tui/widgets/__pycache__/side_bar.cpython-314.pyc +0 -0
  498. package/tui/widgets/__pycache__/slash_complete.cpython-314.pyc +0 -0
  499. package/tui/widgets/__pycache__/strike_text.cpython-314.pyc +0 -0
  500. package/tui/widgets/__pycache__/subagent.cpython-314.pyc +0 -0
  501. package/tui/widgets/__pycache__/subagent_screen.cpython-314.pyc +0 -0
  502. package/tui/widgets/__pycache__/terminal.cpython-314.pyc +0 -0
  503. package/tui/widgets/__pycache__/throbber.cpython-314.pyc +0 -0
  504. package/tui/widgets/__pycache__/tool_call.cpython-314.pyc +0 -0
  505. package/tui/widgets/__pycache__/user_input.cpython-314.pyc +0 -0
  506. package/tui/widgets/acp_content.py +0 -70
  507. package/tui/widgets/agent_response.py +0 -76
  508. package/tui/widgets/agent_thought.py +0 -167
  509. package/tui/widgets/ask_user.py +0 -264
  510. package/tui/widgets/command_pane.py +0 -223
  511. package/tui/widgets/condensed_path.py +0 -115
  512. package/tui/widgets/context_stats.py +0 -66
  513. package/tui/widgets/conversation.py +0 -2641
  514. package/tui/widgets/danger_warning.py +0 -65
  515. package/tui/widgets/diff_view.py +0 -69
  516. package/tui/widgets/directory_input.py +0 -8
  517. package/tui/widgets/flash.py +0 -81
  518. package/tui/widgets/future_text.py +0 -126
  519. package/tui/widgets/grid_select.py +0 -234
  520. package/tui/widgets/highlighted_textarea.py +0 -180
  521. package/tui/widgets/load_more.py +0 -24
  522. package/tui/widgets/mandelbrot.py +0 -294
  523. package/tui/widgets/markdown_note.py +0 -13
  524. package/tui/widgets/menu.py +0 -147
  525. package/tui/widgets/modified_files.py +0 -306
  526. package/tui/widgets/non_selectable_label.py +0 -5
  527. package/tui/widgets/note.py +0 -18
  528. package/tui/widgets/path_search.py +0 -492
  529. package/tui/widgets/plan.py +0 -285
  530. package/tui/widgets/project_directory_tree.py +0 -102
  531. package/tui/widgets/project_grid_select.py +0 -64
  532. package/tui/widgets/project_summary.py +0 -33
  533. package/tui/widgets/prompt.py +0 -795
  534. package/tui/widgets/question.py +0 -360
  535. package/tui/widgets/session_grid_select.py +0 -230
  536. package/tui/widgets/session_summary.py +0 -115
  537. package/tui/widgets/session_tabs.py +0 -188
  538. package/tui/widgets/shell_result.py +0 -35
  539. package/tui/widgets/shell_terminal.py +0 -40
  540. package/tui/widgets/side_bar.py +0 -124
  541. package/tui/widgets/slash_complete.py +0 -235
  542. package/tui/widgets/strike_text.py +0 -70
  543. package/tui/widgets/subagent.py +0 -287
  544. package/tui/widgets/subagent_screen.py +0 -709
  545. package/tui/widgets/terminal.py +0 -576
  546. package/tui/widgets/terminal_tool.py +0 -360
  547. package/tui/widgets/throbber.py +0 -100
  548. package/tui/widgets/tool_call.py +0 -398
  549. package/tui/widgets/user_input.py +0 -23
  550. package/tui/widgets/version.py +0 -5
  551. package/tui/widgets/welcome.py +0 -31
@@ -1,188 +0,0 @@
1
- import asyncio
2
- from functools import partial
3
- from rich.style import Style as RichStyle
4
-
5
- from textual import work
6
- from textual.app import ComposeResult, RenderResult
7
-
8
- from textual import events
9
- from textual.content import Content
10
- from textual.geometry import Offset
11
- from textual.reactive import reactive
12
- from textual.renderables.bar import Bar
13
- from textual.widget import Widget
14
- from textual import containers
15
- from textual import widgets
16
- from textual import getters
17
- from textual.message import Message
18
-
19
- from tui.app import A2TUIApp
20
- from tui.session_tracker import SessionDetails
21
- from tui import messages
22
-
23
-
24
- class SessionLabel(widgets.Label):
25
- ALLOW_SELECT = False
26
-
27
- def on_click(self) -> None:
28
- if self.id is not None:
29
- self.post_message(messages.SessionSwitch(self.id))
30
-
31
-
32
- class Underline(Widget):
33
- """The animated underline beneath tabs."""
34
-
35
- COMPONENT_CLASSES = {"underline--bar"}
36
- """
37
- | Class | Description |
38
- | :- | :- |
39
- | `underline--bar` | Style of the bar (may be used to change the color). |
40
- """
41
-
42
- highlight_start = reactive(0)
43
- """First cell in highlight."""
44
- highlight_end = reactive(0)
45
- """Last cell (inclusive) in highlight."""
46
- show_highlight: reactive[bool] = reactive(True)
47
- """Flag to indicate if a highlight should be shown at all."""
48
-
49
- class Clicked(Message):
50
- """Inform ancestors the underline was clicked."""
51
-
52
- offset: Offset
53
- """The offset of the click, relative to the origin of the bar."""
54
-
55
- def __init__(self, offset: Offset) -> None:
56
- self.offset = offset
57
- super().__init__()
58
-
59
- @property
60
- def _highlight_range(self) -> tuple[int, int]:
61
- """Highlighted range for underline bar."""
62
- return (
63
- (self.highlight_start, self.highlight_end)
64
- if self.show_highlight
65
- else (0, 0)
66
- )
67
-
68
- def render(self) -> RenderResult:
69
- """Render the bar."""
70
- bar_style = self.get_component_rich_style("underline--bar")
71
- return Bar(
72
- highlight_range=self._highlight_range,
73
- highlight_style=RichStyle.from_color(bar_style.color),
74
- background_style=RichStyle.from_color(bar_style.bgcolor),
75
- )
76
-
77
- def _on_click(self, event: events.Click):
78
- """Catch clicks, so that the underline can activate the tabs."""
79
- event.stop()
80
- self.post_message(self.Clicked(event.screen_offset))
81
-
82
-
83
- class SessionsTabs(Widget):
84
-
85
- ALLOW_SELECT = False
86
- app: getters.app[A2TUIApp] = getters.app(A2TUIApp)
87
-
88
- title_container = getters.query_one("#title-container", Widget)
89
-
90
- current_session = reactive("", init=False)
91
-
92
- def on_mount(self) -> None:
93
- self.current_session = self.app.current_mode
94
- self.app.mode_change_signal.subscribe(self, self.handle_mode_change)
95
- self.app.session_update_signal.subscribe(
96
- self, self.handle_session_update_signal, immediate=True
97
- )
98
- self.update_underline(self.current_session, animate=False)
99
- self.call_after_refresh(self.update_underline, self.current_session)
100
-
101
- def handle_mode_change(self, mode: str) -> None:
102
- self.current_session = mode
103
-
104
- def watch_current_session(self, old_session: str, new_session: str) -> None:
105
- self.query(".-current").remove_class("-current")
106
- self.query(f"#{new_session}").add_class("-current")
107
- if old_session:
108
- self.update_underline(old_session, animate=False)
109
-
110
- self.update_underline(new_session, animate=True)
111
-
112
- def update_underline(self, session: str | None = None, animate: bool = True):
113
- if not self.is_mounted or not self.is_attached:
114
- return
115
- if session is None:
116
- session = self.current_session
117
- if not session:
118
- return
119
- if current_label := self.query_one_optional(f"#{session}", SessionLabel):
120
- tab_region = current_label.virtual_region.shrink((0, 1, 0, 1))
121
- if not tab_region:
122
- return
123
- start, end = tab_region.column_span
124
- underline = self.query_one(Underline)
125
- if animate:
126
- underline.animate("highlight_start", start, duration=0.3)
127
- underline.animate(
128
- "highlight_end",
129
- end,
130
- duration=0.3,
131
- on_complete=partial(self.scroll_to_center, current_label),
132
- )
133
- else:
134
- underline.highlight_start = start
135
- underline.highlight_end = end
136
- self.scroll_to_center(current_label, animate=False)
137
-
138
- def render_session_label(self, session: SessionDetails) -> Content:
139
- match session.state:
140
- case "asking":
141
- return Content.assemble(
142
- ("❯ ", "not dim $text-secondary"), session.title
143
- )
144
- case "busy":
145
- return Content(f"⌛ {session.title}")
146
- return Content(session.title)
147
-
148
- def compose(self) -> ComposeResult:
149
- with containers.HorizontalGroup(id="title-container"):
150
- for session in self.app.session_tracker.ordered_sessions:
151
- yield SessionLabel(
152
- self.render_session_label(session),
153
- id=session.mode_name,
154
- classes="-current" if session.mode_name == self.screen.id else "",
155
- )
156
- yield Underline()
157
-
158
- @work(exit_on_error=False)
159
- async def handle_session_update_signal(
160
- self, update: tuple[str, SessionDetails | None]
161
- ) -> None:
162
- mode, details = update
163
- if details is None:
164
- removed_mode = mode
165
- await self.query(f"#{mode}").remove()
166
- if self.current_session == removed_mode:
167
- remaining = list(self.query(SessionLabel))
168
- if remaining:
169
- new_current = remaining[0].id or ""
170
- else:
171
- new_current = ""
172
- self.current_session = new_current
173
- else:
174
- if tab_label := self.query_one_optional(f"#{mode}", SessionLabel):
175
- tab_label.update(self.render_session_label(details))
176
- else:
177
- self.query(SessionLabel).remove_class("-current")
178
- await self.title_container.mount(
179
- SessionLabel(
180
- self.render_session_label(details),
181
- id=details.mode_name,
182
- classes=(
183
- "-current" if details.mode_name == self.screen.id else ""
184
- ),
185
- )
186
- )
187
- await asyncio.sleep(0.05)
188
- self.call_after_refresh(self.update_underline, self.current_session)
@@ -1,35 +0,0 @@
1
- from __future__ import annotations
2
- from typing import Iterable
3
-
4
- from textual.app import ComposeResult
5
- from textual import containers
6
- from textual.highlight import highlight
7
- from textual.widgets import Static
8
-
9
-
10
- from tui.menus import MenuItem
11
- from tui.widgets.non_selectable_label import NonSelectableLabel
12
-
13
-
14
- class ShellResult(containers.HorizontalGroup):
15
- def __init__(
16
- self,
17
- command: str,
18
- *,
19
- name: str | None = None,
20
- id: str | None = None,
21
- classes: str | None = None,
22
- disabled: bool = False,
23
- ) -> None:
24
- self._command = command
25
- super().__init__(name=name, id=id, classes=classes, disabled=disabled)
26
-
27
- def compose(self) -> ComposeResult:
28
- yield NonSelectableLabel("$", id="prompt", markup=False)
29
- yield Static(highlight(self._command, language="sh"))
30
-
31
- def get_block_menu(self) -> Iterable[MenuItem]:
32
- yield from ()
33
-
34
- def get_block_content(self, destination: str) -> str | None:
35
- return self._command
@@ -1,40 +0,0 @@
1
- from dataclasses import dataclass
2
- from typing import Iterable
3
-
4
- from textual.content import Content
5
- from textual.dom import DOMNode
6
- from textual.message import Message
7
-
8
- from tui.menus import MenuItem
9
- from tui.widgets.terminal import Terminal
10
-
11
-
12
- class ShellTerminal(Terminal):
13
- """Subclass of Terminal used in the Shell view."""
14
-
15
- @dataclass
16
- class Terminate(Message):
17
- teminal: ShellTerminal
18
-
19
- @property
20
- def control(self) -> DOMNode:
21
- return self.terminal
22
-
23
- @dataclass
24
- class Interrupt(Message):
25
- teminal: ShellTerminal
26
-
27
- @property
28
- def control(self) -> DOMNode:
29
- return self.terminal
30
-
31
- def get_block_menu(self) -> Iterable[MenuItem]:
32
- if not self.is_finalized:
33
- yield MenuItem("Interrupt", "interrupt", "i")
34
- yield MenuItem("Focus", f"focus_block({self.id!r})", "f")
35
-
36
- def get_block_content(self, destination: str) -> str | None:
37
- return "\n".join(line.content.plain for line in self.state.buffer.lines)
38
-
39
- def on_mount(self) -> None:
40
- self.border_title = Content(self.name)
@@ -1,124 +0,0 @@
1
- from dataclasses import dataclass
2
-
3
- from textual.app import ComposeResult
4
- from textual.binding import Binding
5
- from textual.widget import Widget
6
- from textual import containers
7
- from textual import widgets
8
- from textual.message import Message
9
-
10
-
11
- class SideBarCollapsible(widgets.Collapsible):
12
- BINDING_GROUP_TITLE = "Sidebar collapsible"
13
- BINDINGS = [
14
- Binding("down", "focus_content", "Focus content", show=False),
15
- ]
16
- HELP = """\
17
- ## Sidebar
18
-
19
- This is your sidebar.
20
-
21
- The Sidebar contains additonal information associated with the conversation.
22
-
23
- - **tab / shift+tab** Navigate sections
24
- - **enter** expand or collapse secions
25
- """
26
-
27
- def action_focus_content(self) -> None:
28
- """Move focus into the content area when expanded."""
29
- if self.collapsed:
30
- return
31
- self.screen.focus_next()
32
-
33
-
34
- class SideBar(containers.Vertical):
35
- BINDING_GROUP_TITLE = "Sidebar"
36
- BINDINGS = [("escape", "dismiss", "Dismiss sidebar")]
37
-
38
- class Dismiss(Message):
39
- pass
40
-
41
- @dataclass(frozen=True)
42
- class Panel:
43
- title: str
44
- widget: Widget
45
- flex: bool = False
46
- collapsed: bool = False
47
- id: str | None = None
48
-
49
- def __init__(
50
- self,
51
- *panels: Panel,
52
- name: str | None = None,
53
- id: str | None = None,
54
- classes: str | None = None,
55
- disabled: bool = False,
56
- hide: bool = False,
57
- ) -> None:
58
- super().__init__(name=name, id=id, classes=classes, disabled=disabled)
59
- self.panels: list[SideBar.Panel] = [*panels]
60
- self.hide = hide
61
-
62
- def on_mount(self) -> None:
63
- self.trap_focus()
64
-
65
- def compose(self) -> ComposeResult:
66
- for panel in self.panels:
67
- yield SideBarCollapsible(
68
- panel.widget,
69
- title=panel.title,
70
- collapsed=panel.collapsed,
71
- classes="-flex" if panel.flex else "-fixed",
72
- id=panel.id,
73
- )
74
-
75
- def action_dismiss(self) -> None:
76
- self.post_message(self.Dismiss())
77
-
78
- def has_panel(self, panel_id: str) -> bool:
79
- return self.query_one_optional(f"#{panel_id}") is not None
80
-
81
- async def add_panel(self, panel: Panel) -> SideBarCollapsible:
82
- collapsible = SideBarCollapsible(
83
- panel.widget,
84
- title=panel.title,
85
- collapsed=panel.collapsed,
86
- classes="-flex" if panel.flex else "-fixed",
87
- id=panel.id,
88
- )
89
- await self.mount(collapsible)
90
- self.panels.append(panel)
91
- return collapsible
92
-
93
- def remove_panel(self, panel_id: str) -> bool:
94
- for i, p in enumerate(self.panels):
95
- if p.id == panel_id:
96
- widget = self.query_one_optional(f"#{panel_id}")
97
- if widget is not None:
98
- widget.remove()
99
- self.panels.pop(i)
100
- return True
101
- return False
102
-
103
-
104
- if __name__ == "__main__":
105
- from textual.app import App, ComposeResult
106
-
107
- class SApp(App):
108
- def compose(self) -> ComposeResult:
109
- yield SideBar(
110
- SideBar.Panel("Hello", widgets.Label("Hello, World!")),
111
- SideBar.Panel(
112
- "Files",
113
- widgets.DirectoryTree(
114
- "~/",
115
- ),
116
- flex=True,
117
- ),
118
- SideBar.Panel(
119
- "Hello",
120
- widgets.Static("Where there is a Will! " * 10),
121
- ),
122
- )
123
-
124
- SApp().run()
@@ -1,235 +0,0 @@
1
- from dataclasses import dataclass
2
- from operator import itemgetter
3
- from typing import Iterable, Self, Sequence
4
-
5
- from textual import on
6
- from textual.app import ComposeResult
7
- from textual.binding import Binding
8
- from textual.content import Content, Span
9
-
10
- from textual import getters
11
- from textual.message import Message
12
- from textual.reactive import var
13
- from textual import containers
14
- from textual import widgets
15
- from textual.widgets.option_list import Option
16
-
17
- from tui.fuzzy import FuzzySearch
18
- from tui.messages import Dismiss
19
- from tui.slash_command import SlashCommand
20
- from tui.visuals.columns import Columns
21
-
22
-
23
- class SlashCompleteInput(widgets.Input):
24
- BINDING_GROUP_TITLE = "Fuzzy search slash commands"
25
- HELP = """\
26
- ## Slash command fuzzy search
27
-
28
- Search for slash commands by typing a few characters from the command.
29
-
30
- - **cursor keys** Navigate list
31
- - **enter** Add command to prompt
32
- - **escape** Dismiss fuzzy search
33
- """
34
-
35
-
36
- class SlashComplete(containers.VerticalGroup):
37
- """A widget to auto-complete slash commands."""
38
-
39
- CURSOR_BINDING_GROUP = Binding.Group(description="Select")
40
- BINDINGS = [
41
- Binding(
42
- "up",
43
- "cursor_up",
44
- "Cursor up",
45
- group=CURSOR_BINDING_GROUP,
46
- priority=True,
47
- ),
48
- Binding(
49
- "down",
50
- "cursor_down",
51
- "Cursor down",
52
- group=CURSOR_BINDING_GROUP,
53
- priority=True,
54
- ),
55
- Binding("enter", "submit", "Insert /command", priority=True),
56
- Binding("escape", "dismiss", "Dismiss", priority=True),
57
- ]
58
-
59
- DEFAULT_CSS = """
60
- SlashComplete {
61
- OptionList {
62
- height: auto;
63
- }
64
- }
65
- """
66
-
67
- input = getters.query_one(widgets.Input)
68
- option_list = getters.query_one(widgets.OptionList)
69
-
70
- slash_commands: var[list[SlashCommand]] = var(list)
71
-
72
- @dataclass
73
- class Completed(Message):
74
- command: str
75
-
76
- def __init__(
77
- self,
78
- slash_commands: Iterable[SlashCommand] | None = None,
79
- id: str | None = None,
80
- classes: str | None = None,
81
- ) -> None:
82
- super().__init__(id=id, classes=classes)
83
- self.slash_commands = list(slash_commands) if slash_commands else []
84
- self.hints = {
85
- slash_command.command: slash_command.hint
86
- for slash_command in self.slash_commands
87
- if slash_command.hint
88
- }
89
-
90
- self.fuzzy_search = FuzzySearch(case_sensitive=False)
91
-
92
- def compose(self) -> ComposeResult:
93
- yield SlashCompleteInput(compact=True, placeholder="fuzzy search")
94
- yield widgets.OptionList()
95
-
96
- def focus(self, scroll_visible: bool = False) -> Self:
97
- self.filter_slash_commands("")
98
- self.input.focus(scroll_visible)
99
- return self
100
-
101
- def on_mount(self) -> None:
102
- self.filter_slash_commands("")
103
-
104
- def on_descendant_blur(self) -> None:
105
- self.post_message(Dismiss(self))
106
-
107
- @on(widgets.Input.Changed)
108
- def on_input_changed(self, event: widgets.Input.Changed) -> None:
109
- event.stop()
110
- self.filter_slash_commands(event.value)
111
-
112
- async def watch_slash_commands(self, slash_commands: list[SlashCommand]) -> None:
113
- self.hints = {
114
- slash_command.command: slash_command.hint
115
- for slash_command in slash_commands
116
- if slash_command.hint
117
- }
118
- self.filter_slash_commands(self.input.value)
119
-
120
- def filter_slash_commands(self, prompt: str) -> None:
121
- """Filter slash commands by the given prompt.
122
-
123
- Args:
124
- prompt: Text prompt.
125
- """
126
- prompt = prompt.lstrip("/").casefold().rstrip()
127
- columns = self.columns = Columns("auto", "flex")
128
-
129
- slash_commands = sorted(
130
- self.slash_commands,
131
- key=lambda slash_command: slash_command.command.casefold(),
132
- )
133
- deduplicated_slash_commands = {
134
- slash_command.command: slash_command for slash_command in slash_commands
135
- }
136
- self.fuzzy_search.cache.grow(len(deduplicated_slash_commands))
137
-
138
- if prompt:
139
- slash_prompt = f"/{prompt}"
140
- scores: list[tuple[float, Sequence[int], SlashCommand]] = [
141
- (
142
- *self.fuzzy_search.match(prompt, slash_command.command[1:]),
143
- slash_command,
144
- )
145
- for slash_command in slash_commands
146
- ]
147
-
148
- scores = sorted(
149
- [
150
- (
151
- (
152
- score * 2
153
- if slash_command.command.casefold().startswith(slash_prompt)
154
- else score
155
- ),
156
- highlights,
157
- slash_command,
158
- )
159
- for score, highlights, slash_command in scores
160
- if score
161
- ],
162
- key=itemgetter(0),
163
- reverse=True,
164
- )
165
- else:
166
- scores = [(1.0, [], slash_command) for slash_command in slash_commands]
167
-
168
- def make_row(
169
- slash_command: SlashCommand, indices: Iterable[int]
170
- ) -> tuple[Content, ...]:
171
- """Make a row for the Columns display.
172
-
173
- Args:
174
- slash_command: The slash command instance.
175
- indices: Indices of matching characters.
176
-
177
- Returns:
178
- A tuple of `Content` instances for use as a column row.
179
- """
180
- command = Content.styled(slash_command.command, "$text-success")
181
- command = command.add_spans(
182
- [Span(index + 1, index + 2, "underline not dim") for index in indices]
183
- )
184
- return (command, Content.styled(slash_command.help, "dim"))
185
-
186
- rows = [
187
- (
188
- columns.add_row(
189
- *make_row(slash_command, indices),
190
- ),
191
- slash_command.command,
192
- )
193
- for _, indices, slash_command in scores
194
- ]
195
- self.option_list.set_options(
196
- Option(row, id=command_name) for row, command_name in rows
197
- )
198
- if self.display:
199
- self.option_list.highlighted = 0
200
- else:
201
- with self.option_list.prevent(widgets.OptionList.OptionHighlighted):
202
- self.option_list.highlighted = 0
203
-
204
- def action_cursor_down(self) -> None:
205
- self.option_list.action_cursor_down()
206
-
207
- def action_cursor_up(self) -> None:
208
- self.option_list.action_cursor_up()
209
-
210
- def action_dismiss(self) -> None:
211
- self.post_message(Dismiss(self))
212
-
213
- def action_submit(self) -> None:
214
- option_list = self.option_list
215
- if (option := option_list.highlighted_option) is not None:
216
- with self.input.prevent(widgets.Input.Changed):
217
- self.input.clear()
218
- self.post_message(self.Completed(option.id or ""))
219
-
220
-
221
- if __name__ == "__main__":
222
- from textual.app import App, ComposeResult
223
-
224
- COMMANDS = [
225
- SlashCommand("/help", "Help with slash commands"),
226
- SlashCommand("/foo", "This is FOO"),
227
- SlashCommand("/bar", "This is BAR"),
228
- SlashCommand("/baz", "This is BAZ"),
229
- ]
230
-
231
- class SlashApp(App):
232
- def compose(self) -> ComposeResult:
233
- yield SlashComplete(COMMANDS)
234
-
235
- SlashApp().run()
@@ -1,70 +0,0 @@
1
- from time import monotonic
2
-
3
- from textual.widget import Widget
4
-
5
- from textual.content import Content
6
- from textual.reactive import reactive
7
-
8
-
9
- class StrikeText(Widget):
10
- DEFAULT_CSS = """
11
- StrikeText {
12
- height: auto;
13
- &.-complete {
14
- text-style: strike;
15
- color: $text-primary;
16
- }
17
- }
18
- """
19
-
20
- strike_time: reactive[float | None] = reactive(None)
21
-
22
- def __init__(
23
- self,
24
- content: Content,
25
- name: str | None = None,
26
- id: str | None = None,
27
- classes: str | None = None,
28
- ):
29
- self.content = content
30
- super().__init__(name=name, id=id, classes=classes)
31
-
32
- def strike(self) -> None:
33
- self.strike_time = monotonic()
34
- self.auto_refresh = 1 / 30
35
-
36
- def render(self) -> Content:
37
- content = self.content
38
- if self.strike_time is not None:
39
- position = int((monotonic() - self.strike_time) * 70)
40
- content = content.stylize("strike $text-primary", 0, position)
41
- if position > len(content):
42
- self.auto_refresh = None
43
- return content
44
-
45
-
46
- if __name__ == "__main__":
47
- from textual.app import App, ComposeResult
48
- from textual.widgets import Static
49
-
50
- class StrikeApp(App):
51
- CSS = """
52
- Screen {
53
- overflow: auto;
54
- }
55
-
56
- """
57
- BINDINGS = [("space", "strike", "Strike")]
58
-
59
- def compose(self) -> ComposeResult:
60
- for n in range(20):
61
- yield Static("HELLO")
62
- yield StrikeText(Content("Where there is a Will, there is a way"))
63
- for n in range(200):
64
- yield Static("World")
65
-
66
- def action_strike(self):
67
- self.query_one(StrikeText).strike()
68
-
69
- app = StrikeApp()
70
- app.run()