flowent 0.0.4 → 0.0.5

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 (311) hide show
  1. package/README.md +1 -1
  2. package/backend/README.md +74 -0
  3. package/backend/pyproject.toml +2 -1
  4. package/backend/src/flowent/__pycache__/__init__.cpython-313.pyc +0 -0
  5. package/backend/src/flowent/__pycache__/_version.cpython-313.pyc +0 -0
  6. package/backend/src/flowent/__pycache__/access.cpython-313.pyc +0 -0
  7. package/backend/src/flowent/__pycache__/agent.cpython-313.pyc +0 -0
  8. package/backend/src/flowent/__pycache__/assistant_commands.cpython-313.pyc +0 -0
  9. package/backend/src/flowent/__pycache__/cli.cpython-313.pyc +0 -0
  10. package/backend/src/flowent/__pycache__/config.cpython-313.pyc +0 -0
  11. package/backend/src/flowent/__pycache__/events.cpython-313.pyc +0 -0
  12. package/backend/src/flowent/__pycache__/graph_runtime.cpython-313.pyc +0 -0
  13. package/backend/src/flowent/__pycache__/graph_service.cpython-313.pyc +0 -0
  14. package/backend/src/flowent/__pycache__/image_assets.cpython-313.pyc +0 -0
  15. package/backend/src/flowent/__pycache__/logging.cpython-313.pyc +0 -0
  16. package/backend/src/flowent/__pycache__/main.cpython-313.pyc +0 -0
  17. package/backend/src/flowent/__pycache__/mcp_service.cpython-313.pyc +0 -0
  18. package/backend/src/flowent/__pycache__/model_metadata.cpython-313.pyc +0 -0
  19. package/backend/src/flowent/__pycache__/network.cpython-313.pyc +0 -0
  20. package/backend/src/flowent/__pycache__/{stats_service.cpython-313.pyc → observability_service.cpython-313.pyc} +0 -0
  21. package/backend/src/flowent/__pycache__/registry.cpython-313.pyc +0 -0
  22. package/backend/src/flowent/__pycache__/role_management.cpython-313.pyc +0 -0
  23. package/backend/src/flowent/__pycache__/runtime.cpython-313.pyc +0 -0
  24. package/backend/src/flowent/__pycache__/sandbox.cpython-313.pyc +0 -0
  25. package/backend/src/flowent/__pycache__/security.cpython-313.pyc +0 -0
  26. package/backend/src/flowent/__pycache__/settings.cpython-313.pyc +0 -0
  27. package/backend/src/flowent/__pycache__/settings_management.cpython-313.pyc +0 -0
  28. package/backend/src/flowent/__pycache__/state_db.cpython-313.pyc +0 -0
  29. package/backend/src/flowent/__pycache__/workspace_store.cpython-313.pyc +0 -0
  30. package/backend/src/flowent/agent.py +364 -52
  31. package/backend/src/flowent/assistant_commands.py +31 -22
  32. package/backend/src/flowent/channels/__pycache__/__init__.cpython-313.pyc +0 -0
  33. package/backend/src/flowent/channels/__pycache__/telegram.cpython-313.pyc +0 -0
  34. package/backend/src/flowent/channels/telegram.py +4 -4
  35. package/backend/src/flowent/graph_service.py +1307 -145
  36. package/backend/src/flowent/mcp_service.py +21 -7
  37. package/backend/src/flowent/model_metadata.py +4 -0
  38. package/backend/src/flowent/models/__init__.py +6 -2
  39. package/backend/src/flowent/models/__pycache__/__init__.cpython-313.pyc +0 -0
  40. package/backend/src/flowent/models/__pycache__/agent.cpython-313.pyc +0 -0
  41. package/backend/src/flowent/models/__pycache__/base.cpython-313.pyc +0 -0
  42. package/backend/src/flowent/models/__pycache__/blueprint.cpython-313.pyc +0 -0
  43. package/backend/src/flowent/models/__pycache__/content.cpython-313.pyc +0 -0
  44. package/backend/src/flowent/models/__pycache__/delta.cpython-313.pyc +0 -0
  45. package/backend/src/flowent/models/__pycache__/event.cpython-313.pyc +0 -0
  46. package/backend/src/flowent/models/__pycache__/graph.cpython-313.pyc +0 -0
  47. package/backend/src/flowent/models/__pycache__/history.cpython-313.pyc +0 -0
  48. package/backend/src/flowent/models/__pycache__/llm.cpython-313.pyc +0 -0
  49. package/backend/src/flowent/models/__pycache__/message.cpython-313.pyc +0 -0
  50. package/backend/src/flowent/models/__pycache__/tab.cpython-313.pyc +0 -0
  51. package/backend/src/flowent/models/__pycache__/todo.cpython-313.pyc +0 -0
  52. package/backend/src/flowent/models/agent.py +1 -0
  53. package/backend/src/flowent/models/graph.py +44 -9
  54. package/backend/src/flowent/models/history.py +73 -15
  55. package/backend/src/flowent/models/llm.py +1 -0
  56. package/backend/src/flowent/models/message.py +6 -0
  57. package/backend/src/flowent/models/tab.py +38 -1
  58. package/backend/src/flowent/{stats_service.py → observability_service.py} +4 -4
  59. package/backend/src/flowent/prompts/__pycache__/__init__.cpython-313.pyc +0 -0
  60. package/backend/src/flowent/prompts/__pycache__/common.cpython-313.pyc +0 -0
  61. package/backend/src/flowent/prompts/__pycache__/steward.cpython-313.pyc +0 -0
  62. package/backend/src/flowent/prompts/common.py +2 -2
  63. package/backend/src/flowent/prompts/steward.py +2 -2
  64. package/backend/src/flowent/providers/__pycache__/__init__.cpython-313.pyc +0 -0
  65. package/backend/src/flowent/providers/__pycache__/anthropic.cpython-313.pyc +0 -0
  66. package/backend/src/flowent/providers/__pycache__/base_url.cpython-313.pyc +0 -0
  67. package/backend/src/flowent/providers/__pycache__/configuration.cpython-313.pyc +0 -0
  68. package/backend/src/flowent/providers/__pycache__/content.cpython-313.pyc +0 -0
  69. package/backend/src/flowent/providers/__pycache__/errors.cpython-313.pyc +0 -0
  70. package/backend/src/flowent/providers/__pycache__/gateway.cpython-313.pyc +0 -0
  71. package/backend/src/flowent/providers/__pycache__/headers.cpython-313.pyc +0 -0
  72. package/backend/src/flowent/providers/__pycache__/management.cpython-313.pyc +0 -0
  73. package/backend/src/flowent/providers/__pycache__/openai.cpython-313.pyc +0 -0
  74. package/backend/src/flowent/providers/__pycache__/openai_responses.cpython-313.pyc +0 -0
  75. package/backend/src/flowent/providers/__pycache__/registry.cpython-313.pyc +0 -0
  76. package/backend/src/flowent/providers/__pycache__/sse.cpython-313.pyc +0 -0
  77. package/backend/src/flowent/providers/__pycache__/thinking.cpython-313.pyc +0 -0
  78. package/backend/src/flowent/providers/configuration.py +7 -0
  79. package/backend/src/flowent/role_management.py +12 -0
  80. package/backend/src/flowent/routes/__init__.py +0 -2
  81. package/backend/src/flowent/routes/__pycache__/__init__.cpython-313.pyc +0 -0
  82. package/backend/src/flowent/routes/__pycache__/access.cpython-313.pyc +0 -0
  83. package/backend/src/flowent/routes/__pycache__/assistant.cpython-313.pyc +0 -0
  84. package/backend/src/flowent/routes/__pycache__/image_assets.cpython-313.pyc +0 -0
  85. package/backend/src/flowent/routes/__pycache__/mcp.cpython-313.pyc +0 -0
  86. package/backend/src/flowent/routes/__pycache__/meta.cpython-313.pyc +0 -0
  87. package/backend/src/flowent/routes/__pycache__/nodes.cpython-313.pyc +0 -0
  88. package/backend/src/flowent/routes/__pycache__/prompts.cpython-313.pyc +0 -0
  89. package/backend/src/flowent/routes/__pycache__/providers_route.cpython-313.pyc +0 -0
  90. package/backend/src/flowent/routes/__pycache__/roles.cpython-313.pyc +0 -0
  91. package/backend/src/flowent/routes/__pycache__/settings.cpython-313.pyc +0 -0
  92. package/backend/src/flowent/routes/__pycache__/tabs.cpython-313.pyc +0 -0
  93. package/backend/src/flowent/routes/__pycache__/ws.cpython-313.pyc +0 -0
  94. package/backend/src/flowent/routes/assistant.py +4 -4
  95. package/backend/src/flowent/routes/nodes.py +54 -6
  96. package/backend/src/flowent/routes/providers_route.py +1 -0
  97. package/backend/src/flowent/routes/roles.py +1 -1
  98. package/backend/src/flowent/routes/settings.py +4 -0
  99. package/backend/src/flowent/routes/tabs.py +29 -11
  100. package/backend/src/flowent/runtime.py +7 -30
  101. package/backend/src/flowent/security.py +23 -8
  102. package/backend/src/flowent/settings.py +56 -5
  103. package/backend/src/flowent/settings_management.py +12 -0
  104. package/backend/src/flowent/static/assets/AssistantPage-VBohhz4d.js +1 -0
  105. package/backend/src/flowent/static/assets/ChannelsPage-CIydPZA_.js +1 -0
  106. package/backend/src/flowent/static/assets/McpPage-CHPm2TPY.js +7 -0
  107. package/backend/src/flowent/static/assets/PageScaffold-DteOA8V7.js +1 -0
  108. package/backend/src/flowent/static/assets/PromptsPage-CSmJ3sZg.js +1 -0
  109. package/backend/src/flowent/static/assets/ProvidersPage-sl2jeG4e.js +3 -0
  110. package/backend/src/flowent/static/assets/RolesPage-DCe7W6Km.js +1 -0
  111. package/backend/src/flowent/static/assets/SettingsPage-Bix9e63E.js +3 -0
  112. package/backend/src/flowent/static/assets/ToolsPage-favNkj5C.js +1 -0
  113. package/backend/src/flowent/static/assets/WorkspaceCommandDialog-DRS6wiD6.js +1 -0
  114. package/backend/src/flowent/static/assets/WorkspacePage-KuaDjt_D.js +3 -0
  115. package/backend/src/flowent/static/assets/WorkspacePanels-BZxBw8M5.js +1 -0
  116. package/backend/src/flowent/static/assets/alert-dialog-DIBUCmqM.js +1 -0
  117. package/backend/src/flowent/static/assets/{dialog-BeGSweF6.js → dialog-BOvHIBrg.js} +1 -1
  118. package/backend/src/flowent/static/assets/index-Biio-CoI.js +10 -0
  119. package/backend/src/flowent/static/assets/index-CmQvO7sl.css +1 -0
  120. package/backend/src/flowent/static/assets/modelParams-DcEhGnu0.js +1 -0
  121. package/backend/src/flowent/static/assets/roles-BbIEIMeG.js +1 -0
  122. package/backend/src/flowent/static/assets/select-D9SwnlXF.js +1 -0
  123. package/backend/src/flowent/static/assets/surface-Bzr1FRG4.js +1 -0
  124. package/backend/src/flowent/static/assets/{ui-vendor-Dg9NNnWX.js → ui-vendor-UazN8rcv.js} +15 -15
  125. package/backend/src/flowent/static/index.html +3 -4
  126. package/backend/src/flowent/tools/__init__.py +76 -2
  127. package/backend/src/flowent/tools/__pycache__/__init__.cpython-313.pyc +0 -0
  128. package/backend/src/flowent/tools/__pycache__/connect.cpython-313.pyc +0 -0
  129. package/backend/src/flowent/tools/__pycache__/contacts.cpython-313.pyc +0 -0
  130. package/backend/src/flowent/tools/__pycache__/create_agent.cpython-313.pyc +0 -0
  131. package/backend/src/flowent/tools/__pycache__/create_tab.cpython-313.pyc +0 -0
  132. package/backend/src/flowent/tools/__pycache__/delete_tab.cpython-313.pyc +0 -0
  133. package/backend/src/flowent/tools/__pycache__/edit.cpython-313.pyc +0 -0
  134. package/backend/src/flowent/tools/__pycache__/exec.cpython-313.pyc +0 -0
  135. package/backend/src/flowent/tools/__pycache__/fetch.cpython-313.pyc +0 -0
  136. package/backend/src/flowent/tools/__pycache__/idle.cpython-313.pyc +0 -0
  137. package/backend/src/flowent/tools/__pycache__/list_roles.cpython-313.pyc +0 -0
  138. package/backend/src/flowent/tools/__pycache__/list_tabs.cpython-313.pyc +0 -0
  139. package/backend/src/flowent/tools/__pycache__/list_tools.cpython-313.pyc +0 -0
  140. package/backend/src/flowent/tools/__pycache__/manage_prompts.cpython-313.pyc +0 -0
  141. package/backend/src/flowent/tools/__pycache__/manage_providers.cpython-313.pyc +0 -0
  142. package/backend/src/flowent/tools/__pycache__/manage_roles.cpython-313.pyc +0 -0
  143. package/backend/src/flowent/tools/__pycache__/manage_settings.cpython-313.pyc +0 -0
  144. package/backend/src/flowent/tools/__pycache__/mcp.cpython-313.pyc +0 -0
  145. package/backend/src/flowent/tools/__pycache__/read.cpython-313.pyc +0 -0
  146. package/backend/src/flowent/tools/__pycache__/send.cpython-313.pyc +0 -0
  147. package/backend/src/flowent/tools/__pycache__/set_permissions.cpython-313.pyc +0 -0
  148. package/backend/src/flowent/tools/__pycache__/sleep.cpython-313.pyc +0 -0
  149. package/backend/src/flowent/tools/__pycache__/todo.cpython-313.pyc +0 -0
  150. package/backend/src/flowent/tools/connect.py +10 -66
  151. package/backend/src/flowent/tools/contacts.py +1 -1
  152. package/backend/src/flowent/tools/create_agent.py +9 -88
  153. package/backend/src/flowent/tools/create_tab.py +7 -5
  154. package/backend/src/flowent/tools/exec.py +3 -2
  155. package/backend/src/flowent/tools/list_roles.py +29 -4
  156. package/backend/src/flowent/tools/list_tabs.py +4 -0
  157. package/backend/src/flowent/tools/list_tools.py +5 -1
  158. package/backend/src/flowent/tools/manage_settings.py +18 -0
  159. package/backend/src/flowent/tools/send.py +21 -3
  160. package/backend/src/flowent/tools/set_permissions.py +21 -6
  161. package/backend/tests/__pycache__/__init__.cpython-313.pyc +0 -0
  162. package/backend/tests/__pycache__/conftest.cpython-313-pytest-9.0.3.pyc +0 -0
  163. package/backend/tests/integration/api/__pycache__/conftest.cpython-313-pytest-9.0.3.pyc +0 -0
  164. package/backend/tests/integration/api/__pycache__/test_access_api.cpython-313-pytest-9.0.3.pyc +0 -0
  165. package/backend/tests/integration/api/__pycache__/test_assistant_api.cpython-313-pytest-9.0.3.pyc +0 -0
  166. package/backend/tests/integration/api/__pycache__/test_frontend_mounting.cpython-313-pytest-9.0.3.pyc +0 -0
  167. package/backend/tests/integration/api/__pycache__/test_mcp_api.cpython-313-pytest-9.0.3.pyc +0 -0
  168. package/backend/tests/integration/api/__pycache__/test_meta_api.cpython-313-pytest-9.0.3.pyc +0 -0
  169. package/backend/tests/integration/api/__pycache__/test_nodes_api.cpython-313-pytest-9.0.3.pyc +0 -0
  170. package/backend/tests/integration/api/__pycache__/test_prompts_api.cpython-313-pytest-9.0.3.pyc +0 -0
  171. package/backend/tests/integration/api/__pycache__/test_roles_api.cpython-313-pytest-9.0.3.pyc +0 -0
  172. package/backend/tests/integration/api/__pycache__/test_tabs_api.cpython-313-pytest-9.0.3.pyc +0 -0
  173. package/backend/tests/integration/api/test_assistant_api.py +1 -1
  174. package/backend/tests/integration/api/test_nodes_api.py +257 -21
  175. package/backend/tests/integration/api/test_roles_api.py +3 -2
  176. package/backend/tests/integration/api/test_tabs_api.py +312 -11
  177. package/backend/tests/unit/__pycache__/test_access.cpython-313-pytest-9.0.3.pyc +0 -0
  178. package/backend/tests/unit/__pycache__/test_cli.cpython-313-pytest-9.0.3.pyc +0 -0
  179. package/backend/tests/unit/__pycache__/test_graph_runtime.cpython-313-pytest-9.0.3.pyc +0 -0
  180. package/backend/tests/unit/__pycache__/test_network.cpython-313-pytest-9.0.3.pyc +0 -0
  181. package/backend/tests/unit/__pycache__/test_state_sqlite_storage.cpython-313-pytest-9.0.3.pyc +0 -0
  182. package/backend/tests/unit/__pycache__/test_workspace_store.cpython-313-pytest-9.0.3.pyc +0 -0
  183. package/backend/tests/unit/agent/__pycache__/test_agent_public_api.cpython-313-pytest-9.0.3.pyc +0 -0
  184. package/backend/tests/unit/agent/__pycache__/test_agent_runtime.cpython-313-pytest-9.0.3.pyc +0 -0
  185. package/backend/tests/unit/agent/test_agent_public_api.py +162 -71
  186. package/backend/tests/unit/agent/test_agent_runtime.py +285 -69
  187. package/backend/tests/unit/channels/__pycache__/test_telegram_channel.cpython-313-pytest-9.0.3.pyc +0 -0
  188. package/backend/tests/unit/logging/__pycache__/test_logging.cpython-313-pytest-9.0.3.pyc +0 -0
  189. package/backend/tests/unit/prompts/__pycache__/test_prompts.cpython-313-pytest-9.0.3.pyc +0 -0
  190. package/backend/tests/unit/prompts/test_prompts.py +3 -2
  191. package/backend/tests/unit/providers/__pycache__/test_anthropic_provider.cpython-313-pytest-9.0.3.pyc +0 -0
  192. package/backend/tests/unit/providers/__pycache__/test_errors.cpython-313-pytest-9.0.3.pyc +0 -0
  193. package/backend/tests/unit/providers/__pycache__/test_extract_delta_parts.cpython-313-pytest-9.0.3.pyc +0 -0
  194. package/backend/tests/unit/providers/__pycache__/test_openai_provider.cpython-313-pytest-9.0.3.pyc +0 -0
  195. package/backend/tests/unit/providers/__pycache__/test_openai_responses.cpython-313-pytest-9.0.3.pyc +0 -0
  196. package/backend/tests/unit/providers/__pycache__/test_provider_gateway.cpython-313-pytest-9.0.3.pyc +0 -0
  197. package/backend/tests/unit/providers/__pycache__/test_think_tag_parser.cpython-313-pytest-9.0.3.pyc +0 -0
  198. package/backend/tests/unit/routes/__pycache__/test_prompts_routes.cpython-313-pytest-9.0.3.pyc +0 -0
  199. package/backend/tests/unit/routes/__pycache__/test_providers_route.cpython-313-pytest-9.0.3.pyc +0 -0
  200. package/backend/tests/unit/routes/__pycache__/test_roles_routes.cpython-313-pytest-9.0.3.pyc +0 -0
  201. package/backend/tests/unit/routes/__pycache__/test_settings_routes.cpython-313-pytest-9.0.3.pyc +0 -0
  202. package/backend/tests/unit/routes/test_providers_route.py +2 -0
  203. package/backend/tests/unit/routes/test_roles_routes.py +109 -0
  204. package/backend/tests/unit/routes/test_settings_routes.py +4 -0
  205. package/backend/tests/unit/runtime/__pycache__/test_bootstrap_runtime.cpython-313-pytest-9.0.3.pyc +0 -0
  206. package/backend/tests/unit/runtime/test_bootstrap_runtime.py +8 -18
  207. package/backend/tests/unit/sandbox/__pycache__/test_sandbox_tools.cpython-313-pytest-9.0.3.pyc +0 -0
  208. package/backend/tests/unit/security/__pycache__/test_security.cpython-313-pytest-9.0.3.pyc +0 -0
  209. package/backend/tests/unit/security/test_security.py +16 -2
  210. package/backend/tests/unit/settings/__pycache__/test_settings_roles.cpython-313-pytest-9.0.3.pyc +0 -0
  211. package/backend/tests/unit/settings/test_settings_roles.py +40 -0
  212. package/backend/tests/unit/test_state_sqlite_storage.py +67 -1
  213. package/backend/tests/unit/tools/__pycache__/test_connect_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  214. package/backend/tests/unit/tools/__pycache__/test_create_agent_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  215. package/backend/tests/unit/tools/__pycache__/test_delete_tab_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  216. package/backend/tests/unit/tools/__pycache__/test_edit_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  217. package/backend/tests/unit/tools/__pycache__/test_exec_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  218. package/backend/tests/unit/tools/__pycache__/test_fetch_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  219. package/backend/tests/unit/tools/__pycache__/test_manage_prompts_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  220. package/backend/tests/unit/tools/__pycache__/test_manage_providers_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  221. package/backend/tests/unit/tools/__pycache__/test_manage_roles_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  222. package/backend/tests/unit/tools/__pycache__/test_manage_settings_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  223. package/backend/tests/unit/tools/__pycache__/test_read_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  224. package/backend/tests/unit/tools/__pycache__/test_set_permissions_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  225. package/backend/tests/unit/tools/__pycache__/test_todo_tool.cpython-313-pytest-9.0.3.pyc +0 -0
  226. package/backend/tests/unit/tools/__pycache__/test_tool_registry.cpython-313-pytest-9.0.3.pyc +0 -0
  227. package/backend/tests/unit/tools/test_connect_tool.py +2 -3
  228. package/backend/tests/unit/tools/test_create_agent_tool.py +9 -97
  229. package/backend/tests/unit/tools/test_delete_tab_tool.py +33 -0
  230. package/backend/tests/unit/tools/test_manage_providers_tool.py +2 -0
  231. package/backend/tests/unit/tools/test_manage_settings_tool.py +3 -0
  232. package/backend/tests/unit/tools/test_set_permissions_tool.py +216 -12
  233. package/backend/tests/unit/tools/test_tool_registry.py +103 -0
  234. package/backend/uv.lock +1 -1
  235. package/dist/frontend/assets/AssistantPage-VBohhz4d.js +1 -0
  236. package/dist/frontend/assets/ChannelsPage-CIydPZA_.js +1 -0
  237. package/dist/frontend/assets/McpPage-CHPm2TPY.js +7 -0
  238. package/dist/frontend/assets/PageScaffold-DteOA8V7.js +1 -0
  239. package/dist/frontend/assets/PromptsPage-CSmJ3sZg.js +1 -0
  240. package/dist/frontend/assets/ProvidersPage-sl2jeG4e.js +3 -0
  241. package/dist/frontend/assets/RolesPage-DCe7W6Km.js +1 -0
  242. package/dist/frontend/assets/SettingsPage-Bix9e63E.js +3 -0
  243. package/dist/frontend/assets/ToolsPage-favNkj5C.js +1 -0
  244. package/dist/frontend/assets/WorkspaceCommandDialog-DRS6wiD6.js +1 -0
  245. package/dist/frontend/assets/WorkspacePage-KuaDjt_D.js +3 -0
  246. package/dist/frontend/assets/WorkspacePanels-BZxBw8M5.js +1 -0
  247. package/dist/frontend/assets/alert-dialog-DIBUCmqM.js +1 -0
  248. package/dist/frontend/assets/{dialog-BeGSweF6.js → dialog-BOvHIBrg.js} +1 -1
  249. package/dist/frontend/assets/index-Biio-CoI.js +10 -0
  250. package/dist/frontend/assets/index-CmQvO7sl.css +1 -0
  251. package/dist/frontend/assets/modelParams-DcEhGnu0.js +1 -0
  252. package/dist/frontend/assets/roles-BbIEIMeG.js +1 -0
  253. package/dist/frontend/assets/select-D9SwnlXF.js +1 -0
  254. package/dist/frontend/assets/surface-Bzr1FRG4.js +1 -0
  255. package/dist/frontend/assets/{ui-vendor-Dg9NNnWX.js → ui-vendor-UazN8rcv.js} +15 -15
  256. package/dist/frontend/index.html +3 -4
  257. package/package.json +3 -3
  258. package/backend/src/flowent/routes/__pycache__/stats.cpython-313.pyc +0 -0
  259. package/backend/src/flowent/routes/stats.py +0 -229
  260. package/backend/src/flowent/static/assets/AssistantPage-B3Xc08AS.js +0 -1
  261. package/backend/src/flowent/static/assets/ChannelsPage-ByLd28xk.js +0 -1
  262. package/backend/src/flowent/static/assets/HomePage-C0hAx9_l.js +0 -3
  263. package/backend/src/flowent/static/assets/McpPage-DkrYLvBv.js +0 -7
  264. package/backend/src/flowent/static/assets/PageScaffold-D4jO9ooX.js +0 -1
  265. package/backend/src/flowent/static/assets/PromptsPage-DWA7rRJd.js +0 -1
  266. package/backend/src/flowent/static/assets/ProvidersPage-PUWT8seJ.js +0 -3
  267. package/backend/src/flowent/static/assets/RolesPage-CqcclGRw.js +0 -1
  268. package/backend/src/flowent/static/assets/SettingsPage-8tS2cJgX.js +0 -3
  269. package/backend/src/flowent/static/assets/StatsPage-BX9khYzu.js +0 -1
  270. package/backend/src/flowent/static/assets/ToolsPage-9Tl9FdeD.js +0 -1
  271. package/backend/src/flowent/static/assets/WorkspaceCommandDialog-CCXxjDL8.js +0 -1
  272. package/backend/src/flowent/static/assets/WorkspacePanels-aMdJ7ZH7.js +0 -1
  273. package/backend/src/flowent/static/assets/alert-dialog-kFYVQ7oX.js +0 -1
  274. package/backend/src/flowent/static/assets/badge-74-3jsCg.js +0 -1
  275. package/backend/src/flowent/static/assets/constants-XUzFf6i1.js +0 -1
  276. package/backend/src/flowent/static/assets/index-BHC1Vhy8.css +0 -1
  277. package/backend/src/flowent/static/assets/index-CL1ALZ3r.js +0 -10
  278. package/backend/src/flowent/static/assets/modelParams-CaHd0903.js +0 -1
  279. package/backend/src/flowent/static/assets/roles-2OLDeTc5.js +0 -1
  280. package/backend/src/flowent/static/assets/select-DL_LPeDj.js +0 -1
  281. package/backend/src/flowent/static/assets/shared-CMxbpLeQ.js +0 -1
  282. package/backend/tests/unit/routes/__pycache__/test_stats_routes.cpython-313-pytest-9.0.3.pyc +0 -0
  283. package/backend/tests/unit/routes/test_stats_routes.py +0 -149
  284. package/dist/frontend/assets/AssistantPage-B3Xc08AS.js +0 -1
  285. package/dist/frontend/assets/ChannelsPage-ByLd28xk.js +0 -1
  286. package/dist/frontend/assets/HomePage-C0hAx9_l.js +0 -3
  287. package/dist/frontend/assets/McpPage-DkrYLvBv.js +0 -7
  288. package/dist/frontend/assets/PageScaffold-D4jO9ooX.js +0 -1
  289. package/dist/frontend/assets/PromptsPage-DWA7rRJd.js +0 -1
  290. package/dist/frontend/assets/ProvidersPage-PUWT8seJ.js +0 -3
  291. package/dist/frontend/assets/RolesPage-CqcclGRw.js +0 -1
  292. package/dist/frontend/assets/SettingsPage-8tS2cJgX.js +0 -3
  293. package/dist/frontend/assets/StatsPage-BX9khYzu.js +0 -1
  294. package/dist/frontend/assets/ToolsPage-9Tl9FdeD.js +0 -1
  295. package/dist/frontend/assets/WorkspaceCommandDialog-CCXxjDL8.js +0 -1
  296. package/dist/frontend/assets/WorkspacePanels-aMdJ7ZH7.js +0 -1
  297. package/dist/frontend/assets/alert-dialog-kFYVQ7oX.js +0 -1
  298. package/dist/frontend/assets/badge-74-3jsCg.js +0 -1
  299. package/dist/frontend/assets/constants-XUzFf6i1.js +0 -1
  300. package/dist/frontend/assets/index-BHC1Vhy8.css +0 -1
  301. package/dist/frontend/assets/index-CL1ALZ3r.js +0 -10
  302. package/dist/frontend/assets/modelParams-CaHd0903.js +0 -1
  303. package/dist/frontend/assets/roles-2OLDeTc5.js +0 -1
  304. package/dist/frontend/assets/select-DL_LPeDj.js +0 -1
  305. package/dist/frontend/assets/shared-CMxbpLeQ.js +0 -1
  306. /package/backend/src/flowent/static/assets/{datetime-m6_O_Ci9.js → datetime-eJqd0V2S.js} +0 -0
  307. /package/backend/src/flowent/static/assets/{markdown-vendor-DVdy_w12.js → markdown-vendor-C9RtvaJh.js} +0 -0
  308. /package/backend/src/flowent/static/assets/{triState-DEr3NkXV.js → triState-DgLlKdRR.js} +0 -0
  309. /package/dist/frontend/assets/{datetime-m6_O_Ci9.js → datetime-eJqd0V2S.js} +0 -0
  310. /package/dist/frontend/assets/{markdown-vendor-DVdy_w12.js → markdown-vendor-C9RtvaJh.js} +0 -0
  311. /package/dist/frontend/assets/{triState-DEr3NkXV.js → triState-DgLlKdRR.js} +0 -0
