claude-smart 0.2.44 → 0.2.46

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 (323) hide show
  1. package/.claude-plugin/marketplace.json +3 -3
  2. package/README.md +34 -5
  3. package/bin/claude-smart.js +295 -5
  4. package/package.json +22 -3
  5. package/plugin/.claude-plugin/plugin.json +4 -2
  6. package/plugin/.codex-plugin/plugin.json +1 -1
  7. package/plugin/README.md +22 -2
  8. package/plugin/commands/clear-all.md +1 -0
  9. package/plugin/commands/dashboard.md +1 -0
  10. package/plugin/commands/learn.md +1 -0
  11. package/plugin/commands/restart.md +1 -0
  12. package/plugin/commands/show.md +1 -0
  13. package/plugin/dashboard/app/configure/env/page.tsx +40 -14
  14. package/plugin/dashboard/app/configure/server/page.tsx +51 -1
  15. package/plugin/dashboard/app/preferences/[id]/page.tsx +8 -8
  16. package/plugin/dashboard/app/skills/project/[id]/page.tsx +7 -3
  17. package/plugin/dashboard/app/skills/shared/[id]/page.tsx +10 -3
  18. package/plugin/dashboard/lib/claude-settings-file.ts +20 -10
  19. package/plugin/dashboard/lib/reflexio-client.ts +16 -0
  20. package/plugin/dashboard/lib/status.ts +10 -3
  21. package/plugin/dashboard/lib/types.ts +18 -6
  22. package/plugin/hooks/codex-hooks.json +0 -1
  23. package/plugin/opencode/assistant-buffer.ts +108 -0
  24. package/plugin/opencode/dist/assistant-buffer.js +96 -0
  25. package/plugin/opencode/dist/internal.js +12 -0
  26. package/plugin/opencode/dist/payload.js +85 -0
  27. package/plugin/opencode/dist/server.mjs +158 -0
  28. package/plugin/opencode/internal.ts +18 -0
  29. package/plugin/opencode/package.json +3 -0
  30. package/plugin/opencode/payload.ts +90 -0
  31. package/plugin/opencode/server.mts +174 -0
  32. package/plugin/opencode/tsconfig.json +13 -0
  33. package/plugin/pyproject.toml +20 -3
  34. package/plugin/scripts/_lib.sh +77 -29
  35. package/plugin/scripts/backend-service.sh +27 -5
  36. package/plugin/scripts/dashboard-service.sh +7 -5
  37. package/plugin/scripts/ensure-plugin-root.sh +4 -4
  38. package/plugin/scripts/hook_entry.sh +3 -3
  39. package/plugin/scripts/opencode-claude-compat +4 -0
  40. package/plugin/scripts/opencode-claude-compat.cmd +3 -0
  41. package/plugin/scripts/opencode-claude-compat.js +225 -0
  42. package/plugin/scripts/smart-install.sh +10 -8
  43. package/plugin/src/README.md +1 -1
  44. package/plugin/src/claude_smart/cli.py +304 -6
  45. package/plugin/src/claude_smart/env_config.py +12 -4
  46. package/plugin/src/claude_smart/events/session_start.py +26 -7
  47. package/plugin/src/claude_smart/events/stop.py +1 -1
  48. package/plugin/src/claude_smart/ids.py +1 -1
  49. package/plugin/src/claude_smart/reflexio_adapter.py +5 -5
  50. package/plugin/src/claude_smart/runtime.py +7 -1
  51. package/plugin/uv.lock +1 -1
  52. package/plugin/vendor/reflexio/.env.example +54 -30
  53. package/plugin/vendor/reflexio/README.md +14 -8
  54. package/plugin/vendor/reflexio/pyproject.toml +13 -1
  55. package/plugin/vendor/reflexio/reflexio/README.md +1 -0
  56. package/plugin/vendor/reflexio/reflexio/cli/README.md +9 -7
  57. package/plugin/vendor/reflexio/reflexio/cli/__main__.py +10 -1
  58. package/plugin/vendor/reflexio/reflexio/cli/bootstrap_config.py +22 -5
  59. package/plugin/vendor/reflexio/reflexio/cli/commands/interactions.py +34 -4
  60. package/plugin/vendor/reflexio/reflexio/cli/commands/profiles.py +12 -7
  61. package/plugin/vendor/reflexio/reflexio/cli/commands/services.py +13 -6
  62. package/plugin/vendor/reflexio/reflexio/cli/commands/setup_cmd.py +210 -50
  63. package/plugin/vendor/reflexio/reflexio/cli/commands/shortcuts.py +15 -2
  64. package/plugin/vendor/reflexio/reflexio/cli/env_loader.py +292 -22
  65. package/plugin/vendor/reflexio/reflexio/cli/log_format.py +29 -4
  66. package/plugin/vendor/reflexio/reflexio/cli/run_services.py +17 -8
  67. package/plugin/vendor/reflexio/reflexio/cli/stop_services.py +13 -10
  68. package/plugin/vendor/reflexio/reflexio/client/client.py +57 -13
  69. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/README.md +135 -257
  70. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/npm/openclaw-smart/bin/openclaw-smart.js +13 -0
  71. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/npm/openclaw-smart/package.json +15 -0
  72. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/README.md +38 -0
  73. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/index.ts +151 -110
  74. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/openclaw.plugin.json +20 -10
  75. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/package.json +28 -6
  76. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/pyproject.toml +42 -0
  77. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/_lib.sh +371 -0
  78. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/backend-log-runner.sh +33 -0
  79. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/backend-service.sh +271 -0
  80. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/cli.sh +68 -0
  81. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/dashboard-open.sh +15 -0
  82. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/ensure-plugin-root.sh +84 -0
  83. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/hook_entry.sh +106 -0
  84. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/npm-cli.js +219 -0
  85. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/scripts/smart-install.sh +269 -0
  86. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/skills/clear-all/SKILL.md +8 -0
  87. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/skills/dashboard/SKILL.md +8 -0
  88. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/skills/learn/SKILL.md +10 -0
  89. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/skills/reflexio/SKILL.md +15 -44
  90. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/skills/restart/SKILL.md +6 -0
  91. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/skills/show/SKILL.md +8 -0
  92. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/cli.py +634 -0
  93. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/context_format.py +224 -0
  94. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/context_inject.py +79 -0
  95. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/__init__.py +0 -0
  96. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/after_tool_call.py +160 -0
  97. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/agent_end.py +187 -0
  98. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/before_prompt_build.py +69 -0
  99. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/before_tool_call.py +30 -0
  100. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/session_end.py +36 -0
  101. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/events/session_start.py +130 -0
  102. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/hook.py +131 -0
  103. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/ids.py +94 -0
  104. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/internal_call.py +75 -0
  105. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/oc_cite.py +196 -0
  106. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/optimizer_assistant.py +272 -0
  107. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/publish.py +96 -0
  108. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/query_compose.py +66 -0
  109. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/reflexio_adapter.py +336 -0
  110. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/runtime.py +47 -0
  111. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/stall_banner.py +61 -0
  112. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/src/openclaw_smart/state.py +323 -0
  113. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/__init__.py +0 -0
  114. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/integration/__init__.py +0 -0
  115. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/integration/test_e2e_session_loop.py +190 -0
  116. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/integration/test_publish_to_local_reflexio_integration.py +112 -0
  117. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/integration/test_recursion_guard_integration.py +86 -0
  118. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/integration/test_search_inject_integration.py +144 -0
  119. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_cli.py +184 -0
  120. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_events_after_tool_call.py +142 -0
  121. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_events_agent_end.py +233 -0
  122. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_events_before_prompt_build.py +116 -0
  123. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_events_before_tool_call.py +35 -0
  124. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_events_session_end.py +47 -0
  125. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_events_session_start.py +109 -0
  126. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_hook_dispatch.py +117 -0
  127. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_ids.py +41 -0
  128. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_internal_call.py +50 -0
  129. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_oc_cite.py +88 -0
  130. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_publish.py +48 -0
  131. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_query_compose.py +48 -0
  132. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_reflexio_adapter.py +188 -0
  133. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_runtime.py +41 -0
  134. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests/test_state.py +235 -0
  135. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests-ts/__mocks__/plugin-entry-stub.ts +6 -0
  136. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests-ts/test_npm_cli.test.ts +56 -0
  137. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tests-ts/test_shim_dispatch.test.ts +171 -0
  138. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/tsconfig.build.json +18 -0
  139. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/{tsconfig.json → plugin/tsconfig.json} +2 -2
  140. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/uv.lock +3835 -0
  141. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/vitest.config.ts +18 -0
  142. package/plugin/vendor/reflexio/reflexio/lib/_agent_playbook.py +238 -10
  143. package/plugin/vendor/reflexio/reflexio/lib/_config.py +11 -4
  144. package/plugin/vendor/reflexio/reflexio/lib/_generation.py +16 -5
  145. package/plugin/vendor/reflexio/reflexio/lib/_lineage_parity_readers.py +187 -0
  146. package/plugin/vendor/reflexio/reflexio/lib/_profiles.py +198 -6
  147. package/plugin/vendor/reflexio/reflexio/lib/_reflection.py +1 -1
  148. package/plugin/vendor/reflexio/reflexio/lib/_search.py +29 -20
  149. package/plugin/vendor/reflexio/reflexio/lib/_user_playbook.py +2 -1
  150. package/plugin/vendor/reflexio/reflexio/models/api_schema/domain/entities.py +127 -38
  151. package/plugin/vendor/reflexio/reflexio/models/api_schema/domain/enums.py +4 -0
  152. package/plugin/vendor/reflexio/reflexio/models/api_schema/eval_overview_schema.py +64 -41
  153. package/plugin/vendor/reflexio/reflexio/models/api_schema/internal_schema.py +19 -0
  154. package/plugin/vendor/reflexio/reflexio/models/api_schema/pending_tool_call_schema.py +12 -5
  155. package/plugin/vendor/reflexio/reflexio/models/api_schema/retriever_schema.py +52 -0
  156. package/plugin/vendor/reflexio/reflexio/models/api_schema/ui/converters.py +5 -1
  157. package/plugin/vendor/reflexio/reflexio/models/api_schema/ui/entities.py +5 -1
  158. package/plugin/vendor/reflexio/reflexio/models/config_schema.py +88 -7
  159. package/plugin/vendor/reflexio/reflexio/models/structured_output.py +148 -0
  160. package/plugin/vendor/reflexio/reflexio/server/OVERVIEW.md +3 -3
  161. package/plugin/vendor/reflexio/reflexio/server/README.md +45 -32
  162. package/plugin/vendor/reflexio/reflexio/server/__init__.py +29 -5
  163. package/plugin/vendor/reflexio/reflexio/server/__main__.py +2 -2
  164. package/plugin/vendor/reflexio/reflexio/server/_auth.py +65 -2
  165. package/plugin/vendor/reflexio/reflexio/server/api.py +734 -85
  166. package/plugin/vendor/reflexio/reflexio/server/api_endpoints/precondition_checks.py +7 -0
  167. package/plugin/vendor/reflexio/reflexio/server/api_endpoints/request_context.py +3 -1
  168. package/plugin/vendor/reflexio/reflexio/server/billing_meter.py +173 -0
  169. package/plugin/vendor/reflexio/reflexio/server/billing_signals.py +64 -0
  170. package/plugin/vendor/reflexio/reflexio/server/cache/reflexio_cache.py +46 -16
  171. package/plugin/vendor/reflexio/reflexio/server/env_utils.py +65 -0
  172. package/plugin/vendor/reflexio/reflexio/server/llm/embedding_service.py +19 -4
  173. package/plugin/vendor/reflexio/reflexio/server/llm/litellm_client.py +264 -77
  174. package/plugin/vendor/reflexio/reflexio/server/llm/llm_utils.py +69 -7
  175. package/plugin/vendor/reflexio/reflexio/server/llm/providers/embedding_service_provider.py +75 -16
  176. package/plugin/vendor/reflexio/reflexio/server/llm/providers/openclaw_provider.py +280 -0
  177. package/plugin/vendor/reflexio/reflexio/server/llm/token_accounting.py +48 -0
  178. package/plugin/vendor/reflexio/reflexio/server/llm/tools.py +107 -17
  179. package/plugin/vendor/reflexio/reflexio/server/operation_limiter.py +360 -4
  180. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/memory_reflection/v1.6.0.prompt.md +1 -1
  181. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/memory_reflection/v1.7.0.prompt.md +85 -0
  182. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_aggregation/v2.2.0.prompt.md +1 -1
  183. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_aggregation/v2.3.0.prompt.md +253 -0
  184. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_consolidation/v2.3.2.prompt.md +1 -1
  185. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_consolidation/v2.3.3.prompt.md +74 -0
  186. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_context/v4.2.3.prompt.md +1 -1
  187. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_context/v4.3.0.prompt.md +266 -0
  188. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_context/v4.4.0.prompt.md +266 -0
  189. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_context_expert/v3.3.0.prompt.md +1 -1
  190. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_context_expert/v3.4.0.prompt.md +137 -0
  191. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_main/v1.2.0.prompt.md +1 -1
  192. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/playbook_extraction_main/v1.3.0.prompt.md +34 -0
  193. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/profile_update_instruction_start/v1.0.0.prompt.md +5 -12
  194. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/profile_update_instruction_start/v1.1.0.prompt.md +5 -12
  195. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/profile_update_instruction_start/v1.2.0.prompt.md +155 -0
  196. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_bank/tagging/v1.0.0.prompt.md +23 -0
  197. package/plugin/vendor/reflexio/reflexio/server/prompt/prompt_manager.py +89 -32
  198. package/plugin/vendor/reflexio/reflexio/server/services/README.md +26 -11
  199. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/README.md +22 -0
  200. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/__init__.py +1 -0
  201. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/agent_success_evaluation_constants.py +4 -2
  202. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/agent_success_evaluation_utils.py +1 -0
  203. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/components/__init__.py +7 -0
  204. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/{agent_success_evaluator.py → components/evaluator.py} +3 -16
  205. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/regen_jobs.py +28 -72
  206. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/{group_evaluation_runner.py → runner.py} +12 -10
  207. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/{delayed_group_evaluator.py → scheduler.py} +10 -2
  208. package/plugin/vendor/reflexio/reflexio/server/services/agent_success_evaluation/{agent_success_evaluation_service.py → service.py} +36 -1
  209. package/plugin/vendor/reflexio/reflexio/server/services/base_generation_service.py +160 -0
  210. package/plugin/vendor/reflexio/reflexio/server/services/configurator/base_configurator.py +5 -0
  211. package/plugin/vendor/reflexio/reflexio/server/services/deduplication_utils.py +1 -1
  212. package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/README.md +9 -0
  213. package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/components/__init__.py +0 -0
  214. package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/{rule_attribution.py → components/rule_attribution.py} +10 -9
  215. package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/eval_sampler.py +15 -24
  216. package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/service.py +238 -164
  217. package/plugin/vendor/reflexio/reflexio/server/services/extraction/README.md +31 -0
  218. package/plugin/vendor/reflexio/reflexio/server/services/extraction/outcome.py +13 -3
  219. package/plugin/vendor/reflexio/reflexio/server/services/extraction/pending_tool_call_dispatch.py +3 -2
  220. package/plugin/vendor/reflexio/reflexio/server/services/extraction/resumable_agent.py +32 -118
  221. package/plugin/vendor/reflexio/reflexio/server/services/extraction/resume_worker.py +39 -16
  222. package/plugin/vendor/reflexio/reflexio/server/services/generation_service.py +105 -23
  223. package/plugin/vendor/reflexio/reflexio/server/services/lineage/__init__.py +0 -0
  224. package/plugin/vendor/reflexio/reflexio/server/services/lineage/gc_scheduler.py +193 -0
  225. package/plugin/vendor/reflexio/reflexio/server/services/lineage/resolve.py +98 -0
  226. package/plugin/vendor/reflexio/reflexio/server/services/operation_state_utils.py +26 -0
  227. package/plugin/vendor/reflexio/reflexio/server/services/playbook/README.md +11 -12
  228. package/plugin/vendor/reflexio/reflexio/server/services/playbook/components/__init__.py +5 -0
  229. package/plugin/vendor/reflexio/reflexio/server/services/playbook/{playbook_aggregator.py → components/aggregator.py} +316 -178
  230. package/plugin/vendor/reflexio/reflexio/server/services/playbook/{playbook_consolidator.py → components/consolidator.py} +168 -62
  231. package/plugin/vendor/reflexio/reflexio/server/services/playbook/{playbook_extractor.py → components/extractor.py} +5 -1
  232. package/plugin/vendor/reflexio/reflexio/server/services/playbook/playbook_edit_apply.py +74 -0
  233. package/plugin/vendor/reflexio/reflexio/server/services/playbook/playbook_service_utils.py +33 -3
  234. package/plugin/vendor/reflexio/reflexio/server/services/playbook/{playbook_generation_service.py → service.py} +121 -19
  235. package/plugin/vendor/reflexio/reflexio/server/services/playbook/user_detail_stripping.py +84 -0
  236. package/plugin/vendor/reflexio/reflexio/server/services/playbook_optimizer/README.md +10 -0
  237. package/plugin/vendor/reflexio/reflexio/server/services/playbook_optimizer/models.py +2 -1
  238. package/plugin/vendor/reflexio/reflexio/server/services/playbook_optimizer/optimizer.py +178 -30
  239. package/plugin/vendor/reflexio/reflexio/server/services/pre_retrieval/README.md +9 -0
  240. package/plugin/vendor/reflexio/reflexio/server/services/profile/components/__init__.py +17 -0
  241. package/plugin/vendor/reflexio/reflexio/server/services/profile/{profile_deduplicator.py → components/consolidator.py} +7 -6
  242. package/plugin/vendor/reflexio/reflexio/server/services/profile/{profile_extractor.py → components/extractor.py} +30 -22
  243. package/plugin/vendor/reflexio/reflexio/server/services/profile/profile_generation_service_utils.py +6 -13
  244. package/plugin/vendor/reflexio/reflexio/server/services/profile/{profile_generation_service.py → service.py} +32 -50
  245. package/plugin/vendor/reflexio/reflexio/server/services/reflection/__init__.py +4 -8
  246. package/plugin/vendor/reflexio/reflexio/server/services/reflection/components/__init__.py +7 -0
  247. package/plugin/vendor/reflexio/reflexio/server/services/reflection/reflection_service_utils.py +12 -1
  248. package/plugin/vendor/reflexio/reflexio/server/services/reflection/{reflection_service.py → service.py} +36 -16
  249. package/plugin/vendor/reflexio/reflexio/server/services/retrieval/relevance_floor.py +83 -6
  250. package/plugin/vendor/reflexio/reflexio/server/services/service_utils.py +36 -1
  251. package/plugin/vendor/reflexio/reflexio/server/services/shadow_comparison/README.md +8 -0
  252. package/plugin/vendor/reflexio/reflexio/server/services/shadow_comparison/outcome.py +1 -2
  253. package/plugin/vendor/reflexio/reflexio/server/services/storage/error.py +27 -0
  254. package/plugin/vendor/reflexio/reflexio/server/services/storage/retention.py +9 -9
  255. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/__init__.py +2 -0
  256. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_agent_run.py +4 -1
  257. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_base.py +642 -197
  258. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_extras.py +61 -104
  259. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_lineage.py +628 -0
  260. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_operations.py +38 -6
  261. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_playbook.py +978 -184
  262. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_profiles.py +519 -128
  263. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_requests.py +77 -3
  264. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_shadow_verdicts.py +23 -9
  265. package/plugin/vendor/reflexio/reflexio/server/services/storage/sqlite_storage/_stall_state.py +5 -2
  266. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/__init__.py +131 -20
  267. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_agent_run.py +2 -8
  268. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_base.py +5 -0
  269. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_extras.py +36 -53
  270. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_lineage.py +215 -0
  271. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_operations.py +20 -0
  272. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_playbook.py +243 -7
  273. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_profiles.py +121 -1
  274. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_requests.py +60 -0
  275. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_retrieval_log.py +51 -0
  276. package/plugin/vendor/reflexio/reflexio/server/services/storage/storage_base/_shadow_verdicts.py +17 -0
  277. package/plugin/vendor/reflexio/reflexio/server/services/tagging/README.md +8 -0
  278. package/plugin/vendor/reflexio/reflexio/server/services/tagging/__init__.py +1 -0
  279. package/plugin/vendor/reflexio/reflexio/server/services/tagging/service.py +200 -0
  280. package/plugin/vendor/reflexio/reflexio/server/services/tagging/tagging_scheduler.py +149 -0
  281. package/plugin/vendor/reflexio/reflexio/server/services/unified_search_service.py +229 -32
  282. package/plugin/vendor/reflexio/reflexio/server/site_var/README.md +2 -1
  283. package/plugin/vendor/reflexio/reflexio/server/site_var/feature_flags.py +120 -1
  284. package/plugin/vendor/reflexio/reflexio/server/site_var/site_var_sources/feature_flags.json +4 -0
  285. package/plugin/vendor/reflexio/reflexio/server/site_var/site_var_sources/search_settings.json +5 -0
  286. package/plugin/vendor/reflexio/reflexio/server/tracing.py +30 -0
  287. package/plugin/vendor/reflexio/reflexio/server/usage_metrics.py +18 -0
  288. package/plugin/vendor/reflexio/reflexio/test_support/llm_mock.py +61 -26
  289. package/plugin/vendor/reflexio/reflexio/test_support/llm_model_registry.py +41 -4
  290. package/scripts/setup-claude-smart.sh +8 -3
  291. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/TESTING.md +0 -517
  292. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/hook/handler.js +0 -473
  293. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/package-lock.json +0 -2156
  294. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/package.json +0 -18
  295. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/hook/handler.ts +0 -241
  296. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/hook/setup.ts +0 -140
  297. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/lib/publish.ts +0 -113
  298. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/lib/search.ts +0 -52
  299. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/lib/server.ts +0 -103
  300. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/lib/sqlite-buffer.ts +0 -156
  301. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/lib/user-id.ts +0 -134
  302. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/plugin/rules/reflexio.md +0 -24
  303. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/publish_clawhub.sh +0 -278
  304. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/references/HOOK.md +0 -164
  305. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/scripts/install.sh +0 -36
  306. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/scripts/uninstall.sh +0 -35
  307. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/tests/publish.test.ts +0 -27
  308. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/tests/search.test.ts +0 -31
  309. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/tests/server.test.ts +0 -42
  310. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/tests/setup.test.ts +0 -49
  311. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/tests/sqlite-buffer.test.ts +0 -91
  312. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/tests/user-id.test.ts +0 -50
  313. package/plugin/vendor/reflexio/reflexio/integrations/openclaw/vitest.config.ts +0 -13
  314. package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/group_aggregation.py +0 -192
  315. package/plugin/vendor/reflexio/reflexio/server/services/extraction/invariants.py +0 -303
  316. package/plugin/vendor/reflexio/reflexio/server/services/extraction/plan.py +0 -138
  317. package/plugin/vendor/reflexio/reflexio/server/services/extraction/tools.py +0 -1125
  318. /package/plugin/vendor/reflexio/reflexio/integrations/{__init__.py → openclaw/plugin/src/openclaw_smart/__init__.py} +0 -0
  319. /package/plugin/vendor/reflexio/reflexio/integrations/openclaw/{types → plugin/types}/openclaw.d.ts +0 -0
  320. /package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/{distribution.py → components/distribution.py} +0 -0
  321. /package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/{hero_state.py → components/hero_state.py} +0 -0
  322. /package/plugin/vendor/reflexio/reflexio/server/services/evaluation_overview/{shadow_aggregation.py → components/shadow_aggregation.py} +0 -0
  323. /package/plugin/vendor/reflexio/reflexio/server/services/reflection/{reflection_extractor.py → components/extractor.py} +0 -0