@@ -69,6 +69,7 @@ You are the Conductor role currently used by a workflow's Leader.
69
69
 
70
70
  Your responsibilities:
71
71
  - Receive execution briefs from the Assistant for this workflow through the workflow's Leader identity
72
+ - Receive direct task input from the Human through the current workflow chat
72
73
  - Decide how the task should be decomposed inside the current workflow
73
74
  - Design, expand, adjust, and simplify this workflow's Workflow Graph as the work evolves
74
75
  - Coordinate agents, aggregate their results, and return a coherent result upstream to the Assistant
@@ -89,11 +90,12 @@ Your responsibilities:
89
90
  - Prefer multi-agent parallelism over serial single-agent execution. If subtasks are independent, create separate nodes for them rather than assigning everything to one Worker.
90
91
  - Prefer adding peer nodes to the current workflow with `create_agent`, then wire them with `connect` to match the topology you want.
91
92
  - Treat this workflow as the execution boundary. Do not push internal Workflow Graph design back to the Assistant.
93
+ - If the task belongs in another workflow, or requires browsing, creating, deleting, switching, or choosing another workflow, send the request back to the Assistant instead of trying to inspect or change other workflows yourself.
92
94
  - Do not treat any single topology as the default. Match the network design to the task's decomposition, dependencies, and coordination needs.
93
95
 
94
96
  ## Workflow
95
97
 
96
- 1. **Receive** the brief from the Assistant as the current workflow's Leader
98
+ 1. **Receive** the brief from the Assistant or the direct Human task from the current workflow chat
97
99
  2. **Plan** using `todo` - break into subtasks, decide what to delegate, and design the network structure that best fits the work
98
100
  3. **Inspect roles** with `list_roles`; use `list_tools` for a full tool inventory
99
101
  4. **Create the network structure** with `create_agent` and `connect`
@@ -105,6 +107,8 @@ Your responsibilities:
105
107
  ## Guidelines
106
108
 
107
109
  - Prefer `create_agent` and `connect` as the primary control plane for the current workflow
110
+ - If the workflow is Active, direct Human input in workflow chat can start collaborative execution through you and your `send` coordination
111
+ - If the workflow is Inactive, use workflow chat for discussion, planning, and structure preparation; do not send work to ordinary agent nodes until the workflow is activated
108
112
  - Do not create a node and then `idle` without dispatching work unless you intentionally want the new node to stay idle
109
113
  - Your default posture is orchestration, not being the long-running executor for specialized work
110
114
  - When a task is primarily frontend implementation, UI design, visual design, page redesign, or interaction refinement, prefer creating a Designer node for that work
@@ -139,7 +143,6 @@ WORKER_ROLE_INCLUDED_TOOLS = ["read", "exec"]
139
143
  CONDUCTOR_ROLE_INCLUDED_TOOLS = [
140
144
  "create_agent",
141
145
  "connect",
142
- "list_workflows",
143
146
  "list_roles",
144
147
  "list_tools",
145
148
  ]
@@ -221,6 +224,7 @@ class ProviderModelCatalogEntry:
221
224
  context_window_tokens: int | None = None
222
225
  input_image: bool | None = None
223
226
  output_image: bool | None = None
227
+ structured_output: bool | None = None
224
228
 
225
229
 
226
230
  @dataclass
@@ -335,6 +339,7 @@ class ModelSettings:
335
339
  active_model: str = ""
336
340
  input_image: bool | None = None
337
341
  output_image: bool | None = None
342
+ structured_output: bool | None = None
338
343
  context_window_tokens: int | None = None
339
344
  params: ModelParams = field(default_factory=build_default_model_params)
340
345
  timeout_ms: int = DEFAULT_LLM_TIMEOUT_MS
@@ -585,6 +590,18 @@ def build_model_output_image(
585
590
  return raw_output_image
586
591
 
587
592
 
593
+ def build_model_structured_output(
594
+ raw_structured_output: object,
595
+ *,
596
+ field_name: str = "model.structured_output",
597
+ ) -> bool | None:
598
+ if raw_structured_output is None:
599
+ return None
600
+ if not isinstance(raw_structured_output, bool):
601
+ raise ValueError(f"{field_name} must be a boolean or null")
602
+ return raw_structured_output
603
+
604
+
588
605
  def build_model_context_window_tokens(
589
606
  raw_context_window_tokens: object,
590
607
  *,
@@ -916,6 +933,9 @@ def _normalize_provider_model_catalog_entries(
916
933
  output_image, output_image_migrated = _normalize_nullable_bool(
917
934
  raw_entry.get("output_image")
918
935
  )
936
+ structured_output, structured_output_migrated = _normalize_nullable_bool(
937
+ raw_entry.get("structured_output")
938
+ )
919
939
  context_window_tokens, context_window_tokens_migrated = _normalize_positive_int(
920
940
  raw_entry.get("context_window_tokens")
921
941
  )
@@ -924,6 +944,7 @@ def _normalize_provider_model_catalog_entries(
924
944
  or source_migrated
925
945
  or input_image_migrated
926
946
  or output_image_migrated
947
+ or structured_output_migrated
927
948
  or context_window_tokens_migrated
928
949
  or model != raw_model
929
950
  or model in entries_by_model
@@ -934,6 +955,7 @@ def _normalize_provider_model_catalog_entries(
934
955
  context_window_tokens=context_window_tokens,
935
956
  input_image=input_image,
936
957
  output_image=output_image,
958
+ structured_output=structured_output,
937
959
  )
938
960
  return list(entries_by_model.values()), migrated
939
961
 
@@ -971,6 +993,7 @@ def serialize_provider_model_catalog_entry(
971
993
  "context_window_tokens": entry.context_window_tokens,
972
994
  "input_image": entry.input_image,
973
995
  "output_image": entry.output_image,
996
+ "structured_output": entry.structured_output,
974
997
  }
975
998
 
976
999
 
@@ -1062,6 +1085,7 @@ def serialize_settings(
1062
1085
  model_id=settings.model.active_model,
1063
1086
  input_image=settings.model.input_image,
1064
1087
  output_image=settings.model.output_image,
1088
+ structured_output=settings.model.structured_output,
1065
1089
  context_window_tokens=settings.model.context_window_tokens,
1066
1090
  )
1067
1091
  data["model"]["capabilities"] = (
@@ -1106,6 +1130,7 @@ def resolve_model_info(
1106
1130
  model_id: str,
1107
1131
  input_image: bool | None = None,
1108
1132
  output_image: bool | None = None,
1133
+ structured_output: bool | None = None,
1109
1134
  context_window_tokens: int | None = None,
1110
1135
  ):
1111
1136
  from flowent.model_metadata import build_model_info
@@ -1128,6 +1153,13 @@ def resolve_model_info(
1128
1153
  if catalog_entry is not None
1129
1154
  else None
1130
1155
  ),
1156
+ structured_output=(
1157
+ structured_output
1158
+ if structured_output is not None
1159
+ else catalog_entry.structured_output
1160
+ if catalog_entry is not None
1161
+ else None
1162
+ ),
1131
1163
  context_window_tokens=(
1132
1164
  context_window_tokens
1133
1165
  if context_window_tokens is not None
@@ -1987,6 +2019,9 @@ def _build_settings(data: dict[str, object]) -> tuple[Settings, bool]:
1987
2019
  output_image, migrated_output_image = _normalize_nullable_bool(
1988
2020
  model_data.get("output_image")
1989
2021
  )
2022
+ structured_output, migrated_structured_output = _normalize_nullable_bool(
2023
+ model_data.get("structured_output")
2024
+ )
1990
2025
  context_window_tokens, migrated_context_window_tokens = _normalize_positive_int(
1991
2026
  model_data.get("context_window_tokens")
1992
2027
  )
@@ -2019,6 +2054,7 @@ def _build_settings(data: dict[str, object]) -> tuple[Settings, bool]:
2019
2054
  active_model=str(model_data.get("active_model", "")),
2020
2055
  input_image=input_image,
2021
2056
  output_image=output_image,
2057
+ structured_output=structured_output,
2022
2058
  context_window_tokens=context_window_tokens,
2023
2059
  params=model_params,
2024
2060
  timeout_ms=model_timeout_ms,
@@ -2033,6 +2069,7 @@ def _build_settings(data: dict[str, object]) -> tuple[Settings, bool]:
2033
2069
  migrated
2034
2070
  or migrated_input_image
2035
2071
  or migrated_output_image
2072
+ or migrated_structured_output
2036
2073
  or migrated_context_window_tokens
2037
2074
  or migrated_auto_compact_token_limit
2038
2075
  )
@@ -2133,6 +2170,22 @@ def _build_settings(data: dict[str, object]) -> tuple[Settings, bool]:
2133
2170
  )
2134
2171
  migrated = migrated or role_description_migrated
2135
2172
 
2173
+ included_tools = normalize_tool_names(
2174
+ [name for name in included_tools_raw if isinstance(name, str)]
2175
+ )
2176
+ from flowent.tools import (
2177
+ is_assistant_only_mcp_tool_name,
2178
+ is_assistant_only_tool_name,
2179
+ )
2180
+
2181
+ filtered_included_tools = [
2182
+ tool_name
2183
+ for tool_name in included_tools
2184
+ if not is_assistant_only_tool_name(tool_name)
2185
+ and not is_assistant_only_mcp_tool_name(tool_name)
2186
+ ]
2187
+ migrated = migrated or filtered_included_tools != included_tools
2188
+
2136
2189
  roles.append(
2137
2190
  RoleConfig(
2138
2191
  name=role_name,
@@ -2140,9 +2193,7 @@ def _build_settings(data: dict[str, object]) -> tuple[Settings, bool]:
2140
2193
  description=role_description,
2141
2194
  model=role_model,
2142
2195
  model_params=role_model_params,
2143
- included_tools=normalize_tool_names(
2144
- [name for name in included_tools_raw if isinstance(name, str)]
2145
- ),
2196
+ included_tools=filtered_included_tools,
2146
2197
  excluded_tools=normalize_tool_names(
2147
2198
  [name for name in excluded_tools_raw if isinstance(name, str)]
2148
2199
  ),
@@ -22,6 +22,7 @@ from flowent.settings import (
22
22
  build_model_retry_initial_delay_seconds,
23
23
  build_model_retry_max_delay_seconds,
24
24
  build_model_retry_policy,
25
+ build_model_structured_output,
25
26
  build_model_timeout_ms,
26
27
  build_working_dir,
27
28
  find_role,
@@ -83,6 +84,7 @@ def resolve_settings_update(
83
84
  context_window_tokens: object = MISSING,
84
85
  input_image: object = MISSING,
85
86
  output_image: object = MISSING,
87
+ structured_output: object = MISSING,
86
88
  max_retries: object = MISSING,
87
89
  retry_policy: object = MISSING,
88
90
  timeout_ms: object = MISSING,
@@ -105,6 +107,7 @@ def resolve_settings_update(
105
107
  retry_backoff_cap_retries_field_name: str = "model.retry_backoff_cap_retries",
106
108
  input_image_field_name: str = "model.input_image",
107
109
  output_image_field_name: str = "model.output_image",
110
+ structured_output_field_name: str = "model.structured_output",
108
111
  context_window_tokens_field_name: str = "model.context_window_tokens",
109
112
  auto_compact_token_limit_field_name: str = "model.auto_compact_token_limit",
110
113
  ) -> ResolvedSettingsUpdate:
@@ -176,6 +179,14 @@ def resolve_settings_update(
176
179
  field_name=output_image_field_name,
177
180
  )
178
181
  )
182
+ next_structured_output = (
183
+ settings.model.structured_output
184
+ if structured_output is MISSING
185
+ else build_model_structured_output(
186
+ structured_output,
187
+ field_name=structured_output_field_name,
188
+ )
189
+ )
179
190
  next_retry_policy = (
180
191
  settings.model.retry_policy
181
192
  if retry_policy is MISSING
@@ -261,6 +272,7 @@ def resolve_settings_update(
261
272
  active_model=next_active_model,
262
273
  input_image=next_input_image,
263
274
  output_image=next_output_image,
275
+ structured_output=next_structured_output,
264
276
  context_window_tokens=next_context_window_tokens,
265
277
  params=next_model_params,
266
278
  timeout_ms=next_timeout_ms,
@@ -0,0 +1 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{q as r}from"./ui-vendor-UazN8rcv.js";import{A as i,C as a,D as o,E as s,M as c,N as l,O as u,S as d,T as ee,_ as te,b as ne,g as re,h as ie,j as ae,k as oe,m as f,t as p,v as se,w as ce,x as m,y as le}from"./WorkspacePanels-BZxBw8M5.js";import{B as h,L as g,P as ue,R as _,S as v,b as y,g as b,h as x,m as de,p as fe,rt as S,tt as C,x as pe}from"./index-Biio-CoI.js";async function me(e){return h(`/api/assistant/message`,{method:`POST`,body:e,errorMessage:`Failed to send Assistant message`})}async function he(e){return h(`/api/assistant/messages/${e}/retry`,{method:`POST`,errorMessage:`Failed to retry Assistant message`})}var w=e(t(),1);function T(e){for(let t of e.values())if(t.node_type===`assistant`)return t;return null}function ge(e){return T(e)?.id??null}var E=`assistant`;function _e(){return s(E)}function ve(e){return o(E,e)}function ye(e){ee(E,e)}function D(e={}){let{bottomInset:t=0}=e,{agents:n}=b(),{connected:i}=de(),{agentHistories:o,clearAgentHistory:s,clearHistorySnapshot:c,historyInvalidatedAt:ee,historyClearedAt:ae,historySnapshots:p,streamingDeltas:h}=x(),{activeToolCalls:S}=fe(),[C,T]=(0,w.useState)(null),[E,D]=(0,w.useState)(0),[O,k]=(0,w.useState)(``),[A,j]=(0,w.useState)([]),[M,N]=(0,w.useState)(null),[be,xe]=(0,w.useState)(!1),[Se,Ce]=(0,w.useState)(null),[P,we]=(0,w.useState)(!1),[F,I]=(0,w.useState)([]),[L,R]=(0,w.useState)(null),z=(0,w.useRef)(null),B=(0,w.useRef)(!0),Te=(0,w.useRef)([]),V=(0,w.useRef)(null),H=(0,w.useRef)(!1),U=(0,w.useMemo)(()=>ge(n),[n]),W=(0,w.useMemo)(()=>U?n.get(U)??null:null,[n,U]),Ee=W?.capabilities?.input_image??!1,De=U?ae.get(U)??0:0,Oe=U?ee.get(U)??0:0,G=U?p.get(U)??null:null,ke=A.some(e=>e.status===`uploading`),Ae=A.filter(le),K=(0,w.useSyncExternalStore)(ve,_e,_e),q=M===null?null:K[M]??null,je=q!==null&&O===q.text&&se(A,q),J=W?.state??C?.state??null,Me=(0,w.useCallback)(async e=>{let t=e.pendingMessageTimestamp??Date.now(),n=ie(e.content,e.parts,t);we(!0),I(e=>[...e,n]);try{let n=await me({content:e.content,parts:e.parts});return n.status===`command_executed`?I(n=>y(n,{content:e.content,timestamp:t})):n.message_id&&I(r=>r.map(r=>r.timestamp===t&&r.content===e.content?{...r,message_id:n.message_id}:r)),ye(e.history),e.restoreDraft&&d(e.restoreDraft.images),!0}catch(n){return I(n=>y(n,{content:e.content,timestamp:t})),e.restoreDraft&&(k(e.restoreDraft.input),j(e.restoreDraft.images),N(e.restoreDraft.historyCursor)),r.error(n instanceof Error?n.message:`Failed to send message`),!1}finally{we(!1)}},[]),Y=(0,w.useCallback)((e,t)=>{N(t),k(e?.text??``),j(e?a(e):[])},[]),Ne=(0,w.useCallback)(e=>{N(null),k(e)},[]);(0,w.useEffect)(()=>{Te.current=A},[A]),(0,w.useEffect)(()=>{V.current=L},[L]),(0,w.useEffect)(()=>()=>{d(Te.current)},[]),(0,w.useEffect)(()=>{De&&(I([]),R(null),T(e=>e&&{...e,history:u(e.history)}),D(Date.now()))},[De]),(0,w.useEffect)(()=>{Oe&&(I([]),G&&(T(e=>e&&{...e,history:G}),D(Date.now())))},[Oe,G]),(0,w.useEffect)(()=>{let e=V.current;!e||e.send_failed||e.target_id!==U||J!==e.target_state&&R({...e,target_state:J})},[U,J]),(0,w.useEffect)(()=>{let e=V.current;!e||e.send_failed||!U||e.target_id!==U||J!==`idle`||P||H.current||(H.current=!0,R(null),Me({content:e.content,parts:e.parts??[],history:e.history_entry,pendingMessageTimestamp:e.timestamp}).then(t=>{H.current=!1,t||R({...e,send_failed:!0,target_state:`error`})}).catch(()=>{H.current=!1,R({...e,send_failed:!0,target_state:`error`})}))},[U,J,P,Me]),(0,w.useEffect)(()=>{if(!i||!U){T(null);return}let e=new AbortController,t=!1;return(async()=>{s(U);try{let n=await g(U,e.signal);if(t||!n)return;T(n),D(Date.now()),c(U)}catch{!t&&!e.signal.aborted&&r.error(`Failed to load Assistant history`)}})(),()=>{t=!0,e.abort()}},[De,Oe,U,s,c,i]);let X=(0,w.useMemo)(()=>U?oe({history:G??C?.history??[],incremental:o.get(U),deltas:h.get(U),fetchedAt:E||Date.now()}):[],[o,G,C,E,h,U]);(0,w.useEffect)(()=>{if(!U||F.length===0)return;let e=X.filter(e=>e.type===`ReceivedMessage`&&e.from_id===`human`&&(!!e.content||!!e.message_id||!!e.parts?.length));e.length!==0&&I(t=>e.reduce((e,t)=>y(e,{content:t.content??pe(t.parts,t.content),messageId:t.message_id}),t))},[U,X,F.length]);let Z=(0,w.useMemo)(()=>[...X,...L?[{...L}]:[],...F.map(e=>({...e}))],[X,F,L]),Q=(0,w.useMemo)(()=>{let e=F.length+ +!!L,t=U?h.get(U)??[]:[],n=i&&(e>0||W?.state===`running`||W?.state===`sleeping`||S.has(U??``)||t.length>0),r=[...Z].map((e,t)=>({item:e,index:t})).reverse().find(({item:e})=>e.type===`PendingHumanMessage`?!0:e.type===`ReceivedMessage`&&e.from_id===`human`&&v(e.parts,e.content).length>0)?.index,a=r===void 0?[]:Z.slice(r+1),o=a.some(e=>e.type===`AssistantText`&&v(e.parts,e.content).length>0),s=[...a].reverse().find(e=>e.type===`ToolCall`&&e.streaming===!0),c=(U?S.get(U)??null:null)??s?.tool_name??null;return{running:n,runningHint:n&&r!==void 0&&!o?{label:c?`Running tools...`:`Thinking...`,toolName:c}:null}},[S,U,W?.state,i,F.length,L,h,Z]);(0,w.useLayoutEffect)(()=>{let e=z.current;!e||!B.current||(e.scrollTop=e.scrollHeight)},[t,Q.runningHint?`${Q.runningHint.label}:${Q.runningHint.toolName??``}`:``,Z]),(0,w.useLayoutEffect)(()=>{let e=z.current;if(!e||typeof ResizeObserver>`u`)return;let t=new ResizeObserver(()=>{B.current&&(e.scrollTop=e.scrollHeight)});return t.observe(e),()=>{t.disconnect()}},[]);let Pe=e=>{B.current=ne(e.currentTarget)},$=async(e={})=>{let t=O.trim();if(!t&&Ae.length===0||ke||P)return;let n=f(t,Ae),i=O,a=A,o=M,s=Date.now(),c=t||pe(n),l={text:i,images:ce(a),timestamp:s},u=e.deferWhenBusy&&U&&V.current?.target_id===U&&(J===`error`||J===`terminated`);if(e.deferWhenBusy&&U&&(J===`running`||J===`sleeping`||u)){R(re({content:c,historyEntry:l,historyScope:`assistant`,parts:n,targetId:U,targetState:J,timestamp:s})),N(null),k(``),j([]),d(a);return}if(J===`error`||J===`terminated`){r.error(`Resolve the current chat before sending`);return}N(null),k(``),j([]),await Me({content:c,parts:n,history:l,pendingMessageTimestamp:s,restoreDraft:{input:i,images:a,historyCursor:o}})},Fe=(0,w.useCallback)(async e=>{if(N(null),!Ee){r.error(`Current model does not support image input`);return}let t=Array.from(e).filter(e=>e.type.startsWith(`image/`));if(t.length===0)return;let n=await te(t);j(e=>[...e,...n]),await Promise.all(n.map(async(e,n)=>{let i=t[n];if(i)try{let t=await l(i);j(n=>n.map(n=>n.id===e.id?{...n,assetId:t.id,mimeType:t.mime_type,width:typeof t.width==`number`?t.width:n.width,height:typeof t.height==`number`?t.height:n.height,status:`ready`}:n))}catch(t){m(e),j(t=>t.filter(t=>t.id!==e.id)),r.error(t instanceof Error?t.message:`Failed to upload image`)}}))},[Ee]),Ie=(0,w.useCallback)(e=>{N(null),j(t=>{let n=t.find(t=>t.id===e);return n&&m(n),t.filter(t=>t.id!==e)})},[]),Le=(0,w.useCallback)((e,t)=>{if(K.length===0)return!1;let n=t.start,r=t.end,i=O.length===0&&A.length===0,a=typeof n==`number`&&typeof r==`number`&&n===r&&(n===0||n===O.length);if(!i&&!(q!==null&&je&&a))return!1;if(M===null){if(e!==-1)return!1;let t=K.length-1;return Y(K[t]??null,t),!0}if(e===-1){let e=Math.max(M-1,0);return Y(K[e]??null,e),!0}if(M>=K.length-1)return Y(null,null),!0;let o=M+1;return Y(K[o]??null,o),!0},[q,A,M,O,K,je,Y]),Re=async()=>{if(!(!U||be)){xe(!0);try{await ue(U),I([]),R(null),s(U),T(await g(U)),D(Date.now()),c(U)}catch(e){r.error(e instanceof Error?e.message:`Failed to clear assistant chat`)}finally{xe(!1)}}},ze=(0,w.useCallback)(async()=>{if(U&&!(W?.state!==`running`&&W?.state!==`sleeping`)){await _(U);for(let e=0;e<25;e+=1){let e=await g(U);if(!e)break;if(T(e),D(Date.now()),e.state!==`running`&&e.state!==`sleeping`)return;await new Promise(e=>window.setTimeout(e,120))}throw Error(`Assistant did not stop in time`)}},[U,W?.state]),Be=async e=>{if(!(!U||!e||Se)){Ce(e);try{try{await ze(),await he(e)}catch(e){r.error(e instanceof Error?e.message:`Failed to retry Assistant message`);return}s(U);try{let e=await g(U);e&&(T(e),D(Date.now()),c(U))}catch{return}}finally{Ce(null)}}},Ve=(0,w.useCallback)(async()=>{if(!U)return;await _(U),I([]),s(U);let e=await g(U);e&&(T(e),D(Date.now()),c(U))},[U,s,c]);return{addImages:Fe,connected:i,draftImages:A,handleKeyDown:e=>{if(e.key===`Tab`&&!e.shiftKey){(O.trim()||Ae.length>0)&&(e.preventDefault(),$({deferWhenBusy:!0}));return}e.key===`Enter`&&!e.shiftKey&&(e.preventDefault(),$())},hasUploadingImages:ke,input:O,isBrowsingInputHistory:je,navigateInputHistory:Le,onMessagesScroll:Pe,removeImage:Ie,retryMessage:Be,retryingMessageId:Se,scrollRef:z,clearing:be,sending:P,clearChat:Re,cancelPendingSend:(0,w.useCallback)(e=>{R(t=>t?.id===e?null:t)},[]),sendMessage:$,setInput:Ne,stopAssistant:Ve,supportsInputImage:Ee,timelineItems:Z,assistantActivity:Q}}var O=n();function k({onOpenDetails:e}){let{agents:t}=b(),[n,a]=(0,w.useState)(!1),{height:o,ref:s}=i(),{addImages:l=async()=>{},assistantActivity:u={running:!1,runningHint:null},clearChat:d,cancelPendingSend:ee,clearing:te=!1,connected:ne,draftImages:re=[],handleKeyDown:ie,hasUploadingImages:oe=!1,input:f,isBrowsingInputHistory:p,navigateInputHistory:se,onMessagesScroll:ce,removeImage:m=()=>{},retryMessage:le,retryingMessageId:h,scrollRef:g,sending:ue,sendMessage:_,setInput:v,stopAssistant:y,supportsInputImage:x=!1,timelineItems:de}=D({bottomInset:o}),fe=Array.from(t.values()).find(e=>e.node_type===`assistant`)?.role_name??null;return(0,O.jsxs)(`div`,{className:S(`relative flex h-full flex-col overflow-hidden bg-surface-overlay text-foreground`),children:[(0,O.jsx)(`div`,{"aria-hidden":`true`,className:`pointer-events-none absolute inset-0`,style:{background:`var(--shell-surface-sweep)`}}),(0,O.jsx)(`div`,{"aria-hidden":`true`,className:`pointer-events-none absolute inset-x-0 top-0 h-px`,style:{background:`var(--shell-hairline)`}}),(0,O.jsx)(`div`,{"aria-hidden":`true`,className:S(`pointer-events-none absolute inset-0 z-20 border transition-[opacity,border-color,box-shadow] duration-300`,u.running?`animate-pulse shadow-lg shadow-ring/5`:`opacity-0`,u.running&&`border-ring/25 opacity-100 shadow-ring/10`)}),(0,O.jsx)(A,{connected:ne,onClearChat:()=>void d(),onOpenDetails:e,roleName:fe,clearing:te}),(0,O.jsxs)(`div`,{className:`relative flex min-h-0 flex-1 flex-col`,children:[(0,O.jsx)(ae,{allowHumanMessageRetry:!0,bottomInset:o,items:de,nodes:t,onRetryHumanMessage:e=>void le(e),onCancelPendingSend:ee,onScroll:ce,retryImageInputEnabled:x,retryingMessageId:h,runningHint:u.runningHint,scrollRef:g}),(0,O.jsx)(`div`,{ref:s,style:{paddingBottom:`calc(10px + env(safe-area-inset-bottom, 0px))`},className:`pointer-events-none absolute inset-x-0 bottom-0 z-10 bg-gradient-to-b from-transparent via-background/70 to-background/95 px-2.5 pt-8`,children:(0,O.jsx)(`div`,{className:`mx-auto w-full max-w-3xl`,children:(0,O.jsx)(c,{busy:u.running,disabled:!f.trim()&&re.length===0||oe||ue,commandsEnabled:!0,images:re,imageInputEnabled:x,input:f,onAddImages:e=>void l(e),onChange:v,onNavigateHistory:se,onKeyDown:ie,onRemoveImage:m,onSend:()=>void _(),onStop:()=>{a(!0),y().catch(e=>{r.error(e instanceof Error?e.message:`Failed to stop Assistant`)}).finally(()=>{a(!1)})},overlay:!0,stopping:n,suppressCommandNavigation:p,targetLabel:`Assistant`})})})]})]})}function A({clearing:e,connected:t,onClearChat:n,onOpenDetails:r,roleName:i}){return(0,O.jsxs)(`div`,{className:`relative z-10 flex flex-wrap items-center gap-2.5 border-b border-border px-3.5 py-2.5`,children:[(0,O.jsxs)(`div`,{className:`flex min-w-[220px] flex-1 items-center gap-2`,children:[(0,O.jsx)(`div`,{className:`shrink-0 text-[14px] font-semibold leading-6 text-foreground`,children:`Assistant`}),i?(0,O.jsxs)(`span`,{className:`min-w-0 truncate rounded-full border border-border bg-accent/35 px-2 py-0.5 text-[10px] font-medium leading-4 text-muted-foreground/78`,children:[`Role: `,i]}):null,(0,O.jsx)(j,{connected:t})]}),(0,O.jsxs)(`div`,{className:`flex items-center gap-1.5`,children:[(0,O.jsx)(C,{type:`button`,size:`sm`,variant:`outline`,disabled:e,onClick:n,children:e?`Clearing...`:`Clear Chat`}),(0,O.jsx)(C,{type:`button`,size:`sm`,variant:`outline`,disabled:!r,onClick:r,children:`Assistant Details`})]})]})}function j({connected:e}){return(0,O.jsx)(`span`,{className:S(`rounded-full border px-2.5 py-0.5 text-[9px] font-medium transition-colors`,e?`border-graph-status-running/18 bg-graph-status-running/[0.12] text-graph-status-running`:`border-graph-status-idle/18 bg-graph-status-idle/[0.12] text-graph-status-idle`),children:e?`Online`:`Connecting...`})}function M(){let{agents:e}=b(),t=T(e),[n,r]=(0,w.useState)(!1);return(0,O.jsx)(`div`,{className:`flex h-full flex-col min-h-0`,children:n&&t?(0,O.jsx)(`div`,{className:`h-full overflow-hidden p-6`,children:(0,O.jsx)(`div`,{className:`h-full overflow-hidden rounded-xl border border-border bg-surface-overlay/90 shadow-md`,children:(0,O.jsx)(p,{agent:t,onClose:()=>r(!1)})})}):(0,O.jsx)(k,{onOpenDetails:t?()=>r(!0):void 0})})}export{M as AssistantPage};
@@ -0,0 +1 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{dt as r,nn as i,q as a,tt as o}from"./ui-vendor-UazN8rcv.js";import{B as s,J as c,s as l,tt as u}from"./index-Biio-CoI.js";import{l as d,s as f}from"./surface-Bzr1FRG4.js";import{c as p,n as m,r as h,s as g}from"./PageScaffold-DteOA8V7.js";import{t as _}from"./datetime-eJqd0V2S.js";async function v(){return s(`/api/settings/telegram`,{errorMessage:`Failed to fetch Telegram settings`})}async function y(e){return s(`/api/settings/telegram`,{method:`PATCH`,body:e,errorMessage:`Failed to save Telegram settings`})}async function b(e){return s(`/api/settings/telegram/approve/${e}`,{method:`POST`,errorMessage:`Failed to approve Telegram chat`})}async function x(e){return s(`/api/settings/telegram/pending/${e}`,{method:`DELETE`,errorMessage:`Failed to remove pending Telegram chat`})}async function S(e){return s(`/api/settings/telegram/chat/${e}`,{method:`DELETE`,errorMessage:`Failed to remove Telegram chat`})}var C=e(t(),1),w=n();function T(e){return e?_(e,{fallback:`—`,unit:`seconds`}):`—`}function E(e){return e.display_name.trim()?e.display_name.trim():e.username?.trim()?`@${e.username.trim()}`:`Unknown chat`}function D(){let{data:e,isLoading:t,mutate:n}=p(`telegramSettings`,v),[s,_]=(0,C.useState)(!1),[D,O]=(0,C.useState)(``),[k,A]=(0,C.useState)(!1),j=(0,C.useMemo)(()=>!!e?.bot_token,[e?.bot_token]),M=async()=>{if(e){_(!0);try{let e={};k&&(e.bot_token=D.trim()),n((await y(e)).telegram,!1),O(``),A(!1),a.success(`Telegram settings saved`)}catch{a.error(`Failed to save Telegram settings`)}finally{_(!1)}}},N=async e=>{try{n((await b(e)).telegram,!1),a.success(`Telegram chat approved`)}catch{a.error(`Failed to approve Telegram chat`)}},P=async e=>{try{n((await x(e)).telegram,!1),a.success(`Pending Telegram chat removed`)}catch{a.error(`Failed to remove pending Telegram chat`)}},F=async e=>{try{n((await S(e)).telegram,!1),a.success(`Approved Telegram chat removed`)}catch{a.error(`Failed to remove approved Telegram chat`)}};return t||!e?(0,w.jsx)(l,{label:`Loading channels...`,textClassName:`text-[13px]`}):(0,w.jsx)(m,{children:(0,w.jsx)(`div`,{className:`h-full min-h-0 overflow-y-auto pr-2 scrollbar-none pt-6`,children:(0,w.jsxs)(`div`,{className:`mx-auto max-w-[680px] pb-10`,children:[(0,w.jsx)(h,{title:`Channels`}),(0,w.jsxs)(g,{className:`mt-6 space-y-8`,children:[(0,w.jsxs)(`div`,{className:`flex items-start justify-between gap-4`,children:[(0,w.jsx)(`div`,{children:(0,w.jsx)(`h2`,{className:`text-lg font-medium text-foreground`,children:`Telegram`})}),(0,w.jsx)(d,{tone:j?`running`:`idle`,children:j?`Configured`:`Not configured`})]}),(0,w.jsxs)(`section`,{children:[(0,w.jsxs)(`div`,{className:`flex flex-wrap items-center gap-3`,children:[(0,w.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Bot Token`}),(0,w.jsx)(d,{tone:j?`running`:`idle`,children:j?`Saved`:`Missing`})]}),(0,w.jsxs)(`div`,{className:`mt-3`,children:[(0,w.jsx)(c,{value:D,onChange:e=>{O(e.target.value),A(!0)},placeholder:e.bot_token||`Enter Telegram bot token`,mono:!0,showLabel:`Show Telegram bot token`,hideLabel:`Hide Telegram bot token`}),j&&!k?(0,w.jsx)(`p`,{className:`mt-2 text-[11px] text-muted-foreground`,children:`Leave empty to keep the current token.`}):null]})]}),(0,w.jsxs)(`section`,{className:`border-t border-border pt-8`,children:[(0,w.jsxs)(`div`,{className:`flex flex-wrap items-center gap-3`,children:[(0,w.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Pending Private Chats`}),(0,w.jsxs)(d,{tone:`muted`,className:`px-2 py-0.5`,children:[e.pending_chats.length,` waiting`]})]}),e.pending_chats.length===0?(0,w.jsx)(`p`,{className:`mt-4 text-[13px] text-muted-foreground`,children:`No pending chats.`}):(0,w.jsx)(`div`,{className:`mt-4 space-y-2`,children:e.pending_chats.map(e=>(0,w.jsx)(f,{as:`div`,padding:`sm`,className:`px-4 py-3.5 transition-colors hover:bg-accent/20`,children:(0,w.jsxs)(`div`,{className:`flex items-center justify-between gap-4`,children:[(0,w.jsxs)(`div`,{className:`min-w-0`,children:[(0,w.jsx)(`p`,{className:`text-[13px] font-medium text-foreground`,children:E(e)}),(0,w.jsxs)(`div`,{className:`mt-1 flex items-center gap-3 text-[11px] text-muted-foreground`,children:[(0,w.jsxs)(`span`,{className:`font-mono`,children:[`ID: `,e.chat_id]}),e.username?(0,w.jsxs)(`span`,{children:[`@`,e.username]}):null,(0,w.jsxs)(`span`,{children:[`First seen: `,T(e.first_seen_at)]})]})]}),(0,w.jsxs)(`div`,{className:`flex shrink-0 items-center gap-1.5`,children:[(0,w.jsxs)(u,{type:`button`,variant:`outline`,size:`xs`,onClick:()=>void N(e.chat_id),children:[(0,w.jsx)(i,{className:`size-3.5`}),`Approve`]}),(0,w.jsx)(u,{type:`button`,variant:`ghost`,size:`icon-xs`,onClick:()=>void P(e.chat_id),className:`text-muted-foreground hover:bg-destructive/10 hover:text-destructive`,children:(0,w.jsx)(o,{className:`size-3.5`})})]})]})},e.chat_id))})]}),(0,w.jsxs)(`section`,{className:`border-t border-border pt-8`,children:[(0,w.jsxs)(`div`,{className:`flex flex-wrap items-center gap-3`,children:[(0,w.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Approved Private Chats`}),(0,w.jsxs)(d,{tone:`muted`,className:`px-2 py-0.5`,children:[e.approved_chats.length,` active`]})]}),e.approved_chats.length===0?(0,w.jsx)(`p`,{className:`mt-4 text-[13px] text-muted-foreground`,children:`No approved chats yet.`}):(0,w.jsx)(`div`,{className:`mt-4 space-y-2`,children:e.approved_chats.map(e=>(0,w.jsx)(f,{as:`div`,padding:`sm`,className:`group px-4 py-3.5 transition-colors hover:bg-accent/20`,children:(0,w.jsxs)(`div`,{className:`flex items-center justify-between gap-4`,children:[(0,w.jsxs)(`div`,{className:`min-w-0`,children:[(0,w.jsx)(`p`,{className:`text-[13px] font-medium text-foreground`,children:E(e)}),(0,w.jsxs)(`div`,{className:`mt-1 flex items-center gap-3 text-[11px] text-muted-foreground`,children:[(0,w.jsxs)(`span`,{className:`font-mono`,children:[`ID: `,e.chat_id]}),e.username?(0,w.jsxs)(`span`,{children:[`@`,e.username]}):null,(0,w.jsxs)(`span`,{children:[`Approved: `,T(e.approved_at)]})]})]}),(0,w.jsx)(u,{type:`button`,variant:`ghost`,size:`icon-xs`,onClick:()=>void F(e.chat_id),className:`shrink-0 text-muted-foreground opacity-0 transition-all hover:bg-destructive/10 hover:text-destructive group-hover:opacity-100 focus:opacity-100`,children:(0,w.jsx)(o,{className:`size-3.5`})})]})},e.chat_id))})]}),(0,w.jsx)(`div`,{className:`flex justify-end border-t border-border pt-6`,children:(0,w.jsxs)(u,{type:`button`,size:`sm`,onClick:()=>void M(),disabled:s,className:`text-[13px]`,children:[(0,w.jsx)(r,{className:`size-4`}),s?`Saving...`:`Save Changes`]})})]})]})})})}export{D as ChannelsPage};
@@ -0,0 +1,7 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{$ as r,J as i,_t as a,pt as ee,q as o,ut as s}from"./ui-vendor-UazN8rcv.js";import{$ as c,B as l,K as u,V as d,et as f,rt as p,tt as m}from"./index-Biio-CoI.js";import{a as h,c as te,l as g,o as _,r as v,s as y,t as b,u as ne}from"./surface-Bzr1FRG4.js";import{c as re,n as x,r as ie,s as S}from"./PageScaffold-DteOA8V7.js";import{t as C}from"./datetime-eJqd0V2S.js";import{a as ae,i as w,n as oe,r as T,t as se}from"./select-D9SwnlXF.js";import{n as E,t as ce}from"./WorkspaceCommandDialog-DRS6wiD6.js";async function le(){return l(`/api/mcp`,{method:`GET`,errorMessage:`Failed to fetch MCP state`})}async function ue(){return l(`/api/mcp/refresh`,{method:`POST`,errorMessage:`Failed to refresh MCP servers`,fallback:[],map:e=>e?.servers??[]})}async function de(e){return l(`/api/mcp/servers`,{method:`POST`,body:e,errorMessage:`Failed to create MCP server`,map:e=>{if(!e)throw Error(`Failed to create MCP server`);return e.snapshot}})}async function fe(e,t){return l(`/api/mcp/servers/${e}`,{method:`PATCH`,body:t,errorMessage:`Failed to update MCP server`,map:e=>{if(!e)throw Error(`Failed to update MCP server`);return e.snapshot}})}async function pe(e){await d(`/api/mcp/servers/${e}`,{method:`DELETE`,errorMessage:`Failed to delete MCP server`})}async function me(e){return l(`/api/mcp/servers/${e}/refresh`,{method:`POST`,errorMessage:`Failed to refresh MCP server`,map:e=>{if(!e)throw Error(`Failed to refresh MCP server`);return e.snapshot}})}async function he(e){return l(`/api/mcp/servers/${e}/login`,{method:`POST`,errorMessage:`Failed to login MCP server`,map:e=>{if(!e)throw Error(`Failed to login MCP server`);return e.snapshot}})}async function ge(e){await d(`/api/mcp/servers/${e}/logout`,{method:`POST`,errorMessage:`Failed to logout MCP server`})}async function _e(e,t,n={}){return l(`/api/mcp/servers/${e}/prompt-preview`,{method:`POST`,body:{name:t,arguments:n},errorMessage:`Failed to preview MCP prompt`,map:e=>{if(!e)throw Error(`Failed to preview MCP prompt`);return e.preview}})}var D=n(),ve=`border-border/70 bg-background/45 hover:border-ring/35 hover:bg-accent/65`;function O(e){return e.split(`
2
+ `).map(e=>e.trim()).filter(Boolean)}function k(e){return e.join(`
3
+ `)}function ye(e){let t={};for(let n of e.split(`
4
+ `)){let e=n.trim();if(!e)continue;let r=e.indexOf(`:`);if(r<0)continue;let i=e.slice(0,r).trim(),a=e.slice(r+1).trim();i&&(t[i]=a)}return t}function A(e){return Object.entries(e).map(([e,t])=>`${e}: ${t}`).join(`
5
+ `)}function j({checked:e,disabled:t,label:n,onChange:r}){return(0,D.jsxs)(`label`,{className:`flex items-center justify-between gap-4 rounded-xl border border-border bg-card/20 px-4 py-3 text-sm${t?` opacity-50`:``}`,children:[(0,D.jsx)(`span`,{className:`text-foreground/85`,children:n}),(0,D.jsx)(u,{checked:e,disabled:t,label:n,onCheckedChange:r})]})}function be({draft:e,onChange:t,onOpenChange:n,onSubmit:r,open:i,pending:a,title:ee}){return(0,D.jsxs)(ce,{open:i,onOpenChange:n,title:ee,footer:(0,D.jsxs)(`div`,{className:`flex w-full items-center justify-end gap-3`,children:[(0,D.jsx)(m,{type:`button`,variant:`outline`,className:ve,onClick:()=>n(!1),children:`Cancel`}),(0,D.jsx)(m,{type:`button`,disabled:a,onClick:r,children:a?`Saving...`:`Save Server`})]}),className:`max-w-3xl`,children:[(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`Name`,children:(0,D.jsx)(f,{value:e.name,onChange:n=>t({...e,name:n.target.value}),placeholder:`filesystem`})}),(0,D.jsx)(E,{label:`Transport`,children:(0,D.jsxs)(se,{value:e.transport,onValueChange:n=>t({...e,transport:n}),children:[(0,D.jsx)(w,{className:`h-8 w-full rounded-md bg-background/50 text-sm text-foreground`,children:(0,D.jsx)(ae,{placeholder:`Select transport`})}),(0,D.jsxs)(oe,{className:`rounded-xl bg-popover text-popover-foreground`,children:[(0,D.jsx)(T,{value:`stdio`,children:`stdio`}),(0,D.jsx)(T,{value:`streamable_http`,children:`streamable_http`})]})]})})]}),(0,D.jsx)(E,{label:`Launcher Command`,hint:`optional`,children:(0,D.jsx)(f,{value:e.launcher,onChange:n=>t({...e,launcher:n.target.value}),placeholder:e.transport===`streamable_http`?`https://mcp.example.com`:`npx @playwright/mcp@latest`})}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(j,{checked:e.enabled,label:`Enabled`,onChange:n=>t({...e,enabled:n})}),(0,D.jsx)(j,{checked:e.required,label:`Required`,onChange:n=>t({...e,required:n})})]}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`Startup Timeout`,hint:`seconds`,children:(0,D.jsx)(f,{type:`number`,value:String(e.startup_timeout_sec),onChange:n=>t({...e,startup_timeout_sec:Number(n.target.value)||10})})}),(0,D.jsx)(E,{label:`Tool Timeout`,hint:`seconds`,children:(0,D.jsx)(f,{type:`number`,value:String(e.tool_timeout_sec),onChange:n=>t({...e,tool_timeout_sec:Number(n.target.value)||30})})})]}),e.transport===`stdio`?(0,D.jsxs)(D.Fragment,{children:[(0,D.jsx)(E,{label:`Command`,children:(0,D.jsx)(f,{value:e.command,onChange:n=>t({...e,command:n.target.value}),placeholder:`npx`})}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`Args`,hint:`one per line`,children:(0,D.jsx)(c,{rows:5,value:k(e.args),onChange:n=>t({...e,args:O(n.target.value)})})}),(0,D.jsx)(E,{label:`Env Vars`,hint:`one env var name per line`,children:(0,D.jsx)(c,{rows:5,value:k(e.env_vars),onChange:n=>t({...e,env_vars:O(n.target.value)})})})]}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`Env`,hint:`KEY: value`,children:(0,D.jsx)(c,{rows:5,value:A(e.env),onChange:n=>t({...e,env:ye(n.target.value)})})}),(0,D.jsx)(E,{label:`Cwd`,children:(0,D.jsx)(f,{value:e.cwd,onChange:n=>t({...e,cwd:n.target.value}),placeholder:`/workspace/tools`})})]})]}):(0,D.jsxs)(D.Fragment,{children:[(0,D.jsx)(E,{label:`URL`,children:(0,D.jsx)(f,{value:e.url,onChange:n=>t({...e,url:n.target.value}),placeholder:`https://mcp.example.com`})}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`Bearer Token Env Var`,children:(0,D.jsx)(f,{value:e.bearer_token_env_var,onChange:n=>t({...e,bearer_token_env_var:n.target.value}),placeholder:`MCP_TOKEN`})}),(0,D.jsx)(E,{label:`OAuth Resource`,children:(0,D.jsx)(f,{value:e.oauth_resource,onChange:n=>t({...e,oauth_resource:n.target.value}),placeholder:`https://mcp.example.com`})})]}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`HTTP Headers`,hint:`Header: value`,children:(0,D.jsx)(c,{rows:5,value:A(e.http_headers),onChange:n=>t({...e,http_headers:ye(n.target.value)})})}),(0,D.jsx)(E,{label:`Env HTTP Headers`,hint:`one env var name per line`,children:(0,D.jsx)(c,{rows:5,value:k(e.env_http_headers),onChange:n=>t({...e,env_http_headers:O(n.target.value)})})})]}),(0,D.jsx)(E,{label:`Scopes`,hint:`one scope per line`,children:(0,D.jsx)(c,{rows:4,value:k(e.scopes),onChange:n=>t({...e,scopes:O(n.target.value)})})})]}),(0,D.jsxs)(`div`,{className:`grid gap-4 md:grid-cols-2`,children:[(0,D.jsx)(E,{label:`Enabled Tools`,hint:`one raw tool name per line`,children:(0,D.jsx)(c,{rows:4,value:k(e.enabled_tools),onChange:n=>t({...e,enabled_tools:O(n.target.value)})})}),(0,D.jsx)(E,{label:`Disabled Tools`,hint:`one raw tool name per line`,children:(0,D.jsx)(c,{rows:4,value:k(e.disabled_tools),onChange:n=>t({...e,disabled_tools:O(n.target.value)})})})]})]})}var M=e(t(),1),N=[`overview`,`capabilities`,`activity`],P=[`tools`,`resources`,`resource_templates`,`prompts`],F=[{value:`all`,label:`All`},{value:`connected`,label:`Connected`},{value:`auth_required`,label:`Auth Required`},{value:`error`,label:`Error`},{value:`disabled`,label:`Disabled`},{value:`connecting`,label:`Connecting`}],I=[{value:`all`,label:`All`},{value:`refresh`,label:`Refresh`},{value:`auth`,label:`Auth`},{value:`tool`,label:`Tool`},{value:`resource`,label:`Resource`},{value:`prompt`,label:`Prompt`}],L={name:``,transport:`stdio`,enabled:!0,required:!1,startup_timeout_sec:10,tool_timeout_sec:30,enabled_tools:[],disabled_tools:[],scopes:[],oauth_resource:``,launcher:``,command:``,args:[],env:{},env_vars:[],cwd:``,url:``,bearer_token_env_var:``,http_headers:{},env_http_headers:[]};function R(e){return C(e,{fallback:`Never`})}function z(e){return e.split(`_`).map(e=>e.charAt(0).toUpperCase()+e.slice(1)).join(` `)}function B(e){switch(e){case`unsupported`:return`Unsupported`;case`not_logged_in`:return`Not logged in`;case`logging_in`:return`Logging in`;case`connected`:return`Connected`;case`error`:return`Error`;default:return z(e)}}function xe(e){return C(e,{fallback:`Never`,format:{month:`short`,day:`numeric`,hour:`2-digit`,minute:`2-digit`}})}function V(e){switch(e){case`disabled`:return`Disabled`;case`connecting`:return`Connecting`;case`connected`:return`Connected`;case`auth_required`:return`Auth required`;case`error`:return`Error`;default:return e}}function H(e){switch(e){case`connected`:return`border-graph-status-running/18 bg-graph-status-running/[0.12] text-graph-status-running`;case`auth_required`:return`border-graph-status-idle/18 bg-graph-status-idle/[0.12] text-graph-status-idle`;case`error`:return`border-destructive/30 bg-destructive/10 text-destructive`;case`disabled`:return`border-border bg-accent/20 text-muted-foreground`;default:return`border-primary/20 bg-primary/[0.1] text-primary`}}function Se(e){switch(e){case`success`:return`border-graph-status-running/18 bg-graph-status-running/[0.12] text-graph-status-running`;case`rejected`:return`border-graph-status-idle/18 bg-graph-status-idle/[0.12] text-graph-status-idle`;default:return`border-destructive/30 bg-destructive/10 text-destructive`}}function Ce(e){let t=e.snapshot.capability_counts;return`${t.tools} tools · ${t.resources} resources · ${t.prompts} prompts`}function U(e){return e.visibility.active?`Global`:null}function we(e){return e.length<2?e:e.startsWith(`"`)&&e.endsWith(`"`)||e.startsWith(`'`)&&e.endsWith(`'`)?e.slice(1,-1):e}function Te(e){return(e.match(/'[^']*'|"[^"]*"|\S+/g)??[]).map(e=>we(e))}function W(e){return e.toLowerCase().replace(/[^a-z0-9]+/g,`-`).replace(/^-+|-+$/g,``).slice(0,48)}function Ee(e){return W((e.startsWith(`@`)?e.replace(/@[^/@]+$/u,``):e.replace(/@[^/]+$/u,``)).split(`/`).filter(Boolean).join(`-`))}function De(e){try{let t=new URL(e);return W(t.hostname.replace(/^www\./u,``).split(`.`).filter(e=>e&&![`mcp`,`api`].includes(e))[0]??t.hostname)}catch{return``}}function Oe(e,t){if(/^https?:\/\//u.test(e))return De(e);let n=t[0]??``,r=n===`pnpm`||n===`yarn`?2:n===`npm`?3:1,i=t.slice(r).find(e=>e&&!e.startsWith(`-`));if(i){let e=Ee(i);if(e)return e}return n?W(n.split(`/`).pop()??n):``}function ke(e,t){let n=e.trim(),r=W(t);if(!n)return{draft:null,error:`Enter a launcher command or URL.`};if(!r)return{draft:null,error:`Quick Add needs a valid server name.`};if(/^https?:\/\//u.test(n))try{let e=new URL(n).toString();return{draft:{...L,name:r,transport:`streamable_http`,launcher:n,url:e},error:null}}catch{return{draft:null,error:`Quick Add URL is not valid.`}}let i=Te(n);return i.length===0?{draft:null,error:`Quick Add needs a single-line launcher command.`}:{draft:{...L,name:r,transport:`stdio`,launcher:n,command:i[0],args:i.slice(1)},error:null}}function Ae(e){return e.config.transport===`streamable_http`?e.config.url.trim()||`No URL configured`:[e.config.command,...e.config.args].filter(Boolean).join(` `)}function je(e){return{config:e,snapshot:{server_name:e.name,transport:e.transport,status:`connecting`,auth_status:e.transport===`stdio`?`unsupported`:`not_logged_in`,last_auth_result:null,last_refresh_at:null,last_refresh_result:`never`,last_error:null,tools:[],resources:[],resource_templates:[],prompts:[],capability_counts:{tools:0,resources:0,resource_templates:0,prompts:0}},visibility:{scope:`global`,active:!1},activity:[]}}function Me(e){return e.config.enabled_tools.length>0?`Enabled tools limited to ${e.config.enabled_tools.length} entries`:e.config.disabled_tools.length>0?`${e.config.disabled_tools.length} tools excluded`:`All discovered tools remain available`}function Ne(e){return e.config.transport===`stdio`?`Auth N/A`:e.snapshot.auth_status===`connected`?`Logout`:`Login`}function Pe(e){return e.config.transport===`stdio`}function G(e,t=`Not set`){return typeof e==`string`&&e.trim()||t}function K(e,t=`None`){return e.length===0?t:e.join(`
6
+ `)}function Fe(e,t=`None`){let n=Object.keys(e);return n.length===0?t:n.join(`
7
+ `)}function Ie(e){if(e.action===`login`||e.action===`logout`)return!0;if(e.action!==`refresh`)return!1;let t=`${e.summary} ${e.target??``}`.toLowerCase();return[`auth`,`authentication`,`oauth`,`token`,`bearer`,`login`,`logged out`,`env var`].some(e=>t.includes(e))}function Le(e){if(Ie(e))return`auth`;switch(e.action){case`refresh`:return`refresh`;case`login`:case`logout`:return`auth`;case`tool_call`:return`tool`;case`resource_read`:return`resource`;case`prompt_get`:return`prompt`;default:return`all`}}function Re(e){switch(Le(e)){case`refresh`:return`Refresh`;case`auth`:return`Auth`;case`tool`:return`Tool`;case`resource`:return`Resource`;case`prompt`:return`Prompt`;default:return z(e.action)}}function ze(e,t){return!(t!==`all`&&e.snapshot.status!==t)}function Be(e,t=`Not set`){return e.trim()?e:t}function Ve(e){return Object.fromEntries((e?.arguments??[]).map(e=>e.name).filter(e=>typeof e==`string`&&e.length>0).map(e=>[e,``]))}function He(){let{data:e,error:t,isLoading:n,mutate:r}=re(`mcp-state`,le),[i,a]=(0,M.useState)(null),[ee,s]=(0,M.useState)(`overview`),[c,l]=(0,M.useState)(`tools`),[u,d]=(0,M.useState)(!1),[f,p]=(0,M.useState)(null),[m,h]=(0,M.useState)(L),[te,g]=(0,M.useState)(!1),[_,v]=(0,M.useState)(null),[y,b]=(0,M.useState)(null),[ne,x]=(0,M.useState)(!1),[ie,S]=(0,M.useState)(`{}`),[C,ae]=(0,M.useState)(`all`),[w,oe]=(0,M.useState)(`all`),[T,se]=(0,M.useState)(``),[E,ce]=(0,M.useState)(``),[D,ve]=(0,M.useState)(!1),[O,k]=(0,M.useState)(!1),[ye,A]=(0,M.useState)(null),j=(0,M.useMemo)(()=>Te(T.trim()),[T]),be=(0,M.useMemo)(()=>Oe(T.trim(),j),[T,j]),N=D?E:be,P=(0,M.useMemo)(()=>ke(T,N),[T,N]),F=(0,M.useMemo)(()=>{let t=e?.servers??[];return!O||P.draft===null||t.some(e=>e.config.name===P.draft?.name)?t:[je(P.draft),...t]},[e,P.draft,O]),I=(0,M.useMemo)(()=>F.filter(e=>ze(e,C)),[C,F]),R=(0,M.useMemo)(()=>I.find(e=>e.config.name===i)??I[0]??null,[I,i]);(0,M.useEffect)(()=>{I.length>0&&!I.some(e=>e.config.name===i)&&a(I[0]?.config.name??null)},[I,i]),(0,M.useEffect)(()=>{v(null),b(null),x(!1),S(`{}`),oe(`all`)},[R?.config.name]),(0,M.useEffect)(()=>{D||ce(be)},[D,be]);let z=(0,M.useMemo)(()=>({configured:F.length,connected:F.filter(e=>e.snapshot.status===`connected`).length,authRequired:F.filter(e=>e.snapshot.status===`auth_required`).length,error:F.filter(e=>e.snapshot.status===`error`).length}),[F]),B=(0,M.useMemo)(()=>R?.snapshot.prompts.find(e=>e.name===_)??null,[_,R]),xe=(0,M.useMemo)(()=>R?R.activity.filter(e=>w===`all`?!0:Le(e)===w):[],[w,R]),V=()=>{p(null),h(L),d(!0)},H=e=>{p(e.config.name),h(e.config),d(!0)},Se=e=>{se(e),A(null)},Ce=e=>{ve(!0),ce(e),A(null)},U=()=>{document.getElementById(`mcp-quick-add-input`)?.focus()},we=()=>{ae(`all`)},W=async()=>{try{await ue(),await r(),o.success(`MCP servers refreshed`)}catch(e){o.error(e instanceof Error?e.message:`Failed to refresh MCP servers`)}},Ee=async()=>{g(!0);try{f?await fe(f,m):await de(m),await r(),a(m.name.trim()),d(!1),o.success(`MCP server saved`)}catch(e){o.error(e instanceof Error?e.message:`Failed to save MCP server`)}finally{g(!1)}},De=async()=>{if(P.error||P.draft===null){A(P.error??`Quick Add is not ready yet.`);return}k(!0),A(null),a(P.draft.name);try{await de(P.draft),await r(),a(P.draft.name),se(``),ce(``),ve(!1),o.success(`MCP server added`)}catch(e){await r(),a(P.draft.name),A(e instanceof Error?e.message:`Failed to add MCP server`),o.error(e instanceof Error?e.message:`Failed to add MCP server`)}finally{k(!1)}},Ae=async e=>{try{await pe(e),await r(),o.success(`MCP server removed`)}catch(e){o.error(e instanceof Error?e.message:`Failed to remove MCP server`)}},Me=async e=>{try{await fe(e.config.name,{...e.config,enabled:!e.config.enabled}),await r()}catch(e){o.error(e instanceof Error?e.message:`Failed to update MCP server`)}},Ne=async e=>{try{await me(e),await r(),o.success(`Server refreshed`)}catch(e){o.error(e instanceof Error?e.message:`Failed to refresh server`)}},Pe=async e=>{try{await he(e),await r(),o.success(`Server refreshed after login`)}catch(e){o.error(e instanceof Error?e.message:`Failed to login MCP server`)}},G=async e=>{try{await ge(e),await r(),o.success(`Logout request sent`)}catch(e){o.error(e instanceof Error?e.message:`Failed to logout MCP server`)}},K=async(e,t,n={})=>{x(!0);try{b(await _e(e,t,n))}catch(e){b({error:e instanceof Error?e.message:`Failed to preview prompt`})}finally{x(!1)}};return{error:t,isLoading:n,servers:F,filteredServers:I,selectedServer:R,summaryCounts:z,filteredActivity:xe,detailTab:ee,setDetailTab:s,capabilityTab:c,setCapabilityTab:l,serverStatusFilter:C,setServerStatusFilter:ae,activityFilter:w,setActivityFilter:oe,selectedServerName:i,setSelectedServerName:a,clearServerFilters:we,focusQuickAdd:U,dialog:{draft:m,editingServerName:f,open:u,pending:te,setDraft:h,setOpen:d,openCreateDialog:V,openEditDialog:H,saveServer:Ee},quickAdd:{error:ye,input:T,nameValue:N,parse:P,pending:O,setInput:Se,setName:Ce,submit:De},promptPreviewState:{argumentsText:ie,loading:ne,preview:y,selectedPrompt:B,selectedPromptName:_,setArgumentsText:e=>{S(e)},previewCurrent:()=>{if(!(!R||!_))try{let e=JSON.parse(ie);K(R.config.name,_,e)}catch{b({error:`Arguments must be valid JSON`})}},selectPrompt:(e,t)=>{v(t);let n=Ve(R?.snapshot.prompts.find(e=>e.name===t)??null);S(JSON.stringify(n,null,2)),K(e,t,n)}},actions:{deleteServer:Ae,login:Pe,logout:G,refreshAll:W,refreshServer:Ne,toggleEnabled:Me}}}function q({label:e,value:t}){return(0,D.jsx)(h,{label:e,value:t,className:`min-h-0 px-4`})}function Ue({active:e,label:t,onClick:n,variant:r=`pill`}){return(0,D.jsx)(v,{active:e,label:t,onClick:n,variant:r})}function J({label:e,value:t,mono:n=!1}){return(0,D.jsx)(te,{label:e,value:t,mono:n})}var Y=`bg-card/20`,X=`text-[13px] text-muted-foreground`,Z=ne,Q=`border-border/70 bg-background/45 hover:border-ring/35 hover:bg-accent/65`,We=`border-graph-status-error/35 bg-graph-status-error/10 text-graph-status-error hover:bg-graph-status-error/18`,Ge=`mt-4 max-h-48 bg-background/55 p-3 text-foreground/70`,$=`mt-2 line-clamp-1 text-[13px] leading-6 text-muted-foreground`;function Ke(){return(0,D.jsxs)(`div`,{className:`grid h-full gap-5 lg:grid-cols-[320px_minmax(0,1fr)]`,children:[(0,D.jsxs)(`div`,{className:`space-y-3`,children:[Array.from({length:5}).map((e,t)=>(0,D.jsx)(`div`,{className:`h-24 rounded-xl border border-border bg-card/20 skeleton-shimmer`},t)),(0,D.jsx)(`p`,{className:`px-2 text-[13px] text-muted-foreground`,children:`Loading MCP servers...`})]}),(0,D.jsx)(`div`,{className:`rounded-xl border border-border bg-card/20 skeleton-shimmer`})]})}function qe(){return(0,D.jsx)(S,{className:`flex h-full items-center justify-center text-center text-muted-foreground`,children:`Failed to load MCP state.`})}function Je({quickAdd:e,dialog:t}){return(0,D.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col`,children:[(0,D.jsx)(Ye,{quickAdd:e,dialog:t}),(0,D.jsx)(_,{icon:r,title:`No MCP servers`,minHeightClassName:`h-full`,className:`mt-4`})]})}function Ye({dialog:e,quickAdd:t}){return(0,D.jsx)(S,{className:p(`mt-4`,Y),children:(0,D.jsxs)(`div`,{className:`space-y-4`,children:[(0,D.jsxs)(`div`,{className:`flex flex-wrap items-start justify-between gap-3`,children:[(0,D.jsx)(`div`,{children:(0,D.jsx)(`p`,{className:Z,children:`Quick Add`})}),t.parse.draft?(0,D.jsx)(g,{className:p(H(t.parse.draft.transport===`streamable_http`?`connected`:`connecting`)),children:t.parse.draft.transport===`streamable_http`?`URL`:`Launcher`}):null]}),(0,D.jsxs)(`div`,{className:`grid gap-4 xl:grid-cols-[minmax(0,1.4fr)_minmax(260px,0.6fr)]`,children:[(0,D.jsx)(E,{label:`Launcher or URL`,children:(0,D.jsx)(f,{id:`mcp-quick-add-input`,value:t.input,onChange:e=>t.setInput(e.target.value),placeholder:`npx @playwright/mcp@latest`})}),(0,D.jsx)(E,{label:`Name`,children:(0,D.jsx)(f,{value:t.nameValue,onChange:e=>t.setName(e.target.value),placeholder:`playwright-mcp`})})]}),t.parse.draft?(0,D.jsxs)(`div`,{className:`grid gap-3 xl:grid-cols-3`,children:[(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Transport`}),(0,D.jsx)(`p`,{className:`mt-2 text-[14px] font-medium text-foreground`,children:t.parse.draft.transport})]}),(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Parsed Name`}),(0,D.jsx)(`p`,{className:`mt-2 text-[14px] font-medium text-foreground`,children:t.parse.draft.name})]}),(0,D.jsxs)(S,{className:p(`xl:col-span-1`,Y),children:[(0,D.jsx)(`p`,{className:Z,children:`Parsed Result`}),(0,D.jsx)(`p`,{className:`mt-2 break-all font-mono text-[12px] text-foreground/80`,children:t.parse.draft.transport===`streamable_http`?t.parse.draft.url:[t.parse.draft.command,...t.parse.draft.args].join(` `)})]})]}):null,t.error||t.input.trim()&&t.parse.error?(0,D.jsx)(`p`,{className:`text-[13px] text-destructive`,children:t.error??t.parse.error}):null,(0,D.jsxs)(`div`,{className:`flex flex-wrap items-center gap-3`,children:[(0,D.jsx)(m,{type:`button`,disabled:t.pending||t.parse.draft===null,onClick:()=>void t.submit(),children:t.pending?`Adding...`:`Quick Add`}),(0,D.jsx)(m,{type:`button`,variant:`outline`,className:Q,onClick:e.openCreateDialog,children:`Advanced Add`})]})]})})}function Xe(e){return(0,D.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col`,children:[(0,D.jsx)(Ze,{summaryCounts:e.summaryCounts}),(0,D.jsx)(Ye,{quickAdd:e.quickAdd,dialog:e.dialog}),(0,D.jsx)(Qe,{serverStatusFilter:e.serverStatusFilter,onServerStatusFilterChange:e.onServerStatusFilterChange}),(0,D.jsx)(`div`,{className:`mt-4 min-h-0 flex-1 overflow-hidden`,children:e.filteredServers.length===0?(0,D.jsx)(_,{icon:s,title:`No matching MCP servers`,minHeightClassName:`h-full`,action:(0,D.jsxs)(m,{type:`button`,variant:`outline`,className:Q,onClick:e.clearServerFilters,children:[(0,D.jsx)(i,{className:`mr-2 size-4`}),`Show All Servers`]})}):(0,D.jsxs)(`div`,{className:`grid h-full gap-5 xl:grid-cols-[360px_minmax(0,1fr)]`,children:[(0,D.jsx)($e,{actions:e.actions,dialog:e.dialog,filteredServers:e.filteredServers,onSelectServer:e.onSelectServer,selectedServer:e.selectedServer}),(0,D.jsx)(tt,{actions:e.actions,activityFilter:e.activityFilter,capabilityTab:e.capabilityTab,dialog:e.dialog,detailTab:e.detailTab,filteredActivity:e.filteredActivity,onActivityFilterChange:e.onActivityFilterChange,onCapabilityTabChange:e.onCapabilityTabChange,onDetailTabChange:e.onDetailTabChange,onFocusQuickAdd:e.onFocusQuickAdd,promptPreviewState:e.promptPreviewState,selectedServer:e.selectedServer})]})})]})}function Ze({summaryCounts:e}){return(0,D.jsx)(S,{children:(0,D.jsxs)(`div`,{className:`grid gap-3 sm:grid-cols-2 xl:grid-cols-4`,children:[(0,D.jsx)(q,{label:`Configured`,value:e.configured}),(0,D.jsx)(q,{label:`Connected`,value:e.connected}),(0,D.jsx)(q,{label:`Auth Required`,value:e.authRequired}),(0,D.jsx)(q,{label:`Error`,value:e.error})]})})}function Qe({onServerStatusFilterChange:e,serverStatusFilter:t}){return(0,D.jsx)(S,{className:`mt-4`,children:(0,D.jsx)(`div`,{className:`flex flex-wrap gap-2`,children:F.map(n=>(0,D.jsx)(Ue,{active:t===n.value,label:n.label,onClick:()=>e(n.value)},n.value))})})}function $e({actions:e,dialog:t,filteredServers:n,onSelectServer:r,selectedServer:i}){return(0,D.jsx)(`div`,{className:`min-h-0 overflow-y-auto pr-1 scrollbar-none`,children:(0,D.jsx)(`div`,{className:`space-y-3`,children:n.map(n=>(0,D.jsx)(et,{actions:e,dialog:t,isSelected:i?.config.name===n.config.name,onSelectServer:r,serverRecord:n},n.config.name))})})}function et({actions:e,dialog:t,isSelected:n,onSelectServer:r,serverRecord:i}){let a=U(i);return(0,D.jsx)(y,{as:`div`,padding:`sm`,className:p(`p-4 transition-colors`,n?`bg-accent/20`:`bg-card/20 hover:bg-accent/20`),children:(0,D.jsxs)(`div`,{className:`flex items-start justify-between gap-3`,children:[(0,D.jsxs)(m,{type:`button`,variant:`ghost`,onClick:()=>r(i.config.name),className:`h-auto min-w-0 flex-1 justify-start p-0 text-left hover:bg-transparent hover:text-inherit`,children:[(0,D.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2`,children:[(0,D.jsx)(`p`,{className:`text-[14px] font-medium text-foreground`,children:i.config.name}),i.config.required?(0,D.jsx)(g,{tone:`idle`,className:`px-2 py-0.5`,children:`required`}):null,a?(0,D.jsx)(g,{tone:`primary`,className:`px-2 py-0.5`,children:a}):null]}),(0,D.jsxs)(`div`,{className:`mt-3 grid gap-1.5 text-[12px] text-muted-foreground`,children:[(0,D.jsxs)(`p`,{children:[`Transport `,i.config.transport]}),(0,D.jsxs)(`p`,{children:[`Status `,V(i.snapshot.status)]}),(0,D.jsxs)(`p`,{children:[`Auth `,B(i.snapshot.auth_status)]}),(0,D.jsx)(`p`,{children:Ce(i)})]}),i.snapshot.last_error?(0,D.jsx)(`p`,{className:`mt-3 line-clamp-2 text-[12px] leading-5 text-destructive`,children:i.snapshot.last_error}):null]}),(0,D.jsxs)(`div`,{className:`flex shrink-0 flex-col items-end gap-1.5`,children:[(0,D.jsx)(g,{className:p(H(i.snapshot.status)),children:V(i.snapshot.status)}),(0,D.jsx)(rt,{actions:e,buttonClassName:`h-7 px-2 text-[11px]`,dialog:t,serverRecord:i})]})]})})}function tt({actions:e,activityFilter:t,capabilityTab:n,dialog:r,detailTab:i,filteredActivity:a,onActivityFilterChange:ee,onCapabilityTabChange:o,onDetailTabChange:s,onFocusQuickAdd:c,promptPreviewState:l,selectedServer:u}){return u?(0,D.jsx)(`div`,{className:`min-h-0 overflow-hidden`,children:(0,D.jsxs)(S,{className:`flex h-full min-h-0 flex-col`,children:[(0,D.jsx)(nt,{actions:e,dialog:r,selectedServer:u}),(0,D.jsx)(`div`,{className:`mt-4 flex flex-wrap gap-4 border-b border-border`,children:N.map(e=>(0,D.jsx)(Ue,{active:i===e,label:z(e),onClick:()=>s(e),variant:`tab`},e))}),(0,D.jsxs)(`div`,{className:`mt-5 min-h-0 flex-1 overflow-y-auto pr-1 scrollbar-none`,children:[i===`overview`?(0,D.jsx)(it,{selectedServer:u}):null,i===`capabilities`?(0,D.jsx)(st,{capabilityTab:n,onCapabilityTabChange:o,promptPreviewState:l,selectedServer:u}):null,i===`activity`?(0,D.jsx)(ft,{activityFilter:t,filteredActivity:a,onActivityFilterChange:ee,selectedServer:u}):null]})]})}):(0,D.jsx)(`div`,{className:`min-h-0 overflow-hidden`,children:(0,D.jsx)(_,{title:`Select an MCP server`,action:(0,D.jsx)(m,{type:`button`,size:`sm`,onClick:c,children:`Quick Add`}),minHeightClassName:`h-full`})})}function nt({actions:e,dialog:t,selectedServer:n}){return(0,D.jsxs)(`div`,{className:`flex flex-wrap items-start justify-between gap-4 border-b border-border pb-4`,children:[(0,D.jsxs)(`div`,{children:[(0,D.jsxs)(`div`,{className:`flex flex-wrap items-center gap-3`,children:[(0,D.jsx)(`h2`,{className:`text-[18px] font-medium text-foreground`,children:n.config.name}),(0,D.jsx)(g,{uppercase:!0,className:p(H(n.snapshot.status)),children:V(n.snapshot.status)}),U(n)?(0,D.jsx)(g,{tone:`primary`,children:U(n)}):null]}),(0,D.jsxs)(`p`,{className:`mt-2 text-[13px] text-muted-foreground`,children:[n.config.transport,` · Auth`,` `,B(n.snapshot.auth_status)]}),n.snapshot.last_error?(0,D.jsx)(`p`,{className:`mt-2 max-w-3xl text-[13px] leading-6 text-destructive`,children:n.snapshot.last_error}):null]}),(0,D.jsx)(rt,{actions:e,dialog:t,serverRecord:n})]})}function rt({actions:e,buttonClassName:t,dialog:n,serverRecord:r}){return(0,D.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2`,children:[(0,D.jsx)(m,{type:`button`,variant:`outline`,className:p(Q,t),onClick:()=>e.toggleEnabled(r),children:r.config.enabled?`Disable`:`Enable`}),(0,D.jsx)(m,{type:`button`,variant:`outline`,disabled:Pe(r),className:p(Q,t),onClick:()=>r.snapshot.auth_status===`connected`?e.logout(r.config.name):e.login(r.config.name),children:Ne(r)}),(0,D.jsx)(m,{type:`button`,variant:`outline`,className:p(Q,t),onClick:()=>n.openEditDialog(r),children:`Edit`}),(0,D.jsx)(m,{type:`button`,variant:`outline`,className:p(Q,t),onClick:()=>e.refreshServer(r.config.name),children:`Refresh`}),(0,D.jsx)(m,{type:`button`,variant:`outline`,className:p(We,t),onClick:()=>e.deleteServer(r.config.name),children:`Remove`})]})}function it({selectedServer:e}){return(0,D.jsxs)(`div`,{className:`grid gap-4 xl:grid-cols-2`,children:[(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Status`}),(0,D.jsx)(`p`,{className:`mt-3 text-[22px] font-medium text-foreground`,children:V(e.snapshot.status)}),(0,D.jsxs)(`p`,{className:`mt-2 text-[13px] text-muted-foreground`,children:[`Auth `,B(e.snapshot.auth_status)]})]}),(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Visibility`}),(0,D.jsx)(`p`,{className:`mt-3 text-[22px] font-medium text-foreground`,children:U(e)??`Pending`})]}),(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Last Refresh`}),(0,D.jsx)(`p`,{className:`mt-3 text-[15px] font-medium text-foreground`,children:R(e.snapshot.last_refresh_at)}),(0,D.jsxs)(`p`,{className:`mt-2 text-[13px] text-muted-foreground`,children:[`Result`,` `,z(e.snapshot.last_refresh_result)]})]}),(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Timeouts`}),(0,D.jsxs)(`p`,{className:`mt-3 text-[15px] font-medium text-foreground`,children:[`Startup `,e.config.startup_timeout_sec,`s`]}),(0,D.jsxs)(`p`,{className:`mt-2 text-[13px] text-muted-foreground`,children:[`Tool `,e.config.tool_timeout_sec,`s`]})]}),(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Tool Filters`}),(0,D.jsx)(`p`,{className:`mt-3 text-[15px] font-medium text-foreground`,children:Me(e)}),(0,D.jsxs)(`p`,{className:`mt-2 text-[13px] text-muted-foreground`,children:[`Enabled `,e.config.enabled_tools.length,` · `,`Disabled `,e.config.disabled_tools.length]})]}),(0,D.jsxs)(S,{className:p(`xl:col-span-2`,Y),children:[(0,D.jsx)(`p`,{className:Z,children:`Capability Summary`}),(0,D.jsx)(`div`,{className:`mt-4 grid gap-3 sm:grid-cols-2 xl:grid-cols-4`,children:Object.entries(e.snapshot.capability_counts).map(([e,t])=>(0,D.jsxs)(y,{as:`div`,padding:`sm`,className:`bg-card/20`,children:[(0,D.jsx)(`p`,{className:Z,children:e.replaceAll(`_`,` `)}),(0,D.jsx)(`p`,{className:`mt-2 text-xl font-medium text-foreground`,children:t})]},e))})]}),e.config.launcher?(0,D.jsx)(S,{className:p(`xl:col-span-2`,Y),children:(0,D.jsxs)(`div`,{className:`grid gap-4 xl:grid-cols-2`,children:[(0,D.jsx)(J,{label:`Original Launcher`,value:G(e.config.launcher),mono:!0}),(0,D.jsx)(J,{label:`Parsed Result`,value:Ae(e),mono:!0})]})}):null,e.config.transport===`stdio`?(0,D.jsx)(at,{selectedServer:e}):(0,D.jsx)(ot,{selectedServer:e})]})}function at({selectedServer:e}){return(0,D.jsx)(S,{className:p(`xl:col-span-2`,Y),children:(0,D.jsxs)(`div`,{className:`grid gap-4 xl:grid-cols-2`,children:[(0,D.jsx)(J,{label:`Command`,value:G(e.config.command),mono:!0}),(0,D.jsx)(J,{label:`Cwd`,value:G(e.config.cwd),mono:!0}),(0,D.jsx)(J,{label:`Args`,value:K(e.config.args),mono:!0}),(0,D.jsx)(J,{label:`Env Vars`,value:K(e.config.env_vars),mono:!0})]})})}function ot({selectedServer:e}){return(0,D.jsxs)(S,{className:p(`xl:col-span-2`,Y),children:[(0,D.jsxs)(`div`,{className:`grid gap-4 xl:grid-cols-2`,children:[(0,D.jsx)(J,{label:`URL`,value:G(e.config.url),mono:!0}),(0,D.jsx)(J,{label:`OAuth Resource`,value:G(e.config.oauth_resource),mono:!0}),(0,D.jsx)(J,{label:`Bearer Token Env Var`,value:G(e.config.bearer_token_env_var),mono:!0}),(0,D.jsx)(J,{label:`Scopes`,value:K(e.config.scopes),mono:!0}),(0,D.jsx)(J,{label:`HTTP Headers`,value:Fe(e.config.http_headers),mono:!0}),(0,D.jsx)(J,{label:`Env HTTP Headers`,value:K(e.config.env_http_headers),mono:!0})]}),(0,D.jsxs)(y,{as:`div`,padding:`sm`,className:`mt-4 bg-card/20`,children:[(0,D.jsx)(`p`,{className:Z,children:`Recent Auth Result`}),(0,D.jsx)(`p`,{className:`mt-2 text-[14px] font-medium text-foreground`,children:Be(e.snapshot.last_auth_result??``,`No login action yet`)}),(0,D.jsxs)(`p`,{className:`mt-2 text-[13px] text-muted-foreground`,children:[`Current auth status`,` `,B(e.snapshot.auth_status)]})]})]})}function st({capabilityTab:e,onCapabilityTabChange:t,promptPreviewState:n,selectedServer:r}){return(0,D.jsxs)(`div`,{className:`space-y-4`,children:[(0,D.jsx)(`div`,{className:`flex flex-wrap gap-4 border-b border-border`,children:P.map(n=>(0,D.jsx)(Ue,{active:e===n,label:n===`resource_templates`?`Resource Templates`:z(n),onClick:()=>t(n),variant:`tab`},n))}),e===`tools`?(0,D.jsx)(ct,{selectedServer:r}):null,e===`resources`?(0,D.jsx)(lt,{selectedServer:r}):null,e===`resource_templates`?(0,D.jsx)(ut,{selectedServer:r}):null,e===`prompts`?(0,D.jsx)(dt,{promptPreviewState:n,selectedServer:r}):null]})}function ct({selectedServer:e}){return e.snapshot.tools.length===0?(0,D.jsx)(S,{className:p(Y,X),children:`No tools discovered.`}):(0,D.jsx)(`div`,{className:`space-y-3`,children:e.snapshot.tools.map(e=>(0,D.jsxs)(S,{className:Y,children:[(0,D.jsxs)(`div`,{className:`flex flex-wrap items-start justify-between gap-3`,children:[(0,D.jsxs)(`div`,{children:[(0,D.jsx)(`p`,{className:`font-mono text-[13px] text-foreground`,children:e.tool_name}),e.title?(0,D.jsx)(`p`,{className:`mt-2 text-[13px] text-foreground/70`,children:e.title}):null,(0,D.jsx)(`p`,{className:`mt-1 text-[12px] text-muted-foreground`,children:e.fully_qualified_id})]}),(0,D.jsxs)(`div`,{className:`flex flex-wrap gap-2 text-[10px]`,children:[e.read_only_hint?(0,D.jsx)(g,{tone:`primary`,children:`readOnly`}):null,e.destructive_hint?(0,D.jsx)(g,{tone:`danger`,children:`destructive`}):null,e.open_world_hint?(0,D.jsx)(g,{tone:`idle`,children:`openWorld`}):null]})]}),e.description?(0,D.jsx)(`p`,{className:$,children:e.description}):null,(0,D.jsx)(b,{className:Ge,children:JSON.stringify(e.parameters??{},null,2)})]},e.fully_qualified_id))})}function lt({selectedServer:e}){return e.snapshot.resources.length===0?(0,D.jsx)(S,{className:p(Y,X),children:`No resources discovered.`}):(0,D.jsx)(`div`,{className:`space-y-3`,children:e.snapshot.resources.map(e=>(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:`text-[14px] font-medium text-foreground`,children:e.name}),(0,D.jsx)(`p`,{className:`mt-1 font-mono text-[12px] text-muted-foreground`,children:e.uri}),(0,D.jsx)(`p`,{className:`mt-3 text-[13px] text-foreground/70`,children:e.mime_type??`Unknown MIME`}),e.description?(0,D.jsx)(`p`,{className:$,children:e.description}):null]},e.uri))})}function ut({selectedServer:e}){return e.snapshot.resource_templates.length===0?(0,D.jsx)(S,{className:p(Y,X),children:`No resource templates discovered.`}):(0,D.jsx)(`div`,{className:`space-y-3`,children:e.snapshot.resource_templates.map(e=>(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:`text-[14px] font-medium text-foreground`,children:e.name}),(0,D.jsx)(`p`,{className:`mt-1 font-mono text-[12px] text-muted-foreground`,children:e.uri_template}),e.description?(0,D.jsx)(`p`,{className:$,children:e.description}):null]},e.uri_template))})}function dt({promptPreviewState:e,selectedServer:t}){return(0,D.jsxs)(`div`,{className:`grid gap-4 xl:grid-cols-[minmax(0,0.9fr)_minmax(0,1.1fr)]`,children:[(0,D.jsx)(`div`,{className:`space-y-3`,children:t.snapshot.prompts.length===0?(0,D.jsx)(S,{className:p(Y,X),children:`No prompts discovered.`}):t.snapshot.prompts.map(n=>(0,D.jsxs)(m,{type:`button`,variant:`ghost`,onClick:()=>e.selectPrompt(t.config.name,n.name),className:p(`h-auto w-full flex-col items-stretch rounded-xl border border-border bg-card/20 p-5 text-left transition-colors hover:text-inherit`,e.selectedPromptName===n.name?`border-border bg-accent/20`:`hover:bg-accent/20`),children:[(0,D.jsx)(`p`,{className:`text-[14px] font-medium text-foreground`,children:n.name}),n.description?(0,D.jsx)(`p`,{className:$,children:n.description}):null,(0,D.jsx)(b,{className:Ge,children:JSON.stringify(n.arguments??[],null,2)})]},n.name))}),(0,D.jsxs)(S,{className:Y,children:[(0,D.jsx)(`p`,{className:Z,children:`Prompt Preview`}),e.selectedPromptName?(0,D.jsxs)(D.Fragment,{children:[(0,D.jsx)(`p`,{className:`mt-3 text-[15px] font-medium text-foreground`,children:e.selectedPromptName}),(0,D.jsx)(`p`,{className:`mt-4 text-[11px] text-muted-foreground/80`,children:`Arguments`}),(0,D.jsx)(c,{value:e.argumentsText,onChange:t=>e.setArgumentsText(t.target.value),className:`mt-2 min-h-[120px] bg-background/50 font-mono text-[11px] text-foreground/80`}),(0,D.jsxs)(`div`,{className:`mt-3 flex items-center justify-between gap-3`,children:[(0,D.jsx)(`p`,{className:`text-[12px] text-muted-foreground`,children:`Edit argument JSON, then refresh the preview.`}),(0,D.jsx)(m,{type:`button`,variant:`outline`,className:Q,onClick:e.previewCurrent,children:`Preview`})]}),e.selectedPrompt?.arguments?.length?(0,D.jsx)(b,{className:p(Ge,`max-h-40`),children:JSON.stringify(e.selectedPrompt.arguments,null,2)}):null,(0,D.jsx)(b,{className:p(Ge,`max-h-[420px]`),children:e.loading?`Loading preview...`:JSON.stringify(e.preview??{},null,2)})]}):(0,D.jsx)(`p`,{className:`mt-4 text-[13px] text-muted-foreground`,children:`Select a prompt to preview it.`})]})]})}function ft({activityFilter:e,filteredActivity:t,onActivityFilterChange:n,selectedServer:r}){return(0,D.jsxs)(`div`,{className:`space-y-4`,children:[(0,D.jsx)(`div`,{className:`flex flex-wrap gap-2`,children:I.map(t=>(0,D.jsx)(Ue,{active:e===t.value,label:t.label,onClick:()=>n(t.value)},t.value))}),t.length===0?(0,D.jsx)(S,{className:p(Y,X),children:r.activity.length===0?`No recent MCP activity.`:`No activity matches the current filter.`}):t.map(e=>(0,D.jsx)(pt,{activityRecord:e},e.id))]})}function pt({activityRecord:e}){return(0,D.jsxs)(S,{className:Y,children:[(0,D.jsxs)(`div`,{className:`flex flex-wrap items-start justify-between gap-3`,children:[(0,D.jsxs)(`div`,{children:[(0,D.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2`,children:[(0,D.jsx)(g,{tone:`neutral`,children:Re(e)}),(0,D.jsx)(`p`,{className:`text-[14px] font-medium text-foreground`,children:z(e.action)})]}),(0,D.jsx)(`p`,{className:`mt-2 text-[12px] text-muted-foreground`,children:R(e.started_at)})]}),(0,D.jsx)(g,{uppercase:!0,className:p(Se(e.result)),children:e.result})]}),(0,D.jsx)(`p`,{className:`mt-3 text-[13px] leading-6 text-muted-foreground`,children:e.summary}),(0,D.jsxs)(`div`,{className:`mt-3 flex flex-wrap gap-4 text-[12px] text-muted-foreground`,children:[e.actor_node_id?(0,D.jsxs)(`span`,{children:[`Node `,e.actor_node_id.slice(0,8)]}):null,e.tab_id?(0,D.jsxs)(`span`,{children:[`Workflow `,e.tab_id.slice(0,8)]}):null,e.tool_name?(0,D.jsxs)(`span`,{children:[`Tool `,e.tool_name]}):null,e.target?(0,D.jsxs)(`span`,{children:[`Target `,e.target]}):null,(0,D.jsxs)(`span`,{children:[Math.round(e.duration_ms),` ms`]}),(0,D.jsx)(`span`,{children:xe(e.ended_at)})]})]})}function mt(){let{actions:e,activityFilter:t,capabilityTab:n,clearServerFilters:r,detailTab:i,dialog:o,error:s,filteredActivity:c,filteredServers:l,focusQuickAdd:u,isLoading:d,promptPreviewState:f,quickAdd:p,selectedServer:h,serverStatusFilter:te,servers:g,setActivityFilter:_,setCapabilityTab:v,setDetailTab:y,setSelectedServerName:b,setServerStatusFilter:ne,summaryCounts:re}=He();return(0,D.jsxs)(x,{children:[(0,D.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col px-8 py-6`,children:[(0,D.jsx)(ie,{title:`MCP`,actions:(0,D.jsxs)(D.Fragment,{children:[(0,D.jsxs)(m,{type:`button`,variant:`outline`,className:Q,onClick:()=>void e.refreshAll(),children:[(0,D.jsx)(ee,{className:`mr-2 size-4`}),`Refresh`]}),(0,D.jsxs)(m,{type:`button`,variant:`outline`,className:Q,onClick:u,children:[(0,D.jsx)(a,{className:`mr-2 size-4`}),`Quick Add`]}),(0,D.jsxs)(m,{type:`button`,onClick:o.openCreateDialog,children:[(0,D.jsx)(a,{className:`mr-2 size-4`}),`Advanced Add`]})]})}),(0,D.jsx)(`div`,{className:`mt-6 min-h-0 flex-1 overflow-hidden`,children:d?(0,D.jsx)(Ke,{}):s?(0,D.jsx)(qe,{}):g.length===0?(0,D.jsx)(Je,{quickAdd:p,dialog:o}):(0,D.jsx)(Xe,{actions:e,activityFilter:t,capabilityTab:n,clearServerFilters:r,detailTab:i,dialog:o,filteredActivity:c,filteredServers:l,onActivityFilterChange:_,onCapabilityTabChange:v,onDetailTabChange:y,onFocusQuickAdd:u,onSelectServer:b,onServerStatusFilterChange:ne,promptPreviewState:f,quickAdd:p,selectedServer:h,serverStatusFilter:te,summaryCounts:re})})]}),(0,D.jsx)(be,{draft:o.draft,onChange:o.setDraft,open:o.open,pending:o.pending,title:o.editingServerName?`Edit MCP Server`:`Advanced Add MCP Server`,onOpenChange:o.setOpen,onSubmit:()=>void o.saveServer()})]})}export{mt as McpPage};
@@ -0,0 +1 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{c as t,d as n,l as r}from"./graph-vendor-DRq_-6fV.js";import{Lt as i}from"./ui-vendor-UazN8rcv.js";import{a,i as o,n as s,r as c,rt as l,tt as u}from"./index-Biio-CoI.js";import{s as d}from"./surface-Bzr1FRG4.js";var f=e(n(),1),p=t(),m=Object.prototype.hasOwnProperty;function h(e,t){var n,r;if(e===t)return!0;if(e&&t&&(n=e.constructor)===t.constructor){if(n===Date)return e.getTime()===t.getTime();if(n===RegExp)return e.toString()===t.toString();if(n===Array){if((r=e.length)===t.length)for(;r--&&h(e[r],t[r]););return r===-1}if(!n||typeof e==`object`){for(n in r=0,e)if(m.call(e,n)&&++r&&!m.call(t,n)||!(n in t)||!h(e[n],t[n]))return!1;return Object.keys(t).length===r}}return e!==e&&t!==t}var g=new WeakMap,_=()=>{},v=void 0,y=Object,b=e=>e===v,x=e=>typeof e==`function`,S=(e,t)=>({...e,...t}),ee=e=>x(e.then),C={},w={},T=`undefined`,E=typeof window!=T,D=typeof document!=T,O=E&&`Deno`in window,k=()=>E&&typeof window.requestAnimationFrame!=T,te=(e,t)=>{let n=g.get(e);return[()=>!b(t)&&e.get(t)||C,r=>{if(!b(t)){let i=e.get(t);t in w||(w[t]=i),n[5](t,S(i,r),i||C)}},n[6],()=>!b(t)&&t in w?w[t]:!b(t)&&e.get(t)||C]},A=!0,j=()=>A,[M,N]=E&&window.addEventListener?[window.addEventListener.bind(window),window.removeEventListener.bind(window)]:[_,_],P=()=>{let e=D&&document.visibilityState;return b(e)||e!==`hidden`},ne=e=>(D&&document.addEventListener(`visibilitychange`,e),M(`focus`,e),()=>{D&&document.removeEventListener(`visibilitychange`,e),N(`focus`,e)}),re=e=>{let t=()=>{A=!0,e()},n=()=>{A=!1};return M(`online`,t),M(`offline`,n),()=>{N(`online`,t),N(`offline`,n)}},ie={isOnline:j,isVisible:P},F={initFocus:ne,initReconnect:re},ae=!f.useId,I=!E||O,oe=e=>k()?window.requestAnimationFrame(e):setTimeout(e,1),L=I?f.useEffect:f.useLayoutEffect,R=typeof navigator<`u`&&navigator.connection,z=!I&&R&&([`slow-2g`,`2g`].includes(R.effectiveType)||R.saveData),B=new WeakMap,se=e=>y.prototype.toString.call(e),V=(e,t)=>e===`[object ${t}]`,ce=0,H=e=>{let t=typeof e,n=se(e),r=V(n,`Date`),i=V(n,`RegExp`),a=V(n,`Object`),o,s;if(y(e)===e&&!r&&!i){if(o=B.get(e),o)return o;if(o=++ce+`~`,B.set(e,o),Array.isArray(e)){for(o=`@`,s=0;s<e.length;s++)o+=H(e[s])+`,`;B.set(e,o)}if(a){o=`#`;let t=y.keys(e).sort();for(;!b(s=t.pop());)b(e[s])||(o+=s+`:`+H(e[s])+`,`);B.set(e,o)}}else o=r?e.toJSON():t==`symbol`?e.toString():t==`string`?JSON.stringify(e):``+e;return o},le=e=>{if(x(e))try{e=e()}catch{e=``}let t=e;return e=typeof e==`string`?e:(Array.isArray(e)?e.length:e)?H(e):``,[e,t]},U=0,ue=()=>++U;async function de(...e){let[t,n,r,i]=e,a=S({populateCache:!0,throwOnError:!0},typeof i==`boolean`?{revalidate:i}:i||{}),o=a.populateCache,s=a.rollbackOnError,c=a.optimisticData,l=e=>typeof s==`function`?s(e):s!==!1,u=a.throwOnError;if(x(n)){let e=n,r=[],i=t.keys();for(let n of i)!/^\$(inf|sub)\$/.test(n)&&e(t.get(n)._k)&&r.push(n);return Promise.all(r.map(d))}return d(n);async function d(n){let[i]=le(n);if(!i)return;let[s,d]=te(t,i),[f,p,m,h]=g.get(t),_=()=>{let e=f[i];return(x(a.revalidate)?a.revalidate(s().data,n):a.revalidate!==!1)&&(delete m[i],delete h[i],e&&e[0])?e[0](2).then(()=>s().data):s().data};if(e.length<3)return _();let y=r,S,C=!1,w=ue();p[i]=[w,0];let T=!b(c),E=s(),D=E.data,O=E._c,k=b(O)?D:O;if(T&&(c=x(c)?c(k,D):c,d({data:c,_c:k})),x(y))try{y=y(k)}catch(e){S=e,C=!0}if(y&&ee(y))if(y=await y.catch(e=>{S=e,C=!0}),w!==p[i][0]){if(C)throw S;return y}else C&&T&&l(S)&&(o=!0,d({data:k,_c:v}));if(o&&(C||(x(o)?d({data:o(y,k),error:v,_c:v}):d({data:y,error:v,_c:v}))),p[i][1]=ue(),Promise.resolve(_()).then(()=>{d({_c:v})}),C){if(u)throw S;return}return y}}var W=(e,t)=>{for(let n in e)e[n][0]&&e[n][0](t)},G=(e,t)=>{if(!g.has(e)){let n=S(F,t),r=Object.create(null),i=de.bind(v,e),a=_,o=Object.create(null),s=(e,t)=>{let n=o[e]||[];return o[e]=n,n.push(t),()=>n.splice(n.indexOf(t),1)},c=(t,n,r)=>{e.set(t,n);let i=o[t];if(i)for(let e of i)e(n,r)},l=()=>{if(!g.has(e)&&(g.set(e,[r,Object.create(null),Object.create(null),Object.create(null),i,c,s]),!I)){let t=n.initFocus(setTimeout.bind(v,W.bind(v,r,0))),i=n.initReconnect(setTimeout.bind(v,W.bind(v,r,1)));a=()=>{t&&t(),i&&i(),g.delete(e)}}};return l(),[e,i,l,a]}return[e,g.get(e)[4]]},K=(e,t,n,r,i)=>{let a=n.errorRetryCount,o=i.retryCount,s=~~((Math.random()+.5)*(1<<(o<8?o:8)))*n.errorRetryInterval;!b(a)&&o>a||setTimeout(r,s,i)},q=h,[J,fe]=G(new Map),Y=S({onLoadingSlow:_,onSuccess:_,onError:_,onErrorRetry:K,onDiscarded:_,revalidateOnFocus:!0,revalidateOnReconnect:!0,revalidateIfStale:!0,shouldRetryOnError:!0,errorRetryInterval:z?1e4:5e3,focusThrottleInterval:5*1e3,dedupingInterval:2*1e3,loadingTimeout:z?5e3:3e3,compare:q,isPaused:()=>!1,cache:J,mutate:fe,fallback:{}},ie),X=(e,t)=>{let n=S(e,t);if(t){let{use:r,fallback:i}=e,{use:a,fallback:o}=t;r&&a&&(n.use=r.concat(a)),i&&o&&(n.fallback=S(i,o))}return n},Z=(0,f.createContext)({}),pe=e=>{let{value:t}=e,n=(0,f.useContext)(Z),r=x(t),i=(0,f.useMemo)(()=>r?t(n):t,[r,n,t]),a=(0,f.useMemo)(()=>r?i:X(n,i),[r,n,i]),o=i&&i.provider,s=(0,f.useRef)(v);o&&!s.current&&(s.current=G(o(a.cache||J),i));let c=s.current;return c&&(a.cache=c[0],a.mutate=c[1]),L(()=>{if(c)return c[2]&&c[2](),c[3]},[]),(0,f.createElement)(Z.Provider,S(e,{value:a}))},Q=E&&window.__SWR_DEVTOOLS_USE__,me=Q?window.__SWR_DEVTOOLS_USE__:[],he=()=>{Q&&(window.__SWR_DEVTOOLS_REACT__=f.default)},ge=e=>x(e[1])?[e[0],e[1],e[2]||{}]:[e[0],null,(e[1]===null?e[2]:e[1])||{}],_e=()=>{let e=(0,f.useContext)(Z);return(0,f.useMemo)(()=>S(Y,e),[e])},ve=me.concat(e=>(t,n,r)=>e(t,n&&((...e)=>{let[r]=le(t),[,,,i]=g.get(J);if(r.startsWith(`$inf$`))return n(...e);let a=i[r];return b(a)?n(...e):(delete i[r],a)}),r)),ye=e=>function(...t){let n=_e(),[r,i,a]=ge(t),o=X(n,a),s=e,{use:c}=o,l=(c||[]).concat(ve);for(let e=l.length;e--;)s=l[e](s);return s(r,i||o.fetcher||null,o)},be=(e,t,n)=>{let r=t[e]||(t[e]=[]);return r.push(n),()=>{let e=r.indexOf(n);e>=0&&(r[e]=r[r.length-1],r.pop())}};he();var xe=f.use||(e=>{switch(e.status){case`pending`:throw e;case`fulfilled`:return e.value;case`rejected`:throw e.reason;default:throw e.status=`pending`,e.then(t=>{e.status=`fulfilled`,e.value=t},t=>{e.status=`rejected`,e.reason=t}),e}}),Se={dedupe:!0},Ce=Promise.resolve(v),we=()=>_,Te=(e,t,n)=>{let{cache:r,compare:i,suspense:a,fallbackData:o,revalidateOnMount:s,revalidateIfStale:c,refreshInterval:l,refreshWhenHidden:u,refreshWhenOffline:d,keepPreviousData:m,strictServerPrefetchWarning:h}=n,[_,y,C,w]=g.get(r),[T,E]=le(e),D=(0,f.useRef)(!1),O=(0,f.useRef)(!1),k=(0,f.useRef)(T),A=(0,f.useRef)(t),j=(0,f.useRef)(n),M=()=>j.current,N=()=>M().isVisible()&&M().isOnline(),[P,ne,re,ie]=te(r,T),F=(0,f.useRef)({}).current,R=b(o)?b(n.fallback)?v:n.fallback[T]:o,z=(e,t)=>{for(let n in F){let r=n;if(r===`data`){if(!i(e[r],t[r])&&(!b(e[r])||!i(K,t[r])))return!1}else if(t[r]!==e[r])return!1}return!0},B=!D.current,se=(0,f.useMemo)(()=>{let e=P(),n=ie(),r=e=>{let n=S(e);return delete n._k,!(!T||!t||M().isPaused())&&(B&&!b(s)?s:b(b(R)?n.data:R)||c)?{isValidating:!0,isLoading:!0,...n}:n},i=r(e),a=e===n?i:r(n),o=i;return[()=>{let e=r(P());return z(e,o)?(o.data=e.data,o.isLoading=e.isLoading,o.isValidating=e.isValidating,o.error=e.error,o):(o=e,e)},()=>a]},[r,T]),V=(0,p.useSyncExternalStore)((0,f.useCallback)(e=>re(T,(t,n)=>{z(n,t)||e()}),[r,T]),se[0],se[1]),ce=_[T]&&_[T].length>0,H=V.data,U=b(H)?R&&ee(R)?xe(R):R:H,W=V.error,G=(0,f.useRef)(U),K=m?b(H)?b(G.current)?U:G.current:H:U,q=T&&b(U),J=(0,f.useRef)(null);!I&&(0,p.useSyncExternalStore)(we,()=>(J.current=!1,J),()=>(J.current=!0,J));let fe=J.current;h&&fe&&!a&&q&&console.warn(`Missing pre-initiated data for serialized key "${T}" during server-side rendering. Data fetching should be initiated on the server and provided to SWR via fallback data. You can set "strictServerPrefetchWarning: false" to disable this warning.`);let Y=!T||!t||M().isPaused()||ce&&!b(W)?!1:B&&!b(s)?s:a?b(U)?!1:c:b(U)||c,X=B&&Y,Z=b(V.isValidating)?X:V.isValidating,pe=b(V.isLoading)?X:V.isLoading,Q=(0,f.useCallback)(async e=>{let t=A.current;if(!T||!t||O.current||M().isPaused())return!1;let r,a,o=!0,s=e||{},c=!C[T]||!s.dedupe,l=()=>ae?!O.current&&T===k.current&&D.current:T===k.current,u={isValidating:!1,isLoading:!1},d=()=>{ne(u)},f=()=>{let e=C[T];e&&e[1]===a&&delete C[T]},p={isValidating:!0};b(P().data)&&(p.isLoading=!0);try{if(c&&(ne(p),n.loadingTimeout&&b(P().data)&&setTimeout(()=>{o&&l()&&M().onLoadingSlow(T,n)},n.loadingTimeout),C[T]=[t(E),ue()]),[r,a]=C[T],r=await r,c&&setTimeout(f,n.dedupingInterval),!C[T]||C[T][1]!==a)return c&&l()&&M().onDiscarded(T),!1;u.error=v;let e=y[T];if(!b(e)&&(a<=e[0]||a<=e[1]||e[1]===0))return d(),c&&l()&&M().onDiscarded(T),!1;let s=P().data;u.data=i(s,r)?s:r,c&&l()&&M().onSuccess(r,T,n)}catch(e){f();let t=M(),{shouldRetryOnError:n}=t;t.isPaused()||(u.error=e,c&&l()&&(t.onError(e,T,t),(n===!0||x(n)&&n(e))&&(!M().revalidateOnFocus||!M().revalidateOnReconnect||N())&&t.onErrorRetry(e,T,t,e=>{let t=_[T];t&&t[0]&&t[0](3,e)},{retryCount:(s.retryCount||0)+1,dedupe:!0})))}return o=!1,d(),!0},[T,r]),me=(0,f.useCallback)((...e)=>de(r,k.current,...e),[]);if(L(()=>{A.current=t,j.current=n,b(H)||(G.current=H)}),L(()=>{if(!T)return;let e=Q.bind(v,Se),t=0;M().revalidateOnFocus&&(t=Date.now()+M().focusThrottleInterval);let n=be(T,_,(n,r={})=>{if(n==0){let n=Date.now();M().revalidateOnFocus&&n>t&&N()&&(t=n+M().focusThrottleInterval,e())}else if(n==1)M().revalidateOnReconnect&&N()&&e();else if(n==2)return Q();else if(n==3)return Q(r)});return O.current=!1,k.current=T,D.current=!0,ne({_k:E}),Y&&(C[T]||(b(U)||I?e():oe(e))),()=>{O.current=!0,n()}},[T]),L(()=>{let e;function t(){let t=x(l)?l(P().data):l;t&&e!==-1&&(e=setTimeout(n,t))}function n(){!P().error&&(u||M().isVisible())&&(d||M().isOnline())?Q(Se).then(t):t()}return t(),()=>{e&&=(clearTimeout(e),-1)}},[l,u,d,T]),(0,f.useDebugValue)(K),a){if(!ae&&I&&q)throw Error(`Fallback data is required when using Suspense in SSR.`);q&&(A.current=t,j.current=n,O.current=!1);let e=w[T];if(xe(!b(e)&&q?me(e):Ce),!b(W)&&q)throw W;let r=q?Q(Se):Ce;!b(K)&&q&&(r.status=`fulfilled`,r.value=!0),xe(r)}return{mutate:me,get data(){return F.data=!0,K},get error(){return F.error=!0,W},get isValidating(){return F.isValidating=!0,Z},get isLoading(){return F.isLoading=!0,pe}}};y.defineProperty(pe,`defaultValue`,{value:Y});var Ee=ye(Te),$=r();function De({children:e,className:t}){return(0,$.jsx)(`div`,{className:l(`flex h-full flex-col min-h-0 overflow-hidden`,t),children:e})}function Oe({children:e,className:t}){return(0,$.jsx)(d,{as:`section`,padding:`md`,className:l(`border-transparent bg-card/[0.18] ring-1 ring-white/[0.04]`,t),children:e})}function ke({actions:e,className:t,hint:n,title:r}){return(0,$.jsx)(`div`,{className:l(`border-b border-border/70 pb-4`,t),children:(0,$.jsxs)(`div`,{className:`flex flex-wrap items-start justify-between gap-4`,children:[(0,$.jsxs)(`div`,{className:`flex min-w-0 items-center gap-2`,children:[(0,$.jsx)(`h1`,{className:`text-[28px] font-medium tracking-[-0.04em] text-foreground`,children:r}),n?(0,$.jsx)(o,{delayDuration:150,children:(0,$.jsxs)(s,{children:[(0,$.jsx)(a,{asChild:!0,children:(0,$.jsx)(u,{type:`button`,variant:`ghost`,size:`icon-sm`,className:`inline-flex size-7 items-center justify-center rounded-full border border-border/70 bg-card/20 text-muted-foreground transition-colors hover:bg-accent/35 hover:text-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50`,"aria-label":`${r} details`,children:(0,$.jsx)(i,{className:`size-3.5`})})}),(0,$.jsx)(c,{side:`right`,className:`max-w-xs px-3 py-2`,children:n})]})}):null]}),e?(0,$.jsx)(`div`,{className:`flex shrink-0 flex-wrap items-center gap-2`,children:e}):null]})})}function Ae({title:e}){return(0,$.jsx)(`div`,{className:`mb-4`,children:(0,$.jsx)(`h2`,{className:`text-[14px] font-medium tracking-tight text-foreground/90`,children:e})})}function je({children:e,className:t,contentClassName:n,separated:r=!1,title:i}){return(0,$.jsxs)(`section`,{className:l(r?`border-t border-border pt-8`:`mb-10`,t),children:[(0,$.jsx)(Ae,{title:i}),(0,$.jsx)(`div`,{className:l(`rounded-xl border border-white/[0.04] bg-card/[0.03] shadow-sm px-5 transition-colors`,n),children:e})]})}function Me({label:e,description:t,children:n,valueClassName:r}){return(0,$.jsxs)(`div`,{className:`flex flex-col gap-2 border-b border-border/40 py-5 last:border-b-0 md:flex-row md:items-start md:justify-between md:gap-8 hover:bg-muted/10 transition-colors`,children:[(0,$.jsxs)(`div`,{className:`min-w-0 shrink-0 md:w-[35%] pt-1`,children:[(0,$.jsx)(`label`,{className:`block text-[13px] font-medium text-foreground/80 tracking-tight`,children:e}),t&&(0,$.jsx)(`p`,{className:`mt-1 text-[12px] text-muted-foreground/70 leading-relaxed pr-4`,children:t})]}),(0,$.jsx)(`div`,{className:l(`w-full min-w-0 flex-1 md:w-[65%] flex md:justify-end`,r),children:(0,$.jsx)(`div`,{className:`w-full md:max-w-md space-y-3`,children:n})})]})}function Ne({label:e,description:t,children:n}){return(0,$.jsxs)(`div`,{className:`flex flex-col gap-3 border-b border-border/40 py-5 last:border-b-0 hover:bg-muted/10 transition-colors`,children:[(0,$.jsxs)(`div`,{className:`min-w-0 pt-1`,children:[(0,$.jsx)(`label`,{className:`block text-[13px] font-medium text-foreground/80 tracking-tight`,children:e}),t&&(0,$.jsx)(`p`,{className:`mt-1.5 text-[12px] text-muted-foreground/70 leading-relaxed max-w-2xl`,children:t})]}),(0,$.jsx)(`div`,{className:`w-full mt-1`,children:n})]})}function Pe({children:e,className:t}){return(0,$.jsx)(`div`,{className:l(`mt-3 flex flex-col gap-3 rounded-lg border border-border/40 bg-background/30 p-4`,t),children:e})}export{Me as a,Ee as c,Pe as i,De as n,Ne as o,ke as r,Oe as s,je as t};
@@ -0,0 +1 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{Lt as r,dt as i,q as a}from"./ui-vendor-UazN8rcv.js";import{B as o,a as s,i as c,n as l,q as u,r as d,s as f,tt as p}from"./index-Biio-CoI.js";import{l as m,s as h}from"./surface-Bzr1FRG4.js";import{c as g,n as _,r as v}from"./PageScaffold-DteOA8V7.js";async function y(){return o(`/api/prompts`,{errorMessage:`Failed to fetch prompts`})}async function b(e){return o(`/api/prompts`,{method:`PUT`,body:e,errorMessage:`Failed to save prompts`})}var x=e(t(),1),S=n(),C=`min-h-0 w-full flex-1 resize-none select-text rounded-md bg-transparent p-3 font-mono text-[13px] leading-relaxed text-foreground placeholder:text-muted-foreground transition-colors focus:bg-background/35 focus:outline-none scrollbar-none`;function w(){let{data:e,isLoading:t,mutate:n}=g(`promptSettings`,y),[r,o]=(0,x.useState)(``),[s,c]=(0,x.useState)(``),[l,d]=(0,x.useState)(!1);(0,x.useEffect)(()=>{e&&(o(e.custom_prompt),c(e.custom_post_prompt))},[e]);let w=async()=>{d(!0);try{n(await b({custom_prompt:r,custom_post_prompt:s}),!1),a.success(`Prompts saved`)}catch{a.error(`Failed to save prompts`)}finally{d(!1)}};return t?(0,S.jsx)(f,{label:`Loading prompts...`,textClassName:`text-[13px]`}):(0,S.jsx)(_,{children:(0,S.jsxs)(`div`,{className:`mx-auto flex h-full w-full max-w-[800px] flex-col px-4 pb-10 pt-6`,children:[(0,S.jsx)(v,{title:`Prompts`,hint:`Custom Prompt is appended to the global system prompt layer. Custom Post Prompt is appended after the built-in runtime post prompt.`,actions:(0,S.jsxs)(p,{type:`button`,onClick:()=>void w(),disabled:l,size:`sm`,className:`text-[13px]`,children:[(0,S.jsx)(i,{className:`size-4`}),l?`Saving...`:`Save Changes`]})}),(0,S.jsxs)(`div`,{className:`grid min-h-0 flex-1 gap-8 pt-6`,children:[(0,S.jsxs)(`div`,{className:`flex min-h-0 flex-col`,children:[(0,S.jsx)(`div`,{className:`mb-3 flex items-center justify-between px-1`,children:(0,S.jsxs)(`div`,{className:`flex items-center gap-3`,children:[(0,S.jsx)(`h2`,{className:`text-[15px] font-medium text-foreground`,children:`Custom Prompt`}),T(`Custom Prompt details`,`Appended to every node's system prompt.`),(0,S.jsxs)(m,{tone:`neutral`,className:`px-2 py-0.5`,children:[r.length,` chars`]})]})}),(0,S.jsx)(h,{as:`div`,padding:`none`,className:`relative flex min-h-0 flex-1 p-1`,children:(0,S.jsx)(u,{"aria-label":`Custom Prompt`,value:r,onChange:e=>o(e.target.value),placeholder:`Appended to every node's system prompt...`,className:C,mono:!0})})]}),(0,S.jsxs)(`div`,{className:`flex min-h-0 flex-col`,children:[(0,S.jsx)(`div`,{className:`mb-3 flex items-center justify-between px-1`,children:(0,S.jsxs)(`div`,{className:`flex items-center gap-3`,children:[(0,S.jsx)(`h2`,{className:`text-[15px] font-medium text-foreground`,children:`Custom Post Prompt`}),T(`Custom Post Prompt details`,`Appended after the built-in runtime post prompt.`),(0,S.jsxs)(m,{tone:`neutral`,className:`px-2 py-0.5`,children:[s.length,` chars`]})]})}),(0,S.jsx)(h,{as:`div`,padding:`none`,className:`relative flex min-h-0 flex-1 p-1`,children:(0,S.jsx)(u,{"aria-label":`Custom Post Prompt`,value:s,onChange:e=>c(e.target.value),placeholder:`Appended after the built-in runtime post prompt...`,className:C,mono:!0})})]})]})]})})}var T=(e,t)=>(0,S.jsx)(c,{delayDuration:150,children:(0,S.jsxs)(l,{children:[(0,S.jsx)(s,{asChild:!0,children:(0,S.jsx)(p,{type:`button`,variant:`ghost`,size:`icon-xs`,"aria-label":e,className:`rounded-full text-muted-foreground hover:bg-accent/35 hover:text-foreground`,children:(0,S.jsx)(r,{className:`size-3.5`})})}),(0,S.jsx)(d,{className:`max-w-xs`,children:t})]})});export{w as PromptsPage};
@@ -0,0 +1,3 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{_t as r,bt as i,nn as a,pt as o,q as s,sn as c,st as l,tt as u,xt as d}from"./ui-vendor-UazN8rcv.js";import{B as f,G as p,J as m,Q as h,V as g,W as _,d as ee,f as v,l as y,q as te,rt as b,tt as x}from"./index-Biio-CoI.js";import{l as ne,o as S,s as C}from"./surface-Bzr1FRG4.js";import{a as w,c as re,n as ie,r as ae,t as T}from"./PageScaffold-DteOA8V7.js";import{a as E,i as D,n as O,r as k,t as A}from"./select-D9SwnlXF.js";import{a as j,i as M,o as N,r as P,s as F,t as I}from"./dialog-BOvHIBrg.js";import{i as L,n as R,r as z,t as B}from"./triState-DgLlKdRR.js";import{a as oe,c as se,i as ce,n as le,o as ue,r as V,s as H,t as U}from"./alert-dialog-DIBUCmqM.js";async function de(){return f(`/api/providers`,{errorMessage:`Failed to fetch providers`,fallback:[],map:e=>e?.providers??[]})}async function fe(e){return f(`/api/providers`,{method:`POST`,body:e,errorMessage:`Failed to create provider`})}async function pe(e,t){return f(`/api/providers/${e}`,{method:`PUT`,body:t,errorMessage:`Failed to update provider`})}async function me(e){await g(`/api/providers/${e}`,{method:`DELETE`,errorMessage:`Failed to delete provider`})}async function he(e){return f(`/api/providers/models`,{method:`POST`,body:e,errorMessage:`Failed to fetch provider models`,fallback:[],map:e=>e?.models??[]})}async function W(e){return f(`/api/providers/models/test`,{method:`POST`,body:e,errorMessage:`Failed to test provider model`})}function G(e){return typeof e==`object`&&!!e&&!Array.isArray(e)}function ge(e){return!e||Object.keys(e).length===0?``:JSON.stringify(e,null,2)}function _e(e){if(!e.trim())return{headers:{},error:null};let t;try{t=JSON.parse(e)}catch{return{headers:{},error:`Headers must be valid JSON`}}if(!G(t))return{headers:{},error:`Headers must be a JSON object`};let n={};for(let[e,r]of Object.entries(t)){if(typeof r!=`string`)return{headers:{},error:`Headers values must all be strings`};n[e]=r}return{headers:n,error:null}}function K(e){return e?{name:e.name,type:e.type,base_url:e.base_url,api_key:e.api_key,headers_text:ge(e.headers),retry_429_delay_seconds:e.retry_429_delay_seconds,models:e.models.map(e=>({...e}))}:{name:``,type:`openai_compatible`,base_url:``,api_key:``,headers_text:``,retry_429_delay_seconds:0,models:[]}}function q(e){return{model:e?.model??``,context_window_tokens:e?.context_window_tokens===null||e?.context_window_tokens===void 0?``:String(e.context_window_tokens),input_image:R(e?.input_image??null),output_image:R(e?.output_image??null),structured_output:R(e?.structured_output??null),source:e?.source??`manual`}}function J(e){return JSON.stringify({name:e.name,type:e.type,base_url:e.base_url,api_key:e.api_key,headers_text:e.headers_text,retry_429_delay_seconds:e.retry_429_delay_seconds,models:e.models})}function Y(e,t){return{name:e.name,type:e.type,base_url:e.base_url,api_key:e.api_key,headers:t,retry_429_delay_seconds:e.retry_429_delay_seconds,models:e.models}}function X(e,t,n){return{provider_id:n,name:e.name,type:e.type,base_url:e.base_url,api_key:e.api_key,headers:t,retry_429_delay_seconds:e.retry_429_delay_seconds}}function ve(e,t){let n=new Map(e.map(e=>[e.model,e])),r=new Map(t.map(e=>[e.model,e])),i=[];for(let t of e){let e=r.get(t.model);if(!e){i.push(t);continue}if(t.source===`manual`){i.push({...t,context_window_tokens:t.context_window_tokens??e.context_window_tokens,input_image:t.input_image??e.input_image,output_image:t.output_image??e.output_image,structured_output:t.structured_output??e.structured_output}),r.delete(t.model);continue}i.push(e),r.delete(t.model)}for(let e of t)n.has(e.model)||i.push(e);return i}function ye(e){let t=[];return e.context_window_tokens!==null&&t.push(`${e.context_window_tokens.toLocaleString()} tokens`),e.input_image!==null&&t.push(`input_image=${e.input_image?`true`:`false`}`),e.output_image!==null&&t.push(`output_image=${e.output_image?`true`:`false`}`),e.structured_output!==null&&e.structured_output!==void 0&&t.push(`structured_output=${e.structured_output?`true`:`false`}`),t.length>0?t.join(` · `):`No capability metadata`}function Z(e){let t=new Set;for(let n of e){let e=n.model.trim();if(t.has(e))return e;t.add(e)}return null}function be(e){return e.model.trim()?e.context_window_tokens&&!/^\d+$/.test(e.context_window_tokens)?`Context Window must be a positive integer`:null:`Model ID is required`}function xe(e){let t=B(e.structured_output??`auto`);return{model:e.model.trim(),source:e.source,context_window_tokens:e.context_window_tokens?Number.parseInt(e.context_window_tokens,10):null,input_image:B(e.input_image),output_image:B(e.output_image),...t===null?{}:{structured_output:t}}}var Q=n();function Se({draft:e,onClose:t,onDraftChange:n,onSave:r,state:i}){return(0,Q.jsx)(I,{open:i!==null,onOpenChange:e=>{e||t()},children:(0,Q.jsxs)(P,{children:[(0,Q.jsxs)(N,{children:[(0,Q.jsx)(F,{children:i?.mode===`edit`?`Edit Model`:`Add Model`}),(0,Q.jsx)(M,{className:`sr-only`,children:i?.mode===`edit`?`Edit Model`:`Add Model`})]}),(0,Q.jsxs)(`div`,{className:`space-y-4 px-5 py-4`,children:[(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Model ID`}),(0,Q.jsx)(p,{"aria-label":`Model ID`,value:e.model,onChange:t=>n({...e,model:t.target.value}),placeholder:`gpt-5`,mono:!0})]}),(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Source`}),(0,Q.jsx)(`div`,{className:`rounded-md border border-border bg-card/30 px-3 py-2 text-[13px] text-foreground/80`,children:e.source===`manual`?`Manual`:`Discovered`})]}),(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Context Window`}),(0,Q.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,Q.jsx)(p,{"aria-label":`Context Window`,inputMode:`numeric`,pattern:`[0-9]*`,value:e.context_window_tokens,onChange:t=>{let r=t.target.value.trim();/^\d*$/.test(r)&&n({...e,context_window_tokens:r})},placeholder:`Optional`,mono:!0}),(0,Q.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`tokens`})]})]}),(0,Q.jsxs)(`div`,{className:`grid gap-4 sm:grid-cols-3`,children:[(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Input Image`}),(0,Q.jsxs)(A,{value:e.input_image,onValueChange:t=>n({...e,input_image:t}),children:[(0,Q.jsx)(D,{className:h,children:(0,Q.jsx)(E,{})}),(0,Q.jsxs)(O,{className:`rounded-xl border-border bg-popover`,children:[(0,Q.jsx)(k,{value:`auto`,children:`Auto`}),(0,Q.jsx)(k,{value:`enabled`,children:`Enabled`}),(0,Q.jsx)(k,{value:`disabled`,children:`Disabled`})]})]})]}),(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Output Image`}),(0,Q.jsxs)(A,{value:e.output_image,onValueChange:t=>n({...e,output_image:t}),children:[(0,Q.jsx)(D,{className:h,children:(0,Q.jsx)(E,{})}),(0,Q.jsxs)(O,{className:`rounded-xl border-border bg-popover`,children:[(0,Q.jsx)(k,{value:`auto`,children:`Auto`}),(0,Q.jsx)(k,{value:`enabled`,children:`Enabled`}),(0,Q.jsx)(k,{value:`disabled`,children:`Disabled`})]})]})]}),(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Structured Output`}),(0,Q.jsxs)(A,{value:e.structured_output??`auto`,onValueChange:t=>n({...e,structured_output:t}),children:[(0,Q.jsx)(D,{className:h,children:(0,Q.jsx)(E,{})}),(0,Q.jsxs)(O,{className:`rounded-xl border-border bg-popover`,children:[(0,Q.jsx)(k,{value:`auto`,children:`Auto`}),(0,Q.jsx)(k,{value:`enabled`,children:`Enabled`}),(0,Q.jsx)(k,{value:`disabled`,children:`Disabled`})]})]})]})]})]}),(0,Q.jsxs)(j,{className:`px-5 pb-5`,children:[(0,Q.jsx)(x,{variant:`ghost`,onClick:t,children:`Cancel`}),(0,Q.jsx)(x,{onClick:r,children:i?.mode===`edit`?`Save Model`:`Add Model`})]})]})})}function Ce({isDragging:e,loading:t,onCreate:n,onDelete:i,onRefresh:a,onResizeStart:s,onSelect:d,panelWidth:f,providers:p,selectedId:m}){return(0,Q.jsxs)(`div`,{style:{width:`${f}px`},className:`relative flex shrink-0 flex-col border-r border-border bg-card/20 pt-8 pl-8`,children:[(0,Q.jsxs)(`div`,{className:`flex shrink-0 items-center justify-between px-5 py-4`,children:[(0,Q.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,Q.jsx)(l,{className:`size-4 text-muted-foreground`}),(0,Q.jsx)(`span`,{className:`text-[13px] font-medium text-foreground/80`,children:`Providers`})]}),(0,Q.jsxs)(`div`,{className:`flex items-center gap-1`,children:[(0,Q.jsx)(_,{onClick:a,disabled:t,className:`size-7`,children:(0,Q.jsx)(o,{className:b(`size-3.5`,t&&`animate-spin`)})}),(0,Q.jsx)(_,{onClick:n,className:`size-7`,children:(0,Q.jsx)(r,{className:`size-3.5`})})]})]}),(0,Q.jsx)(`div`,{className:`min-h-0 flex-1 overflow-y-auto px-3 pb-4`,children:t?(0,Q.jsx)(`div`,{className:`space-y-1`,children:[...[,,,]].map((e,t)=>(0,Q.jsx)(`div`,{className:`h-10 w-full animate-pulse rounded-lg bg-accent/20`},t))}):p.length===0?(0,Q.jsxs)(c.div,{initial:{opacity:0},animate:{opacity:1},className:`py-10 text-center`,children:[(0,Q.jsx)(`p`,{className:`text-[13px] text-muted-foreground`,children:`No providers`}),(0,Q.jsxs)(x,{type:`button`,size:`sm`,onClick:n,className:`mt-4`,children:[(0,Q.jsx)(r,{className:`size-3`}),`Add your first provider`]})]}):(0,Q.jsx)(`div`,{className:`space-y-0.5`,children:p.map((e,t)=>(0,Q.jsxs)(c.div,{initial:{opacity:0,x:-4},animate:{opacity:1,x:0},transition:{delay:t*.03},className:b(`group relative flex w-full items-center justify-between rounded-lg transition-all`,m===e.id?`bg-accent/55 text-foreground`:`text-muted-foreground hover:bg-accent/30 hover:text-foreground`),children:[(0,Q.jsx)(`div`,{className:b(`absolute inset-y-1 left-0 w-px rounded-full bg-ring/60 transition-opacity`,m===e.id?`opacity-100`:`opacity-0`)}),(0,Q.jsx)(x,{type:`button`,variant:`ghost`,onClick:()=>d(e),className:`h-auto min-w-0 flex-1 justify-start rounded-lg bg-transparent px-3 py-2.5 text-left text-inherit shadow-none hover:bg-transparent hover:text-inherit focus-visible:ring-2 focus-visible:ring-ring/50`,children:(0,Q.jsxs)(`span`,{className:`min-w-0 flex-1 pl-2`,children:[(0,Q.jsx)(`span`,{className:`block truncate text-[13px] font-medium`,children:e.name}),(0,Q.jsx)(`span`,{className:`block truncate text-[11px] text-muted-foreground`,children:z(e.type)})]})}),(0,Q.jsx)(_,{onClick:()=>{i(e)},className:`mr-2 size-6 shrink-0 border-transparent bg-transparent opacity-0 transition-opacity hover:bg-destructive/10 hover:text-destructive group-hover:opacity-100`,children:(0,Q.jsx)(u,{className:`size-3`})})]},e.id))})}),(0,Q.jsx)(y,{position:`right`,isDragging:e,onMouseDown:s})]})}var $=e(t(),1),we={openai_compatible:`/v1`,openai_responses:`/v1`,anthropic:`/v1`,gemini:`/v1beta`},Te={openai_compatible:`/chat/completions`,openai_responses:`/responses`,anthropic:`/messages`,gemini:`/models/{model}:streamGenerateContent`},Ee=Array.from(new Set(Object.values(we))).sort((e,t)=>t.length-e.length);function De(e){return e.trim().toLowerCase()}function Oe(e){return e.trim().replace(/\/+$/,``)}function ke(e,t){let n=De(e),r=we[n],i=Oe(t);if(!r||!i)return{resolvedBaseUrl:null,error:null};let a=i.toLowerCase();for(let e of Ee)if(a.endsWith(e))return e===r?{resolvedBaseUrl:i,error:null}:{resolvedBaseUrl:null,error:`Base URL suffix '${e}' does not match type '${n}' (expected '${r}')`};return{resolvedBaseUrl:`${i}${r}`,error:null}}function Ae(e,t){let n=De(e),r=Te[n],{resolvedBaseUrl:i,error:a}=ke(n,t);return a?{previewUrl:null,error:a}:!i||!r?{previewUrl:null,error:null}:{previewUrl:`${i}${r}`,error:null}}function je(){let[e,t]=(0,$.useState)(null),[n,r]=(0,$.useState)(!1),[i,a]=(0,$.useState)(K()),[o,c]=(0,$.useState)(!1),[l,u]=(0,$.useState)(null),[d,f]=(0,$.useState)(!1),[p,m]=(0,$.useState)(!1),[h,g]=(0,$.useState)(null),[_,y]=(0,$.useState)(q()),[te,b]=(0,$.useState)({}),{data:x=[],isLoading:ne,mutate:S}=re(`providers`,de,{onSuccess:n=>{!e||n.find(t=>t.id===e)||(t(null),r(!1),a(K()),b({}),f(!1))}}),[C,w]=v(`providers-panel-width`,300,200,500),{isDragging:ie,startDrag:ae}=ee(C,w,`right`),T=(0,$.useMemo)(()=>x.find(t=>t.id===e),[x,e]),E=(0,$.useMemo)(()=>Ae(i.type,i.base_url),[i.base_url,i.type]),D=(0,$.useMemo)(()=>_e(i.headers_text),[i.headers_text]),O=(0,$.useMemo)(()=>{let e=n?K():K(T);return J(i)!==J(e)},[i,n,T]),k=(0,$.useCallback)(async()=>{await S()},[S]),A=(0,$.useCallback)(e=>{t(e.id),r(!1),a(K(e)),b({}),g(null),f(!1)},[]),j=(0,$.useCallback)(()=>{r(!0),t(null),a(K()),b({}),g(null),f(!1)},[]),M=(0,$.useCallback)(()=>{n?(r(!1),a(K())):a(K(T)),b({}),g(null),f(!1)},[n,T]),N=(0,$.useCallback)(async()=>{if(!i.name.trim()){s.error(`Provider name is required`);return}if(!i.base_url.trim()){s.error(`Provider base URL is required`);return}if(E.error){s.error(E.error);return}if(D.error){s.error(D.error);return}let o=Z(i.models);if(o){s.error(`Model ID '${o}' is duplicated`);return}let l=Y(i,D.headers);c(!0);try{if(n){let e=await fe(l);S([...x,e],!1),r(!1),t(e.id),a(K(e)),s.success(`Provider created`)}else if(e){let t=await pe(e,l);S(x.map(n=>n.id===e?t:n),!1),a(K(t)),s.success(`Provider updated`)}b({}),f(!1)}catch{s.error(n?`Failed to create provider`:`Failed to update provider`)}finally{c(!1)}},[i,E.error,n,S,D.error,D.headers,x,e]),P=(0,$.useCallback)(async()=>{if(!l)return;let n=l.id;u(null),f(!1);try{await me(n),S(x.filter(e=>e.id!==n),!1),e===n&&(t(null),a(K())),b({}),s.success(`Provider deleted`)}catch{s.error(`Failed to delete provider`)}},[S,l,x,e]),F=(0,$.useCallback)(()=>{g({mode:`create`,originalModel:null}),y(q())},[]),I=(0,$.useCallback)(e=>{g({mode:`edit`,originalModel:e.model}),y(q(e))},[]),L=(0,$.useCallback)(()=>{g(null),y(q())},[]),R=(0,$.useCallback)(()=>{let e=be(_);if(e){s.error(e);return}let t=_.model.trim();if(i.models.some(e=>e.model===t&&e.model!==h?.originalModel)){s.error(`Model ID '${t}' already exists in this provider`);return}let n=xe(_);a(e=>h?.mode===`edit`&&h.originalModel?{...e,models:e.models.map(e=>e.model===h.originalModel?n:e)}:{...e,models:[...e.models,n]}),b(e=>{let n={...e};return h?.originalModel&&h.originalModel!==t&&delete n[h.originalModel],n}),L()},[L,i.models,_,h]),z=(0,$.useCallback)(e=>{a(t=>({...t,models:t.models.filter(t=>t.model!==e)})),b(t=>{let n={...t};return delete n[e],n})},[]),B=(0,$.useCallback)(()=>{i.models.length!==0&&f(!0)},[i.models.length]);return{cancelClearModels:(0,$.useCallback)(()=>{f(!1)},[]),clearModelsConfirmOpen:d,draft:i,endpointPreview:E,fetchingModels:p,handleCancel:M,handleClearModels:(0,$.useCallback)(()=>{a(e=>({...e,models:[]})),b({}),f(!1)},[]),handleCreateNew:j,handleDelete:P,handleDeleteModel:z,handleFetchModels:(0,$.useCallback)(async()=>{if(!i.type.trim()||!i.base_url.trim()){s.error(`Provider type and base URL are required before fetching models`);return}if(E.error){s.error(E.error);return}if(D.error){s.error(D.error);return}m(!0);try{let t=await he(X(i,D.headers,e??void 0));a(e=>({...e,models:ve(e.models,t)})),s.success(`Provider models fetched`)}catch(e){s.error(e instanceof Error?e.message:`Failed to fetch provider models`)}finally{m(!1)}},[i,E.error,D.error,D.headers,e]),handleSave:N,handleSaveModel:R,handleSelect:A,handleTestModel:(0,$.useCallback)(async t=>{if(E.error){s.error(E.error);return}if(D.error){s.error(D.error);return}b(e=>({...e,[t.model]:{state:`running`}}));try{let n=await W({...X(i,D.headers,e??void 0),model:t.model});b(e=>({...e,[t.model]:n.ok?{state:`success`,duration_ms:n.duration_ms??0}:{state:`error`,error_summary:n.error_summary??`Provider test failed`}}))}catch(e){b(n=>({...n,[t.model]:{state:`error`,error_summary:e instanceof Error?e.message:`Provider test failed`}}))}},[i,E.error,D.error,D.headers,e]),hasChanges:O,isCreating:n,isDragging:ie,loading:ne,modelEditorDraft:_,modelEditorState:h,modelTestStates:te,openCreateModelDialog:F,openEditModelDialog:I,panelWidth:C,parsedHeaders:D,providerToDelete:l,providers:x,refreshProviders:k,requestClearModels:B,saving:o,selectedId:e,selectedProvider:T,setDraft:a,setModelEditorDraft:y,setProviderToDelete:u,startDrag:ae,closeModelDialog:L}}function Me(){let{cancelClearModels:e,clearModelsConfirmOpen:t,draft:n,endpointPreview:s,fetchingModels:f,handleCancel:g,handleClearModels:_,handleCreateNew:ee,handleDelete:v,handleDeleteModel:y,handleFetchModels:re,handleSave:j,handleSaveModel:M,handleSelect:N,handleTestModel:P,hasChanges:F,isCreating:I,isDragging:R,loading:z,modelEditorDraft:B,modelEditorState:de,modelTestStates:fe,openCreateModelDialog:pe,openEditModelDialog:me,panelWidth:he,parsedHeaders:W,providerToDelete:G,providers:ge,refreshProviders:_e,requestClearModels:K,saving:q,selectedId:J,selectedProvider:Y,setDraft:X,setModelEditorDraft:ve,setProviderToDelete:Z,startDrag:be,closeModelDialog:xe}=je();return(0,Q.jsx)(ie,{className:`overflow-hidden px-4 pt-6 sm:px-5`,children:(0,Q.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col`,children:[(0,Q.jsx)(ae,{title:`Providers`}),(0,Q.jsxs)(C,{as:`div`,padding:`none`,className:`mt-6 flex min-h-0 flex-1 overflow-hidden border-border/60 bg-card/[0.14]`,children:[(0,Q.jsx)(Ce,{isDragging:R,loading:z,onCreate:ee,onDelete:Z,onRefresh:()=>{_e()},onResizeStart:be,onSelect:N,panelWidth:he,providers:ge,selectedId:J}),(0,Q.jsx)(`div`,{className:`min-w-0 flex-1 overflow-y-auto bg-transparent`,children:I||Y?(0,Q.jsxs)(`div`,{className:`flex min-h-full flex-col px-8 py-8 md:px-12 md:py-10`,children:[(0,Q.jsxs)(`div`,{className:`mb-8 flex items-center justify-between`,children:[(0,Q.jsxs)(`div`,{children:[(0,Q.jsx)(`h2`,{className:`text-xl font-medium text-foreground`,children:I?`New Provider`:Y?.name}),I?null:(0,Q.jsx)(`p`,{className:`mt-1 select-text font-mono text-[12px] text-muted-foreground`,children:Y?.id})]}),(0,Q.jsx)(`div`,{className:`flex items-center gap-2`,children:F?(0,Q.jsxs)(Q.Fragment,{children:[(0,Q.jsx)(x,{type:`button`,variant:`ghost`,size:`sm`,onClick:g,disabled:q,children:`Cancel`}),(0,Q.jsxs)(x,{type:`button`,size:`sm`,onClick:()=>void j(),disabled:q,children:[(0,Q.jsx)(a,{className:`size-3.5`}),q?`Saving...`:`Save`]})]}):null})]}),(0,Q.jsxs)(`div`,{className:`mx-auto w-full max-w-[720px] flex-1`,children:[(0,Q.jsxs)(T,{title:`Identity`,className:`mb-10`,contentClassName:`rounded-lg border-dashed bg-card/30`,children:[(0,Q.jsx)(w,{label:`Name`,children:(0,Q.jsx)(p,{value:n.name,onChange:e=>X({...n,name:e.target.value}),placeholder:`e.g., OpenAI Production`})}),(0,Q.jsx)(w,{label:`Type`,children:(0,Q.jsxs)(A,{value:n.type,onValueChange:e=>X({...n,type:e}),children:[(0,Q.jsx)(D,{className:h,children:(0,Q.jsx)(E,{})}),(0,Q.jsx)(O,{className:`rounded-xl border-border bg-popover`,children:L.map(e=>(0,Q.jsx)(k,{value:e.value,className:`text-[13px]`,children:e.label},e.value))})]})})]}),(0,Q.jsxs)(T,{title:`Endpoint & Auth`,separated:!0,contentClassName:`rounded-lg border-dashed bg-card/30`,children:[(0,Q.jsx)(w,{label:`Base URL`,children:(0,Q.jsx)(p,{value:n.base_url,onChange:e=>X({...n,base_url:e.target.value}),placeholder:`https://api.openai.com/v1`})}),(0,Q.jsx)(w,{label:`Request Preview`,children:(0,Q.jsx)(`div`,{className:b(`w-full select-text rounded-md border px-3 py-2 text-[12px]`,s.error?`border-destructive/20 bg-destructive/8 text-destructive`:`border-border bg-card/30 text-foreground/80`),children:s.error?s.error:s.previewUrl?(0,Q.jsx)(`code`,{className:`select-text font-mono`,children:s.previewUrl}):(0,Q.jsx)(`span`,{className:`text-muted-foreground`,children:`Enter a base URL to preview`})})}),(0,Q.jsx)(w,{label:`API Key`,children:(0,Q.jsx)(m,{value:n.api_key,onChange:e=>X({...n,api_key:e.target.value}),placeholder:`sk-...`,mono:!0,showLabel:`Show API key`,hideLabel:`Hide API key`})}),(0,Q.jsx)(w,{label:`Headers`,children:(0,Q.jsxs)(`div`,{className:`space-y-2`,children:[(0,Q.jsx)(te,{value:n.headers_text,onChange:e=>X({...n,headers_text:e.target.value}),placeholder:`{
2
+ "Authorization": "Bearer ..."
3
+ }`,spellCheck:!1,className:b(`min-h-[140px]`,W.error?`border-destructive/30 text-destructive focus-visible:border-destructive/50 focus-visible:ring-destructive/20`:``),mono:!0}),W.error?(0,Q.jsx)(`p`,{className:`text-[11px] text-destructive`,children:W.error}):null]})}),(0,Q.jsx)(w,{label:`429 Retry Delay`,children:(0,Q.jsx)(`div`,{className:`space-y-2`,children:(0,Q.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,Q.jsx)(p,{"aria-label":`429 Retry Delay`,inputMode:`numeric`,pattern:`[0-9]*`,value:String(n.retry_429_delay_seconds),onChange:e=>{let t=e.target.value.trim();if(!/^\d+$/.test(t))return;let r=Number.parseInt(t,10);!Number.isSafeInteger(r)||r<0||X({...n,retry_429_delay_seconds:r})},mono:!0}),(0,Q.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`s`})]})})})]}),(0,Q.jsx)(`div`,{className:`border-t border-border pt-8`,children:(0,Q.jsxs)(T,{title:`Models`,contentClassName:`space-y-4 bg-card/30 p-5`,children:[(0,Q.jsxs)(`div`,{className:`flex flex-wrap items-center justify-between gap-3`,children:[(0,Q.jsx)(`div`,{children:(0,Q.jsxs)(`p`,{className:`text-[13px] font-medium text-foreground/80`,children:[n.models.length,` model`,n.models.length===1?``:`s`]})}),(0,Q.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,Q.jsxs)(x,{type:`button`,variant:`ghost`,size:`sm`,disabled:f,onClick:()=>void re(),children:[(0,Q.jsx)(o,{className:b(`size-3.5`,f&&`animate-spin`)}),`Fetch Models`]}),(0,Q.jsxs)(x,{type:`button`,variant:`outline`,size:`sm`,onClick:pe,children:[(0,Q.jsx)(r,{className:`size-3.5`}),`Add Model`]}),(0,Q.jsxs)(x,{type:`button`,variant:`ghost`,size:`sm`,disabled:n.models.length===0||f,onClick:K,children:[(0,Q.jsx)(u,{className:`size-3.5`}),`Clear Models`]})]})]}),n.models.length===0?(0,Q.jsxs)(C,{as:`div`,padding:`sm`,className:`border-dashed bg-background/35 py-5 text-center`,children:[(0,Q.jsx)(`p`,{className:`text-[13px] font-medium text-foreground/80`,children:`No models in this provider draft`}),(0,Q.jsx)(`p`,{className:`mt-1 text-[11px] leading-relaxed text-muted-foreground`,children:`Fetch models or add a manual entry.`})]}):(0,Q.jsx)(`div`,{className:`space-y-2`,children:n.models.map(e=>{let t=fe[e.model];return(0,Q.jsx)(C,{as:`div`,padding:`sm`,className:`bg-background/35`,children:(0,Q.jsxs)(`div`,{className:`flex flex-wrap items-start justify-between gap-3`,children:[(0,Q.jsxs)(`div`,{className:`min-w-0 flex-1`,children:[(0,Q.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2`,children:[(0,Q.jsx)(`p`,{className:`truncate select-text font-mono text-[13px] text-foreground/85`,children:e.model}),(0,Q.jsx)(ne,{tone:e.source===`manual`?`idle`:`running`,className:`px-2 py-0.5`,children:e.source===`manual`?`Manual`:`Discovered`})]}),(0,Q.jsx)(`p`,{className:`mt-1 select-text text-[11px] leading-relaxed text-muted-foreground`,children:ye(e)}),t?.state===`running`?(0,Q.jsx)(`p`,{className:`mt-2 select-text text-[11px] text-muted-foreground`,children:`Testing this model against the current draft provider...`}):null,t?.state===`success`?(0,Q.jsxs)(`p`,{className:`mt-2 select-text text-[11px] text-graph-status-running`,children:[`Test succeeded in`,` `,t.duration_ms,`ms`]}):null,t?.state===`error`?(0,Q.jsx)(`p`,{className:`mt-2 select-text text-[11px] text-destructive`,children:t.error_summary}):null]}),(0,Q.jsxs)(`div`,{className:`flex shrink-0 items-center gap-1.5`,children:[(0,Q.jsxs)(x,{type:`button`,variant:`ghost`,size:`sm`,disabled:t?.state===`running`,onClick:()=>void P(e),children:[(0,Q.jsx)(i,{className:`size-3.5`}),`Test`]}),(0,Q.jsxs)(x,{type:`button`,variant:`ghost`,size:`sm`,onClick:()=>me(e),children:[(0,Q.jsx)(d,{className:`size-3.5`}),`Edit`]}),(0,Q.jsxs)(x,{type:`button`,variant:`ghost`,size:`sm`,onClick:()=>y(e.model),children:[(0,Q.jsx)(u,{className:`size-3.5`}),`Delete`]})]})]})},e.model)})})]})}),!I&&Y?(0,Q.jsx)(`div`,{className:`border-t border-border pt-8`,children:(0,Q.jsx)(T,{title:`Provider`,contentClassName:`rounded-lg border-dashed bg-card/30`,children:(0,Q.jsx)(w,{label:`Provider ID`,children:(0,Q.jsx)(`div`,{className:`select-text rounded-md border border-border bg-card/30 px-3 py-2 font-mono text-[12px] text-foreground/80`,children:Y.id})})})}):null]})]}):(0,Q.jsx)(c.div,{initial:{opacity:0},animate:{opacity:1},className:`flex h-full flex-col items-center justify-center px-6 text-center`,children:(0,Q.jsx)(S,{icon:l,title:`No provider selected`,className:`border-transparent bg-transparent`})})})]}),(0,Q.jsx)(Se,{draft:B,onClose:xe,onDraftChange:ve,onSave:M,state:de}),(0,Q.jsx)(U,{open:t,onOpenChange:t=>{t||e()},children:(0,Q.jsxs)(ce,{children:[(0,Q.jsxs)(H,{children:[(0,Q.jsx)(se,{children:`Clear all models?`}),(0,Q.jsx)(oe,{children:`This removes every model from this provider, including discovered and manual entries. Save the provider to keep the cleared list.`})]}),(0,Q.jsxs)(ue,{children:[(0,Q.jsx)(V,{asChild:!0,children:(0,Q.jsx)(x,{type:`button`,variant:`ghost`,children:`Cancel`})}),(0,Q.jsx)(le,{asChild:!0,children:(0,Q.jsx)(x,{type:`button`,variant:`destructive`,onClick:_,children:`Clear Models`})})]})]})}),(0,Q.jsx)(U,{open:G!==null,onOpenChange:e=>{e||Z(null)},children:(0,Q.jsxs)(ce,{children:[(0,Q.jsxs)(H,{children:[(0,Q.jsx)(se,{children:`Delete provider?`}),(0,Q.jsx)(oe,{children:G?`This will permanently remove ${G.name}.`:`This will permanently remove the selected provider.`})]}),(0,Q.jsxs)(ue,{children:[(0,Q.jsx)(V,{asChild:!0,children:(0,Q.jsx)(x,{variant:`ghost`,children:`Cancel`})}),(0,Q.jsx)(le,{asChild:!0,children:(0,Q.jsx)(x,{variant:`destructive`,onClick:()=>void v(),children:`Delete`})})]})]})})]})})}export{Me as ProvidersPage};
@@ -0,0 +1 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{J as r,Lt as i,St as a,X as o,_t as s,pt as c,q as l,qt as u,sn as d,tt as f}from"./ui-vendor-UazN8rcv.js";import{a as p,i as m,n as h,t as g}from"./roles-BbIEIMeG.js";import{G as _,Q as v,W as y,Z as b,a as x,i as S,n as C,q as w,r as T,rt as E,s as D,tt as O,y as k}from"./index-Biio-CoI.js";import{l as A,o as j,s as M}from"./surface-Bzr1FRG4.js";import{a as N,c as ee,n as P,r as F,t as I}from"./PageScaffold-DteOA8V7.js";import{a as L,i as R,n as z,r as B,t as V}from"./select-D9SwnlXF.js";import{a as H,c as U,i as W,n as G,o as te,r as ne,s as re,t as ie}from"./alert-dialog-DIBUCmqM.js";import{i as ae,n as oe,r as se,t as K}from"./modelParams-DcEhGnu0.js";var q=n();function ce({onConfirmDelete:e,onOpenChange:t,roleToDelete:n}){return(0,q.jsx)(ie,{open:n!==null,onOpenChange:t,children:(0,q.jsxs)(W,{children:[(0,q.jsxs)(re,{children:[(0,q.jsx)(U,{children:`Delete role?`}),(0,q.jsx)(H,{children:n?`This will permanently remove ${n.name}.`:`This will permanently remove the selected role.`})]}),(0,q.jsxs)(te,{children:[(0,q.jsx)(ne,{asChild:!0,children:(0,q.jsx)(O,{variant:`ghost`,children:`Cancel`})}),(0,q.jsx)(G,{asChild:!0,children:(0,q.jsx)(O,{variant:`destructive`,onClick:()=>void e(),children:`Delete`})})]})]})})}function le({activeRole:e,draft:t,isReadOnly:n,onUpdateDraft:r,shouldLockIdentityFields:i}){let a=n||i;return(0,q.jsxs)(I,{title:`Identity`,className:`mb-10`,contentClassName:`rounded-lg border-dashed bg-card/30`,children:[(0,q.jsx)(N,{label:`Role Name`,children:(0,q.jsx)(_,{value:t.name,onChange:e=>r(t=>({...t,name:e.target.value})),readOnly:a,placeholder:`e.g., Code Reviewer`,className:E(a?b:``)})}),(0,q.jsx)(N,{label:`Description`,children:(0,q.jsx)(w,{value:t.description,onChange:e=>r(t=>({...t,description:e.target.value})),readOnly:a,placeholder:`Briefly explain what this role is best suited for`,rows:3,className:E(`resize-y`,a?b:``)})}),(0,q.jsx)(N,{label:`System Prompt`,children:(0,q.jsxs)(`div`,{className:`space-y-2`,children:[(0,q.jsx)(w,{value:t.system_prompt,onChange:e=>r(t=>({...t,system_prompt:e.target.value})),readOnly:a,placeholder:`You are a helpful assistant that...`,rows:12,className:E(`resize-y`,a?b:``),mono:!0}),a?(0,q.jsx)(`p`,{className:`text-[11px] text-muted-foreground`,children:e?.is_builtin||i?`Built-in role fields are locked.`:`View only.`}):null]})})]})}function J({disabled:e,isDefaultSelected:t,onSelectDefault:n,onSelectOverride:r,overrideLabel:i}){return(0,q.jsxs)(q.Fragment,{children:[(0,q.jsx)(O,{type:`button`,variant:`ghost`,size:`sm`,disabled:e,onClick:n,className:E(`h-8 rounded-md border px-3 text-[13px] font-medium transition-colors`,t?`border-border bg-accent/45 text-foreground`:`border-transparent bg-card/20 text-muted-foreground hover:bg-accent/25`,e&&`cursor-default`),children:`Use Settings Default`}),(0,q.jsx)(O,{type:`button`,variant:`ghost`,size:`sm`,disabled:e,onClick:r,className:E(`h-8 rounded-md border px-3 text-[13px] font-medium transition-colors`,t?`border-transparent bg-card/20 text-muted-foreground hover:bg-accent/25`:`border-border bg-accent/45 text-foreground`,e&&`cursor-default`),children:i}),t?(0,q.jsx)(A,{tone:`muted`,children:`Settings default`}):null]})}function ue({draft:e,isReadOnly:t,onModelParamsModeChange:n,onUpdateDraft:r}){let i=!oe(e.model_params);return(0,q.jsx)(I,{title:`Model Parameters`,className:`mb-10`,separated:!0,contentClassName:`border-transparent bg-transparent p-0 shadow-none`,children:(0,q.jsxs)(`div`,{className:`space-y-6`,children:[(0,q.jsxs)(`div`,{className:`flex flex-wrap gap-3`,children:[(0,q.jsx)(J,{disabled:t,isDefaultSelected:!i,onSelectDefault:()=>n(!1),onSelectOverride:()=>n(!0),overrideLabel:`Set Parameter Overrides`}),i?null:(0,q.jsx)(de,{})]}),i?(0,q.jsx)(M,{children:(0,q.jsx)(ae,{value:K(e.model_params),onChange:e=>r(t=>({...t,model_params:e})),disabled:t,emptyLabel:`Inherit settings default`,numberPlaceholder:`Inherit settings default`,reasoningDisableLabel:`Disable`})}):(0,q.jsx)(A,{tone:`muted`,children:`Settings default`})]})})}function de(){return(0,q.jsx)(S,{delayDuration:150,children:(0,q.jsxs)(C,{children:[(0,q.jsx)(x,{asChild:!0,children:(0,q.jsx)(O,{type:`button`,variant:`ghost`,size:`icon-xs`,className:`rounded-full text-muted-foreground hover:bg-accent/35 hover:text-foreground`,"aria-label":`Parameter override details`,children:(0,q.jsx)(i,{className:`size-3.5`})})}),(0,q.jsx)(T,{className:`max-w-xs`,children:`Overrides affect this role only. Unsupported fields may be ignored.`})]})})}function fe({availableProviderModels:e,draft:t,isReadOnly:n,onModelModeChange:r,onOpenProvidersPage:i,onProviderChange:a,onUpdateDraft:o,providers:s}){return(0,q.jsx)(I,{title:`Model Configuration`,className:`mb-10`,separated:!0,contentClassName:`border-transparent bg-transparent p-0 shadow-none`,children:(0,q.jsxs)(`div`,{className:`space-y-6`,children:[(0,q.jsx)(J,{disabled:n,isDefaultSelected:t.model===null,onSelectDefault:()=>r(!1),onSelectOverride:()=>r(!0),overrideLabel:`Set Role Override`}),t.model?(0,q.jsx)(M,{children:(0,q.jsxs)(`div`,{className:`grid gap-6 md:grid-cols-2`,children:[(0,q.jsxs)(`div`,{className:`space-y-2`,children:[(0,q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Provider`}),(0,q.jsxs)(V,{value:t.model.provider_id||void 0,onValueChange:a,disabled:n,children:[(0,q.jsx)(R,{className:v,children:(0,q.jsx)(L,{placeholder:`Select a provider`})}),(0,q.jsx)(z,{className:`rounded-xl border-border bg-popover`,children:s.map(e=>(0,q.jsx)(B,{value:e.id,className:`text-[13px]`,children:e.name},e.id))})]})]}),(0,q.jsx)(pe,{availableProviderModels:e,draft:t,isReadOnly:n,onOpenProvidersPage:i,onUpdateDraft:o}),(0,q.jsxs)(`div`,{className:`space-y-2 md:col-span-2`,children:[(0,q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Model ID`}),(0,q.jsx)(_,{value:t.model.model,onChange:e=>o(t=>({...t,model:t.model?{...t.model,model:e.target.value}:null})),readOnly:n,placeholder:`e.g., gpt-4o-mini`,className:E(n?b:``),mono:!0}),(0,q.jsx)(`p`,{className:`text-[11px] text-muted-foreground`,children:`Catalog or manual ID`})]})]})}):(0,q.jsx)(A,{tone:`muted`,children:`Settings default`})]})})}function pe({availableProviderModels:e,draft:t,isReadOnly:n,onOpenProvidersPage:r,onUpdateDraft:i}){let a=e.some(e=>e.model===t.model?.model)?t.model?.model:void 0;return(0,q.jsxs)(`div`,{className:`space-y-2`,children:[(0,q.jsx)(`label`,{className:`text-[13px] font-medium text-foreground/80`,children:`Provider Models`}),(0,q.jsxs)(V,{value:a,onValueChange:e=>i(t=>({...t,model:t.model?{...t.model,model:e}:null})),disabled:n||!t.model?.provider_id||e.length===0,children:[(0,q.jsx)(R,{className:v,children:(0,q.jsx)(L,{placeholder:e.length>0?`Pick a provider model`:`No saved provider models`})}),(0,q.jsx)(z,{className:`max-h-[300px] rounded-xl border-border bg-popover`,children:e.map(e=>(0,q.jsx)(B,{value:e.model,className:`text-[13px]`,children:e.model},e.model))})]}),e.length===0?(0,q.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2 text-[11px] text-muted-foreground`,children:[(0,q.jsx)(`span`,{children:`No saved provider models.`}),(0,q.jsx)(O,{type:`button`,variant:`outline`,size:`xs`,onClick:r,children:`Open Providers`})]}):null]})}function me({configurableTools:e,getToolState:t,isReadOnly:n,onToolStateCycle:r,shouldLockIdentityFields:i}){return(0,q.jsx)(I,{title:`Tool Configuration`,className:`mb-10`,separated:!0,contentClassName:`bg-card/30`,children:e.map(e=>(0,q.jsx)(he,{isDisabled:n||i,onToolStateCycle:r,state:t(e.name),tool:e},e.name))})}function he({isDisabled:e,onToolStateCycle:t,state:n,tool:r}){return(0,q.jsxs)(`div`,{className:`flex items-center justify-between gap-4 border-b border-border px-5 py-4 last:border-b-0`,children:[(0,q.jsxs)(`div`,{className:`min-w-0 flex-1`,title:r.description,children:[(0,q.jsx)(`p`,{className:`font-mono text-[13px] text-foreground/80`,children:r.name}),(0,q.jsx)(`p`,{className:`mt-1 truncate text-[12px] text-muted-foreground`,children:r.description})]}),(0,q.jsx)(O,{type:`button`,variant:`ghost`,size:`xs`,onClick:()=>t(r.name),disabled:e,className:E(`shrink-0 rounded-full px-3 py-1 text-xs font-medium transition-colors`,n===`included`&&`bg-accent/50 text-foreground`,n===`excluded`&&`bg-transparent text-muted-foreground line-through`,n===`allowed`&&`bg-accent/20 text-muted-foreground hover:bg-accent/35`,e&&`cursor-default hover:bg-inherit opacity-60`),children:n===`allowed`?`Allowed`:n===`included`?`Included`:`Excluded`})]})}function ge({activeRole:e,availableProviderModels:t,canSave:n,configurableTools:r,draft:i,getToolState:a,isReadOnly:o,onClosePanel:s,onEditRole:c,onModelModeChange:l,onModelParamsModeChange:u,onOpenProvidersPage:d,onProviderChange:f,onSaveRole:p,onToolStateCycle:m,onUpdateDraft:h,panelBadgeLabel:g,panelMode:_,panelTitle:v,providers:y,saving:b,shouldLockIdentityFields:x}){return(0,q.jsx)(`div`,{className:`h-full min-h-0 overflow-y-auto pr-2 scrollbar-none`,children:(0,q.jsxs)(`div`,{className:`mx-auto max-w-3xl pb-10`,children:[(0,q.jsx)(_e,{badgeLabel:g,onClosePanel:s,title:v}),(0,q.jsx)(le,{activeRole:e,draft:i,isReadOnly:o,onUpdateDraft:h,shouldLockIdentityFields:x}),(0,q.jsx)(fe,{availableProviderModels:t,draft:i,isReadOnly:o,onModelModeChange:l,onOpenProvidersPage:d,onProviderChange:f,onUpdateDraft:h,providers:y}),(0,q.jsx)(ue,{draft:i,isReadOnly:o,onModelParamsModeChange:u,onUpdateDraft:h}),(0,q.jsx)(me,{configurableTools:r,getToolState:a,isReadOnly:o,onToolStateCycle:m,shouldLockIdentityFields:x}),(0,q.jsx)(ve,{activeRole:e,canSave:n,isReadOnly:o,onClosePanel:s,onEditRole:c,onSaveRole:p,panelMode:_,saving:b})]})})}function _e({badgeLabel:e,onClosePanel:t,title:n}){return(0,q.jsxs)(M,{as:`div`,padding:`sm`,className:`mb-8 flex items-center justify-between px-5 py-4`,children:[(0,q.jsxs)(`div`,{className:`flex items-center gap-3`,children:[(0,q.jsx)(A,{tone:`neutral`,className:`py-0.5 text-[11px]`,children:e}),(0,q.jsx)(`h2`,{className:`text-[15px] font-medium text-foreground`,children:n})]}),(0,q.jsx)(O,{type:`button`,variant:`ghost`,size:`icon-xs`,onClick:t,className:`text-muted-foreground hover:bg-accent/45 hover:text-foreground`,children:(0,q.jsx)(r,{className:`size-3.5`})})]})}function ve({activeRole:e,canSave:t,isReadOnly:n,onClosePanel:r,onEditRole:i,onSaveRole:a,panelMode:o,saving:s}){return(0,q.jsxs)(`div`,{className:`flex items-center justify-end gap-3 border-t border-border pt-6`,children:[(0,q.jsx)(O,{type:`button`,variant:`ghost`,size:`sm`,onClick:r,disabled:s,children:`Cancel`}),n?null:(0,q.jsx)(O,{type:`button`,size:`sm`,onClick:()=>void a(),disabled:!t,children:s?`Saving...`:o===`create`?`Create Role`:`Save Changes`}),n&&e&&!e.is_builtin?(0,q.jsx)(O,{type:`button`,variant:`secondary`,size:`sm`,onClick:()=>i(e),children:`Edit Role`}):null]})}var ye=new Set([`idle`,`sleep`,`todo`,`contacts`]);function Y(){return{name:``,description:``,system_prompt:``,model:null,model_params:null,included_tools:[],excluded_tools:[]}}function X(e){return e?{name:e.name,description:e.description,system_prompt:e.system_prompt,model:e.model?{provider_id:e.model.provider_id,model:e.model.model}:null,model_params:e.model_params?K(e.model_params):null,included_tools:[...e.included_tools],excluded_tools:[...e.excluded_tools]}:Y()}function be(e){return e.filter(e=>!ye.has(e.name))}function xe(e){return Object.fromEntries(e.map(e=>[e.id,e]))}function Z(e,t){return e.included_tools.includes(t)?`included`:e.excluded_tools.includes(t)?`excluded`:`allowed`}function Se(e,t){let n=Z(e,t);return n===`allowed`?{...e,included_tools:[...e.included_tools,t],excluded_tools:e.excluded_tools.filter(e=>e!==t)}:n===`included`?{...e,included_tools:e.included_tools.filter(e=>e!==t),excluded_tools:[...e.excluded_tools,t]}:{...e,included_tools:e.included_tools.filter(e=>e!==t),excluded_tools:e.excluded_tools.filter(e=>e!==t)}}function Ce(e){return e.length===0?null:{provider_id:e[0]?.id??``,model:``}}function we(e){let{activeRoleName:t,draft:n,roles:r}=e,i=n.name.trim();if(!i)return`Role name is required`;if(!n.description.trim())return`Role description is required`;if(!n.system_prompt.trim())return`System prompt is required`;if(n.model){if(!n.model.provider_id.trim())return`Provider is required for a role model override`;if(!n.model.model.trim())return`Model is required for a role model override`}return r.some(e=>e.name===i&&e.name!==t)?`Role name already exists`:null}function Te(e){return{name:e.name.trim(),description:e.description.trim(),system_prompt:e.system_prompt,model:e.model?{provider_id:e.model.provider_id.trim(),model:e.model.model.trim()}:null,model_params:se(e.model_params),included_tools:e.included_tools,excluded_tools:e.excluded_tools}}function Ee(e){return e===`view`}function De(e,t){return e!==`create`&&e!==null&&t?.is_builtin===!0}function Oe(e,t){return e===`create`?`New Role`:t?.is_builtin?`Built-in`:`Custom`}function Q(e,t){return e===`create`?`Create Role`:t?.is_builtin?`Role Details`:t?.name??`Role Details`}function ke(e,t){return!(t||!e.name.trim()||!e.description.trim()||!e.system_prompt.trim())}function Ae(e,t){return e.model?`${t[e.model.provider_id]?.name??e.model.provider_id} / ${e.model.model}`:`Settings default`}function je(e){let t=e.included_tools.length,n=e.excluded_tools.length;return t===0&&n===0?`Default`:[t>0?`+${t}`:null,n>0?`-${n}`:null].filter(Boolean).join(` `)}function Me({activeRole:e,onCreateRole:t,onDeleteRole:n,onEditRole:r,onViewRole:i,providersById:a,roles:c}){return c.length===0?(0,q.jsx)(d.div,{initial:{opacity:0},animate:{opacity:1},className:`flex h-full flex-col items-center justify-center text-center`,children:(0,q.jsx)(j,{icon:o,title:`No roles yet`,action:(0,q.jsxs)(O,{type:`button`,size:`sm`,onClick:t,children:[(0,q.jsx)(s,{className:`size-4`}),`New Role`]}),className:`border-transparent bg-transparent`})}):(0,q.jsx)(`div`,{className:`h-full min-h-0 overflow-y-auto pr-2 scrollbar-none`,children:(0,q.jsxs)(`div`,{className:`mx-auto w-full max-w-5xl`,children:[(0,q.jsxs)(`div`,{className:`mb-2 grid grid-cols-[260px_1fr_120px_100px] gap-4 px-4 pb-3`,children:[(0,q.jsx)(`span`,{className:`text-[11px] font-medium text-muted-foreground`,children:`Name`}),(0,q.jsx)(`span`,{className:`text-[11px] font-medium text-muted-foreground`,children:`Model`}),(0,q.jsx)(`span`,{className:`text-[11px] font-medium text-muted-foreground`,children:`Tools`}),(0,q.jsx)(`span`,{})]}),(0,q.jsx)(`div`,{className:`space-y-1`,children:c.map((t,o)=>(0,q.jsx)(Ne,{activeRoleName:e?.name??null,index:o,onDeleteRole:n,onEditRole:r,onViewRole:i,providersById:a,role:t},t.name))})]})})}function Ne({activeRoleName:e,index:t,onDeleteRole:n,onEditRole:r,onViewRole:i,providersById:o,role:s}){return(0,q.jsxs)(d.div,{initial:{opacity:0,y:4},animate:{opacity:1,y:0},transition:{delay:t*.03},className:E(`group grid grid-cols-[220px_1fr_100px_80px] items-center gap-4 rounded-xl px-4 py-3.5 transition-colors`,e===s.name?`bg-accent/25`:`hover:bg-accent/15`),children:[(0,q.jsxs)(`div`,{className:`min-w-0 pr-2`,children:[(0,q.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,q.jsx)(`span`,{className:`truncate text-[13px] font-medium text-foreground`,children:s.name}),s.is_builtin?(0,q.jsx)(A,{tone:`muted`,className:`px-1.5 py-0.5 text-[9px]`,children:`Built-in`}):null]}),(0,q.jsx)(`p`,{className:`mt-1 line-clamp-2 text-[12px] leading-relaxed text-muted-foreground`,children:s.description})]}),(0,q.jsx)(`div`,{className:`min-w-0 pr-2`,children:(0,q.jsx)(`span`,{className:`block truncate text-[13px] text-muted-foreground`,children:Ae(s,o)})}),(0,q.jsx)(`div`,{className:`pr-2`,children:(0,q.jsx)(`span`,{className:`font-mono text-[13px] text-muted-foreground`,children:je(s)})}),(0,q.jsxs)(`div`,{className:`flex items-center justify-end gap-0.5 opacity-0 transition-opacity group-hover:opacity-100 focus-within:opacity-100`,children:[(0,q.jsx)(y,{onClick:()=>i(s),"aria-label":`View ${s.name}`,title:`View ${s.name}`,className:`size-7`,children:(0,q.jsx)(u,{className:`size-3.5`})}),(0,q.jsx)(y,{onClick:()=>r(s),"aria-label":`Edit ${s.name}`,title:`Edit ${s.name}`,className:`size-7`,children:(0,q.jsx)(a,{className:`size-3.5`})}),s.is_builtin?null:(0,q.jsx)(y,{onClick:()=>n(s),"aria-label":`Delete ${s.name}`,title:`Delete ${s.name}`,className:`flex size-7 items-center justify-center rounded-md text-muted-foreground transition-colors hover:bg-destructive/10 hover:text-destructive`,children:(0,q.jsx)(f,{className:`size-3.5`})})]})]})}var $=e(t(),1);function Pe(){let[e,t]=(0,$.useState)(null),[n,r]=(0,$.useState)(null),[i,a]=(0,$.useState)(Y()),[o,s]=(0,$.useState)(!1),[c,u]=(0,$.useState)(null),{data:d,isLoading:f,mutate:_}=ee(`rolesBootstrap`,m),v=(0,$.useMemo)(()=>d?.roles??[],[d?.roles]),y=(0,$.useMemo)(()=>d?.tools??[],[d?.tools]),b=(0,$.useMemo)(()=>d?.providers??[],[d?.providers]),x=(0,$.useMemo)(()=>be(y),[y]),S=(0,$.useMemo)(()=>xe(b),[b]),C=(0,$.useMemo)(()=>n?v.find(e=>e.name===n)??null:null,[n,v]),w=i.model?.provider_id??``,T=(0,$.useMemo)(()=>w?S[w]?.models??[]:[],[w,S]),E=e!==null,D=Ee(e),O=De(e,C),k=Oe(e,C),A=Q(e,C),j=ke(i,o),M=(0,$.useCallback)(e=>{_({roles:e,tools:y,providers:b},!1)},[_,b,y]),N=(0,$.useCallback)(async()=>{await _()},[_]),P=(0,$.useCallback)(()=>{t(null),r(null),a(Y())},[]),F=(0,$.useCallback)(()=>{t(`create`),r(null),a(Y())},[]),I=(0,$.useCallback)(e=>{t(`view`),r(e.name),a(X(e))},[]),L=(0,$.useCallback)(e=>{t(`edit`),r(e.name),a(X(e))},[]),R=(0,$.useCallback)(e=>{a(t=>e(t))},[]),z=(0,$.useCallback)(e=>{if(!e){R(e=>({...e,model:null}));return}if(b.length===0){l.error(`Create a provider before setting a role model`);return}R(e=>({...e,model:e.model??Ce(b)}))},[b,R]),B=(0,$.useCallback)(e=>{R(t=>({...t,model:t.model?{provider_id:e,model:``}:null}))},[R]),V=(0,$.useCallback)(e=>{R(t=>({...t,model_params:e?K(t.model_params):null}))},[R]),H=(0,$.useCallback)(async()=>{let t=we({activeRoleName:n,draft:i,roles:v});if(t){l.error(t);return}s(!0);try{let t=Te(i);if(e===`edit`&&n){let e=await p(n,C?.is_builtin?{model:t.model,model_params:t.model_params}:t);M(v.map(t=>t.name===n?e:t)),l.success(`Role updated`)}else M([await g(t),...v]),l.success(`Role created`);P()}catch(e){l.error(e instanceof Error?e.message:`Failed to save role`)}finally{s(!1)}},[C,n,P,i,e,v,M]),U=(0,$.useCallback)(e=>{u(e)},[]),W=(0,$.useCallback)(()=>{u(null)},[]),G=(0,$.useCallback)(async()=>{if(!c)return;let e=c.name;u(null);try{await h(e),M(v.filter(t=>t.name!==e)),n===e&&P(),l.success(`Role deleted`)}catch(e){l.error(e instanceof Error?e.message:`Failed to delete role`)}},[n,P,c,v,M]);return{activeRole:C,activeRoleName:n,availableActiveProviderModelOptions:T,canSave:j,configurableTools:x,draft:i,isPanelOpen:E,isReadOnly:D,loading:f,panelBadgeLabel:k,panelMode:e,panelTitle:A,providers:b,providersById:S,refreshRoles:N,roleToDelete:c,roles:v,saving:o,shouldLockIdentityFields:O,actions:{clearRoleToDelete:W,closePanel:P,cycleRoleToolState:(0,$.useCallback)(e=>{R(t=>Se(t,e))},[R]),handleDelete:G,handleModelModeChange:z,handleModelParamsModeChange:V,handleProviderChange:B,handleSave:H,openCreate:F,openEdit:L,openView:I,requestDeleteRole:U,updateDraft:R},getToolState:e=>Z(i,e)}}function Fe(){let e=k(),{activeRole:t,availableActiveProviderModelOptions:n,canSave:r,configurableTools:i,draft:a,getToolState:o,isPanelOpen:l,isReadOnly:u,loading:d,panelBadgeLabel:f,panelMode:p,panelTitle:m,providers:h,providersById:g,refreshRoles:_,roleToDelete:v,roles:y,saving:b,shouldLockIdentityFields:x,actions:S}=Pe(),C={...S,openProvidersPage:()=>e?.setCurrentPage(`providers`)};return d&&!l?(0,q.jsx)(D,{label:`Loading roles...`}):(0,q.jsxs)(P,{className:`px-4 pt-6 sm:px-5`,children:[(0,q.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col`,children:[(0,q.jsx)(F,{title:`Roles`,actions:(0,q.jsxs)(q.Fragment,{children:[(0,q.jsx)(O,{type:`button`,variant:`outline`,size:`icon-sm`,onClick:()=>void _(),disabled:d,className:`bg-accent/20 text-muted-foreground hover:bg-accent/45 hover:text-foreground`,children:(0,q.jsx)(c,{className:E(`size-4`,d&&`animate-spin`)})}),(0,q.jsxs)(O,{type:`button`,size:`sm`,onClick:S.openCreate,disabled:l,children:[(0,q.jsx)(s,{className:`size-4`}),`New Role`]})]})}),(0,q.jsx)(`div`,{className:`mt-6 min-h-0 flex-1`,children:l?(0,q.jsx)(ge,{activeRole:t,availableProviderModels:n,canSave:r,configurableTools:i,draft:a,getToolState:o,isReadOnly:u,onClosePanel:S.closePanel,onEditRole:S.openEdit,onModelModeChange:S.handleModelModeChange,onModelParamsModeChange:S.handleModelParamsModeChange,onOpenProvidersPage:C.openProvidersPage,onProviderChange:S.handleProviderChange,onSaveRole:S.handleSave,onToolStateCycle:S.cycleRoleToolState,onUpdateDraft:S.updateDraft,panelBadgeLabel:f,panelMode:p,panelTitle:m,providers:h,saving:b,shouldLockIdentityFields:x}):(0,q.jsx)(Me,{activeRole:t,onCreateRole:S.openCreate,onDeleteRole:S.requestDeleteRole,onEditRole:S.openEdit,onViewRole:S.openView,providersById:g,roles:y})})]}),(0,q.jsx)(ce,{roleToDelete:v,onConfirmDelete:S.handleDelete,onOpenChange:e=>{e||S.clearRoleToDelete()}})]})}export{Fe as RolesPage};
@@ -0,0 +1,3 @@
1
+ import{a as e}from"./rolldown-runtime-BYbx6iT9.js";import{d as t,l as n}from"./graph-vendor-DRq_-6fV.js";import{c as r,d as i,dt as a,l as o,q as s,u as c}from"./ui-vendor-UazN8rcv.js";import{B as l,G as u,J as d,K as f,Q as p,U as m,X as h,Y as g,q as _,rt as v,s as y,tt as b}from"./index-Biio-CoI.js";import{a as x,c as S,i as C,n as w,o as T,r as E,t as D}from"./PageScaffold-DteOA8V7.js";import{a as O,i as k,n as A,r as j,t as M}from"./select-D9SwnlXF.js";import{n as N,r as ee,t as P}from"./triState-DgLlKdRR.js";import{i as F,t as I}from"./modelParams-DcEhGnu0.js";async function L(){return l(`/api/settings/bootstrap`,{errorMessage:`Failed to fetch settings bootstrap`})}async function R(e){return l(`/api/settings`,{method:`POST`,body:e,errorMessage:`Failed to save settings`,map:e=>{if(!e)throw Error(`Failed to save settings`);return{settings:e.settings,reauthRequired:e.reauth_required===!0}}})}var z=e(t(),1),B=n(),V=c,H=z.forwardRef(({className:e,...t},n)=>(0,B.jsx)(o,{ref:n,className:v(`inline-flex h-9 items-center justify-center rounded-lg bg-muted p-1 text-muted-foreground`,e),...t}));H.displayName=o.displayName;var U=z.forwardRef(({className:e,...t},n)=>(0,B.jsx)(i,{ref:n,className:v(`inline-flex items-center justify-center whitespace-nowrap rounded-md px-3 py-1.5 text-sm font-medium ring-offset-background transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50 data-[state=active]:bg-background data-[state=active]:text-foreground data-[state=active]:shadow`,e),...t}));U.displayName=i.displayName;var W=z.forwardRef(({className:e,...t},n)=>(0,B.jsx)(r,{ref:n,className:v(`mt-2 ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2`,e),...t}));W.displayName=r.displayName;var G=1024;function K(e){let t=[],n=new Set;for(let r of e){let e=r.trim();if(!e)continue;let i=e.replace(/\/+$/u,``)||`/`;n.has(i)||(n.add(i),t.push(i))}return t}function q(e,t){return e.find(e=>e.id===t)??null}function J(e,t){return e.find(e=>e.name===t)??null}function Y(e){return e?.models??[]}function X(e,t){return t?e.find(e=>e.model===t)??null:null}function Z(e,t){return e.model.context_window_tokens??t?.context_window_tokens??e.model.resolved_context_window_tokens??null}function Q(e,t){return{input_image:e.model.input_image??t?.input_image??e.model.capabilities?.input_image??!1,output_image:e.model.output_image??t?.output_image??e.model.capabilities?.output_image??!1,structured_output:e.model.structured_output??t?.structured_output??e.model.capabilities?.structured_output??!1}}function te(e,t){if(!e)return null;let n=t.max_output_tokens??1024;return Math.max(1,e-n-G)}function ne(e,t){return e!==null&&t!==null&&e>=t?`Automatic Compact token limit must stay below the known safe input window`:null}function re(e,t){let n=t&&(t.newCode||t.confirmCode)?{new_code:t.newCode,confirm_code:t.confirmCode}:void 0;return{...n?{access:n}:{},working_dir:e.working_dir.trim(),assistant:{role_name:e.assistant.role_name,allow_network:e.assistant.allow_network,write_dirs:K(e.assistant.write_dirs)},leader:e.leader,model:{active_provider_id:e.model.active_provider_id,active_model:e.model.active_model,input_image:e.model.input_image,output_image:e.model.output_image,structured_output:e.model.structured_output,context_window_tokens:e.model.context_window_tokens,timeout_ms:e.model.timeout_ms,retry_policy:e.model.retry_policy,max_retries:e.model.max_retries,retry_initial_delay_seconds:e.model.retry_initial_delay_seconds,retry_max_delay_seconds:e.model.retry_max_delay_seconds,retry_backoff_cap_retries:e.model.retry_backoff_cap_retries,auto_compact_token_limit:e.model.auto_compact_token_limit,params:e.model.params}}}var ie=[{value:`no_retry`,label:`No retry`},{value:`limited`,label:`Limited`},{value:`unlimited`,label:`Unlimited`}];function ae({accessDraftError:e,onSave:t,saving:n,settings:r}){return(0,B.jsx)(E,{title:`Settings`,actions:(0,B.jsxs)(b,{type:`button`,size:`sm`,onClick:t,disabled:n||!!e||!r.working_dir.trim(),className:`text-[13px]`,children:[(0,B.jsx)(a,{className:`size-4`}),n?`Saving...`:`Save Changes`]}),className:`mb-8`})}function oe({accessDraft:e,accessDraftError:t,onAccessDraftChange:n}){let r=!!(e.newCode.trim()||e.confirmCode.trim());return(0,B.jsxs)(D,{title:`Access Configuration`,className:`mt-8 first:mt-0`,children:[(0,B.jsx)(T,{label:`New Access Code`,children:(0,B.jsxs)(`div`,{className:`space-y-2 w-full max-w-lg`,children:[(0,B.jsx)(d,{id:`new-access-code`,value:e.newCode,onChange:e=>n(t=>({...t,newCode:e.target.value})),placeholder:`Leave empty to keep`,showLabel:`Show new access code`,hideLabel:`Hide new access code`,buttonSize:`default`}),r?(0,B.jsx)(`p`,{className:g,children:`Saving signs you out; use the new code to return.`}):null]})}),(0,B.jsx)(T,{label:`Confirm Access Code`,children:(0,B.jsxs)(`div`,{className:`space-y-2 w-full max-w-lg`,children:[(0,B.jsx)(d,{id:`confirm-access-code`,value:e.confirmCode,onChange:e=>n(t=>({...t,confirmCode:e.target.value})),placeholder:`Repeat the new access code`,showLabel:`Show confirmed access code`,hideLabel:`Hide confirmed access code`,buttonSize:`default`}),t?(0,B.jsx)(`p`,{className:v(`text-destructive font-medium pt-1`,g),children:t}):null]})})]})}function $({onSettingsChange:e,settings:t}){return(0,B.jsxs)(D,{title:`Path Configuration`,className:`mt-10`,children:[(0,B.jsx)(T,{label:`App Data Directory`,children:(0,B.jsxs)(`div`,{className:`space-y-2 max-w-lg`,children:[(0,B.jsx)(u,{"aria-label":`App Data Directory`,value:t.app_data_dir,readOnly:!0,mono:!0}),(0,B.jsx)(`p`,{className:g,children:`Read-only while Flowent is running.`})]})}),(0,B.jsx)(T,{label:`Working Directory`,children:(0,B.jsxs)(`div`,{className:`space-y-2 max-w-lg`,children:[(0,B.jsx)(u,{"aria-label":`Working Directory`,value:t.working_dir,onChange:t=>e(e=>({...e,working_dir:t.target.value})),placeholder:`/workspace/project`,mono:!0}),(0,B.jsx)(`p`,{className:g,children:`Changing this does not expand saved allowed folders.`}),(0,B.jsx)(`div`,{className:v(`space-y-2`,g),children:t.working_dir.trim()?null:(0,B.jsx)(`p`,{className:`text-destructive`,children:`Working Directory must not be empty.`})})]})})]})}function se({assistantRole:e,onSettingsChange:t,roles:n,settings:r}){return(0,B.jsxs)(D,{title:`Assistant Configuration`,children:[(0,B.jsx)(x,{label:`Assistant Role`,children:(0,B.jsxs)(`div`,{className:`w-full`,children:[(0,B.jsxs)(M,{value:r.assistant.role_name,onValueChange:e=>t(t=>({...t,assistant:{...t.assistant,role_name:e}})),children:[(0,B.jsx)(k,{className:p,children:(0,B.jsx)(O,{placeholder:`Select a role`})}),(0,B.jsx)(A,{children:n.map(e=>(0,B.jsx)(j,{value:e.name,children:(0,B.jsxs)(`div`,{className:`flex min-w-0 flex-col items-start`,children:[(0,B.jsx)(`span`,{children:e.name}),(0,B.jsx)(`span`,{className:`text-[11px] text-muted-foreground`,children:e.description})]})},e.name))})]}),e?(0,B.jsx)(`div`,{"data-testid":`assistant-role-guidance`,className:v(`mt-2`,g),children:(0,B.jsx)(`p`,{children:e.description})}):null]})}),(0,B.jsx)(x,{label:`Network Access`,children:(0,B.jsxs)(`div`,{className:`space-y-2`,children:[(0,B.jsx)(f,{checked:r.assistant.allow_network,label:`Network Access`,onCheckedChange:e=>t(t=>({...t,assistant:{...t.assistant,allow_network:e}})),showStateText:!0}),r.assistant.allow_network?null:(0,B.jsx)(`p`,{className:g,children:`Assistant cannot connect to the web.`})]})}),(0,B.jsx)(T,{label:`Write Directories`,children:(0,B.jsxs)(`div`,{className:`space-y-2 max-w-xl`,children:[(0,B.jsx)(_,{"aria-label":`Write Dirs`,value:r.assistant.write_dirs.join(`
2
+ `),onChange:e=>t(t=>({...t,assistant:{...t.assistant,write_dirs:e.target.value.split(`
3
+ `)}})),rows:4,spellCheck:!1,placeholder:`/workspace/output`,className:`min-h-[108px]`,mono:!0}),(0,B.jsx)(`p`,{className:g,children:`One absolute folder path per line.`})]})})]})}function ce({leaderRole:e,onSettingsChange:t,roles:n,settings:r}){return(0,B.jsx)(D,{title:`Leader Configuration`,className:`mt-10`,children:(0,B.jsx)(x,{label:`Leader Role`,children:(0,B.jsxs)(`div`,{className:`w-full`,children:[(0,B.jsxs)(M,{value:r.leader.role_name,onValueChange:e=>t(t=>({...t,leader:{role_name:e}})),children:[(0,B.jsx)(k,{className:p,children:(0,B.jsx)(O,{placeholder:`Select a role`})}),(0,B.jsx)(A,{children:n.map(e=>(0,B.jsx)(j,{value:e.name,children:(0,B.jsxs)(`div`,{className:`flex min-w-0 flex-col items-start`,children:[(0,B.jsx)(`span`,{children:e.name}),(0,B.jsx)(`span`,{className:`text-[11px] text-muted-foreground`,children:e.description})]})},e.name))})]}),e?(0,B.jsx)(`p`,{className:v(`mt-2`,g),children:e.description}):null]})})})}function le({activeProvider:e,activeProviderModels:t,availableActiveProviderModels:n,effectiveContextWindowTokens:r,effectiveModelCapabilities:i,knownSafeInputTokens:a,onSettingsChange:o,providers:s,settings:c}){return(0,B.jsxs)(D,{title:`Model Configuration`,className:`mt-10`,children:[(0,B.jsxs)(x,{label:`Active Provider`,children:[(0,B.jsxs)(M,{value:c.model.active_provider_id,onValueChange:e=>{o(t=>({...t,model:{...t.model,active_provider_id:e,active_model:``}}))},children:[(0,B.jsx)(k,{className:p,children:(0,B.jsx)(O,{placeholder:`Select a provider`})}),(0,B.jsx)(A,{children:s.map(e=>(0,B.jsxs)(j,{value:e.id,children:[e.name,` (`,ee(e.type),`)`]},e.id))})]}),e?(0,B.jsxs)(`p`,{className:`mt-2 text-xs text-muted-foreground`,children:[`Using `,e.name,` (`,e.base_url,`)`]}):null]}),(0,B.jsxs)(x,{label:`Model`,children:[(0,B.jsxs)(`div`,{className:`space-y-3`,children:[c.model.active_provider_id?t.length>0?(0,B.jsxs)(`div`,{className:`space-y-2`,children:[(0,B.jsx)(`label`,{className:h,children:`Provider Models`}),(0,B.jsxs)(M,{value:n.some(e=>e.model===c.model.active_model)?c.model.active_model:void 0,onValueChange:e=>o(t=>({...t,model:{...t.model,active_model:e}})),children:[(0,B.jsx)(k,{className:p,children:(0,B.jsx)(O,{placeholder:`Select a provider model`})}),(0,B.jsx)(A,{children:n.map(e=>(0,B.jsx)(j,{value:e.model,children:e.model},e.model))})]})]}):(0,B.jsx)(`p`,{className:g,children:`No saved provider models.`}):null,(0,B.jsx)(u,{value:c.model.active_model,onChange:e=>o(t=>({...t,model:{...t.model,active_model:e.target.value}})),placeholder:c.model.active_provider_id?`Enter model ID manually`:`Select a provider first`})]}),c.model.active_model?(0,B.jsxs)(`div`,{className:v(`mt-2 space-y-1`,g),children:[(0,B.jsxs)(`p`,{children:[`Context window:`,` `,r?r.toLocaleString():`Not resolved`]}),(0,B.jsxs)(`p`,{children:[`Capabilities: input_image=`,i.input_image?`true`:`false`,`, output_image=`,i.output_image?`true`:`false`,`, structured_output=`,i.structured_output?`true`:`false`]})]}):null]}),(0,B.jsx)(T,{label:`Model Metadata Overrides`,children:(0,B.jsx)(`div`,{className:`space-y-3 w-full`,children:(0,B.jsxs)(`div`,{className:`grid gap-3 md:grid-cols-4`,children:[(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{htmlFor:`model-context-window`,className:h,children:`Context Window`}),(0,B.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,B.jsx)(u,{id:`model-context-window`,"aria-label":`Context Window`,inputMode:`numeric`,pattern:`[0-9]*`,value:c.model.context_window_tokens===null?``:String(c.model.context_window_tokens),onChange:e=>{let t=e.target.value.trim();/^\d*$/.test(t)&&(t&&Number.parseInt(t,10)<=0||o(e=>({...e,model:{...e.model,context_window_tokens:t?Number.parseInt(t,10):null}})))},placeholder:`Auto`,mono:!0}),(0,B.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`tokens`})]})]}),(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{className:h,children:`Input Image`}),(0,B.jsxs)(M,{value:N(c.model.input_image),onValueChange:e=>o(t=>({...t,model:{...t.model,input_image:P(e)}})),children:[(0,B.jsx)(k,{"aria-label":`Input Image`,className:p,children:(0,B.jsx)(O,{placeholder:`Auto`})}),(0,B.jsxs)(A,{children:[(0,B.jsx)(j,{value:`auto`,children:`Auto`}),(0,B.jsx)(j,{value:`enabled`,children:`Enabled`}),(0,B.jsx)(j,{value:`disabled`,children:`Disabled`})]})]})]}),(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{className:h,children:`Output Image`}),(0,B.jsxs)(M,{value:N(c.model.output_image),onValueChange:e=>o(t=>({...t,model:{...t.model,output_image:P(e)}})),children:[(0,B.jsx)(k,{"aria-label":`Output Image`,className:p,children:(0,B.jsx)(O,{placeholder:`Auto`})}),(0,B.jsxs)(A,{children:[(0,B.jsx)(j,{value:`auto`,children:`Auto`}),(0,B.jsx)(j,{value:`enabled`,children:`Enabled`}),(0,B.jsx)(j,{value:`disabled`,children:`Disabled`})]})]})]}),(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{className:h,children:`Structured Output`}),(0,B.jsxs)(M,{value:N(c.model.structured_output??null),onValueChange:e=>o(t=>({...t,model:{...t.model,structured_output:P(e)}})),children:[(0,B.jsx)(k,{"aria-label":`Structured Output`,className:p,children:(0,B.jsx)(O,{placeholder:`Auto`})}),(0,B.jsxs)(A,{children:[(0,B.jsx)(j,{value:`auto`,children:`Auto`}),(0,B.jsx)(j,{value:`enabled`,children:`Enabled`}),(0,B.jsx)(j,{value:`disabled`,children:`Disabled`})]})]})]})]})})}),(0,B.jsx)(T,{label:`Default Model Parameters`,children:(0,B.jsx)(`div`,{className:`rounded-xl border border-border bg-card/30 p-5`,children:(0,B.jsx)(F,{className:`w-full`,value:I(c.model.params),onChange:e=>o(t=>({...t,model:{...t.model,params:e}})),emptyLabel:`Not set`,numberPlaceholder:`Not set`,reasoningDisableLabel:null})})}),(0,B.jsx)(x,{label:`Request Timeout`,children:(0,B.jsx)(`div`,{className:`space-y-2 w-full max-w-xs`,children:(0,B.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,B.jsx)(u,{"aria-label":`Request Timeout`,inputMode:`numeric`,pattern:`[0-9]*`,value:String(c.model.timeout_ms),onChange:e=>{let t=e.target.value.trim();if(!/^\d+$/.test(t))return;let n=Number.parseInt(t,10);!Number.isSafeInteger(n)||n<=0||o(e=>({...e,model:{...e.model,timeout_ms:n}}))},mono:!0}),(0,B.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`ms`})]})})}),(0,B.jsx)(T,{label:`Retry Strategy`,children:(0,B.jsxs)(C,{className:`max-w-3xl`,children:[(0,B.jsxs)(`div`,{className:`grid gap-6 md:grid-cols-[1fr_2fr]`,children:[(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{className:h,children:`Policy`}),(0,B.jsxs)(M,{value:c.model.retry_policy,onValueChange:e=>o(t=>({...t,model:{...t.model,retry_policy:e}})),children:[(0,B.jsx)(k,{className:p,children:(0,B.jsx)(O,{placeholder:`Select a retry policy`})}),(0,B.jsx)(A,{children:ie.map(e=>(0,B.jsx)(j,{value:e.value,children:e.label},e.value))})]})]}),c.model.retry_policy===`limited`?(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{htmlFor:`retry-attempts`,className:h,children:`Max Attempts`}),(0,B.jsx)(u,{id:`retry-attempts`,"aria-label":`Retry Attempts`,inputMode:`numeric`,pattern:`[0-9]*`,value:String(c.model.max_retries),onChange:e=>{let t=e.target.value.trim();if(!/^\d+$/.test(t))return;let n=Number.parseInt(t,10);!Number.isSafeInteger(n)||n<=0||o(e=>({...e,model:{...e.model,max_retries:n}}))},mono:!0})]}):(0,B.jsx)(`div`,{})]}),(0,B.jsxs)(`div`,{className:`grid gap-3 md:grid-cols-3 mt-2 border-t border-border/40 pt-4`,children:[(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{htmlFor:`retry-initial-delay`,className:h,children:`Initial Delay`}),(0,B.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,B.jsx)(u,{id:`retry-initial-delay`,"aria-label":`Initial Delay`,inputMode:`decimal`,value:String(c.model.retry_initial_delay_seconds),onChange:e=>{let t=e.target.value.trim();if(!/^\d+(\.\d+)?$/.test(t))return;let n=Number.parseFloat(t);!Number.isFinite(n)||n<=0||o(e=>({...e,model:{...e.model,retry_initial_delay_seconds:n}}))},mono:!0}),(0,B.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`s`})]})]}),(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{htmlFor:`retry-max-delay`,className:h,children:`Max Delay`}),(0,B.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,B.jsx)(u,{id:`retry-max-delay`,"aria-label":`Max Delay`,inputMode:`decimal`,value:String(c.model.retry_max_delay_seconds),onChange:e=>{let t=e.target.value.trim();if(!/^\d+(\.\d+)?$/.test(t))return;let n=Number.parseFloat(t);!Number.isFinite(n)||n<=0||o(e=>({...e,model:{...e.model,retry_max_delay_seconds:n}}))},mono:!0}),(0,B.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`s`})]})]}),(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{htmlFor:`retry-backoff-cap-retries`,className:h,children:`Cap Retries`}),(0,B.jsx)(u,{id:`retry-backoff-cap-retries`,"aria-label":`Cap Retries`,inputMode:`numeric`,pattern:`[0-9]*`,value:String(c.model.retry_backoff_cap_retries),onChange:e=>{let t=e.target.value.trim();if(!/^\d+$/.test(t))return;let n=Number.parseInt(t,10);!Number.isSafeInteger(n)||n<=0||o(e=>({...e,model:{...e.model,retry_backoff_cap_retries:n}}))},mono:!0})]})]})]})}),(0,B.jsx)(T,{label:`Automatic Compact`,children:(0,B.jsxs)(`div`,{className:`space-y-3 w-full max-w-sm`,children:[(0,B.jsxs)(`div`,{className:`space-y-1`,children:[(0,B.jsx)(`label`,{htmlFor:`auto-compact-token-limit`,className:h,children:`Token Limit`}),(0,B.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,B.jsx)(u,{id:`auto-compact-token-limit`,"aria-label":`Automatic Compact Token Limit`,inputMode:`numeric`,pattern:`[0-9]*`,value:c.model.auto_compact_token_limit===null?``:String(c.model.auto_compact_token_limit),onChange:e=>{let t=e.target.value.trim();/^\d*$/.test(t)&&(t&&Number.parseInt(t,10)<=0||o(e=>({...e,model:{...e.model,auto_compact_token_limit:t?Number.parseInt(t,10):null}})))},placeholder:`Disabled`,mono:!0}),(0,B.jsx)(`span`,{className:`text-[13px] font-medium text-muted-foreground`,children:`tokens`})]})]}),a===null?c.model.auto_compact_token_limit===null?null:(0,B.jsx)(`p`,{className:`text-[11px] leading-relaxed text-graph-status-idle`,children:`The current model window is not resolved, so this token limit can be saved but cannot be fully validated yet.`}):(0,B.jsxs)(`p`,{className:g,children:[`Known safe input window: `,a.toLocaleString(),` `,`tokens.`,c.model.auto_compact_token_limit!==null&&c.model.auto_compact_token_limit>=a?` Save is blocked until the token limit is lower than this window.`:null]})]})})]})}function ue({appVersion:e}){return(0,B.jsx)(`div`,{className:`mt-12 flex flex-col items-center pt-2 pb-6 text-center`,children:(0,B.jsxs)(`p`,{className:`text-[11px] font-medium text-muted-foreground`,children:[`Flowent Agent Studio v`,e??`—`]})})}function de(){let{requireReauth:e}=m(),{data:t,isLoading:n,mutate:r}=S(`settingsBootstrap`,()=>L()),[i,a]=(0,z.useState)(null),[o,c]=(0,z.useState)(!1),[l,u]=(0,z.useState)({newCode:``,confirmCode:``}),d=(0,z.useMemo)(()=>t?.providers??[],[t?.providers]),f=(0,z.useMemo)(()=>t?.roles??[],[t?.roles]),p=t?.version??null;(0,z.useEffect)(()=>{t?.settings&&!i&&a(t.settings)},[t?.settings,i]);let h=i??t?.settings??null,g=(0,z.useCallback)(e=>{a(n=>{let r=n??t?.settings??null;return r?e(r):n})},[t?.settings]),_=(0,z.useCallback)(e=>{u(t=>e(t))},[]),v=(0,z.useMemo)(()=>h?q(d,h.model.active_provider_id):null,[d,h]),y=(0,z.useMemo)(()=>h?J(f,h.assistant.role_name):null,[f,h]),b=(0,z.useMemo)(()=>Y(v),[v]),x=b,C=(0,z.useMemo)(()=>h?X(b,h.model.active_model):null,[b,h]),w=(0,z.useMemo)(()=>h?Z(h,C):null,[C,h]),T=(0,z.useMemo)(()=>h?Q(h,C):{input_image:!1,output_image:!1,structured_output:!1},[C,h]),E=(0,z.useMemo)(()=>h?te(w,h.model.params):null,[w,h]),D=(0,z.useMemo)(()=>h?J(f,h.leader.role_name):null,[f,h]),O=(0,z.useMemo)(()=>!l.newCode&&!l.confirmCode?null:l.newCode.trim()?l.confirmCode===l.newCode?null:`Confirm Access Code must exactly match New Access Code.`:`New Access Code must not be empty.`,[l.confirmCode,l.newCode]);return{accessDraft:l,accessDraftError:O,activeProvider:v,activeProviderModels:b,availableActiveProviderModels:x,appVersion:p,assistantRole:y,effectiveContextWindowTokens:w,effectiveModelCapabilities:T,handleSave:(0,z.useCallback)(async()=>{if(!h)return;if(O){s.error(O);return}if(!h.working_dir.trim()){s.error(`Working Directory must not be empty`);return}if(h.model.retry_max_delay_seconds<h.model.retry_initial_delay_seconds){s.error(`Max Delay must be greater than or equal to Initial Delay`);return}let t=ne(h.model.auto_compact_token_limit,E);if(t){s.error(t);return}c(!0);try{let t=await R(re(h,l)),n=t.settings;if(a(n),u({newCode:``,confirmCode:``}),r(e=>e&&{...e,settings:n},!1),t.reauthRequired){s.success(`Access code updated. Sign in again with the new code.`),e();return}s.success(`Settings saved`)}catch(e){s.error(e instanceof Error?e.message:`Failed to save settings`)}finally{c(!1)}},[l,O,E,r,e,h]),knownSafeInputTokens:E,leaderRole:D,loading:n,providers:d,roles:f,saving:o,settings:h,updateAccessDraft:_,updateSettings:g}}function fe(){let{accessDraft:e,accessDraftError:t,activeProvider:n,activeProviderModels:r,availableActiveProviderModels:i,appVersion:a,assistantRole:o,effectiveContextWindowTokens:s,effectiveModelCapabilities:c,handleSave:l,knownSafeInputTokens:u,leaderRole:d,loading:f,providers:p,roles:m,saving:h,settings:g,updateAccessDraft:_,updateSettings:v}=de();return f||!g?(0,B.jsx)(y,{label:`Loading settings...`,textClassName:`text-[13px]`}):(0,B.jsx)(w,{children:(0,B.jsx)(`div`,{className:`h-full min-h-0 overflow-y-auto pr-2 scrollbar-none pb-20`,children:(0,B.jsxs)(`div`,{className:`mx-auto max-w-[680px] pb-10 pt-6`,children:[(0,B.jsx)(ae,{accessDraftError:t,onSave:()=>{l()},saving:h,settings:g}),(0,B.jsxs)(V,{defaultValue:`model`,className:`w-full`,children:[(0,B.jsx)(H,{className:`mb-8 w-full justify-start h-auto flex-wrap bg-transparent p-0 gap-6 border-b border-border/40 rounded-none`,children:[`model`,`assistant`,`leader`,`access`,`path`].map(e=>(0,B.jsx)(U,{value:e,className:`data-[state=active]:bg-transparent data-[state=active]:shadow-none bg-transparent border-b-2 border-transparent data-[state=active]:border-primary data-[state=active]:text-foreground text-muted-foreground rounded-none px-1 pb-2.5 pt-2 hover:text-foreground transition-colors`,children:e.charAt(0).toUpperCase()+e.slice(1)},e))}),(0,B.jsx)(W,{value:`model`,className:`mt-0`,children:(0,B.jsx)(le,{activeProvider:n,activeProviderModels:r,availableActiveProviderModels:i,effectiveContextWindowTokens:s,effectiveModelCapabilities:c,knownSafeInputTokens:u,onSettingsChange:v,providers:p,settings:g})}),(0,B.jsx)(W,{value:`assistant`,className:`mt-0`,children:(0,B.jsx)(se,{assistantRole:o,onSettingsChange:v,roles:m,settings:g})}),(0,B.jsx)(W,{value:`leader`,className:`mt-0`,children:(0,B.jsx)(ce,{leaderRole:d,onSettingsChange:v,roles:m,settings:g})}),(0,B.jsx)(W,{value:`access`,className:`mt-0`,children:(0,B.jsx)(oe,{accessDraft:e,accessDraftError:t,onAccessDraftChange:_})}),(0,B.jsx)(W,{value:`path`,className:`mt-0`,children:(0,B.jsx)($,{onSettingsChange:v,settings:g})})]}),(0,B.jsx)(ue,{appVersion:a})]})})})}export{fe as SettingsPage};