@@ -4,14 +4,14 @@
4
4
  "name": "Yi Lu"
5
5
  },
6
6
  "metadata": {
7
- "description": "claude-smart — self-improving Claude Code and Codex plugin via reflexio"
7
+ "description": "claude-smart — self-improving Claude Code, Codex, and OpenCode plugin powered by Reflexio"
8
8
  },
9
9
  "plugins": [
10
10
  {
11
11
  "name": "claude-smart",
12
- "version": "0.2.44",
12
+ "version": "0.2.46",
13
13
  "source": "./plugin",
14
- "description": "Turns user corrections into project-specific and shared skills via reflexio — uses Claude Code or Codex as the LLM backend (no external API key required)"
14
+ "description": "Turns corrections into Preferences, Project-specific skills, and Shared skills — uses Claude Code, Codex, or OpenCode as the LLM backend (no external API key required)"
15
15
  }
16
16
  ]
17
17
  }
package/README.md CHANGED
@@ -6,14 +6,14 @@
6
6
  claude-smart
7
7
  </h1>
8
8
 
9
- <h4 align="center">A self-improvement plugin for <a href="https://claude.com/claude-code" target="_blank">Claude Code</a> and Codex that turns interactions into durable skills they follow in future sessions.</h4>
9
+ <h4 align="center">A self-improvement plugin for <a href="https://claude.com/claude-code" target="_blank">Claude Code</a>, Codex, and OpenCode that turns interactions into durable skills they follow in future sessions.</h4>
10
10
 
11
11
  <p align="center">
12
12
  <a href="LICENSE">
13
13
  <img src="https://img.shields.io/badge/License-Apache%202.0-blue.svg" alt="License">
14
14
  </a>
15
15
  <a href="plugin/pyproject.toml">
16
- <img src="https://img.shields.io/badge/version-0.2.44-green.svg" alt="Version">
16
+ <img src="https://img.shields.io/badge/version-0.2.46-green.svg" alt="Version">
17
17
  </a>
18
18
  <a href="plugin/pyproject.toml">
19
19
  <img src="https://img.shields.io/badge/python-%3E%3D3.12-brightgreen.svg" alt="Python">
@@ -22,7 +22,10 @@
22
22
  <img src="https://img.shields.io/badge/node-%3E%3D20-brightgreen.svg" alt="Node">
23
23
  </a>
24
24
  <a href="#quick-start">
25
- <img src="https://img.shields.io/badge/hosts-Claude%20Code%20%2B%20Codex-purple.svg" alt="Hosts">
25
+ <img src="https://img.shields.io/badge/hosts-Claude%20Code%20%2B%20Codex%20%2B%20OpenCode-purple.svg" alt="Hosts">
26
+ </a>
27
+ <a href="https://discord.gg/7fnCxahase">
28
+ <img src="https://img.shields.io/badge/Discord-Join%20community-5865F2?logo=discord&logoColor=white" alt="Discord">
26
29
  </a>
27
30
  </p>
28
31
 
@@ -95,6 +98,24 @@ npx claude-smart uninstall --host codex
95
98
 
96
99
  Restart Codex after uninstalling. The uninstaller stops local claude-smart services and removes plugin/cache/config state; learned data under `~/.reflexio/` and `~/.claude-smart/` is preserved and shared with Claude Code, so you can switch between hosts without losing skills or preferences.
97
100
 
101
+ ### OpenCode
102
+
103
+ ```bash
104
+ npx claude-smart install --host opencode
105
+ ```
106
+
107
+ Then restart OpenCode in your project so it loads the plugin from `opencode.json`, the documented project config file. If that project does not already have a root config but does have `.opencode/opencode.json` or `.opencode/opencode.jsonc`, the installer updates that existing file instead of creating a second config. If both locations exist, the root config wins. Use `--global` to install into `~/.config/opencode/opencode.json` for all OpenCode projects on this machine. When run through `npx`, long-lived local services are prepared from OpenCode's installed plugin package on the next OpenCode launch instead of from npm's temporary `npx` cache.
108
+
109
+ OpenCode support is new and uses OpenCode's npm plugin loader to inject relevant learned context before each model request. Learning extraction runs `opencode run --pure` from an isolated temp project, so it uses OpenCode's default model unless you set `CLAUDE_SMART_OPENCODE_MODEL=provider/model`. Set that env var if your normal project config pins a different provider or model.
110
+
111
+ To uninstall:
112
+
113
+ ```bash
114
+ npx claude-smart uninstall --host opencode
115
+ ```
116
+
117
+ Restart OpenCode after uninstalling. The uninstaller removes only the `claude-smart` entry from OpenCode's plugin list; learned data under `~/.reflexio/` and `~/.claude-smart/` is preserved and shared across hosts.
118
+
98
119
  Developing the plugin itself? See [DEVELOPER.md](./DEVELOPER.md#developing-locally) for what the installer does, manual toggles via `/plugins`, and clone-based development.
99
120
 
100
121
  > **Not supported:** Claude Code Cowork, claude.ai/code web, or remote Codex environments without local plugin hooks — they run outside your local machine, so the local backend/dashboard and `~/.reflexio/` aren't reachable.
@@ -160,7 +181,7 @@ A web UI for browsing session histories, inspecting preferences, and editing pro
160
181
 
161
182
  ## How It Works
162
183
 
163
- claude-smart builds three artifacts as you work and injects the relevant ones into Claude Code or Codex:
184
+ claude-smart builds three artifacts as you work and injects the relevant ones into Claude Code, Codex, or OpenCode:
164
185
 
165
186
  - **Preferences** (project-scoped) — how you work in this specific repo (stack, role, small quirks). *e.g.* "uses pnpm, not npm"; "prefers terse answers"; "backend engineer — explain frontend with backend analogues."
166
187
  - **Project-specific skills** — durable rules with triggers and rationales learned from corrections in a project. *e.g.* "always pass `--run` to `npm test` — watch mode hangs CI."
@@ -213,6 +234,7 @@ Advanced users can tune claude-smart via environment variables — see [DEVELOPE
213
234
  | `.claude/settings.local.json` or `~/.claude/settings.json` | Claude Code hook environment, such as `CLAUDE_SMART_ENABLE_OPTIMIZER`; use project-local settings for one repo or user settings for all projects. |
214
235
  | `~/.codex/config.toml` | Codex plugin state, hook feature flags, and per-hook trust entries after `claude-smart install --host codex`. |
215
236
  | `~/.codex/plugins/cache/reflexioai/claude-smart/<version>/` | Codex's cached install of the `claude-smart` plugin from the `ReflexioAI` marketplace. |
237
+ | `opencode.json` / `opencode.jsonc`, or existing `.opencode/opencode.json*` | OpenCode local plugin config patched by `claude-smart install --host opencode`; the installer updates only the claude-smart entry in OpenCode's plugin list. |
216
238
  | `~/.reflexio/plugin-root` | Self-healed symlink to the active plugin dir (managed by `ensure-plugin-root.sh` — written on install, refreshed each `SessionStart`). Claude Code slash commands and Codex shell-command helpers resolve through it, so don't delete it; if you do, the next session will recreate it. |
217
239
  | `~/.claude-smart/sessions/{session_id}.jsonl` | Per-session buffer. User turns, assistant turns, tool invocations, `{"published_up_to": N}` watermarks. Safe to inspect and safe to delete — everything past the latest watermark has already been written to reflexio's DB. |
218
240
  | `~/.claude-smart/node/current/` | Private Node.js/npm runtime used by hooks and the dashboard after install. |
@@ -222,6 +244,12 @@ For troubleshooting, see [TROUBLESHOOTING.md](./TROUBLESHOOTING.md).
222
244
 
223
245
  ---
224
246
 
247
+ ## Powered by Reflexio
248
+
249
+ claude-smart is powered by [**Reflexio**](https://reflexio.ai) — the self-improving engine that turns interactions into durable, reusable skills.
250
+
251
+ ---
252
+
225
253
  ## License
226
254
 
227
255
  This project is licensed under the **Apache License 2.0**. Reflexio is a separate Apache 2.0 project consumed as the `reflexio-ai` Python package. Claude Code is Anthropic's and not covered by this license.
@@ -232,8 +260,9 @@ See the [LICENSE](LICENSE) file for details.
232
260
 
233
261
  ## Support
234
262
 
263
+ - **Discord**: join the community at [discord.gg/7fnCxahase](https://discord.gg/7fnCxahase).
235
264
  - **Issues**: open one on GitHub describing the symptom and include the reflexio backend log (`~/.claude-smart/backend.log`) and the relevant lines of `~/.claude-smart/sessions/{session_id}.jsonl`.
236
265
 
237
266
  ---
238
267
 
239
- **Built on** [reflexio](https://github.com/ReflexioAI/reflexio) · **Runs on** [Claude Code](https://claude.com/claude-code) and Codex · **Written in** Python 3.12+
268
+ **Powered by** [Reflexio](https://reflexio.ai) · **Runs on** [Claude Code](https://claude.com/claude-code), Codex, and OpenCode · **Written in** Python 3.12+
@@ -17,8 +17,10 @@ const { execSync, spawn, spawnSync } = require("child_process");
17
17
  const crypto = require("crypto");
18
18
  const {
19
19
  chmodSync,
20
+ constants,
20
21
  cpSync,
21
22
  existsSync,
23
+ accessSync,
22
24
  lstatSync,
23
25
  mkdirSync,
24
26
  readFileSync,
@@ -37,6 +39,8 @@ const PLUGIN_SPEC = "claude-smart@reflexioai";
37
39
  const CODEX_MARKETPLACE_NAME = "reflexioai";
38
40
  const CODEX_MARKETPLACE_DISPLAY_NAME = "ReflexioAI";
39
41
  const CODEX_PLUGIN_ID = `claude-smart@${CODEX_MARKETPLACE_NAME}`;
42
+ const OPENCODE_PLUGIN_SPEC = "claude-smart";
43
+ const OPENCODE_CONFIG_NAMES = ["opencode.json", "opencode.jsonc"];
40
44
  const REFLEXIO_ENV_PATH = join(homedir(), ".reflexio", ".env");
41
45
  const MANAGED_REFLEXIO_URL = "https://www.reflexio.ai/";
42
46
  const MANAGED_SETUP_ENV = "CLAUDE_SMART_MANAGED_SETUP";
@@ -79,6 +83,9 @@ const CODEX_REQUIRED_FILES = [
79
83
  "plugin/scripts/codex-claude-compat",
80
84
  "plugin/scripts/codex-claude-compat.cmd",
81
85
  "plugin/scripts/codex-claude-compat.js",
86
+ "plugin/scripts/opencode-claude-compat",
87
+ "plugin/scripts/opencode-claude-compat.cmd",
88
+ "plugin/scripts/opencode-claude-compat.js",
82
89
  "plugin/scripts/codex-hook.js",
83
90
  "plugin/scripts/_codex_env.sh",
84
91
  ];
@@ -342,6 +349,170 @@ function configureReflexioSetup() {
342
349
  return loadReflexioSetupEnv();
343
350
  }
344
351
 
352
+ function stripJsonc(text) {
353
+ let out = "";
354
+ let inString = false;
355
+ let escaped = false;
356
+ const skipTrivia = (index) => {
357
+ while (index < text.length) {
358
+ while (index < text.length && /\s/.test(text[index])) index += 1;
359
+ if (text[index] === "/" && text[index + 1] === "/") {
360
+ index += 2;
361
+ while (index < text.length && !"\r\n".includes(text[index])) index += 1;
362
+ continue;
363
+ }
364
+ if (text[index] === "/" && text[index + 1] === "*") {
365
+ index += 2;
366
+ while (index + 1 < text.length && !(text[index] === "*" && text[index + 1] === "/")) index += 1;
367
+ index = Math.min(index + 2, text.length);
368
+ continue;
369
+ }
370
+ break;
371
+ }
372
+ return index;
373
+ };
374
+ for (let i = 0; i < text.length; i += 1) {
375
+ const ch = text[i];
376
+ const next = text[i + 1] || "";
377
+ if (inString) {
378
+ out += ch;
379
+ if (escaped) escaped = false;
380
+ else if (ch === "\\") escaped = true;
381
+ else if (ch === '"') inString = false;
382
+ continue;
383
+ }
384
+ if (ch === '"') {
385
+ inString = true;
386
+ out += ch;
387
+ continue;
388
+ }
389
+ if (ch === "/" && next === "/") {
390
+ while (i < text.length && !"\r\n".includes(text[i])) i += 1;
391
+ i -= 1;
392
+ continue;
393
+ }
394
+ if (ch === "/" && next === "*") {
395
+ i += 2;
396
+ while (i + 1 < text.length && !(text[i] === "*" && text[i + 1] === "/")) i += 1;
397
+ i += 1;
398
+ continue;
399
+ }
400
+ if (ch === ",") {
401
+ const j = skipTrivia(i + 1);
402
+ if (text[j] === "}" || text[j] === "]") continue;
403
+ }
404
+ out += ch;
405
+ }
406
+ return out;
407
+ }
408
+
409
+ function readJsoncObject(path) {
410
+ const text = existsSync(path) ? readFileSync(path, "utf8") : "{}";
411
+ const parsed = JSON.parse(stripJsonc(text || "{}"));
412
+ if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
413
+ throw new Error(`OpenCode config ${path} must be a JSON object`);
414
+ }
415
+ return parsed;
416
+ }
417
+
418
+ function parseGlobalFlag(args) {
419
+ return args.includes("--global");
420
+ }
421
+
422
+ function opencodeGlobalConfigDir() {
423
+ const xdg = (process.env.XDG_CONFIG_HOME || "").trim();
424
+ const base = xdg ? xdg : join(homedir(), ".config");
425
+ return join(base, "opencode");
426
+ }
427
+
428
+ function opencodeConfigPath(args = [], cwd = process.cwd()) {
429
+ if (parseGlobalFlag(args)) {
430
+ const configDir = opencodeGlobalConfigDir();
431
+ for (const name of OPENCODE_CONFIG_NAMES) {
432
+ const candidate = join(configDir, name);
433
+ if (existsSync(candidate)) return candidate;
434
+ }
435
+ return join(configDir, "opencode.json");
436
+ }
437
+ const candidates = [
438
+ ...OPENCODE_CONFIG_NAMES.map((name) => join(cwd, name)),
439
+ ...OPENCODE_CONFIG_NAMES.map((name) => join(cwd, ".opencode", name)),
440
+ ];
441
+ for (const candidate of candidates) {
442
+ if (existsSync(candidate)) return candidate;
443
+ }
444
+ return join(cwd, "opencode.json");
445
+ }
446
+
447
+ function opencodePluginSpec(entry) {
448
+ if (typeof entry === "string") return entry;
449
+ if (Array.isArray(entry) && typeof entry[0] === "string") return entry[0];
450
+ return null;
451
+ }
452
+
453
+ function patchOpenCodePluginConfig(configPath, { install }) {
454
+ const data = readJsoncObject(configPath);
455
+ for (const field of ["plugins", "plugin"]) {
456
+ if (data[field] !== undefined && !Array.isArray(data[field])) {
457
+ throw new Error(`OpenCode config ${configPath} field "${field}" must be a JSON array`);
458
+ }
459
+ }
460
+ const current = [
461
+ ...(Array.isArray(data.plugin) ? data.plugin : []),
462
+ ...(Array.isArray(data.plugins) ? data.plugins : []),
463
+ ];
464
+ const kept = current.filter((entry) => opencodePluginSpec(entry) !== OPENCODE_PLUGIN_SPEC);
465
+ const next = install ? [...kept, OPENCODE_PLUGIN_SPEC] : kept;
466
+ const changed =
467
+ data.plugins !== undefined ||
468
+ (Array.isArray(data.plugin)
469
+ ? next.length !== data.plugin.length || next.some((entry, index) => entry !== data.plugin[index])
470
+ : install && next.length > 0);
471
+ if (!changed) return { changed: false, configPath };
472
+ let backupPath = null;
473
+ if (existsSync(configPath)) {
474
+ const original = readFileSync(configPath, "utf8");
475
+ if (original.trim() && original !== stripJsonc(original)) {
476
+ backupPath = `${configPath}.bak`;
477
+ writeFileSync(backupPath, original);
478
+ }
479
+ }
480
+ data.plugin = next;
481
+ delete data.plugins;
482
+ mkdirSync(dirname(configPath), { recursive: true });
483
+ writeFileSync(configPath, JSON.stringify(data, null, 2) + "\n");
484
+ return { changed: true, configPath, backupPath };
485
+ }
486
+
487
+ function isNpxPackageRoot(path) {
488
+ return path.split(/[\\/]+/).includes("_npx");
489
+ }
490
+
491
+ function hasExtractionProvider() {
492
+ if ((process.env.REFLEXIO_API_KEY || "").trim()) return true;
493
+ const cliPath = (process.env.CLAUDE_SMART_CLI_PATH || "").trim();
494
+ if (cliPath && isExecutableFile(cliPath)) return true;
495
+ return hasCli("claude") || hasCli("codex") || hasCli("opencode");
496
+ }
497
+
498
+ function isExecutableFile(path) {
499
+ try {
500
+ if (!statSync(path).isFile()) return false;
501
+ accessSync(path, constants.X_OK);
502
+ return true;
503
+ } catch {
504
+ return false;
505
+ }
506
+ }
507
+
508
+ function extractionProviderError() {
509
+ return (
510
+ "error: OpenCode support needs a working learning/extraction provider.\n" +
511
+ "Run `npx claude-smart setup` to configure Reflexio, or install " +
512
+ "OpenCode, Claude Code, or Codex so local extraction can use a supported CLI.\n"
513
+ );
514
+ }
515
+
345
516
  function findClaudeCodePluginRoot() {
346
517
  const cacheRoot = join(homedir(), ".claude", "plugins", "cache", CODEX_MARKETPLACE_NAME, "claude-smart");
347
518
  const candidates = [];
@@ -925,7 +1096,9 @@ async function bootstrapPluginRuntime(pluginRoot, options = {}) {
925
1096
  assertSupportedRuntimePlatform();
926
1097
  process.stdout.write("Preparing claude-smart runtime for hooks...\n");
927
1098
  const nodeRuntime = await ensurePrivateNode();
928
- patchCodexHooksForNode(pluginRoot, nodeRuntime.node);
1099
+ if (options.patchCodexHooks !== false) {
1100
+ patchCodexHooksForNode(pluginRoot, nodeRuntime.node);
1101
+ }
929
1102
  if (options.readOnly) prunePublishHooksForReadOnly(pluginRoot);
930
1103
  ensurePluginRoot(pluginRoot);
931
1104
  const uv = await ensureUv();
@@ -970,13 +1143,15 @@ async function bootstrapPluginRuntime(pluginRoot, options = {}) {
970
1143
  function printHelp() {
971
1144
  process.stdout.write(
972
1145
  [
973
- "claude-smart — install helper for Claude Code and Codex",
1146
+ "claude-smart — install helper for Claude Code, Codex, and OpenCode",
974
1147
  "",
975
1148
  "Usage:",
976
1149
  " npx claude-smart install Install the plugin into Claude Code",
977
1150
  " npx claude-smart install --host codex Register the plugin marketplace for Codex",
1151
+ " npx claude-smart install --host opencode Add claude-smart to OpenCode config",
978
1152
  " npx claude-smart setup Configure managed/read-only/global setup",
979
1153
  " npx claude-smart uninstall --host codex Remove the Codex marketplace registration",
1154
+ " npx claude-smart uninstall --host opencode Remove claude-smart from OpenCode config",
980
1155
  " npx claude-smart --help Show this help",
981
1156
  "",
982
1157
  "Claude Code install:",
@@ -993,9 +1168,15 @@ function printHelp() {
993
1168
  " 6. Trusts and enables claude-smart hook entries in ~/.codex/config.toml",
994
1169
  " 7. Restart Codex.",
995
1170
  "",
1171
+ "OpenCode install:",
1172
+ " 1. Adds \"claude-smart\" to OpenCode's plugin list in opencode.json",
1173
+ " 2. Prepares local services now for stable installs; npx prepares on next OpenCode launch",
1174
+ " 3. Restart OpenCode.",
1175
+ "",
996
1176
  "Update:",
997
1177
  " npx claude-smart update Reinstall Claude Code support from this package",
998
1178
  " npx claude-smart update --host codex Reinstall Codex support from this package",
1179
+ " npx claude-smart update --host opencode Reinstall OpenCode support from this package",
999
1180
  " npx claude-smart setup Configure managed/read-only/global setup",
1000
1181
  "",
1001
1182
  "Uninstall:",
@@ -1010,11 +1191,11 @@ function parseHost(args) {
1010
1191
  if (idx === -1) return "claude-code";
1011
1192
  const value = args[idx + 1];
1012
1193
  if (!value) {
1013
- process.stderr.write("error: --host requires a value: claude-code or codex\n");
1194
+ process.stderr.write("error: --host requires a value: claude-code, codex, or opencode\n");
1014
1195
  process.exit(1);
1015
1196
  }
1016
- if (value !== "claude-code" && value !== "codex") {
1017
- process.stderr.write("error: --host must be claude-code or codex\n");
1197
+ if (value !== "claude-code" && value !== "codex" && value !== "opencode") {
1198
+ process.stderr.write("error: --host must be claude-code, codex, or opencode\n");
1018
1199
  process.exit(1);
1019
1200
  }
1020
1201
  return value;
@@ -1433,6 +1614,10 @@ async function runUpdate(args) {
1433
1614
  await runUpdateCodex(args);
1434
1615
  return;
1435
1616
  }
1617
+ if (parseHost(args) === "opencode") {
1618
+ await runUpdateOpenCode(args);
1619
+ return;
1620
+ }
1436
1621
 
1437
1622
  const pluginRoot = findClaudeCodePluginRoot();
1438
1623
  if (pluginRoot) {
@@ -1449,11 +1634,22 @@ async function runUpdateCodex(args) {
1449
1634
  await runInstallCodex(args);
1450
1635
  }
1451
1636
 
1637
+ async function runUpdateOpenCode(args) {
1638
+ const pluginRoot = join(PACKAGE_ROOT, "plugin");
1639
+ stopClaudeSmartServices(pluginRoot);
1640
+ process.stdout.write("Updating claude-smart OpenCode support by reinstalling from this package...\n");
1641
+ await runInstallOpenCode(args);
1642
+ }
1643
+
1452
1644
  async function runUninstall(args) {
1453
1645
  if (parseHost(args) === "codex") {
1454
1646
  await runUninstallCodex();
1455
1647
  return;
1456
1648
  }
1649
+ if (parseHost(args) === "opencode") {
1650
+ await runUninstallOpenCode(args);
1651
+ return;
1652
+ }
1457
1653
 
1458
1654
  if (!hasClaudeCli()) {
1459
1655
  process.stderr.write(
@@ -1504,6 +1700,10 @@ async function runInstall(args, options = {}) {
1504
1700
  await runInstallCodex(args);
1505
1701
  return;
1506
1702
  }
1703
+ if (parseHost(args) === "opencode") {
1704
+ await runInstallOpenCode(args);
1705
+ return;
1706
+ }
1507
1707
 
1508
1708
  if (!hasClaudeCli()) {
1509
1709
  process.stderr.write(
@@ -1686,6 +1886,66 @@ async function runInstallCodex(args) {
1686
1886
  );
1687
1887
  }
1688
1888
 
1889
+ async function runInstallOpenCode(args) {
1890
+ const setup = configureReflexioSetup();
1891
+ const readOnly = setup.readOnly;
1892
+ if (!hasExtractionProvider()) {
1893
+ process.stderr.write(extractionProviderError());
1894
+ process.exit(1);
1895
+ }
1896
+
1897
+ const pluginRoot = join(PACKAGE_ROOT, "plugin");
1898
+ let result;
1899
+ if (isNpxPackageRoot(PACKAGE_ROOT)) {
1900
+ try {
1901
+ result = patchOpenCodePluginConfig(opencodeConfigPath(args), { install: true });
1902
+ } catch (err) {
1903
+ process.stderr.write(`error: could not update OpenCode config: ${err && err.message ? err.message : err}\n`);
1904
+ process.exit(1);
1905
+ }
1906
+ process.stdout.write(
1907
+ "Skipped starting claude-smart services from npx's temporary package cache; OpenCode will prepare the runtime from its installed plugin package on next launch.\n",
1908
+ );
1909
+ } else {
1910
+ try {
1911
+ await bootstrapPluginRuntime(pluginRoot, { readOnly, patchCodexHooks: false });
1912
+ } catch (err) {
1913
+ process.stderr.write(
1914
+ `error: claude-smart OpenCode setup failed during dependency bootstrap: ${err && err.message ? err.message : err}\n`,
1915
+ );
1916
+ process.exit(1);
1917
+ }
1918
+ try {
1919
+ result = patchOpenCodePluginConfig(opencodeConfigPath(args), { install: true });
1920
+ } catch (err) {
1921
+ process.stderr.write(`error: could not update OpenCode config: ${err && err.message ? err.message : err}\n`);
1922
+ stopClaudeSmartServices(pluginRoot);
1923
+ process.exit(1);
1924
+ }
1925
+ if (readOnly) {
1926
+ process.stdout.write("Installed read-only hook manifest; publish interactions hooks are disabled.\n");
1927
+ }
1928
+ if (startBackendService(pluginRoot, "opencode")) {
1929
+ process.stdout.write("Started claude-smart backend service.\n");
1930
+ }
1931
+ if (refreshDashboardService(pluginRoot)) {
1932
+ process.stdout.write("Refreshed claude-smart dashboard service.\n");
1933
+ }
1934
+ }
1935
+ if (result.backupPath) {
1936
+ process.stdout.write(`Saved a comment-preserving backup of your previous config at ${result.backupPath}.\n`);
1937
+ }
1938
+ process.stdout.write(
1939
+ [
1940
+ "",
1941
+ `${result.changed ? "Updated" : "OpenCode config already includes"} "${OPENCODE_PLUGIN_SPEC}" in ${result.configPath}.`,
1942
+ "claude-smart OpenCode support is installed.",
1943
+ "Restart OpenCode in your project so it loads the plugin.",
1944
+ "",
1945
+ ].join("\n"),
1946
+ );
1947
+ }
1948
+
1689
1949
  async function runUninstallCodex() {
1690
1950
  stopClaudeSmartServices(join(PACKAGE_ROOT, "plugin"));
1691
1951
  if (!hasCli("codex")) {
@@ -1713,6 +1973,31 @@ async function runUninstallCodex() {
1713
1973
  );
1714
1974
  }
1715
1975
 
1976
+ async function runUninstallOpenCode(args) {
1977
+ stopClaudeSmartServices(join(PACKAGE_ROOT, "plugin"));
1978
+ let result;
1979
+ try {
1980
+ result = patchOpenCodePluginConfig(opencodeConfigPath(args), { install: false });
1981
+ } catch (err) {
1982
+ process.stderr.write(`error: could not update OpenCode config: ${err && err.message ? err.message : err}\n`);
1983
+ process.exit(1);
1984
+ }
1985
+ if (result.backupPath) {
1986
+ process.stdout.write(`Saved a comment-preserving backup of your previous config at ${result.backupPath}.\n`);
1987
+ }
1988
+ process.stdout.write(
1989
+ [
1990
+ "",
1991
+ result.changed
1992
+ ? `Removed "${OPENCODE_PLUGIN_SPEC}" from ${result.configPath}.`
1993
+ : `OpenCode config did not include "${OPENCODE_PLUGIN_SPEC}".`,
1994
+ "Restart OpenCode to apply.",
1995
+ ...LOCAL_DATA_NOTICE,
1996
+ "",
1997
+ ].join("\n"),
1998
+ );
1999
+ }
2000
+
1716
2001
  async function main() {
1717
2002
  const args = process.argv.slice(2);
1718
2003
  const cmd = args[0] || "install";
@@ -1764,7 +2049,12 @@ module.exports = {
1764
2049
  ensureUv,
1765
2050
  configureReflexioSetup,
1766
2051
  patchCodexHooksForNode,
2052
+ opencodeConfigPath,
2053
+ isNpxPackageRoot,
2054
+ patchOpenCodePluginConfig,
2055
+ hasExtractionProvider,
1767
2056
  platformSupportError,
1768
2057
  prunePublishHooksForReadOnly,
1769
2058
  restorePublishHooksFromSource,
2059
+ stripJsonc,
1770
2060
  };
package/package.json CHANGED
@@ -1,13 +1,15 @@
1
1
  {
2
2
  "name": "claude-smart",
3
- "version": "0.2.44",
4
- "description": "Self-improving Claude Code and Codex plugin turns corrections into durable skills via reflexio",
3
+ "version": "0.2.46",
4
+ "description": "Self-improving Claude Code, Codex, and OpenCode plugin that turns corrections into Preferences, Project-specific skills, and Shared skills",
5
5
  "keywords": [
6
6
  "claude",
7
7
  "claude-code",
8
8
  "claude-code-plugin",
9
9
  "codex",
10
10
  "codex-plugin",
11
+ "opencode",
12
+ "opencode-plugin",
11
13
  "memory",
12
14
  "agent-memory",
13
15
  "plugin",
@@ -28,6 +30,18 @@
28
30
  "license": "Apache-2.0",
29
31
  "author": "Yi Lu",
30
32
  "type": "commonjs",
33
+ "oc-plugin": [
34
+ "server"
35
+ ],
36
+ "exports": {
37
+ "./server": {
38
+ "import": "./plugin/opencode/dist/server.mjs"
39
+ }
40
+ },
41
+ "scripts": {
42
+ "build:opencode": "tsc -p plugin/opencode/tsconfig.json",
43
+ "prepack": "npm run build:opencode"
44
+ },
31
45
  "bin": {
32
46
  "claude-smart": "bin/claude-smart.js"
33
47
  },
@@ -49,6 +63,11 @@
49
63
  "LICENSE"
50
64
  ],
51
65
  "engines": {
52
- "node": ">=20.9.0"
66
+ "node": ">=20.9.0",
67
+ "opencode": ">=1.17.0"
68
+ },
69
+ "devDependencies": {
70
+ "@types/node": "^20.19.0",
71
+ "typescript": "^5.8.3"
53
72
  }
54
73
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "claude-smart",
3
- "version": "0.2.44",
4
- "description": "Self-improving Claude Code and Codex plugin turns corrections into durable skills via reflexio",
3
+ "version": "0.2.46",
4
+ "description": "Self-improving Claude Code, Codex, and OpenCode plugin that turns corrections into Preferences, Project-specific skills, and Shared skills",
5
5
  "author": {
6
6
  "name": "Yi Lu"
7
7
  },
@@ -11,6 +11,8 @@
11
11
  "claude-code-plugin",
12
12
  "codex",
13
13
  "codex-plugin",
14
+ "opencode",
15
+ "opencode-plugin",
14
16
  "memory",
15
17
  "agent-memory",
16
18
  "plugin",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "claude-smart",
3
- "version": "0.2.44",
3
+ "version": "0.2.46",
4
4
  "description": "Self-improving coding assistant plugin — learns from corrections across sessions via reflexio",
5
5
  "author": {
6
6
  "name": "Yi Lu"
package/plugin/README.md CHANGED
@@ -1,8 +1,8 @@
1
1
  # claude-smart
2
2
 
3
- Self-improving [Claude Code](https://claude.com/claude-code) and Codex plugin — turns your corrections into durable skills that future sessions follow, via [reflexio](https://github.com/ReflexioAI/reflexio).
3
+ Self-improving [Claude Code](https://claude.com/claude-code), Codex, and OpenCode plugin — turns corrections and successful workflows into durable Preferences, Project-specific skills, and Shared skills that future sessions follow, via [reflexio](https://github.com/ReflexioAI/reflexio).
4
4
 
5
- This directory is the published Python package (`claude-smart` on PyPI) and the Claude Code/Codex plugin payload shipped through the marketplace. For the project overview, install instructions, benchmarks, and feature walkthrough, see the [top-level README](https://github.com/ReflexioAI/claude-smart#readme).
5
+ This directory is the published Python package (`claude-smart` on PyPI) and the Claude Code/Codex/OpenCode plugin payload shipped through the marketplace and npm. For the project overview, install instructions, benchmarks, and feature walkthrough, see the [top-level README](https://github.com/ReflexioAI/claude-smart#readme).
6
6
 
7
7
  ## Install
8
8
 
@@ -36,6 +36,17 @@ npx claude-smart install --host codex
36
36
  Then fully quit and reopen Codex so hooks reload. Codex installs reuse the same
37
37
  local Preferences, Project-specific skills, and Shared skills as Claude Code.
38
38
 
39
+ ### OpenCode
40
+
41
+ ```bash
42
+ npx claude-smart install --host opencode
43
+ ```
44
+
45
+ Then restart OpenCode in your project so it loads the plugin from `opencode.json`
46
+ or your existing `.opencode/opencode.json*` config. OpenCode installs reuse the
47
+ same local Preferences, Project-specific skills, and Shared skills as Claude Code
48
+ and Codex.
49
+
39
50
  ## Uninstall
40
51
 
41
52
  ### Claude Code
@@ -59,6 +70,15 @@ npx claude-smart uninstall --host codex
59
70
  Restart Codex after uninstalling. Local data under `~/.reflexio/` and
60
71
  `~/.claude-smart/` is left in place for both hosts — remove manually if desired.
61
72
 
73
+ ### OpenCode
74
+
75
+ ```bash
76
+ npx claude-smart uninstall --host opencode
77
+ ```
78
+
79
+ Restart OpenCode after uninstalling. Local data under `~/.reflexio/` and
80
+ `~/.claude-smart/` is preserved and shared across supported hosts.
81
+
62
82
  ## License
63
83
 
64
84
  Apache 2.0 — see [LICENSE](LICENSE).
@@ -1,4 +1,5 @@
1
1
  ---
2
+ name: clear-all
2
3
  description: Delete ALL local claude-smart learned data and restart the backend (destructive)
3
4
  allowed-tools: Bash(bash:*)
4
5
  ---
@@ -1,4 +1,5 @@
1
1
  ---
2
+ name: dashboard
2
3
  description: Open the claude-smart dashboard (http://localhost:3001) in the browser, starting the backend and dashboard if they aren't running
3
4
  allowed-tools: Bash(bash:*)
4
5
  ---
@@ -1,4 +1,5 @@
1
1
  ---
2
+ name: learn
2
3
  description: Force claude-smart to extract learnings from this session now
3
4
  argument-hint: [optional note to capture]
4
5
  allowed-tools: Bash(bash:*)
@@ -1,4 +1,5 @@
1
1
  ---
2
+ name: restart
2
3
  description: Restart the reflexio backend and dashboard to pick up new changes
3
4
  allowed-tools: Bash(bash:*)
4
5
  ---