@bendyline/gezel-service 1.1.1 → 1.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/NOTICE.md +3 -3
- package/dist/bin/gezeld.js +8471 -5311
- package/dist/handboek-content/technical/building-connected-apps-with-gezel-app-sdk.md +78 -0
- package/dist/handboek-content/whats-new/{1.26250.md → 1.26251.md} +5 -5
- package/dist/index-store/static-index-worker.js +160 -51
- package/dist/index.d.ts +416 -71
- package/dist/index.js +8465 -5305
- package/dist/memory/embed-worker.js +132 -4
- package/dist/memory/image-embed-worker.js +14 -5
- package/dist/providers/mlx/python/cache_persist.py +52 -8
- package/dist/providers/mlx/python/gezel_mlx_server.py +44 -1
- package/dist/providers/mlx/python/qwen4_ple.py +159 -0
- package/dist/providers/mlx/python/spec_decode.py +73 -31
- package/dist/providers/mlx/python/tool_call_stream.py +10 -2
- package/dist/providers/mlx/python/tool_grammar.py +16 -0
- package/dist/ui/assets/{AmbientDashboardCard-DcVHxEdC.js → AmbientDashboardCard-_xnAQGnk.js} +1 -1
- package/dist/ui/assets/{AudioEngineSettings-BFM2S1mm.js → AudioEngineSettings-CgXgbX0i.js} +1 -1
- package/dist/ui/assets/{BenchmarksView-84-YeULA.js → BenchmarksView-BlExZpYA.js} +1 -1
- package/dist/ui/assets/CatalogBrowser-DYXUZQ_t.js +1 -0
- package/dist/ui/assets/{ChannelsSettings-7NAVUk4k.js → ChannelsSettings-EH27HcqZ.js} +1 -1
- package/dist/ui/assets/ChatTimelineView-Dn1TNyVn.js +7 -0
- package/dist/ui/assets/{ConnectedAppsPanel-CIgF4Q3R.js → ConnectedAppsPanel-BROry-Y0.js} +1 -1
- package/dist/ui/assets/CraftbookEditor-B2RNJnFf.js +1 -0
- package/dist/ui/assets/{CraftbookScriptEditorView-Ck5tzj3Y.js → CraftbookScriptEditorView-B-vySmHP.js} +1 -1
- package/dist/ui/assets/{CraftbookTabContent-BWg7FhK_.js → CraftbookTabContent-BW_2KC89.js} +1 -1
- package/dist/ui/assets/{CraftbookToolsetSetup-EuFOiUzR.js → CraftbookToolsetSetup-J7rEa835.js} +1 -1
- package/dist/ui/assets/{CraftbooksView-BIzQ1VVn.js → CraftbooksView-BjBUWPGF.js} +1 -1
- package/dist/ui/assets/DiffpackReviewView-CD4qJmgT.js +1 -0
- package/dist/ui/assets/DocumentDetail-SYozruTJ.js +1 -0
- package/dist/ui/assets/DocumentsView-DE7eL49Z.js +1 -0
- package/dist/ui/assets/{Ds4Settings-9soZCSeO.js → Ds4Settings-DGzc7JcD.js} +1 -1
- package/dist/ui/assets/{EmbeddedChat-Cce7nxXT.js → EmbeddedChat-D92TaJQ8.js} +1 -1
- package/dist/ui/assets/{FaceRecognitionCard-BVZyOwB8.js → FaceRecognitionCard-CB1Dt9X4.js} +1 -1
- package/dist/ui/assets/FileMapView-kVBG22FU.js +1 -0
- package/dist/ui/assets/FoldersSettings-BWFQU5B4.js +1 -0
- package/dist/ui/assets/GezelDetail-Br4v42Nv.js +1 -0
- package/dist/ui/assets/{GezelJsonEditor-DXXt165-.js → GezelJsonEditor-B9XEiW5Y.js} +1 -1
- package/dist/ui/assets/GezellenView-DheEBAy4.js +1 -0
- package/dist/ui/assets/{GildeUpdatesCard-CtY8mUTA.js → GildeUpdatesCard-BeIYv09f.js} +1 -1
- package/dist/ui/assets/{GithubSignInChip-DT3l6E0Q.js → GithubSignInChip-eEGCe9ar.js} +1 -1
- package/dist/ui/assets/{HandboekMediaProvider-ByJ4NAzz.js → HandboekMediaProvider-D0zcbbpf.js} +1 -1
- package/dist/ui/assets/HandboekView-p0BZT1rH.js +1 -0
- package/dist/ui/assets/{HistoryView-CkinzFEC.js → HistoryView-CKWcWW-Y.js} +1 -1
- package/dist/ui/assets/{HomeView-DNBrQnwy.js → HomeView-b_TT5oV3.js} +1 -1
- package/dist/ui/assets/{ImageEngineSettings-BfM9HSd_.js → ImageEngineSettings-CJfk4OJ4.js} +1 -1
- package/dist/ui/assets/{ImageRecognitionSettings-CaSQu5Br.js → ImageRecognitionSettings-DzbvZk5S.js} +1 -1
- package/dist/ui/assets/{IncompleteDownloads-C36lTCMG.js → IncompleteDownloads-C8_XyP8O.js} +1 -1
- package/dist/ui/assets/{KnowledgeCatalogsCard-CK9bqdf6.js → KnowledgeCatalogsCard-CHopG_j-.js} +1 -1
- package/dist/ui/assets/KnowledgeView-CXNKZUJq.js +1 -0
- package/dist/ui/assets/{LlamaCppSettings-CdNMHBbp.js → LlamaCppSettings-ohcM7kes.js} +1 -1
- package/dist/ui/assets/{MarkdownField-Dugmfr_e.js → MarkdownField-BX0qsaFq.js} +1 -1
- package/dist/ui/assets/{MemoriesTree-CgFqUNEr.js → MemoriesTree-BPj5Rod8.js} +1 -1
- package/dist/ui/assets/{MicrophoneSettings-DzDe9y1q.js → MicrophoneSettings-CWjeYnfI.js} +1 -1
- package/dist/ui/assets/MlxSettings-Dq6dRpcl.js +1 -0
- package/dist/ui/assets/{ModelPicker-BVkJhNAH.js → ModelPicker-0Ue-eEKj.js} +1 -1
- package/dist/ui/assets/NewPathDialog-BhAZm9dp.js +1 -0
- package/dist/ui/assets/{NewScriptDialog-TEAd0KLl.js → NewScriptDialog-DuryIe50.js} +1 -1
- package/dist/ui/assets/NewTaskDialog-BX24flMY.js +2 -0
- package/dist/ui/assets/{OllamaSettings-CPy2vxyZ.js → OllamaSettings-Boj8Nd1G.js} +1 -1
- package/dist/ui/assets/ProjectChat-Dhw_M5bq.js +5 -0
- package/dist/ui/assets/ProjectConnectionsTab-BwpMQNrg.js +1 -0
- package/dist/ui/assets/{ProjectGitStatusBar-BgHZ2ijN.js → ProjectGitStatusBar-BORGYx5l.js} +1 -1
- package/dist/ui/assets/{ProjectGithubView-BV2uTNU0.js → ProjectGithubView-CTP1BOMv.js} +1 -1
- package/dist/ui/assets/{ProjectMailTab-DLtJdXSL.js → ProjectMailTab-qFmAeV3M.js} +1 -1
- package/dist/ui/assets/{ProjectOverviewView-ZMs9nL5N.js → ProjectOverviewView-Cq1FsoaT.js} +1 -1
- package/dist/ui/assets/{ProjectTimeline-CTPcn4Kc.js → ProjectTimeline-Cqae2Z92.js} +1 -1
- package/dist/ui/assets/ProjectsView-D0uJjUB-.js +7 -0
- package/dist/ui/assets/{RecommendedBadge-iUoisQBi.js → RecommendedBadge-CN1jEmSn.js} +1 -1
- package/dist/ui/assets/{RemoteServersPanel-CTVJ0IRh.js → RemoteServersPanel-CMakvCCM.js} +1 -1
- package/dist/ui/assets/{ScriptEditorTabs-CCDFZjdC.js → ScriptEditorTabs-st6dJePd.js} +2 -2
- package/dist/ui/assets/{ScriptEditorView-CergLqKj.js → ScriptEditorView-BkySh57_.js} +2 -2
- package/dist/ui/assets/{ScriptsView-v7ckdhDi.js → ScriptsView-7uPKwjDB.js} +1 -1
- package/dist/ui/assets/{SecurityComplianceSettings-Bd0-66Gs.js → SecurityComplianceSettings-Tsv_pXfy.js} +1 -1
- package/dist/ui/assets/SessionSwitcher-D0fSeeHO.js +1 -0
- package/dist/ui/assets/SettingsView-cli_z8ZW.js +3 -0
- package/dist/ui/assets/{SquisqIntegration-C5l_OPvD.js → SquisqIntegration-BTZ1kBlg.js} +1 -1
- package/dist/ui/assets/{StorageCleanupDialog-3kv9-2mT.js → StorageCleanupDialog-CDBjl8JQ.js} +1 -1
- package/dist/ui/assets/{StorageUsageCard-7sWTrZFa.js → StorageUsageCard-DXY1j0dZ.js} +1 -1
- package/dist/ui/assets/TaskTabContent-C0P681SL.js +1 -0
- package/dist/ui/assets/TasksView-Ddwz10ri.js +1 -0
- package/dist/ui/assets/{TerminalCodeEditor-ChmdzmCz.js → TerminalCodeEditor-BkNQ6QoQ.js} +2 -2
- package/dist/ui/assets/ToolsetsEditor-KVigemfL.js +8 -0
- package/dist/ui/assets/{TransformToolbarButton-gzIxUBH7.js → TransformToolbarButton-8wfJR1bO.js} +2 -2
- package/dist/ui/assets/{UnrecognizedModels-0hptopv6.js → UnrecognizedModels-BzdU1clO.js} +1 -1
- package/dist/ui/assets/{VideoEngineSettings-BdNzCEdR.js → VideoEngineSettings-f79ff57u.js} +1 -1
- package/dist/ui/assets/{WorkspaceIndexPane-DnsOO916.js → WorkspaceIndexPane-fu5V6o1W.js} +1 -1
- package/dist/ui/assets/{api-C0I7spBl.js → api-CmrgM5Rf.js} +1 -1
- package/dist/ui/assets/chat-thread-memory-8MCtb17Q.js +1 -0
- package/dist/ui/assets/{chunk-6ECMNUIP-BvCy0HUI.js → chunk-6ECMNUIP-D5AA6ozp.js} +1 -1
- package/dist/ui/assets/{chunk-A6N6IN3I-ofeM4l8g.js → chunk-A6N6IN3I-BpxihS5H.js} +1 -1
- package/dist/ui/assets/{chunk-ATWVNF7D-CYuW1Yc6.js → chunk-ATWVNF7D-CKIWh7bN.js} +1 -1
- package/dist/ui/assets/{chunk-UBFT2CDQ-FexGDigd.js → chunk-CW24CH7I-BD0FIooX.js} +1 -1
- package/dist/ui/assets/{chunk-DXYWKZ52-zxe8pjH4.js → chunk-DXYWKZ52-DMKPZnpo.js} +1 -1
- package/dist/ui/assets/chunk-IIQYS2YH-BtDJt4Xr.js +1 -0
- package/dist/ui/assets/{chunk-KGWT454C-v5-l6U5m.js → chunk-KGWT454C-DsQOBuLg.js} +1 -1
- package/dist/ui/assets/{chunk-Q77KNJIN-BLuPdsQF.js → chunk-Q77KNJIN-BdWizq9s.js} +1 -1
- package/dist/ui/assets/{chunk-USU6HTKB-B_p-YcDp.js → chunk-USU6HTKB-DyGZplh4.js} +1 -1
- package/dist/ui/assets/{chunk-UXEANVBI-Bt0kX-0Z.js → chunk-UXEANVBI-BUBXvqyE.js} +1 -1
- package/dist/ui/assets/{chunk-O7JILDEF-CqcO1qaI.js → chunk-X7BNDUNI-D14WIvlD.js} +2 -2
- package/dist/ui/assets/{chunk-AE3IUKMM-mZjzzO8Z.js → chunk-ZSU5DJLX-CrjQf-vs.js} +1 -1
- package/dist/ui/assets/{container-BI8hxN1N.js → container-iFj1r6Hk.js} +1 -1
- package/dist/ui/assets/csv-Di411Mv-.js +1 -0
- package/dist/ui/assets/data-Q05qqAp4.js +1 -0
- package/dist/ui/assets/{dist-APSIK7H3.js → dist-1FNFiksd.js} +3 -3
- package/dist/ui/assets/dist-BMZhqfv7.js +2 -0
- package/dist/ui/assets/dist-CE5CbmDb.js +225 -0
- package/dist/ui/assets/doc-BHcGsJZd.js +587 -0
- package/dist/ui/assets/{document-import-DPK4r8Am.js → document-import-B2Ya6sbf.js} +1 -1
- package/dist/ui/assets/{docx-DRLuCTaC.js → docx-B8Pwz5Ih.js} +1 -1
- package/dist/ui/assets/{epub-a0p2Xb1b.js → epub-BQ4g8Q9j.js} +1 -1
- package/dist/ui/assets/{export-options-BqYFyzWx.js → export-options-Dylv69b3.js} +1 -1
- package/dist/ui/assets/file-browser-BLOPfnS0.js +5 -0
- package/dist/ui/assets/{html-BbQNmJ5X.js → html-BnA7qFwq.js} +1 -1
- package/dist/ui/assets/icons-CyM7Cg4E.js +1 -0
- package/dist/ui/assets/index-DW6qHqhU.css +1 -0
- package/dist/ui/assets/index-DivKnJyx.js +36 -0
- package/dist/ui/assets/{mail-link-CWfsP5Aq.js → mail-link-NtlcX5OE.js} +1 -1
- package/dist/ui/assets/{markdown-ryKA_OmY.js → markdown-CLKH_zzl.js} +1 -1
- package/dist/ui/assets/markdown-baseline-0dqv9qbV.js +1 -0
- package/dist/ui/assets/materialize-G4WC5UG3-xq2dcwS8.js +1 -0
- package/dist/ui/assets/{monaco-base-C0VTMpv-.js → monaco-base-BSvdAweA.js} +1 -1
- package/dist/ui/assets/{monaco-setup-CX8q88c5.js → monaco-setup-CT7LZ0o_.js} +1 -1
- package/dist/ui/assets/{new-project-meta-ZmDPGYzC.js → new-project-meta-5Y9Blozr.js} +1 -1
- package/dist/ui/assets/outside-in-Msmhxf_U.js +3 -0
- package/dist/ui/assets/{pdf-BHrygJa5.js → pdf-C4BhW3zg.js} +1 -1
- package/dist/ui/assets/{pending-drafts-27ujtQxX.js → pending-drafts-BD227X9H.js} +1 -1
- package/dist/ui/assets/{poppetje-CfaAvFkE.js → poppetje-DvCJO36y.js} +3 -3
- package/dist/ui/assets/{pptx-nDW64jAN.js → pptx-B6uaM2s7.js} +3 -3
- package/dist/ui/assets/{run-export-86KzLZ7R.js → run-export-TscWwR6y.js} +2 -2
- package/dist/ui/assets/{standalone-source-7QdiNsDW.js → standalone-source-Cw9SF7Zk.js} +1 -1
- package/dist/ui/assets/storage-Cmhlwx70.js +1 -0
- package/dist/ui/assets/styles-BjDaWeMA.css +1 -0
- package/dist/ui/assets/styles-CqO-rmOt.js +554 -0
- package/dist/ui/assets/{terminal-monaco-setup-Bar-sYKd.js → terminal-monaco-setup-me523-j-.js} +1 -1
- package/dist/ui/assets/{transform-CmAXy0Ck.js → transform-DxJCwK68.js} +1 -1
- package/dist/ui/assets/{use-local-model-manager-D1yiurrC.js → use-local-model-manager-8wvk-I-y.js} +1 -1
- package/dist/ui/assets/{useCompactLayout-BDtPQcDh.js → useCompactLayout-cm4E9Vja.js} +0 -0
- package/dist/ui/assets/{useCopilotAvailability-BHOfHrfT.js → useCopilotAvailability-D9hglSH_.js} +1 -1
- package/dist/ui/assets/{useDiffpacks-B0kYhlWQ.js → useDiffpacks-1BN2XJWg.js} +1 -1
- package/dist/ui/assets/{useGitSync-DOt-ODiw.js → useGitSync-7m9YA7h5.js} +1 -1
- package/dist/ui/assets/{useShowWorkInProgressFeatures-BtpredG7.js → useShowWorkInProgressFeatures-D6QOaTUT.js} +1 -1
- package/dist/ui/assets/{useTotalRamBytes-B8NFM27w.js → useTotalRamBytes-Durk383U.js} +1 -1
- package/dist/ui/assets/{xlsx-B_pu1ZvY.js → xlsx-BbHA9bxA.js} +1 -1
- package/dist/ui/index.html +15 -15
- package/package.json +12 -11
- package/dist/ui/assets/CatalogBrowser-7_jHy5Q3.js +0 -1
- package/dist/ui/assets/ChatTimelineView-Cg_kLK_U.js +0 -7
- package/dist/ui/assets/CraftbookEditor-BKAIsnXv.js +0 -1
- package/dist/ui/assets/DiffpackReviewView-B2a3zgE-.js +0 -1
- package/dist/ui/assets/DocumentDetail-GCYhwQqV.js +0 -1
- package/dist/ui/assets/DocumentsView-Cm3RaQ5N.js +0 -1
- package/dist/ui/assets/FileMapView-BKJovLcL.js +0 -1
- package/dist/ui/assets/FoldersSettings-CuJd2JdE.js +0 -1
- package/dist/ui/assets/GezelDetail-D_KIPDhQ.js +0 -1
- package/dist/ui/assets/GezellenView-BOOW1QQU.js +0 -1
- package/dist/ui/assets/HandboekView-gRzJcIbJ.js +0 -1
- package/dist/ui/assets/KnowledgeView-DJ3cJVHA.js +0 -1
- package/dist/ui/assets/MlxSettings-45mBFHbA.js +0 -1
- package/dist/ui/assets/NewTaskDialog-CIXVunZn.js +0 -2
- package/dist/ui/assets/ProjectChat-BiJRweob.js +0 -5
- package/dist/ui/assets/ProjectConnectionsTab-CQgaIzuv.js +0 -1
- package/dist/ui/assets/ProjectsView-BUdR76n6.js +0 -7
- package/dist/ui/assets/SessionSwitcher-BgZqyiRn.js +0 -1
- package/dist/ui/assets/SettingsView-DLhOYiR5.js +0 -3
- package/dist/ui/assets/TaskTabContent-CG2KmfwV.js +0 -1
- package/dist/ui/assets/TasksView-Dy5Ue4zS.js +0 -1
- package/dist/ui/assets/ToolsetsEditor-J9XxQ5Ms.js +0 -8
- package/dist/ui/assets/chat-thread-memory-CI2-giEq.js +0 -1
- package/dist/ui/assets/chunk-IIQYS2YH-DEkyBlHg.js +0 -1
- package/dist/ui/assets/csv-B0D9jJG2.js +0 -1
- package/dist/ui/assets/data-BIL84EaT.js +0 -1
- package/dist/ui/assets/dist-CJqyWK6E.js +0 -2
- package/dist/ui/assets/dist-DOqbRmFj.js +0 -225
- package/dist/ui/assets/doc-C2Ph2FWI.js +0 -584
- package/dist/ui/assets/document-companion-aDThLOwl.js +0 -1
- package/dist/ui/assets/file-browser-DVyWN0LD.js +0 -5
- package/dist/ui/assets/icons-DWaUNQbT.js +0 -1
- package/dist/ui/assets/index-DDu8nyO6.js +0 -34
- package/dist/ui/assets/index-DEDUSiCx.css +0 -1
- package/dist/ui/assets/markdown-baseline-9B52XlX2.js +0 -1
- package/dist/ui/assets/materialize-G4WC5UG3-BlZQe-88.js +0 -1
- package/dist/ui/assets/outside-in-BmIIeMid.js +0 -3
- package/dist/ui/assets/storage-B-vhjyV2.js +0 -1
- package/dist/ui/assets/styles-BvkZd-EV.js +0 -550
- package/dist/ui/assets/styles-IQ4adxWr.css +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{t as r}from"./api-
|
|
1
|
+
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{t as r}from"./api-CmrgM5Rf.js";import{G as i,H as a,J as o,K as s,W as c,Y as l,q as u}from"./primitives-CWrGZpPI.js";import{o as d,t as f}from"./pending-drafts-BD227X9H.js";var p=e(t(),1),m=n(),h=[{id:`post-message`,title:`Post a message when a phase starts`,blurb:`Writes a note onto the task so the team sees it.`,requires:[`tasks.write`]},{id:`fetch-and-summarize`,title:`Fetch a URL and summarize it`,blurb:`Pulls a page and produces a one-paragraph summary.`,requires:[`network`,`llm`]},{id:`check-files`,title:`Check files and decide`,blurb:`Inspects the workspace and outputs a yes/no a phase can advance on.`,requires:[`workspace.read`]},{id:`call-tool`,title:`Call a tool`,blurb:`Runs any registered tool — search, git, GitHub, browser.`,requires:[`network`]},{id:`ask-ai`,title:`Ask the AI about this task`,blurb:`Reads a task and answers a question about it.`,requires:[`llm`,`tasks.read`]},{id:`blank`,title:`Start blank`,blurb:`Just the skeleton every script needs.`,requires:[]}];function g(e){let t=e.toLowerCase().replace(/[^a-z0-9\s-]/g,``).split(/[\s-]+/).filter(Boolean).slice(0,4).join(`-`);return/^[a-z]/.test(t)?t:t?`do-${t}`:``}function _({open:e,projectId:t,scope:n,onClose:_,onCreated:v}){let[y,b]=(0,p.useState)(``),[x,S]=(0,p.useState)(!1),[C,w]=(0,p.useState)(``),[T,E]=(0,p.useState)(`blank`),[D,O]=(0,p.useState)(!1),[k,A]=(0,p.useState)(null);(0,p.useEffect)(()=>{e&&(b(``),S(!1),w(``),E(`blank`),O(!1),A(null))},[e]);let j=x||y?y:g(C),M=/^[a-zA-Z][\w-]*$/.test(j),N=async e=>{if(!(D||!M)){O(!0),A(null);try{let i={name:j,...C.trim()?{description:C.trim()}:{},template:e?`blank`:T};await(n===`user`?r.createUserScript(i):r.createProjectScript(t,i)),e&&C.trim()&&f(`${n?`${n}:`:``}${t}/${j}`,C.trim()),v(j)}catch(e){A(e.message)}finally{O(!1)}}};return(0,m.jsx)(o,{open:e,onOpenChange:e=>{!e&&!D&&_()},children:(0,m.jsxs)(u,{children:[(0,m.jsx)(s,{}),(0,m.jsxs)(c,{className:`new-script-dialog`,children:[(0,m.jsx)(l,{asChild:!0,children:(0,m.jsx)(`h3`,{children:`New script`})}),(0,m.jsxs)(i,{className:`muted small`,children:[`Scripts run automatically when task phases start or finish — or whenever you run them yourself.`,n===`user`&&` This one goes in the shared library, so every project can use it.`]}),(0,m.jsxs)(`div`,{className:`new-script-dialog__body`,children:[(0,m.jsxs)(`label`,{className:`new-script-field`,children:[(0,m.jsx)(`span`,{children:`Describe what it should do (optional)`}),(0,m.jsx)(`textarea`,{value:C,onChange:e=>w(e.target.value),placeholder:`When this phase starts, fetch the PR diff and post a one-paragraph summary…`,rows:3,disabled:D})]}),(0,m.jsxs)(`div`,{className:`new-script-ai`,children:[(0,m.jsx)(`button`,{type:`button`,className:`primary`,disabled:D||!C.trim()||!M,onClick:()=>void N(!0),children:`Draft it with AI`}),(0,m.jsx)(`span`,{className:`muted small`,children:`or pick a starting point:`})]}),(0,m.jsx)(`div`,{className:`new-script-templates`,"aria-label":`Starter template`,children:h.map(e=>(0,m.jsxs)(`button`,{type:`button`,"aria-pressed":T===e.id,className:`new-script-template${T===e.id?` active`:``}`,onClick:()=>E(e.id),disabled:D,children:[(0,m.jsx)(`strong`,{children:e.title}),(0,m.jsx)(`span`,{className:`muted small`,children:e.blurb}),(0,m.jsx)(d,{requires:e.requires})]},e.id))}),(0,m.jsxs)(`label`,{className:`new-script-field`,children:[(0,m.jsx)(`span`,{children:`Name`}),(0,m.jsx)(`input`,{type:`text`,value:j,onChange:e=>{b(e.target.value),S(!0)},placeholder:`summarize-and-post`,disabled:D}),j&&!M&&(0,m.jsx)(`span`,{className:`scripts-view__error small`,children:`Names start with a letter and use only letters, digits, dashes, underscores.`})]}),k&&(0,m.jsx)(`p`,{className:`scripts-view__error`,children:k})]}),(0,m.jsxs)(a,{children:[(0,m.jsx)(`button`,{type:`button`,onClick:_,disabled:D,children:`Cancel`}),(0,m.jsx)(`button`,{type:`button`,className:`primary`,disabled:D||!M,onClick:()=>void N(!1),children:D?`Creating…`:`Create`})]})]})]})})}export{_ as t};
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{Wt as r,wn as i}from"./dist-CE5CbmDb.js";import{t as a}from"./dist-BMZhqfv7.js";import{t as o}from"./api-CmrgM5Rf.js";import{H as ee,J as te,K as ne,W as re,Y as ie,d as s,l as c,m as l,p as ae,q as oe,s as se}from"./primitives-CWrGZpPI.js";import{t as ce}from"./GezelJsonEditor-B9XEiW5Y.js";import{r as u}from"./new-project-meta-5Y9Blozr.js";import{at as le,ct as ue,dt as de,ft as fe,lt as pe,mt as me,ot as d,pt as he,st as ge,ut as _e}from"./index-DivKnJyx.js";import{t as ve}from"./CraftbookToolsetSetup-J7rEa835.js";import{t as ye}from"./useShowWorkInProgressFeatures-D6QOaTUT.js";var f=e(t(),1);function be(e){if(e instanceof a){let t=e.details;if(t&&typeof t==`object`&&`error`in t){let e=t.error;if(typeof e==`string`&&e.length>0&&e!==`internal_error`)return e}return e.message}return e instanceof Error?e.message:String(e)}var p=n(),m=`__auto`,xe={"one-time":{title:`New Task`,subtitle:`Pick a craftbook — a proven recipe your crew follows step by step — or start blank.`,generalLabel:d.label,generalDescription:d.description,featuredLabel:`Recommended`,featuredTitle:`Recommended`,featuredTagline:`proven recipes for this kind of project`,submitLabel:`Create task`,footnote:`Lands ready to fire — nothing runs until you fire it.`},scheduled:{title:`New Scheduled Task`,subtitle:`Choose a repeatable craftbook, then set when each fresh run should begin.`,generalLabel:`Blank scheduled task`,generalDescription:`Define a repeatable job from scratch and run a fresh copy on a cadence.`,featuredLabel:`For schedules`,featuredTitle:`Scheduled craftbooks`,featuredTagline:`recipes identified as safe for recurring unattended runs`,submitLabel:`Create schedule`,footnote:`Starts active and creates a fresh task on each scheduled run.`},"night-shift":{title:`New Night Shift Task`,subtitle:`Choose work your crew can pick up unattended during the Night Shift window.`,generalLabel:`Blank Night Shift task`,generalDescription:`Define a one-off job that waits for Night Shift before it begins.`,featuredLabel:`For Night Shift`,featuredTitle:`Night Shift craftbooks`,featuredTagline:`recipes identified as safe for unattended overnight work`,submitLabel:`Queue for Night Shift`,footnote:`Starts active, but only runs while Night Shift is on.`}};function h({open:e,creationMode:t=`one-time`,defaultProjectId:n,projects:a,gezels:h,projectLocked:we,onClose:g,onCreated:Te}){let _=xe[t],Ee=ye(),[v,De]=(0,f.useState)(n),[y,b]=(0,f.useState)([]),[x,Oe]=(0,f.useState)(!1),S=(0,f.useRef)(0),[ke,Ae]=(0,f.useState)({}),[je,Me]=(0,f.useState)(null),[C,Ne]=(0,f.useState)(new Set),[w,T]=(0,f.useState)(null),[E,D]=(0,f.useState)(`pick`),[Pe,O]=(0,f.useState)(!1),[k,Fe]=(0,f.useState)(``),[A,j]=(0,f.useState)(`all`),[Ie,M]=(0,f.useState)(!1),[N,P]=(0,f.useState)(``),[F,Le]=(0,f.useState)(!1),[I,Re]=(0,f.useState)(``),[L,ze]=(0,f.useState)(`Main`),[Be,R]=(0,f.useState)(``),[Ve,He]=(0,f.useState)(!1),[z,B]=(0,f.useState)({}),[Ue,We]=(0,f.useState)(``),[V,Ge]=(0,f.useState)(`skip`),[H,U]=(0,f.useState)(!1),[Ke,W]=(0,f.useState)(``),[qe,Je]=(0,f.useState)(null),Ye=(0,f.useRef)(0);(0,f.useEffect)(()=>{e&&(De(n),T(null),O(!1),D(`pick`),Fe(``),j(`all`),M(!1),P(``),Le(!1),Re(``),ze(`Main`),R(``),He(!1),B({}),We(``),Ge(`skip`),U(!1),W(``),Je(null))},[e,n]);let Xe=(0,f.useCallback)(async()=>{let e=++S.current;if(!v){if(e!==S.current)return;b([]),Oe(!0);return}try{let t=await o.listProjectCraftbooks(v);if(e!==S.current)return;let n=i(t.items??[],Ee),r=new Set(n.map(e=>e.manifest.id));b(me(n)),Ae(t.missingToolsets??{}),Me(t.projectType??null),Ne(new Set((t.suggestedIds??[]).filter(e=>r.has(e)))),T(e=>e&&!r.has(e)?null:e)}catch{if(e!==S.current)return;b([]),Ae({}),Me(null),Ne(new Set)}finally{e===S.current&&Oe(!0)}},[v,Ee]);(0,f.useEffect)(()=>{e&&(Oe(!1),Xe())},[e,Xe]),(0,f.useEffect)(()=>{!e||!x||Ie||(M(!0),(t===`one-time`?C.size>0:y.some(e=>t===`scheduled`?e.manifest.runModes?.scheduled:e.manifest.runModes?.nightShift))&&j(`recommended`))},[e,x,Ie,C,t,y]);let G=w?y.find(e=>e.manifest.id===w)??null:null,K=(()=>{if(!G)return null;let e=G.manifest;return(e.steps.find(t=>t.id===e.entryStepId)??e.steps[0])?.suggestedRole??null})(),Ze=t!==`scheduled`&&(G?.manifest.connectors??[]).some(e=>e.typeId===`github-pulls`&&!e.optional),Qe=String(z.number??``).trim();(0,f.useEffect)(()=>{let t=++Ye.current;Je(null),!(!e||!Ze||!v)&&(async()=>{try{let[e,n]=await Promise.all([o.getProjectGitStatus(v),o.listProjectGitHubPulls(v)]);if(t!==Ye.current)return;let{matchingCount:i}=r(n.pulls??[],e.branch);if(i>0)return;Je(e.branch?`No open pull request for branch "${e.branch}" — enter a pull request number above, or switch branches first.`:`This checkout is not on a branch — enter a pull request number above.`)}catch{}})()},[e,Ze,v]);let $e=(0,f.useCallback)(()=>{T(null),O(!0),B({}),W(``),D(`configure`),F||P(``)},[F]),et=(0,f.useCallback)(()=>{D(`pick`),W(``)},[]),tt=(0,f.useCallback)(e=>{De(e),T(null),O(!1),B({}),j(`all`),M(!1),W(``)},[]),nt=(0,f.useCallback)(e=>{if(T(e.manifest.id),O(!1),B(_e(e.manifest.paramSchema)),W(``),D(`configure`),F||P(e.manifest.name),!Ve){let t=e.manifest.defaultAssignee;t?.kind===`gezel`&&h.some(e=>e.id===t.gezelId)&&R(t.gezelId)}},[F,Ve,h]),q=Be||(K?m:h[0]?.id??`__user`),J=q===m?null:q===`__user`?{kind:`user`}:{kind:`gezel`,gezelId:q},Y=(0,f.useMemo)(()=>he(y),[y]),X=k.trim().toLowerCase(),Z=X.length>0,Q=(0,f.useMemo)(()=>{if(t===`one-time`)return y.filter(e=>C.has(e.manifest.id));let e=t===`scheduled`?`scheduled`:`nightShift`;return y.filter(t=>t.manifest.runModes?.[e]).sort((t,n)=>{let r=+(t.manifest.runModes?.[e]===`recommended`);return+(n.manifest.runModes?.[e]===`recommended`)-r||t.manifest.name.localeCompare(n.manifest.name)})},[y,C,t]),rt=(0,f.useCallback)(e=>{if(t===`one-time`)return C.has(e.manifest.id);let n=t===`scheduled`?`scheduled`:`nightShift`;return e.manifest.runModes?.[n]===`recommended`},[t,C]),it=(0,f.useMemo)(()=>Z?y.filter(e=>`${e.manifest.id} ${e.manifest.name} ${e.manifest.description} ${(e.manifest.tags??[]).join(` `)}`.toLowerCase().includes(X)).sort((e,t)=>{let n=C.has(e.manifest.id)||e.manifest.tags?.includes(`recommended`)?1:0;return(C.has(t.manifest.id)||t.manifest.tags?.includes(`recommended`)?1:0)-n||Se(e,X)-Se(t,X)||e.manifest.name.localeCompare(t.manifest.name)}):y,[y,Z,X,C]),at=!Z||`${_.generalLabel} ${_.generalDescription} blank fresh`.toLowerCase().includes(X),ot=(0,f.useMemo)(()=>{if(Z)return[{id:`search`,title:`Craftbooks`,tagline:`matching "${k.trim()}"`,books:it}];if(A===`recommended`&&Q.length>0)return[{id:`recommended`,title:t===`one-time`&&je?`Recommended for ${je.label}`:_.featuredTitle,tagline:_.featuredTagline,books:Q}];let e=Y.find(e=>e.id===A);return e?[{id:e.id,title:e.label,tagline:e.tagline,books:y.filter(t=>e.bookIds.has(t.manifest.id))}]:[{id:`all`,title:`All craftbooks`,tagline:void 0,books:y}]},[Z,k,it,A,Q,je,Y,y,t,_]),$=G?ke[G.manifest.id]??[]:[],st=(0,f.useCallback)(async e=>{if(e.preventDefault(),H||E!==`configure`)return;if(W(``),!v){W(`Pick a project.`);return}let n=Ue.trim();if(t===`scheduled`&&!n){W(`Enter a schedule.`);return}if(G){let e=G.manifest;if((ke[e.id]?.length??0)>0){W(`This craftbook needs its toolsets installed first — see the setup list.`);return}let r=e.paramSchema,i=(Array.isArray(r?.required)?r.required:[]).find(e=>{let t=z[e];return t==null||t===``});if(i){W(`"${i}" is required.`);return}let a=de(z);U(!0);try{let r=t===`scheduled`?await o.createTask(v,{title:N.trim()||e.name,description:`Recurring scheduled task. ${ge(e,a)} Each scheduled run creates a fresh task from this recipe.`,steps:[{name:`Wait for schedule`,prompt:`This host holds a recurring schedule. It does not perform the work itself; each tick creates a fresh child task.`}],spawnsCraftbookId:e.id,...G.item.sourceId?{spawnsCraftbookSourceId:G.item.sourceId}:{},...J?{assignee:J}:{},cron:{expression:n,overlap:V},...Object.keys(a).length>0?{spawnsCraftbookParams:a}:{}}):await o.createTask(v,{title:N.trim()||e.name,description:ge(e,a),craftbookId:e.id,...G.item.sourceId?{craftbookSourceId:G.item.sourceId}:{},...J?{assignee:J}:{},...t===`one-time`?{dispatchEntry:!0}:{nightShift:{enabled:!0},dispatchEntry:!0},...Object.keys(a).length>0?{craftbookParams:a}:{}});if(t!==`scheduled`&&Object.keys(a).length>0&&r.activeStepId){let e=[`# Invocation parameters`,``];for(let[t,n]of Object.entries(a))e.push(`- **${t}**: ${n}`);await o.appendTaskNote(r.projectId,r.num,{text:e.join(`
|
|
2
|
+
`),stepId:r.activeStepId}).catch(()=>{})}await Te(r),g()}catch(e){W(be(e))}finally{U(!1)}return}let r=N.trim();if(!r){W(`Title is required.`);return}if(I.trim().length<40){W(`Description must be at least 40 characters — the job-to-be-done from the user's perspective. What does success look like?`);return}let i=L.split(/\n|,/).map(e=>e.trim()).filter(Boolean).map(e=>({name:e}));i.length===0&&i.push({name:`Main`}),U(!0);try{await Te(t===`scheduled`?await o.createTask(v,{title:r,description:I.trim(),steps:[{name:`Wait for schedule`,prompt:`This host holds a recurring schedule. It does not perform the work itself; each tick creates a fresh child task.`}],spawnsSteps:i,...J?{assignee:J}:{},cron:{expression:n,overlap:V}}):await o.createTask(v,{title:r,description:I.trim(),steps:i,...J?{assignee:J}:{},...t===`one-time`?{status:`draft`}:{nightShift:{enabled:!0},dispatchEntry:!0}})),g()}catch(e){W(be(e))}finally{U(!1)}},[H,E,t,v,G,ke,z,N,J,I,L,Ue,V,Te,g]),ct=G&&pe(G.manifest)?G.manifest.paramSchema:null,lt=H||G!==null&&$.length>0,ut=G?`Craftbook${rt(G)?t===`night-shift`?` · recommended for Night Shift`:t===`scheduled`?` · recommended for schedules`:` · recommended`:``}`:t===`one-time`?`Blank task`:t===`scheduled`?`Blank schedule`:`Blank Night Shift task`,dt=a.find(e=>e.id===v)?.name??``;return(0,p.jsx)(te,{open:e,onOpenChange:e=>{e||g()},children:(0,p.jsxs)(oe,{children:[(0,p.jsx)(ne,{}),(0,p.jsx)(re,{className:`gz-npd gz-ntd gz-npd-step-${E}`,children:(0,p.jsx)(`form`,{onSubmit:st,style:{display:`contents`},children:E===`pick`?(0,p.jsxs)(p.Fragment,{children:[(0,p.jsxs)(`header`,{className:`gz-npd-header`,children:[(0,p.jsxs)(`div`,{className:`gz-npd-header-copy`,children:[(0,p.jsx)(ie,{asChild:!0,children:(0,p.jsx)(`h3`,{children:_.title})}),(0,p.jsx)(`p`,{className:`gz-npd-header-sub`,children:_.subtitle})]}),(0,p.jsxs)(`div`,{className:`gz-ntd-header-controls`,children:[!we&&(0,p.jsxs)(`label`,{className:`gz-ntd-header-project`,children:[(0,p.jsx)(`span`,{children:`Project`}),(0,p.jsxs)(s,{value:v,onValueChange:tt,children:[(0,p.jsx)(ae,{children:(0,p.jsx)(l,{})}),(0,p.jsx)(se,{children:a.map(e=>(0,p.jsx)(c,{value:e.id,children:e.name},e.id))})]})]}),(0,p.jsxs)(`label`,{className:`gz-npd-search`,children:[(0,p.jsx)(`span`,{className:`sr-only`,children:`Search craftbooks`}),(0,p.jsx)(`input`,{type:`search`,value:k,onChange:e=>Fe(e.target.value),placeholder:`Search craftbooks…`})]})]})]}),(0,p.jsxs)(`div`,{className:`gz-npd-body`,children:[(0,p.jsxs)(`nav`,{className:`gz-npd-rail`,"aria-label":`Craftbook shelves`,children:[Q.length>0&&(0,p.jsxs)(`button`,{type:`button`,className:`gz-npd-rail-item${!Z&&A===`recommended`?` active`:``}`,onClick:()=>j(`recommended`),children:[(0,p.jsx)(u,{glyph:`sprout`,size:16}),(0,p.jsx)(`span`,{className:`gz-npd-rail-label`,children:_.featuredLabel}),(0,p.jsx)(`span`,{className:`gz-npd-rail-count`,children:Q.length})]}),(0,p.jsxs)(`button`,{type:`button`,className:`gz-npd-rail-item${!Z&&A===`all`?` active`:``}`,onClick:()=>j(`all`),children:[(0,p.jsx)(u,{glyph:`sheet`,size:16}),(0,p.jsx)(`span`,{className:`gz-npd-rail-label`,children:`All craftbooks`}),(0,p.jsx)(`span`,{className:`gz-npd-rail-count`,children:y.length})]}),Y.map((e,t)=>{let n=Y[t-1]?.family===e.family?null:fe(e.family);return(0,p.jsxs)(f.Fragment,{children:[n&&(0,p.jsx)(`span`,{className:`gz-npd-rail-group`,children:n}),(0,p.jsxs)(`button`,{type:`button`,className:`gz-npd-rail-item${!Z&&A===e.id?` active`:``}`,onClick:()=>j(e.id),children:[(0,p.jsx)(u,{glyph:e.glyph,size:16}),(0,p.jsx)(`span`,{className:`gz-npd-rail-label`,children:e.label}),(0,p.jsx)(`span`,{className:`gz-npd-rail-count`,children:e.bookIds.size})]})]},e.id)})]}),(0,p.jsxs)(`div`,{className:`gz-npd-gallery`,role:`radiogroup`,"aria-label":`Task type`,children:[at&&(0,p.jsxs)(`section`,{className:`gz-npd-section`,children:[(0,p.jsx)(`div`,{className:`gz-npd-section-head`,children:(0,p.jsx)(`span`,{className:`gz-npd-section-title`,children:`Start fresh`})}),(0,p.jsx)(`div`,{className:`gz-npd-grid`,children:(0,p.jsx)(Ce,{label:_.generalLabel,description:_.generalDescription,glyph:d.glyph,index:0,active:Pe,onSelect:$e})})]}),ot.map(e=>(0,p.jsxs)(`section`,{className:`gz-npd-section`,children:[(0,p.jsxs)(`div`,{className:`gz-npd-section-head`,children:[(0,p.jsx)(`span`,{className:`gz-npd-section-title`,children:e.title}),e.tagline&&(0,p.jsx)(`span`,{className:`gz-npd-section-tagline`,children:e.tagline})]}),e.books.length>0?(0,p.jsx)(`div`,{className:`gz-npd-grid`,children:e.books.map((e,t)=>(0,p.jsx)(Ce,{label:e.manifest.name,description:e.manifest.description,glyph:ue(e.manifest),...e.item.iconSvg?{iconSvg:e.item.iconSvg}:{},...e.item.logoUrl?{logoUrl:e.item.logoUrl}:{},suggested:rt(e),index:t+1,active:e.manifest.id===w,onSelect:()=>nt(e)},e.manifest.id))}):(0,p.jsx)(`p`,{className:`gz-npd-empty`,children:x?Z?`No craftbooks match your search.`:`No craftbooks here yet.`:`Loading craftbooks…`}),e.id===`recommended`&&y.length>Q.length&&(0,p.jsxs)(`button`,{type:`button`,className:`gz-ntd-show-all`,onClick:()=>j(`all`),children:[`Browse all `,y.length,` craftbooks`]})]},e.id))]})]}),(0,p.jsxs)(`div`,{className:`gz-npd-pane-footer gz-npd-pick-footer`,children:[(0,p.jsx)(`p`,{className:`gz-npd-footnote`,children:`Pick one to see what it does — nothing is created until the next screen.`}),(0,p.jsx)(ee,{children:(0,p.jsx)(`button`,{type:`button`,onClick:g,children:`Cancel`})})]})]}):(0,p.jsxs)(p.Fragment,{children:[(0,p.jsxs)(`header`,{className:`gz-npd-header gz-npd-detail-header`,children:[(0,p.jsxs)(`button`,{type:`button`,className:`gz-npd-back`,onClick:et,children:[(0,p.jsx)(`span`,{"aria-hidden":`true`,children:`‹`}),G?`Craftbooks`:`Back`]}),(0,p.jsxs)(`div`,{className:`gz-npd-detail-id`,children:[(0,p.jsx)(`span`,{className:`gz-npd-detail-art`,"aria-hidden":`true`,children:G?(0,p.jsx)(le,{...G.item.iconSvg?{iconSvg:G.item.iconSvg}:{},...G.item.logoUrl?{logoUrl:G.item.logoUrl}:{},svgClassName:`gz-npd-hero-art-svg`,fallback:(0,p.jsx)(u,{glyph:ue(G.manifest),size:26})}):(0,p.jsx)(u,{glyph:d.glyph,size:26})}),(0,p.jsxs)(`div`,{className:`gz-npd-header-copy`,children:[(0,p.jsx)(`p`,{className:`gz-npd-hero-eyebrow`,children:ut}),(0,p.jsx)(ie,{asChild:!0,children:(0,p.jsx)(`h3`,{className:`gz-npd-hero-name`,children:G?G.manifest.name:_.generalLabel})})]})]}),!we&&dt&&(0,p.jsxs)(`p`,{className:`gz-ntd-detail-project`,children:[`in `,(0,p.jsx)(`strong`,{children:dt})]})]}),(0,p.jsxs)(`div`,{className:`gz-npd-detail`,"data-blank":G?void 0:`true`,children:[G&&(0,p.jsxs)(`div`,{className:`gz-npd-brief`,children:[(0,p.jsx)(`p`,{className:`gz-npd-brief-lede`,children:G.manifest.description}),G.manifest.basedOn&&(0,p.jsxs)(`p`,{className:`gz-ntd-based-on`,children:[`Based on`,` `,(0,p.jsx)(`a`,{href:G.manifest.basedOn.url,target:`_blank`,rel:`noreferrer`,children:G.manifest.basedOn.name})]}),(0,p.jsxs)(`div`,{className:`gz-ntd-steps`,children:[(0,p.jsxs)(`p`,{className:`gz-npd-give-eyebrow`,children:[G.manifest.steps.length,` step`,G.manifest.steps.length===1?``:`s`]}),(0,p.jsx)(`ol`,{className:`gz-ntd-steps-list`,children:G.manifest.steps.map(e=>(0,p.jsxs)(`li`,{children:[(0,p.jsxs)(`span`,{className:`gz-ntd-step-head`,children:[(0,p.jsx)(`span`,{className:`gz-ntd-step-name`,children:e.name}),e.suggestedRole&&(0,p.jsx)(`span`,{className:`gz-ntd-step-role`,children:e.suggestedRole})]}),e.description&&(0,p.jsx)(`span`,{className:`gz-ntd-step-note`,children:e.description})]},e.id))})]})]}),(0,p.jsxs)(`div`,{className:`gz-npd-setup`,children:[!G&&(0,p.jsx)(`p`,{className:`gz-npd-brief-lede`,children:_.generalDescription}),(0,p.jsxs)(`div`,{className:`gz-npd-pane-form`,children:[(0,p.jsxs)(`label`,{children:[`Title`,(0,p.jsx)(`input`,{value:N,onChange:e=>{P(e.target.value),Le(!0)},placeholder:G?G.manifest.name:`e.g. Ship the landing page`})]}),$.length>0&&G&&(0,p.jsxs)(`div`,{className:`gz-ntd-needs`,children:[(0,p.jsx)(`p`,{className:`gz-npd-give-eyebrow`,children:`Needs setup`}),(0,p.jsx)(ve,{missing:$,onAllInstalled:()=>void Xe(),onCancel:et})]}),ct&&$.length===0&&(0,p.jsxs)(`div`,{className:`gz-npd-params`,children:[(0,p.jsx)(`p`,{className:`gz-npd-give-eyebrow`,children:`Parameters`}),(0,p.jsx)(ce,{schema:ct,value:z,onChange:e=>{B(e??{}),W(``)},density:`comfortable`})]}),!G&&(0,p.jsxs)(p.Fragment,{children:[(0,p.jsxs)(`label`,{children:[`Description `,(0,p.jsx)(`span`,{className:`muted`,children:`· a sentence or two`}),(0,p.jsx)(`textarea`,{value:I,onChange:e=>Re(e.target.value),rows:4,placeholder:`What's the problem? What does success look like for the user?`})]}),(0,p.jsxs)(`label`,{children:[`Steps `,(0,p.jsx)(`span`,{className:`muted`,children:`(one per line)`}),(0,p.jsx)(`textarea`,{value:L,onChange:e=>ze(e.target.value),rows:4})]})]}),(0,p.jsxs)(`label`,{children:[`Assign to`,(0,p.jsxs)(s,{value:q,onValueChange:e=>{R(e),He(!0)},children:[(0,p.jsx)(ae,{children:(0,p.jsx)(l,{})}),(0,p.jsxs)(se,{children:[K&&(0,p.jsxs)(c,{value:m,children:[`Auto — the `,K,` for step 1`]}),h.map(e=>(0,p.jsxs)(c,{value:e.id,children:[e.name,e.role?` — ${e.role}`:``]},e.id)),(0,p.jsx)(c,{value:`__user`,children:`Me (no gezel)`})]})]}),q===m?(0,p.jsxs)(`small`,{className:`muted`,children:[`Every step picks its own specialist by role when the task fires. Step 1 goes to the `,K,`, and whoever that turns out to be owns the task.`]}):G&&(0,p.jsx)(`small`,{className:`muted`,children:`Steps that name a role pick their own specialist when the task fires — this only covers steps that name none.`}),q===`__user`&&(0,p.jsx)(`small`,{className:`muted`,children:`Assigned to you — firing won't hand it to a gezel.`})]}),t===`scheduled`&&(0,p.jsxs)(`div`,{className:`gz-ntd-schedule`,children:[(0,p.jsx)(`p`,{className:`gz-npd-give-eyebrow`,children:`Schedule`}),(0,p.jsxs)(`label`,{children:[`Cron expression `,(0,p.jsx)(`span`,{className:`muted`,children:`(UTC, 5-field)`}),(0,p.jsx)(`input`,{value:Ue,placeholder:`e.g. 0 9 * * 1 — every Monday 09:00`,onChange:e=>We(e.target.value)})]}),(0,p.jsxs)(`label`,{children:[`Overlap policy`,(0,p.jsxs)(s,{value:V,onValueChange:e=>Ge(e),children:[(0,p.jsx)(ae,{children:(0,p.jsx)(l,{})}),(0,p.jsxs)(se,{children:[(0,p.jsx)(c,{value:`skip`,children:`skip — don't spawn if a prior run is still active`}),(0,p.jsx)(c,{value:`queue`,children:`queue — always spawn, let the runner throttle`}),(0,p.jsx)(c,{value:`concurrent`,children:`concurrent — spawn unconditionally`})]})]})]})]})]})]})]},w??`__general`),(0,p.jsxs)(`div`,{className:`gz-npd-pane-footer gz-npd-detail-footer`,children:[Ke?(0,p.jsx)(`p`,{className:`error small gz-npd-submit-error`,role:`alert`,children:Ke}):qe&&!Qe?(0,p.jsx)(`p`,{className:`gz-npd-footnote gz-ntd-launch-hint`,children:qe}):(0,p.jsx)(`p`,{className:`gz-npd-footnote`,children:t===`one-time`&&G?`Starts immediately — the first gezel gets to work as soon as you create it.`:_.footnote}),(0,p.jsxs)(ee,{children:[(0,p.jsx)(`button`,{type:`button`,onClick:g,disabled:H,children:`Cancel`}),(0,p.jsx)(`button`,{type:`submit`,className:`primary`,disabled:lt,children:H?t===`one-time`&&G?`Starting…`:`Creating…`:t===`one-time`&&G?`Create & start`:_.submitLabel})]})]})]})})})]})})}function Se(e,t){let n=e.manifest.name.toLowerCase();return n===t?0:n.startsWith(t)?1:n.split(/\s+/).some(e=>e.startsWith(t))?2:n.includes(t)?3:`${e.manifest.id} ${(e.manifest.tags??[]).join(` `)}`.toLowerCase().includes(t)?4:5}function Ce({label:e,description:t,active:n,iconSvg:r,logoUrl:i,glyph:a,suggested:o=!1,index:ee,onSelect:te}){return(0,p.jsxs)(`button`,{type:`button`,role:`radio`,"aria-checked":n,"aria-label":e,className:`gz-npd-card${n?` active`:``}${o?` gz-ntd-card-suggested`:``}`,onClick:te,style:{"--card-i":Math.min(ee,11)},children:[(0,p.jsx)(`span`,{className:`gz-npd-card-mark`,"aria-hidden":`true`,children:(0,p.jsx)(le,{...r?{iconSvg:r}:{},...i?{logoUrl:i}:{},svgClassName:`gz-npd-card-mark-svg`,fallback:(0,p.jsx)(u,{glyph:a,size:22})})}),(0,p.jsx)(`span`,{className:`gz-npd-card-name`,children:e}),(0,p.jsx)(`span`,{className:`gz-npd-card-description`,children:t})]})}export{h as t};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{bt as r}from"./dist-DOqbRmFj.js";import{t as i}from"./api-C0I7spBl.js";import{t as a}from"./model-context-DBqdK0PS.js";import{t as o}from"./ConfirmDialog-Dt1ed4Fh.js";import{t as s}from"./CatalogBrowser-7_jHy5Q3.js";import{t as c}from"./LicenseButton-D3VmcVG1.js";import{t as l}from"./TimeoutRow-B9SZiKH6.js";var u=e(t(),1),d=n(),f=1.2,p={"mix of experts":`Only a fraction of the model's parameters run per token, so it's faster than a dense model of the same nominal size. Gezels generally benefit from MoE models.`,moe:`Only a fraction of the model's parameters run per token, so it's faster than a dense model of the same nominal size. Gezels generally benefit from MoE models.`,thinking:`The model reasons through the problem step-by-step before answering. Slower, but generally more accurate on hard questions.`,agentic:`Tuned for multi-step agent workflows — tool use, planning, and iterating toward a goal.`,vision:`Can accept images alongside text.`,tools:`Supports function/tool calling via the API.`,multimodal:`Handles multiple input types (text + images).`,large:`Heavy model — needs a lot of memory and runs more slowly.`,small:`Compact model — runs quickly on modest hardware.`};function m(e){return e>=1024**3?`${(e/1024**3).toFixed(1)} GB`:e>=1024**2?`${(e/1024**2).toFixed(0)} MB`:e>=1024?`${(e/1024).toFixed(0)} KB`:`${e} B`}function h(e){return e>=1024**3?`~${(e/1024**3).toFixed(1)} GB`:e>=1024**2?`~${(e/1024**2).toFixed(0)} MB`:e>=1024?`~${(e/1024).toFixed(0)} KB`:`~${e} B`}function g(e){if(!e)return null;let t=new Date(e);return Number.isNaN(t.getTime())?null:t.toLocaleDateString(void 0,{year:`numeric`,month:`short`})}function _(e){return e.kind!==`chat-model`||!e.ollama?null:e}function v({enabled:e,onModelsChanged:t,compact:n=!1}){let[l,m]=(0,u.useState)([]),[v,b]=(0,u.useState)(null),[C,w]=(0,u.useState)(new Map),[T,E]=(0,u.useState)(``),[D,O]=(0,u.useState)(null),[k,A]=(0,u.useState)(null),[j,M]=(0,u.useState)(!1),[N,P]=(0,u.useState)(`all`),[F,I]=(0,u.useState)([]),L=(0,u.useRef)(C);L.current=C;let R=(0,u.useRef)(null);(0,u.useEffect)(()=>{let e=!1;return i.getMemoryProfile().then(t=>{e||A(t)}).catch(()=>{}),()=>{e=!0}},[]);let z=(0,u.useCallback)(async()=>{try{let e=await i.listProviderModels(`ollama`);m(e.models),b(null)}catch(e){b(e.message),m([])}},[]);(0,u.useEffect)(()=>{e&&z()},[e,z]),(0,u.useEffect)(()=>{if(!e)return;let t=!1;return(async()=>{try{let[{pulls:e},{models:n}]=await Promise.all([i.listPendingOllamaPulls(),i.listProviderModels(`ollama`)]);if(t)return;let r=new Set(n.map(e=>e.id));for(let t of e){if(r.has(t.name)){i.clearPendingOllamaPull(t.name).catch(()=>{});continue}L.current.has(t.name)||R.current?.(t.name)}}catch{}})(),()=>{t=!0}},[e]);let B=(0,u.useCallback)(async e=>{if(L.current.has(e))return;let n=new AbortController,r={name:e,status:`queued`,completed:0,total:0,controller:n};w(t=>new Map(t).set(e,r));try{await i.pullOllamaModel(e,t=>{if(t.type===`progress`){let n=t.chunk;w(t=>{let r=new Map(t),i=r.get(e);return i?(r.set(e,{...i,status:n.status,completed:n.completed??i.completed,total:n.total??i.total}),r):t})}else t.type===`error`&&w(n=>{let r=new Map(n),i=r.get(e);return i&&r.set(e,{...i,error:t.error}),r})},n.signal),setTimeout(()=>{w(t=>{let n=new Map(t);return n.delete(e),n}),z(),t?.(),(async()=>{try{let t=await i.getConfig();t.defaultModel?.ollama||await i.updateConfig({defaultModel:{...t.defaultModel,ollama:e}})}catch{}})()},900)}catch(t){if(n.signal.aborted){w(t=>{let n=new Map(t);return n.delete(e),n});return}w(n=>{let r=new Map(n),i=r.get(e);return i&&r.set(e,{...i,error:t.message}),r})}},[z,t]);R.current=B;let V=(0,u.useCallback)(e=>{L.current.get(e)?.controller.abort(),i.clearPendingOllamaPull(e).catch(()=>{})},[]),H=(0,u.useCallback)(async()=>{if(D)try{await i.deleteOllamaModel(D),await z(),t?.()}catch(e){b(e.message)}finally{O(null)}},[D,z,t]),U=(0,u.useMemo)(()=>new Set(l.map(e=>e.id)),[l]),W=(0,u.useMemo)(()=>{let e=new Set;for(let t of F){let n=_(t.manifest);n&&e.add(n.category??`general`)}return[`all`,...[`general`,`coding`,`reasoning`,`vision`,`embedding`].filter(t=>e.has(t))]},[F]),G=(0,u.useMemo)(()=>{if(!k)return new Set;let e=k.usableBytes,t=new Map;for(let n of F){let i=_(n.manifest);if(!i||r(i)||i.supportsTools===!1||i.approxSizeBytes*f>e)continue;let a=i.category??`general`;if(N!==`all`&&a!==N)continue;let o=t.get(a);(!o||i.approxSizeBytes>o.size)&&t.set(a,{tag:i.ollama.tag,size:i.approxSizeBytes})}return new Set([...t.values()].map(e=>e.tag))},[F,k,N]);return(0,d.jsxs)(`div`,{className:`ollama-model-manager`,children:[C.size>0&&(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Downloading…`}),(0,d.jsx)(`div`,{className:`ollama-pull-list`,children:Array.from(C.values()).map(e=>(0,d.jsx)(S,{pull:e,onCancel:()=>V(e.name)},e.name))})]}),(l.length>0||v)&&(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:n?`Models on this device`:`Local models`}),v&&(0,d.jsx)(`p`,{className:`error`,children:v}),l.length>0&&(0,d.jsxs)(`table`,{className:`ollama-model-table`,children:[(0,d.jsx)(`thead`,{children:(0,d.jsxs)(`tr`,{children:[(0,d.jsx)(`th`,{children:`Name`}),(0,d.jsx)(`th`,{children:`Size`}),(0,d.jsx)(`th`,{title:`Effective per-turn context size Gezel sends to Ollama`,children:`Context size`}),(0,d.jsx)(`th`,{children:`Tools`}),(0,d.jsx)(`th`,{})]})}),(0,d.jsx)(`tbody`,{children:l.map(e=>(0,d.jsxs)(`tr`,{children:[(0,d.jsx)(`td`,{children:(0,d.jsx)(`code`,{children:e.id})}),(0,d.jsx)(`td`,{children:e.parameterSize??`—`}),(0,d.jsx)(`td`,{children:a(e.contextWindow)}),(0,d.jsx)(`td`,{children:e.supportsTools?(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--ok`,children:`✓`}):(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--warn`,children:`no`})}),(0,d.jsx)(`td`,{children:(0,d.jsx)(`button`,{type:`button`,className:`gz-link-button`,onClick:()=>O(e.id),children:`Delete`})})]},e.id))})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section ollama-section--flat ollama-section--download`,children:[(0,d.jsx)(`h4`,{children:`Download a model`}),(0,d.jsx)(y,{memory:k,showAll:j,setShowAll:M}),(0,d.jsx)(x,{active:N,onChange:P,available:W}),(0,d.jsx)(s,{kind:`chat-model`,emptyMessage:`No model recommendations in the catalog yet.`,onItemsLoaded:I,tagTooltips:p,filter:e=>{let t=_(e.manifest);return!(!t||!j&&r(t)||N!==`all`&&(t.category??`general`)!==N||!j&&k&&t.approxSizeBytes*f>k.usableBytes)},action:t=>{let n=_(t.manifest);if(!n)return null;let r=n.ollama.tag,i=U.has(r),a=C.get(r),o=!!a,s=a&&a.total>0?Math.min(100,Math.round(a.completed/a.total*100)):null,l=k?n.approxSizeBytes*f>k.usableBytes:!1,u=G.has(r);return(0,d.jsxs)(`div`,{className:`catalog-ollama-action`,children:[(0,d.jsxs)(`div`,{className:`catalog-ollama-meta`,children:[(0,d.jsxs)(`div`,{className:`catalog-ollama-specs muted small`,children:[(0,d.jsx)(`code`,{children:r}),(0,d.jsx)(`span`,{children:`·`}),(0,d.jsx)(`span`,{children:n.parameterSize}),(0,d.jsx)(`span`,{children:`·`}),(0,d.jsx)(`span`,{children:h(n.approxSizeBytes)}),g(n.releasedAt)&&(0,d.jsxs)(d.Fragment,{children:[(0,d.jsx)(`span`,{children:`·`}),(0,d.jsx)(`span`,{children:g(n.releasedAt)})]})]}),(0,d.jsxs)(`div`,{className:`catalog-ollama-pills`,children:[(0,d.jsx)(c,{manifest:n,allowOllamaLink:!0}),u&&(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--ok`,title:`Largest model in this category that fits your device's memory budget — a good default.`,children:`★ recommended`}),l&&(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--warn`,title:`This model is larger than the memory Gezel estimates your device can dedicate to inference. It may run very slowly or fail to load.`,children:`may not fit`})]})]}),(0,d.jsx)(`button`,{type:`button`,disabled:i||o||!e,onClick:()=>void B(r),children:i?`On device`:o?s===null?`Downloading…`:`Downloading… ${s}%`:`Download`})]})}}),(0,d.jsxs)(`div`,{className:`new-row`,style:{marginTop:`0.5rem`},children:[(0,d.jsx)(`input`,{placeholder:`Or download by name: e.g. qwen2.5-coder:14b`,value:T,onChange:e=>E(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,disabled:!T.trim()||C.has(T.trim())||!e,onClick:()=>{let e=T.trim();e&&(B(e),E(``))},children:`Download`})]})]}),(0,d.jsx)(o,{open:D!==null,title:`Delete model?`,message:D?`"${D}" will be removed from your device. This frees disk space, but you'll need to download it again to use it.`:``,confirmLabel:`Delete`,danger:!0,onCancel:()=>O(null),onConfirm:H})]})}function y({memory:e,showAll:t,setShowAll:n}){let r=e?m(e.usableBytes):null;return(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[r?`Models larger than your ~${r} budget, and retired models, are hidden by default. `:`Retired models are hidden by default. `,(0,d.jsx)(`button`,{type:`button`,className:`gz-link-button`,onClick:()=>n(!t),children:t?r?`Hide retired and oversized models`:`Hide retired models`:`Show all models`})]})}var b={all:`All`,general:`General`,coding:`Coding`,reasoning:`Reasoning`,vision:`Vision`,embedding:`Embedding`};function x({active:e,onChange:t,available:n}){return n.length<=1?null:(0,d.jsx)(`div`,{className:`ollama-category-tabs`,role:`tablist`,style:{display:`flex`,flexWrap:`wrap`,gap:`0.4rem`,margin:`0.5rem 0 0.75rem`},children:n.map(n=>(0,d.jsx)(`button`,{type:`button`,role:`tab`,"aria-selected":e===n,className:`provider-pill${e===n?` provider-pill-active`:``}`,onClick:()=>t(n),children:b[n]},n))})}function S({pull:e,onCancel:t}){let n=e.total>0,r=n?Math.min(100,Math.round(e.completed/e.total*100)):0,i=e.error?e.error:n?`Downloading… (${r}%)`:`${C(e.status)}…`;return(0,d.jsxs)(`div`,{className:`ollama-pull${e.error?` ollama-pull-error`:``}`,children:[(0,d.jsxs)(`div`,{className:`ollama-pull-head`,children:[(0,d.jsx)(`code`,{children:e.name}),(0,d.jsx)(`span`,{className:`muted small`,children:i}),(0,d.jsx)(`button`,{type:`button`,className:`gz-link-button`,onClick:t,children:`Cancel`})]}),n?(0,d.jsxs)(`div`,{className:`ollama-pull-bar`,children:[(0,d.jsx)(`div`,{className:`ollama-pull-bar-fill`,style:{width:`${r}%`}}),(0,d.jsxs)(`span`,{className:`ollama-pull-bar-label`,children:[r,`%`]})]}):(0,d.jsx)(`div`,{className:`ollama-pull-bar ollama-pull-bar-indeterminate`,children:(0,d.jsx)(`div`,{className:`ollama-pull-bar-fill`})})]})}function C(e){return e.length===0?e:e.charAt(0).toUpperCase()+e.slice(1)}function w({config:e,onConfigChanged:t}){let[n,r]=(0,u.useState)(e?.ollamaBaseUrl??``),[a,o]=(0,u.useState)({kind:`idle`}),[s,c]=(0,u.useState)(e?.ollamaNumCtx?String(e.ollamaNumCtx):``),[f,p]=(0,u.useState)(e?.ollamaStreamingIdleSec?String(e.ollamaStreamingIdleSec):``),[m,h]=(0,u.useState)(e?.ollamaPreFirstByteIdleSec?String(e.ollamaPreFirstByteIdleSec):``),[g,_]=(0,u.useState)(e?.ollamaTurnTimeoutMin?String(e.ollamaTurnTimeoutMin):``),[y,b]=(0,u.useState)(e?.ollamaNumPredict?String(e.ollamaNumPredict):``);(0,u.useEffect)(()=>{r(e?.ollamaBaseUrl??``)},[e?.ollamaBaseUrl]),(0,u.useEffect)(()=>{c(e?.ollamaNumCtx?String(e.ollamaNumCtx):``)},[e?.ollamaNumCtx]),(0,u.useEffect)(()=>{p(e?.ollamaStreamingIdleSec?String(e.ollamaStreamingIdleSec):``)},[e?.ollamaStreamingIdleSec]),(0,u.useEffect)(()=>{h(e?.ollamaPreFirstByteIdleSec?String(e.ollamaPreFirstByteIdleSec):``)},[e?.ollamaPreFirstByteIdleSec]),(0,u.useEffect)(()=>{_(e?.ollamaTurnTimeoutMin?String(e.ollamaTurnTimeoutMin):``)},[e?.ollamaTurnTimeoutMin]),(0,u.useEffect)(()=>{b(e?.ollamaNumPredict?String(e.ollamaNumPredict):``)},[e?.ollamaNumPredict]);let x=(0,u.useCallback)(async()=>{o({kind:`probing`});try{let t=await i.ollamaStatus();if(t.ok){o({kind:`ok`,baseUrl:t.baseUrl,modelCount:t.modelCount});return}if(e?.autoStartOllama!==!1&&(await i.ollamaStart()).started){let e=await i.ollamaStatus();if(e.ok){o({kind:`ok`,baseUrl:e.baseUrl,modelCount:e.modelCount});return}}o({kind:`fail`,baseUrl:t.baseUrl,error:t.error})}catch(e){o({kind:`fail`,error:e.message})}},[e?.autoStartOllama]),S=(0,u.useCallback)(async()=>{o({kind:`probing`});try{let e=await i.ollamaStart();e.started?await x():o({kind:`fail`,error:e.error??`Ollama did not start`})}catch(e){o({kind:`fail`,error:e.message})}},[x]),C=(0,u.useCallback)(async e=>{t(await i.updateConfig({autoStartOllama:e}))},[t]);(0,u.useEffect)(()=>{x()},[x,e?.ollamaBaseUrl]);let w=(0,u.useCallback)(async()=>{let e=n.trim();t(await i.updateConfig({ollamaBaseUrl:e||void 0})),await x()},[n,t,x]),E=(0,u.useCallback)(async()=>{let e=s.trim(),n=e?Number.parseInt(e,10):void 0;e&&(!Number.isFinite(n)||(n??0)<=0)||t(await i.updateConfig({ollamaNumCtx:n}))},[s,t]),D=(0,u.useCallback)(async()=>{let e=y.trim(),n=e?Number.parseInt(e,10):void 0;e&&(!Number.isFinite(n)||(n??0)<=0)||t(await i.updateConfig({ollamaNumPredict:n}))},[y,t]),O=(0,u.useCallback)(async(e,n)=>{let r=n.trim(),a=r?Number.parseInt(r,10):void 0;r&&(!Number.isFinite(a)||(a??0)<=0)||t(await i.updateConfig({[e]:a}))},[t]);return(0,d.jsxs)(`div`,{className:`ollama-settings`,children:[(0,d.jsx)(`h3`,{children:`Ollama (local models)`}),(0,d.jsxs)(`p`,{className:`muted`,style:{marginTop:0},children:[`Run models locally — no credentials, no traffic leaving the machine. Install`,` `,(0,d.jsx)(`code`,{children:`ollama serve`}),` and point gezel at it below.`]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Server`}),(0,d.jsxs)(`div`,{className:`new-row`,children:[(0,d.jsx)(`input`,{placeholder:`http://localhost:11434`,value:n,onChange:e=>r(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void w(),disabled:n.trim()===(e?.ollamaBaseUrl??``),children:`Save`}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void x(),children:a.kind===`probing`?`Testing…`:`Test`}),a.kind===`fail`&&(0,d.jsx)(`button`,{type:`button`,onClick:()=>void S(),children:`Start Ollama`})]}),(0,d.jsx)(T,{status:a}),(0,d.jsxs)(`label`,{style:{display:`flex`,alignItems:`center`,gap:`0.5rem`,marginTop:`0.5rem`,fontSize:`0.85rem`},children:[(0,d.jsx)(`input`,{type:`checkbox`,checked:e?.autoStartOllama!==!1,onChange:e=>void C(e.target.checked)}),(0,d.jsx)(`span`,{children:`Automatically start Ollama when it's installed but not running.`})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Context window`}),(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[`How much of the conversation the model can keep in mind at once. Ollama's own default is small and silently forgets older messages; Gezel picks a sensible size for each model. Set a value here to force one for every session (Ollama's `,(0,d.jsx)(`code`,{children:`num_ctx`}),`).`]}),(0,d.jsxs)(`div`,{className:`new-row`,children:[(0,d.jsx)(`input`,{type:`number`,min:1,placeholder:`e.g. 8192`,value:s,onChange:e=>c(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void E(),disabled:s.trim()===(e?.ollamaNumCtx?String(e.ollamaNumCtx):``),children:`Save`})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Response budget`}),(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[`How much the model may write in a single reply. Ollama's own limit is so low that answers can get cut off before a word appears — Gezel raises it to a comfortable length. Raise it further if long replies get cut short (Ollama's `,(0,d.jsx)(`code`,{children:`num_predict`}),`).`]}),(0,d.jsxs)(`div`,{className:`new-row`,children:[(0,d.jsx)(`input`,{type:`number`,min:1,placeholder:`e.g. 4096`,value:y,onChange:e=>b(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void D(),disabled:y.trim()===(e?.ollamaNumPredict?String(e.ollamaNumPredict):``),children:`Save`})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Timeouts`}),(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[`Local models on consumer hardware can take minutes for one turn — these caps decide when we give up. Two of them watch for `,(0,d.jsx)(`em`,{children:`silence`}),` (reset on activity); the third is a hard ceiling that ticks down regardless. Leave blank to use the defaults.`]}),(0,d.jsx)(l,{label:`Pre-first-byte cap`,unit:`seconds`,help:`Cold-start load + prompt prefill before the first visible token. Default 300s. Bump for big models with heavy system prompts or reasoning models that think silently before output.`,value:m,onChange:h,configValue:e?.ollamaPreFirstByteIdleSec,onSave:()=>void O(`ollamaPreFirstByteIdleSec`,m)}),(0,d.jsx)(l,{label:`Mid-stream silence cap`,unit:`seconds`,help:`How long the model can go silent mid-reply before we abort. Default 300s. Bump for reasoning models that pause between visible bursts. The 'wire pulse' dots in the chat tell you whether silence is real or just framing chunks.`,value:f,onChange:p,configValue:e?.ollamaStreamingIdleSec,onSave:()=>void O(`ollamaStreamingIdleSec`,f)}),(0,d.jsx)(l,{label:`Hard turn timeout`,unit:`minutes`,help:`Total wall-clock cap from when the model takes the slot to when it's done. Default 30m. Fires regardless of whether bytes are flowing — the backstop for runaway tool loops.`,value:g,onChange:_,configValue:e?.ollamaTurnTimeoutMin,onSave:()=>void O(`ollamaTurnTimeoutMin`,g)})]}),(0,d.jsx)(v,{enabled:a.kind===`ok`,onModelsChanged:()=>void x()})]})}function T({status:e}){return e.kind===`idle`||e.kind===`probing`?(0,d.jsx)(`p`,{className:`muted small`,children:`Checking…`}):e.kind===`ok`?(0,d.jsxs)(`p`,{className:`muted small`,children:[`✓ Reachable at `,(0,d.jsx)(`code`,{children:e.baseUrl}),` — `,e.modelCount,` model`,e.modelCount===1?``:`s`,` available locally.`]}):(0,d.jsxs)(`p`,{className:`error small`,title:e.error,children:[`Ollama isn't running at `,(0,d.jsx)(`code`,{children:e.baseUrl??`the configured address`}),` — press Start Ollama above to launch it.`]})}export{w as OllamaSettings};
|
|
1
|
+
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{xt as r}from"./dist-CE5CbmDb.js";import{t as i}from"./api-CmrgM5Rf.js";import{t as a}from"./model-context-DBqdK0PS.js";import{t as o}from"./ConfirmDialog-Dt1ed4Fh.js";import{t as s}from"./CatalogBrowser-DYXUZQ_t.js";import{t as c}from"./LicenseButton-D3VmcVG1.js";import{t as l}from"./TimeoutRow-B9SZiKH6.js";var u=e(t(),1),d=n(),f=1.2,p={"mix of experts":`Only a fraction of the model's parameters run per token, so it's faster than a dense model of the same nominal size. Gezels generally benefit from MoE models.`,moe:`Only a fraction of the model's parameters run per token, so it's faster than a dense model of the same nominal size. Gezels generally benefit from MoE models.`,thinking:`The model reasons through the problem step-by-step before answering. Slower, but generally more accurate on hard questions.`,agentic:`Tuned for multi-step agent workflows — tool use, planning, and iterating toward a goal.`,vision:`Can accept images alongside text.`,tools:`Supports function/tool calling via the API.`,multimodal:`Handles multiple input types (text + images).`,large:`Heavy model — needs a lot of memory and runs more slowly.`,small:`Compact model — runs quickly on modest hardware.`};function m(e){return e>=1024**3?`${(e/1024**3).toFixed(1)} GB`:e>=1024**2?`${(e/1024**2).toFixed(0)} MB`:e>=1024?`${(e/1024).toFixed(0)} KB`:`${e} B`}function h(e){return e>=1024**3?`~${(e/1024**3).toFixed(1)} GB`:e>=1024**2?`~${(e/1024**2).toFixed(0)} MB`:e>=1024?`~${(e/1024).toFixed(0)} KB`:`~${e} B`}function g(e){if(!e)return null;let t=new Date(e);return Number.isNaN(t.getTime())?null:t.toLocaleDateString(void 0,{year:`numeric`,month:`short`})}function _(e){return e.kind!==`chat-model`||!e.ollama?null:e}function v({enabled:e,onModelsChanged:t,compact:n=!1}){let[l,m]=(0,u.useState)([]),[v,b]=(0,u.useState)(null),[C,w]=(0,u.useState)(new Map),[T,E]=(0,u.useState)(``),[D,O]=(0,u.useState)(null),[k,A]=(0,u.useState)(null),[j,M]=(0,u.useState)(!1),[N,P]=(0,u.useState)(`all`),[F,I]=(0,u.useState)([]),L=(0,u.useRef)(C);L.current=C;let R=(0,u.useRef)(null);(0,u.useEffect)(()=>{let e=!1;return i.getMemoryProfile().then(t=>{e||A(t)}).catch(()=>{}),()=>{e=!0}},[]);let z=(0,u.useCallback)(async()=>{try{let e=await i.listProviderModels(`ollama`);m(e.models),b(null)}catch(e){b(e.message),m([])}},[]);(0,u.useEffect)(()=>{e&&z()},[e,z]),(0,u.useEffect)(()=>{if(!e)return;let t=!1;return(async()=>{try{let[{pulls:e},{models:n}]=await Promise.all([i.listPendingOllamaPulls(),i.listProviderModels(`ollama`)]);if(t)return;let r=new Set(n.map(e=>e.id));for(let t of e){if(r.has(t.name)){i.clearPendingOllamaPull(t.name).catch(()=>{});continue}L.current.has(t.name)||R.current?.(t.name)}}catch{}})(),()=>{t=!0}},[e]);let B=(0,u.useCallback)(async e=>{if(L.current.has(e))return;let n=new AbortController,r={name:e,status:`queued`,completed:0,total:0,controller:n};w(t=>new Map(t).set(e,r));try{await i.pullOllamaModel(e,t=>{if(t.type===`progress`){let n=t.chunk;w(t=>{let r=new Map(t),i=r.get(e);return i?(r.set(e,{...i,status:n.status,completed:n.completed??i.completed,total:n.total??i.total}),r):t})}else t.type===`error`&&w(n=>{let r=new Map(n),i=r.get(e);return i&&r.set(e,{...i,error:t.error}),r})},n.signal),setTimeout(()=>{w(t=>{let n=new Map(t);return n.delete(e),n}),z(),t?.(),(async()=>{try{let t=await i.getConfig();t.defaultModel?.ollama||await i.updateConfig({defaultModel:{...t.defaultModel,ollama:e}})}catch{}})()},900)}catch(t){if(n.signal.aborted){w(t=>{let n=new Map(t);return n.delete(e),n});return}w(n=>{let r=new Map(n),i=r.get(e);return i&&r.set(e,{...i,error:t.message}),r})}},[z,t]);R.current=B;let V=(0,u.useCallback)(e=>{L.current.get(e)?.controller.abort(),i.clearPendingOllamaPull(e).catch(()=>{})},[]),H=(0,u.useCallback)(async()=>{if(D)try{await i.deleteOllamaModel(D),await z(),t?.()}catch(e){b(e.message)}finally{O(null)}},[D,z,t]),U=(0,u.useMemo)(()=>new Set(l.map(e=>e.id)),[l]),W=(0,u.useMemo)(()=>{let e=new Set;for(let t of F){let n=_(t.manifest);n&&e.add(n.category??`general`)}return[`all`,...[`general`,`coding`,`reasoning`,`vision`,`embedding`].filter(t=>e.has(t))]},[F]),G=(0,u.useMemo)(()=>{if(!k)return new Set;let e=k.usableBytes,t=new Map;for(let n of F){let i=_(n.manifest);if(!i||r(i)||i.supportsTools===!1||i.approxSizeBytes*f>e)continue;let a=i.category??`general`;if(N!==`all`&&a!==N)continue;let o=t.get(a);(!o||i.approxSizeBytes>o.size)&&t.set(a,{tag:i.ollama.tag,size:i.approxSizeBytes})}return new Set([...t.values()].map(e=>e.tag))},[F,k,N]);return(0,d.jsxs)(`div`,{className:`ollama-model-manager`,children:[C.size>0&&(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Downloading…`}),(0,d.jsx)(`div`,{className:`ollama-pull-list`,children:Array.from(C.values()).map(e=>(0,d.jsx)(S,{pull:e,onCancel:()=>V(e.name)},e.name))})]}),(l.length>0||v)&&(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:n?`Models on this device`:`Local models`}),v&&(0,d.jsx)(`p`,{className:`error`,children:v}),l.length>0&&(0,d.jsxs)(`table`,{className:`ollama-model-table`,children:[(0,d.jsx)(`thead`,{children:(0,d.jsxs)(`tr`,{children:[(0,d.jsx)(`th`,{children:`Name`}),(0,d.jsx)(`th`,{children:`Size`}),(0,d.jsx)(`th`,{title:`Effective per-turn context size Gezel sends to Ollama`,children:`Context size`}),(0,d.jsx)(`th`,{children:`Tools`}),(0,d.jsx)(`th`,{})]})}),(0,d.jsx)(`tbody`,{children:l.map(e=>(0,d.jsxs)(`tr`,{children:[(0,d.jsx)(`td`,{children:(0,d.jsx)(`code`,{children:e.id})}),(0,d.jsx)(`td`,{children:e.parameterSize??`—`}),(0,d.jsx)(`td`,{children:a(e.contextWindow)}),(0,d.jsx)(`td`,{children:e.supportsTools?(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--ok`,children:`✓`}):(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--warn`,children:`no`})}),(0,d.jsx)(`td`,{children:(0,d.jsx)(`button`,{type:`button`,className:`gz-link-button`,onClick:()=>O(e.id),children:`Delete`})})]},e.id))})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section ollama-section--flat ollama-section--download`,children:[(0,d.jsx)(`h4`,{children:`Download a model`}),(0,d.jsx)(y,{memory:k,showAll:j,setShowAll:M}),(0,d.jsx)(x,{active:N,onChange:P,available:W}),(0,d.jsx)(s,{kind:`chat-model`,emptyMessage:`No model recommendations in the catalog yet.`,onItemsLoaded:I,tagTooltips:p,filter:e=>{let t=_(e.manifest);return!(!t||!j&&r(t)||N!==`all`&&(t.category??`general`)!==N||!j&&k&&t.approxSizeBytes*f>k.usableBytes)},action:t=>{let n=_(t.manifest);if(!n)return null;let r=n.ollama.tag,i=U.has(r),a=C.get(r),o=!!a,s=a&&a.total>0?Math.min(100,Math.round(a.completed/a.total*100)):null,l=k?n.approxSizeBytes*f>k.usableBytes:!1,u=G.has(r);return(0,d.jsxs)(`div`,{className:`catalog-ollama-action`,children:[(0,d.jsxs)(`div`,{className:`catalog-ollama-meta`,children:[(0,d.jsxs)(`div`,{className:`catalog-ollama-specs muted small`,children:[(0,d.jsx)(`code`,{children:r}),(0,d.jsx)(`span`,{children:`·`}),(0,d.jsx)(`span`,{children:n.parameterSize}),(0,d.jsx)(`span`,{children:`·`}),(0,d.jsx)(`span`,{children:h(n.approxSizeBytes)}),g(n.releasedAt)&&(0,d.jsxs)(d.Fragment,{children:[(0,d.jsx)(`span`,{children:`·`}),(0,d.jsx)(`span`,{children:g(n.releasedAt)})]})]}),(0,d.jsxs)(`div`,{className:`catalog-ollama-pills`,children:[(0,d.jsx)(c,{manifest:n,allowOllamaLink:!0}),u&&(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--ok`,title:`Largest model in this category that fits your device's memory budget — a good default.`,children:`★ recommended`}),l&&(0,d.jsx)(`span`,{className:`gz-status-pill gz-status-pill--warn`,title:`This model is larger than the memory Gezel estimates your device can dedicate to inference. It may run very slowly or fail to load.`,children:`may not fit`})]})]}),(0,d.jsx)(`button`,{type:`button`,disabled:i||o||!e,onClick:()=>void B(r),children:i?`On device`:o?s===null?`Downloading…`:`Downloading… ${s}%`:`Download`})]})}}),(0,d.jsxs)(`div`,{className:`new-row`,style:{marginTop:`0.5rem`},children:[(0,d.jsx)(`input`,{placeholder:`Or download by name: e.g. qwen2.5-coder:14b`,value:T,onChange:e=>E(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,disabled:!T.trim()||C.has(T.trim())||!e,onClick:()=>{let e=T.trim();e&&(B(e),E(``))},children:`Download`})]})]}),(0,d.jsx)(o,{open:D!==null,title:`Delete model?`,message:D?`"${D}" will be removed from your device. This frees disk space, but you'll need to download it again to use it.`:``,confirmLabel:`Delete`,danger:!0,onCancel:()=>O(null),onConfirm:H})]})}function y({memory:e,showAll:t,setShowAll:n}){let r=e?m(e.usableBytes):null;return(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[r?`Models larger than your ~${r} budget, and retired models, are hidden by default. `:`Retired models are hidden by default. `,(0,d.jsx)(`button`,{type:`button`,className:`gz-link-button`,onClick:()=>n(!t),children:t?r?`Hide retired and oversized models`:`Hide retired models`:`Show all models`})]})}var b={all:`All`,general:`General`,coding:`Coding`,reasoning:`Reasoning`,vision:`Vision`,embedding:`Embedding`};function x({active:e,onChange:t,available:n}){return n.length<=1?null:(0,d.jsx)(`div`,{className:`ollama-category-tabs`,role:`tablist`,style:{display:`flex`,flexWrap:`wrap`,gap:`0.4rem`,margin:`0.5rem 0 0.75rem`},children:n.map(n=>(0,d.jsx)(`button`,{type:`button`,role:`tab`,"aria-selected":e===n,className:`provider-pill${e===n?` provider-pill-active`:``}`,onClick:()=>t(n),children:b[n]},n))})}function S({pull:e,onCancel:t}){let n=e.total>0,r=n?Math.min(100,Math.round(e.completed/e.total*100)):0,i=e.error?e.error:n?`Downloading… (${r}%)`:`${C(e.status)}…`;return(0,d.jsxs)(`div`,{className:`ollama-pull${e.error?` ollama-pull-error`:``}`,children:[(0,d.jsxs)(`div`,{className:`ollama-pull-head`,children:[(0,d.jsx)(`code`,{children:e.name}),(0,d.jsx)(`span`,{className:`muted small`,children:i}),(0,d.jsx)(`button`,{type:`button`,className:`gz-link-button`,onClick:t,children:`Cancel`})]}),n?(0,d.jsxs)(`div`,{className:`ollama-pull-bar`,children:[(0,d.jsx)(`div`,{className:`ollama-pull-bar-fill`,style:{width:`${r}%`}}),(0,d.jsxs)(`span`,{className:`ollama-pull-bar-label`,children:[r,`%`]})]}):(0,d.jsx)(`div`,{className:`ollama-pull-bar ollama-pull-bar-indeterminate`,children:(0,d.jsx)(`div`,{className:`ollama-pull-bar-fill`})})]})}function C(e){return e.length===0?e:e.charAt(0).toUpperCase()+e.slice(1)}function w({config:e,onConfigChanged:t}){let[n,r]=(0,u.useState)(e?.ollamaBaseUrl??``),[a,o]=(0,u.useState)({kind:`idle`}),[s,c]=(0,u.useState)(e?.ollamaNumCtx?String(e.ollamaNumCtx):``),[f,p]=(0,u.useState)(e?.ollamaStreamingIdleSec?String(e.ollamaStreamingIdleSec):``),[m,h]=(0,u.useState)(e?.ollamaPreFirstByteIdleSec?String(e.ollamaPreFirstByteIdleSec):``),[g,_]=(0,u.useState)(e?.ollamaTurnTimeoutMin?String(e.ollamaTurnTimeoutMin):``),[y,b]=(0,u.useState)(e?.ollamaNumPredict?String(e.ollamaNumPredict):``);(0,u.useEffect)(()=>{r(e?.ollamaBaseUrl??``)},[e?.ollamaBaseUrl]),(0,u.useEffect)(()=>{c(e?.ollamaNumCtx?String(e.ollamaNumCtx):``)},[e?.ollamaNumCtx]),(0,u.useEffect)(()=>{p(e?.ollamaStreamingIdleSec?String(e.ollamaStreamingIdleSec):``)},[e?.ollamaStreamingIdleSec]),(0,u.useEffect)(()=>{h(e?.ollamaPreFirstByteIdleSec?String(e.ollamaPreFirstByteIdleSec):``)},[e?.ollamaPreFirstByteIdleSec]),(0,u.useEffect)(()=>{_(e?.ollamaTurnTimeoutMin?String(e.ollamaTurnTimeoutMin):``)},[e?.ollamaTurnTimeoutMin]),(0,u.useEffect)(()=>{b(e?.ollamaNumPredict?String(e.ollamaNumPredict):``)},[e?.ollamaNumPredict]);let x=(0,u.useCallback)(async()=>{o({kind:`probing`});try{let t=await i.ollamaStatus();if(t.ok){o({kind:`ok`,baseUrl:t.baseUrl,modelCount:t.modelCount});return}if(e?.autoStartOllama!==!1&&(await i.ollamaStart()).started){let e=await i.ollamaStatus();if(e.ok){o({kind:`ok`,baseUrl:e.baseUrl,modelCount:e.modelCount});return}}o({kind:`fail`,baseUrl:t.baseUrl,error:t.error})}catch(e){o({kind:`fail`,error:e.message})}},[e?.autoStartOllama]),S=(0,u.useCallback)(async()=>{o({kind:`probing`});try{let e=await i.ollamaStart();e.started?await x():o({kind:`fail`,error:e.error??`Ollama did not start`})}catch(e){o({kind:`fail`,error:e.message})}},[x]),C=(0,u.useCallback)(async e=>{t(await i.updateConfig({autoStartOllama:e}))},[t]);(0,u.useEffect)(()=>{x()},[x,e?.ollamaBaseUrl]);let w=(0,u.useCallback)(async()=>{let e=n.trim();t(await i.updateConfig({ollamaBaseUrl:e||void 0})),await x()},[n,t,x]),E=(0,u.useCallback)(async()=>{let e=s.trim(),n=e?Number.parseInt(e,10):void 0;e&&(!Number.isFinite(n)||(n??0)<=0)||t(await i.updateConfig({ollamaNumCtx:n}))},[s,t]),D=(0,u.useCallback)(async()=>{let e=y.trim(),n=e?Number.parseInt(e,10):void 0;e&&(!Number.isFinite(n)||(n??0)<=0)||t(await i.updateConfig({ollamaNumPredict:n}))},[y,t]),O=(0,u.useCallback)(async(e,n)=>{let r=n.trim(),a=r?Number.parseInt(r,10):void 0;r&&(!Number.isFinite(a)||(a??0)<=0)||t(await i.updateConfig({[e]:a}))},[t]);return(0,d.jsxs)(`div`,{className:`ollama-settings`,children:[(0,d.jsx)(`h3`,{children:`Ollama (local models)`}),(0,d.jsxs)(`p`,{className:`muted`,style:{marginTop:0},children:[`Run models locally — no credentials, no traffic leaving the machine. Install`,` `,(0,d.jsx)(`code`,{children:`ollama serve`}),` and point gezel at it below.`]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Server`}),(0,d.jsxs)(`div`,{className:`new-row`,children:[(0,d.jsx)(`input`,{placeholder:`http://localhost:11434`,value:n,onChange:e=>r(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void w(),disabled:n.trim()===(e?.ollamaBaseUrl??``),children:`Save`}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void x(),children:a.kind===`probing`?`Testing…`:`Test`}),a.kind===`fail`&&(0,d.jsx)(`button`,{type:`button`,onClick:()=>void S(),children:`Start Ollama`})]}),(0,d.jsx)(T,{status:a}),(0,d.jsxs)(`label`,{style:{display:`flex`,alignItems:`center`,gap:`0.5rem`,marginTop:`0.5rem`,fontSize:`0.85rem`},children:[(0,d.jsx)(`input`,{type:`checkbox`,checked:e?.autoStartOllama!==!1,onChange:e=>void C(e.target.checked)}),(0,d.jsx)(`span`,{children:`Automatically start Ollama when it's installed but not running.`})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Context window`}),(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[`How much of the conversation the model can keep in mind at once. Ollama's own default is small and silently forgets older messages; Gezel picks a sensible size for each model. Set a value here to force one for every session (Ollama's `,(0,d.jsx)(`code`,{children:`num_ctx`}),`).`]}),(0,d.jsxs)(`div`,{className:`new-row`,children:[(0,d.jsx)(`input`,{type:`number`,min:1,placeholder:`e.g. 8192`,value:s,onChange:e=>c(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void E(),disabled:s.trim()===(e?.ollamaNumCtx?String(e.ollamaNumCtx):``),children:`Save`})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Response budget`}),(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[`How much the model may write in a single reply. Ollama's own limit is so low that answers can get cut off before a word appears — Gezel raises it to a comfortable length. Raise it further if long replies get cut short (Ollama's `,(0,d.jsx)(`code`,{children:`num_predict`}),`).`]}),(0,d.jsxs)(`div`,{className:`new-row`,children:[(0,d.jsx)(`input`,{type:`number`,min:1,placeholder:`e.g. 4096`,value:y,onChange:e=>b(e.target.value),style:{flex:1}}),(0,d.jsx)(`button`,{type:`button`,onClick:()=>void D(),disabled:y.trim()===(e?.ollamaNumPredict?String(e.ollamaNumPredict):``),children:`Save`})]})]}),(0,d.jsxs)(`div`,{className:`ollama-section`,children:[(0,d.jsx)(`h4`,{children:`Timeouts`}),(0,d.jsxs)(`p`,{className:`muted small`,style:{marginTop:0},children:[`Local models on consumer hardware can take minutes for one turn — these caps decide when we give up. Two of them watch for `,(0,d.jsx)(`em`,{children:`silence`}),` (reset on activity); the third is a hard ceiling that ticks down regardless. Leave blank to use the defaults.`]}),(0,d.jsx)(l,{label:`Pre-first-byte cap`,unit:`seconds`,help:`Cold-start load + prompt prefill before the first visible token. Default 300s. Bump for big models with heavy system prompts or reasoning models that think silently before output.`,value:m,onChange:h,configValue:e?.ollamaPreFirstByteIdleSec,onSave:()=>void O(`ollamaPreFirstByteIdleSec`,m)}),(0,d.jsx)(l,{label:`Mid-stream silence cap`,unit:`seconds`,help:`How long the model can go silent mid-reply before we abort. Default 300s. Bump for reasoning models that pause between visible bursts. The 'wire pulse' dots in the chat tell you whether silence is real or just framing chunks.`,value:f,onChange:p,configValue:e?.ollamaStreamingIdleSec,onSave:()=>void O(`ollamaStreamingIdleSec`,f)}),(0,d.jsx)(l,{label:`Hard turn timeout`,unit:`minutes`,help:`Total wall-clock cap from when the model takes the slot to when it's done. Default 30m. Fires regardless of whether bytes are flowing — the backstop for runaway tool loops.`,value:g,onChange:_,configValue:e?.ollamaTurnTimeoutMin,onSave:()=>void O(`ollamaTurnTimeoutMin`,g)})]}),(0,d.jsx)(v,{enabled:a.kind===`ok`,onModelsChanged:()=>void x()})]})}function T({status:e}){return e.kind===`idle`||e.kind===`probing`?(0,d.jsx)(`p`,{className:`muted small`,children:`Checking…`}):e.kind===`ok`?(0,d.jsxs)(`p`,{className:`muted small`,children:[`✓ Reachable at `,(0,d.jsx)(`code`,{children:e.baseUrl}),` — `,e.modelCount,` model`,e.modelCount===1?``:`s`,` available locally.`]}):(0,d.jsxs)(`p`,{className:`error small`,title:e.error,children:[`Ollama isn't running at `,(0,d.jsx)(`code`,{children:e.baseUrl??`the configured address`}),` — press Start Ollama above to launch it.`]})}export{w as OllamaSettings};
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["assets/TerminalCodeEditor-BkNQ6QoQ.js","assets/rolldown-runtime-aKtaBQYM.js","assets/jsx-runtime-CEpd2cAX.js","assets/preload-helper-Czpn1I53.js","assets/index-DivKnJyx.js","assets/react-dom-OL4w_gzs.js","assets/dist-CE5CbmDb.js","assets/dist-BMZhqfv7.js","assets/api-CmrgM5Rf.js","assets/primitives-CWrGZpPI.js","assets/Tabs-jE0Z5Tzd.js","assets/NewPathDialog-BhAZm9dp.js","assets/DropdownMenu-DlrvEmoV.js","assets/dist-Q59u9cBl.js","assets/relative-time-B2kBaekd.js","assets/FileTypeIcon-Cwzl1GkZ.js","assets/model-context-DBqdK0PS.js","assets/model-memory-copy-Ds9w1uJE.js","assets/StorageCleanupDialog-CDBjl8JQ.js","assets/poppetje-DvCJO36y.js","assets/safe-svg-image-NbuPaBIv.js","assets/ConfirmDialog-Dt1ed4Fh.js","assets/model-inventory-ykSm_IT5.js","assets/doc-BHcGsJZd.js","assets/chunk-X7BNDUNI-D14WIvlD.js","assets/chunk-BAOV476U-CEOFYt8X.js","assets/chunk-4VOD55SX-BFSSw0c8.js","assets/chunk-GAZKTT4R-w1SNypWQ.js","assets/chunk-CW24CH7I-BD0FIooX.js","assets/chunk-XRW6P7IF-BeQQgMVK.js","assets/chunk-7ZAAICW4-BsCpYJH6.js","assets/markdown-CLKH_zzl.js","assets/schemas-BvLZUsGm.js","assets/chunk-6ECMNUIP-D5AA6ozp.js","assets/inlineIconMarker-BQI2HLeD.js","assets/chunk-TT6ENR6T-BOA-qiwP.js","assets/chunk-DQRELU4S--U9FIVtY.js","assets/new-project-meta-5Y9Blozr.js","assets/chunk-ZSU5DJLX-CrjQf-vs.js","assets/index-DW6qHqhU.css"])))=>i.map(i=>d[i]);
|
|
2
|
+
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{W as r,Yt as i,lt as a,pt as o,wn as s}from"./dist-CE5CbmDb.js";import{t as c}from"./api-CmrgM5Rf.js";import{_ as l,g as u,o as d,v as f,y as p}from"./primitives-CWrGZpPI.js";import{l as m,n as h,o as g,r as _,s as v}from"./DropdownMenu-DlrvEmoV.js";import{n as y,t as b}from"./relative-time-B2kBaekd.js";import{t as x}from"./preload-helper-Czpn1I53.js";import{R as S,Wt as C,b as w,j as T,qt as E,r as D,vt as O,yt as k,z as A}from"./index-DivKnJyx.js";import{t as ee}from"./NewTaskDialog-BX24flMY.js";import{t as j}from"./useShowWorkInProgressFeatures-D6QOaTUT.js";import{i as te,n as M,r as N}from"./ChatTimelineView-Dn1TNyVn.js";import{a as P,i as F,t as ne}from"./SessionSwitcher-D0fSeeHO.js";import{n as re,t as I}from"./ProjectTimeline-Cqae2Z92.js";import{a as ie,c as ae,i as L,l as oe,o as se,s as ce,u as R}from"./chat-thread-memory-8MCtb17Q.js";import{r as le,t as z}from"./completion-data--97asQiQ.js";var B=e(t(),1),V=[/<function=([a-zA-Z_][a-zA-Z0-9_]*)/,/<invoke\s+name="([a-zA-Z_][a-zA-Z0-9_]*)/,/"(?:tool|name|function)"\s*:\s*"([a-zA-Z_][a-zA-Z0-9_]*)"/],H=/<function[=\s>]|<tool_call>|<invoke[\s>]|<parameter[=\s]|<\|tool_call\|>/i,ue=/<\/?think>|<\|?channel\|?>|(?:^|\n)(?:thought|analysis|commentary)\|/i,de=/!\[[^\]]*\]\(/,fe=/<think>(?![\s\S]*<\/think>)/i,U=/\{\s*"(?:tool|name|function)"\s*:\s*"[a-zA-Z_][a-zA-Z0-9_]*"/g;function pe(e){if(!e.includes(`{`))return e;let t=``,n=0;U.lastIndex=0;for(let r=U.exec(e);r;r=U.exec(e)){if(r.index<n)continue;let i=0,a=!1,o=!1,s=-1;for(let t=r.index;t<e.length;t++){let n=e[t];if(o)o=!1;else if(n===`\\`&&a)o=!0;else if(n===`"`)a=!a;else if(!a&&n===`{`)i++;else if(!a&&n===`}`&&(i--,i===0)){s=t+1;break}}t+=e.slice(n,r.index),n=s===-1?e.length:s,U.lastIndex=n}return t+e.slice(n)}function W(e){return e.replace(/!\[([^\]]*)\]\([^)]*\)/g,`$1`).replace(/@\[([^\]]+)\]\([^)]+\)/g,`@$1`).replace(/\[([^\]]+)\]\([^)]+\)/g,`$1`).replace(/[*_~`#>]+/g,``).replace(/\s+/g,` `).trim()}function me(e){let t=A(e);if(t.length>0)return{name:t[0].name,trusted:!0};for(let t of V){let n=e.match(t);if(n?.[1])return{name:n[1],trusted:!1}}return null}function G(e){if(!e)return``;let t=a(e);if(t)return t;let n=e.search(fe),r=n===-1?e:e.slice(0,n),i=W(pe(S(r,{hideMidStreamOpener:!0})));if(i)return i;let o=me(r);return o&&(o.trusted||O(o.name))?`${k(o.name)}…`:o||H.test(r)?`Using a tool…`:ue.test(e)?`Thinking…`:de.test(r)?`Shared an image`:``}function K(e,t){let n=(0,B.useRef)(new Map),r=(0,B.useRef)(new Set),[i,a]=(0,B.useState)(0),o=(0,B.useMemo)(()=>[...new Set(e)].sort().join(`
|
|
3
|
+
`),[e]);return(0,B.useEffect)(()=>{for(let[e,t]of[...n.current])t||n.current.delete(e)},[t]),(0,B.useEffect)(()=>{let e=(o?o.split(`
|
|
4
|
+
`):[]).filter(e=>!n.current.has(e)&&!r.current.has(e));if(e.length===0)return;let t=!1;for(let t of e)r.current.add(t);return Promise.all(e.map(async e=>{try{let t=await c.getTaskByRef(e);n.current.set(e,t.status===`complete`||t.status===`canceled`)}catch{n.current.set(e,!1)}finally{r.current.delete(e)}})).then(()=>{t||a(e=>e+1)}),()=>{t=!0}},[o,t]),(0,B.useMemo)(()=>{let e=o?o.split(`
|
|
5
|
+
`):[];return new Set(e.filter(e=>n.current.get(e)===!0))},[o,i])}var q=750,J=2e4,Y={inflight:0,errored:1,idle:2};function X(e){let t=Date.parse(e);return Number.isNaN(t)?0:t}function he(e){let t=e.replace(/\s+/g,` `).trim(),n=``;for(let e of t){if(n.length+e.length>200)break;n+=e}return n}function ge(e,t,n){let r=!1,i=e.map(e=>{if(e.id!==t)return e;r=!0;let i=new Set(e.involvedGezelIds??[e.gezelId]);n.from&&i.add(n.from.gezelId);let a=he(n.content);return{...e,lastActivityAt:n.at,involvedGezelIds:[...i],...a?{lastMessagePreview:a}:{}}});return r?i:null}function _e(e){let{sessions:t,inflight:n,errored:r,now:i,pinnedSessionId:a,groupedTaskRefs:o,finishedTaskRefs:s,liveTools:c,maxInline:l=6}=e,u=[],d=new Map,f=t.filter(e=>!e.archived&&!e.taskRef).reduce((e,t)=>!e||X(t.lastActivityAt)>X(e.lastActivityAt)?t:e,null)?.id;for(let e of t){if(e.archived)continue;let t=r.get(e.id)??e.lastTurnError,l=n.has(e.id)?`inflight`:t?`errored`:`idle`,p=l===`inflight`?c?.get(e.id):void 0,m={sessionId:e.id,gezelId:e.gezelId,title:P(F(e.title)),lastActivityAt:e.lastActivityAt,state:l,involvedGezelIds:e.involvedGezelIds&&e.involvedGezelIds.length>0?e.involvedGezelIds:[e.gezelId],...e.lastMessagePreview?{lastMessagePreview:e.lastMessagePreview}:{},...p?{liveToolName:p}:{},...e.taskRef?{taskRef:e.taskRef}:{},...t?{error:t}:{}};if(e.taskRef&&o?.has(e.taskRef)){let t=d.get(e.taskRef);(!t||X(m.lastActivityAt)>X(t.lastActivityAt))&&d.set(e.taskRef,m);continue}let h=a!==void 0&&e.id===a;if(l===`idle`&&!h&&e.taskRef&&s?.has(e.taskRef))continue;let g=e.id===f;l===`idle`&&!h&&!g&&i-X(e.lastActivityAt)>864e5||u.push(m)}u.sort((e,t)=>{let n=Y[e.state]-Y[t.state];return n===0?X(t.lastActivityAt)-X(e.lastActivityAt):n});let p=u.filter(e=>e.state!==`idle`).length,m=Math.max(l,p);for(let e of[a,f]){if(e===void 0)continue;let t=u.findIndex(t=>t.sessionId===e);t>=m&&(m=t+1)}return{pills:u.slice(0,m),overflow:u.slice(m),taskPills:d}}function ve({projectId:e,gezelId:t,pinnedSessionId:n,groupedTaskRefs:r,refreshKey:i}){let[a,o]=(0,B.useState)([]),s=(0,B.useRef)([]),[l,u]=(0,B.useState)(!0),[d,f]=(0,B.useState)(()=>new Set),[p,m]=(0,B.useState)(()=>new Map),[h,g]=(0,B.useState)(()=>new Map),[_,v]=(0,B.useState)(0),y=(0,B.useCallback)(async()=>{try{let n=await c.listChatSessions({projectId:e,...t?{gezelId:t}:{}});s.current=n.sessions,o(n.sessions)}catch{}finally{u(!1)}},[e,t]),b=(0,B.useCallback)(async()=>{try{let{inflight:n}=await c.listInflightTurns({projectId:e,...t?{gezelId:t}:{}});f(new Set(n.map(e=>e.sessionId)))}catch{}},[e,t]);(0,B.useEffect)(()=>{u(!0),y(),b()},[y,b,i,n]),(0,B.useEffect)(()=>{let e=window.setInterval(()=>void b(),J);return()=>window.clearInterval(e)},[b]),(0,B.useEffect)(()=>{let e=window.setInterval(()=>v(e=>e+1),6e4);return()=>window.clearInterval(e)},[]),(0,B.useEffect)(()=>{let e=()=>void y();return window.addEventListener(`gezel:session-error-cleared`,e),()=>window.removeEventListener(`gezel:session-error-cleared`,e)},[y]);let x=(0,B.useCallback)((e,t)=>{g(n=>{if(t===null){if(!n.has(e))return n;let t=new Map(n);return t.delete(e),t}if(n.get(e)===t)return n;let r=new Map(n);return r.set(e,t),r})},[]),S=(0,B.useRef)(null);(0,B.useEffect)(()=>{let n=new AbortController,r=()=>{S.current!==null&&window.clearTimeout(S.current),S.current=window.setTimeout(()=>{S.current=null,y()},q)};return(async()=>{try{for await(let i of E({url:c.projectEventsUrl(e),headers:c.authHeader(),signal:n.signal,fetch:c.getFetch()})){let{event:e,sessionId:n}=i;if(!(t&&i.gezelId!==t)){if(e.type===`tool_args_delta`||e.type===`tool`?x(n,e.name):(e.type===`complete`||e.type===`done`||e.type===`error`||e.type===`cancelled`)&&x(n,null),e.type===`user_message`){f(e=>{if(e.has(n))return e;let t=new Set(e);return t.add(n),t});let t=ge(s.current,n,e.message);t?(s.current=t,o(t)):y()}else(e.type===`done`||e.type===`error`||e.type===`cancelled`)&&f(e=>{if(!e.has(n))return e;let t=new Set(e);return t.delete(n),t});if(e.type===`error`)m(t=>{let r=new Map(t);return r.set(n,e.error),r});else if(e.type===`complete`){let t=ge(s.current,n,e.message);t&&(s.current=t,o(t)),m(e=>{if(!e.has(n))return e;let t=new Map(e);return t.delete(n),t})}(e.type===`done`||e.type===`complete`)&&r()}}}catch{}})(),()=>{n.abort(),S.current!==null&&(window.clearTimeout(S.current),S.current=null)}},[e,t,y,x]);let C=K((0,B.useMemo)(()=>{let e=new Set;for(let t of a)t.archived||!t.taskRef||r?.has(t.taskRef)||e.add(t.taskRef);return[...e]},[a,r]),i),{pills:w,overflow:T,taskPills:D}=(0,B.useMemo)(()=>_e({sessions:a,inflight:d,errored:p,now:Date.now(),pinnedSessionId:n,liveTools:h,finishedTaskRefs:C,...r?{groupedTaskRefs:r}:{}}),[a,d,p,h,n,r,C,_]);return{pills:w,overflow:T,taskPills:D,loading:l}}var Z=n(),ye=1440*60*1e3;function be(e){let t=Date.parse(e);return Number.isNaN(t)?0:t}function xe({projectId:e,gezelId:t,gezels:n,activeSessionId:i,activeTaskRef:a,activeTerminalThreadId:o,onFocusThread:s,onFocusTask:l,onFocusTerminal:u,onNewTask:d,refreshKey:f,terminalRefreshKey:p}){let{tasks:y,loading:b}=re({projectId:e,refreshKey:f}),{pills:x,overflow:S,taskPills:C,loading:w}=ve({projectId:e,gezelId:t,pinnedSessionId:i,groupedTaskRefs:(0,B.useMemo)(()=>new Set(y.map(e=>e.ref)),[y]),refreshKey:f}),[E,D]=(0,B.useState)([]),O=u!==void 0;(0,B.useEffect)(()=>{if(!O){D([]);return}let t=!1;return c.listTerminalThreads(e).then(e=>{if(t)return;let n=Date.now()-ye;D(e.threads.filter(e=>!e.archived&&be(e.lastActivityAt)>=n))}).catch(()=>{}),()=>{t=!0}},[e,O,p]);let k=(0,B.useMemo)(()=>E.filter(t=>t.projectId===e),[E,e]),A=T(),ee=e=>{let t=n.find(t=>t.id===e);return t?r({name:t.name,roleBasedName:t.roleBasedName},A):`someone`},j=e=>[...new Set(e.involvedGezelIds.map(ee))].join(`, `),te=[...x,...C.values()],M=te.filter(e=>e.state===`inflight`).length,N=te.filter(e=>e.state===`errored`).length,P=[M>0?`${M} ${M===1?`thread`:`threads`} working`:``,N>0?`${N} needs attention`:``].filter(Boolean).join(`, `),F=!(b||w)&&x.length===0&&k.length===0&&y.length===0,{scrollRef:ne,overflowBar:I}=Se(x.length+S.length+k.length+y.length+ +!!F);return(0,Z.jsxs)(`div`,{className:`chat-pill-row`,role:`toolbar`,"aria-label":`Threads, terminal windows, and tasks`,children:[(0,Z.jsx)(`output`,{className:`sr-only`,children:P}),(0,Z.jsxs)(`div`,{className:`chat-pill-row-scroller`,children:[(0,Z.jsxs)(`div`,{className:`chat-pill-row-scroll`,ref:ne,onScroll:I.onScroll,children:[F&&(0,Z.jsx)(`span`,{className:`chat-pill-row-empty muted small`,children:`No recent threads`}),y.map(e=>{let t=C.get(e.ref);return(0,Z.jsx)(Ae,{task:e,latestThread:t,gezels:n,gezelNames:t?j(t):e.assignee.kind===`gezel`?ee(e.assignee.gezelId):`You`,active:e.ref===a,onFocus:l},e.ref)}),x.map(e=>(0,Z.jsx)(we,{pill:e,gezels:n,gezelNames:j(e),active:e.sessionId===i,onFocus:s},e.sessionId)),S.length>0&&(0,Z.jsxs)(v,{children:[(0,Z.jsxs)(m,{className:`chat-pill chat-pill-overflow`,children:[`+`,S.length,` more`]}),(0,Z.jsx)(g,{children:(0,Z.jsx)(h,{className:`chat-rail-section-tab-menu chat-pill-overflow-menu`,align:`start`,sideOffset:4,children:S.map(e=>(0,Z.jsx)(_,{onSelect:()=>s(e),className:`chat-pill-overflow-item chat-pill-${e.state}`,children:(0,Z.jsx)(Te,{pill:e,gezelNames:j(e)})},e.sessionId))})})]}),u&&k.map(e=>(0,Z.jsx)(Ce,{thread:e,active:e.id===o,onFocus:u},e.id))]}),I.node]}),d&&(0,Z.jsx)(`button`,{type:`button`,className:`chat-pill-new-task`,onClick:d,"aria-label":`New task`,title:`New task — pick a craftbook`,children:`Do +`})]})}function Se(e){let t=(0,B.useRef)(null),[n,r]=(0,B.useState)(null),i=(0,B.useCallback)(()=>{let e=t.current;if(!e)return;let{scrollWidth:n,clientWidth:i,scrollLeft:a}=e;if(n-i<2){r(e=>e===null?e:null);return}let o=i/n,s=a/n;r(e=>e&&Math.abs(e.left-s)<5e-4&&Math.abs(e.width-o)<5e-4?e:{left:s,width:o})},[]);return(0,B.useEffect)(()=>{i()},[i,e]),(0,B.useEffect)(()=>{let e=t.current;if(!e||typeof ResizeObserver>`u`)return;let n=new ResizeObserver(()=>i());return n.observe(e),()=>n.disconnect()},[i]),{scrollRef:t,overflowBar:{onScroll:i,node:n&&(0,Z.jsx)(`div`,{className:`chat-pill-row-bar`,"aria-hidden":`true`,onPointerDown:e=>{let r=t.current;if(!r||!n)return;let i=e.currentTarget.getBoundingClientRect(),a=(e.clientX-i.left)/i.width<n.left?-r.clientWidth:r.clientWidth;r.scrollBy({left:a,behavior:`smooth`})},children:(0,Z.jsx)(`div`,{className:`chat-pill-row-bar-thumb`,style:{left:`${n.left*100}%`,width:`${n.width*100}%`},onPointerDown:e=>{let n=t.current,r=e.currentTarget.parentElement;if(!n||!r)return;e.preventDefault(),e.stopPropagation();let i=n.scrollWidth/r.clientWidth,a=e.clientX,o=n.scrollLeft,s=e=>{n.scrollLeft=o+(e.clientX-a)*i},c=()=>{window.removeEventListener(`pointermove`,s),window.removeEventListener(`pointerup`,c)};window.addEventListener(`pointermove`,s),window.addEventListener(`pointerup`,c)}})})}}}function Ce({thread:e,active:t,onFocus:n}){let r=N(e.workingDir),i=$(e.lastActivityAt),a=e.lastCommand?.replace(/\s+/g,` `).trim()||null,o=a?Q(a,40):null;return(0,Z.jsxs)(`button`,{type:`button`,className:`chat-pill chat-pill-thread chat-pill-terminal${t?` is-active`:``}`,"aria-pressed":t,"aria-label":`Terminal ${r}.${a?` Last command: ${a}.`:``} Updated ${i}`,title:`Terminal · ${r}${a?` · last command: ${a}`:``} · updated ${i}`,onClick:()=>n(e),children:[(0,Z.jsx)(`span`,{className:`chat-pill-thread-line chat-pill-thread-title`,children:`Terminal`}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-thread-context`,children:[(0,Z.jsx)(`span`,{className:`terminal-prompt-sigil`,"aria-hidden":`true`,children:`>`}),(0,Z.jsx)(`span`,{className:`chat-pill-message-preview${a?` chat-pill-terminal-command`:``}`,children:o??r})]}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-thread-update`,children:[a&&(0,Z.jsxs)(Z.Fragment,{children:[(0,Z.jsx)(`span`,{className:`chat-pill-terminal-folder`,children:r}),(0,Z.jsx)(`span`,{className:`chat-pill-separator`,"aria-hidden":`true`,children:`·`})]}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-updated-at`,title:b(e.lastActivityAt),children:[`Updated `,i]})]})]})}function we({pill:e,gezels:t,gezelNames:n,active:r,onFocus:i}){let a=t.find(t=>t.id===e.gezelId),o=$(e.lastActivityAt),s=ke(e.state),c=Oe(e),l=`${n} · ${e.title} · updated ${o} · ${s}${e.error?`: ${e.error}`:``}`;return(0,Z.jsx)(`button`,{type:`button`,className:`chat-pill chat-pill-thread chat-pill-${e.state}${r?` is-active`:``}`,"aria-pressed":r,"aria-label":`${n}: ${e.title}. ${c}. Updated ${o}. ${s}`,title:l,onClick:()=>i(e),children:(0,Z.jsx)(Te,{pill:e,gezelNames:n,gezel:a})})}function Te({pill:e,gezelNames:t,gezel:n}){let r=Oe(e);return(0,Z.jsxs)(Z.Fragment,{children:[(0,Z.jsx)(`span`,{className:`chat-pill-thread-line chat-pill-thread-title`,children:Q(e.title,40)}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-thread-context`,children:[n&&(0,Z.jsx)(C,{svg:n.icon??null,poppetje:n.poppetje,iconOverride:n.iconOverride,name:t,size:14}),(0,Z.jsx)(`span`,{className:`chat-pill-participants`,children:t}),(0,Z.jsx)(`span`,{className:`chat-pill-separator`,"aria-hidden":`true`,children:`·`}),(0,Z.jsx)(`span`,{className:`chat-pill-message-preview`,children:r})]}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-thread-update`,children:[(0,Z.jsxs)(`span`,{className:`chat-pill-thread-updated-at`,title:b(e.lastActivityAt),children:[`Updated `,$(e.lastActivityAt)]}),(0,Z.jsx)(`span`,{className:`chat-pill-separator`,"aria-hidden":`true`,children:`·`}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-status`,children:[(0,Z.jsx)(`span`,{className:`chat-pill-dot`,"aria-hidden":`true`}),ke(e.state)]})]})]})}var Ee=30,De=34;function Oe(e){if(e.state===`inflight`&&e.liveToolName)return Q(`${k(e.liveToolName)}…`,De);let t=e.lastMessagePreview?G(e.lastMessagePreview):``;return t?Q(t,Ee):`No messages yet`}function Q(e,t){let n=Array.from(e.trim());return n.length<=t?n.join(``):`${n.slice(0,t-1).join(``)}…`}function ke(e){return e===`inflight`?`Working`:e===`errored`?`Needs attention`:`Ready`}function $(e){return y(e,{style:`long`,fallback:e})}function Ae({task:e,latestThread:t,gezels:n,gezelNames:r,active:i,onFocus:a}){let o=e.assignee.kind===`user`,s=e.assignee.kind===`gezel`?e.assignee.gezelId:null,c=t?n.find(e=>e.id===t.gezelId):s?n.find(e=>e.id===s):void 0,l=t?$(t.lastActivityAt):null,u=t?ke(t.state):`Active`,d=t?Oe(t):`No chat yet`,f=t?`Latest chat with ${r}: ${t.title}. ${d}. Updated ${l}. ${u}`:`${d}. Assigned to ${r}. ${u}`;return(0,Z.jsxs)(`button`,{type:`button`,className:`chat-pill chat-pill-thread chat-pill-task${t?` chat-pill-${t.state}`:``}${i?` is-active`:``}`,"aria-pressed":i,"aria-label":`Task ${e.ref}: ${e.title}. ${f}`,title:t?`${e.ref} · ${e.title} · latest chat: ${t.title} · ${r} · updated ${l} · ${u}${t.error?`: ${t.error}`:``}`:o?`${e.ref} · ${e.title} — assigned to you · no chat yet`:`${e.ref} · ${e.title} · no chat yet`,onClick:()=>a(e),children:[(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-task-title`,children:[(0,Z.jsx)(w,{area:`tasks`,size:13,className:`chat-pill-task-icon`}),(0,Z.jsxs)(`span`,{className:`chat-pill-task-number`,children:[`#`,e.num]}),(0,Z.jsx)(`span`,{className:`chat-pill-label`,children:e.title})]}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-thread-context`,children:[c&&(0,Z.jsx)(C,{svg:c.icon??null,poppetje:c.poppetje,iconOverride:c.iconOverride,name:r,size:14}),(0,Z.jsx)(`span`,{className:`chat-pill-participants`,children:r}),(0,Z.jsx)(`span`,{className:`chat-pill-separator`,"aria-hidden":`true`,children:`·`}),(0,Z.jsx)(`span`,{className:`chat-pill-message-preview`,children:d})]}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-line chat-pill-thread-update`,children:[(0,Z.jsx)(`span`,{className:`chat-pill-thread-updated-at`,title:t?b(t.lastActivityAt):void 0,children:l?`Updated ${l}`:e.ref}),(0,Z.jsx)(`span`,{className:`chat-pill-separator`,"aria-hidden":`true`,children:`·`}),(0,Z.jsxs)(`span`,{className:`chat-pill-thread-status`,children:[t?(0,Z.jsx)(`span`,{className:`chat-pill-dot`,"aria-hidden":`true`}):(0,Z.jsx)(`span`,{className:`task-status-dot task-status-active`,"aria-hidden":`true`}),u]})]})]})}function je({projectId:e,workingDir:t,onChangeWorkingDir:n}){let[r,i]=(0,B.useState)([]),[a,o]=(0,B.useState)(null),[s,l]=(0,B.useState)(!1),u=(0,B.useRef)(null);(0,B.useEffect)(()=>{if(!s&&r.length>0)return;let t=!1;return(async()=>{try{let n=await c.listProjectWorkspace(e,void 0,!0);if(t)return;let r=n.files.filter(e=>e.isDirectory).map(e=>{let t=e.path.split(`/`).length-1;return{path:e.path,name:e.name,depth:t}});r.sort((e,t)=>e.path<t.path?-1:+(e.path>t.path)),i(r)}catch(e){if(t)return;o(e instanceof Error?e.message:String(e))}})(),()=>{t=!0}},[e,s]),(0,B.useEffect)(()=>{if(!s)return;function e(e){u.current?.contains(e.target)||l(!1)}return document.addEventListener(`mousedown`,e),()=>document.removeEventListener(`mousedown`,e)},[s]);let d=(0,B.useMemo)(()=>[{path:``,name:`/`,depth:0},...r],[r]),f=N(t);return(0,Z.jsxs)(`div`,{className:`folder-tree-switcher`,ref:u,children:[(0,Z.jsx)(`span`,{className:`folder-tree-label`,children:`Folder:`}),(0,Z.jsxs)(`button`,{type:`button`,className:`folder-tree-trigger`,onClick:()=>l(e=>!e),title:`Pick a working folder`,"aria-expanded":s,children:[(0,Z.jsx)(`span`,{className:`folder-tree-trigger-value`,children:f}),(0,Z.jsx)(p,{className:`folder-tree-trigger-caret`})]}),s&&(0,Z.jsxs)(`div`,{className:`folder-tree-popup`,role:`listbox`,children:[a&&(0,Z.jsx)(`div`,{className:`terminal-error-banner`,children:a}),d.map(e=>{let r=e.path===t;return(0,Z.jsx)(`button`,{type:`button`,role:`option`,"aria-selected":r,className:`folder-tree-node${r?` active`:``}`,style:{paddingLeft:`${.4+e.depth*.9}rem`},onClick:()=>{n(e.path),l(!1)},title:e.path||`/`,children:(0,Z.jsx)(`span`,{children:e.path===``?`/`:e.name})},e.path||`__root__`)})]})]})}function Me(){return(0,Z.jsxs)(`div`,{className:`project-chat project-chat-placeholder`,"aria-busy":`true`,children:[(0,Z.jsx)(`span`,{className:`sr-only`,children:`Loading this project's chat…`}),(0,Z.jsx)(`div`,{className:`project-chat-placeholder-timeline`,"aria-hidden":`true`}),(0,Z.jsx)(`div`,{className:`project-chat-compose-shell`,"aria-hidden":`true`,children:(0,Z.jsxs)(`div`,{className:`project-chat-compose-main`,children:[(0,Z.jsx)(`div`,{className:`project-chat-placeholder-band`}),(0,Z.jsx)(`div`,{className:`project-chat-placeholder-entry`})]})})]})}function Ne(e){let t=j(),[n,r]=(0,B.useState)(null),[i,a]=(0,B.useState)([]),[o,l]=(0,B.useState)([]),u=(0,B.useRef)(void 0);(0,B.useEffect)(()=>{let n=!1,i=async()=>{try{let t=await c.getProjectIndex(e);n||r(t)}catch{}},o=async()=>{try{let r=await c.listProjectCraftbooks(e);if(n)return;a(s(r.items,t).flatMap(e=>{let t=e.manifest;return t.kind&&t.kind!==`craftbook-template`||!t.id?[]:[{id:t.id,command:t.command??t.id,name:t.name,description:t.description,paramSchema:t.paramSchema}]}))}catch{}},d=async()=>{try{let t=await c.listProjectTools(e);n||l(t.tools)}catch{}},f=async()=>{n||o();try{let t=await c.getProjectIndexStatus(e);if(n)return;let r=t.meta?.scannedAt;r&&r!==u.current?(u.current=r,await i()):t.state===`never`&&await c.refreshProjectIndex(e).catch(()=>{})}catch{}};i(),o(),d();let p=window.setInterval(f,3e4);return()=>{n=!0,window.clearInterval(p)}},[e,t]),(0,B.useEffect)(()=>{le(e,{index:n,craftbooks:i,mcpTools:o})},[e,n,i,o]),(0,B.useEffect)(()=>()=>z(e),[e])}var Pe=(0,B.lazy)(()=>x(()=>import(`./TerminalCodeEditor-BkNQ6QoQ.js`),__vite__mapDeps([0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39]))),Fe=`build, test, git status, … — Enter runs, Shift+Enter for newline, ↑/↓ recalls history`,Ie=[{section:`commands`,label:`Commands`,title:`Everyday terminal commands, and the tools installed on this machine`,icon:(0,Z.jsxs)(Z.Fragment,{children:[(0,Z.jsx)(`path`,{d:`M2.5 4 L6 8 L2.5 12`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.6`,strokeLinecap:`round`,strokeLinejoin:`round`}),(0,Z.jsx)(`path`,{d:`M8 12 H13.5`,stroke:`currentColor`,strokeWidth:`1.6`,strokeLinecap:`round`})]})},{section:`scripts`,label:`Scripts`,title:`Scripts this project already defines — package.json, scripts/, launches`,icon:(0,Z.jsxs)(Z.Fragment,{children:[(0,Z.jsx)(`rect`,{x:`3`,y:`2`,width:`10`,height:`12`,rx:`1.5`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.4`}),(0,Z.jsx)(`path`,{d:`M5.5 5.5h5M5.5 8h5M5.5 10.5h3`,stroke:`currentColor`,strokeWidth:`1.3`,strokeLinecap:`round`})]})},{section:`tasks`,label:`Tasks`,title:`Craftbooks and workspace skills a gezel can run for you`,icon:(0,Z.jsxs)(Z.Fragment,{children:[(0,Z.jsx)(`path`,{d:`M2.5 4.5 L4 6 L6.5 3`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`,strokeLinejoin:`round`}),(0,Z.jsx)(`path`,{d:`M8.5 5 H14`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`}),(0,Z.jsx)(`path`,{d:`M2.5 11 L4 12.5 L6.5 9.5`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`,strokeLinejoin:`round`}),(0,Z.jsx)(`path`,{d:`M8.5 11.5 H14`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`})]})}];function Le({projectId:e,workingDir:t,contextRow:n,toolbarTrailing:r,onSent:i,initialInput:a,onChatEscape:o}){let[s]=(0,B.useState)(()=>a??``),[p,m]=(0,B.useState)(null),[h,g]=(0,B.useState)(null),_=(0,B.useRef)(null),v=(0,B.useRef)([]),y=(0,B.useRef)(-1),b=(0,B.useCallback)(e=>{_.current?.setValue(e),g(null)},[]);Ne(e);let x=(0,B.useCallback)(async n=>{let r=n.trim();if(r!==``){_.current?.setValue(``),m(null),v.current.unshift(r),v.current.length>50&&(v.current.length=50),y.current=-1;try{let n=await c.runTerminalCommand(e,{workingDir:t,input:r});i?.(r,n)}catch(e){m(e instanceof Error?e.message:String(e)),_.current?.focus()}}},[e,t,i]),S=(0,B.useCallback)(()=>{let e=_.current;e&&(x(e.getValue()),e.focus())},[x]),C=(0,B.useCallback)(()=>{if(v.current.length===0)return;let e=Math.min(v.current.length-1,y.current+1);y.current=e,_.current?.setValue(v.current[e])},[]),w=(0,B.useCallback)(()=>{if(y.current<0)return;let e=y.current-1;y.current=e,_.current?.setValue(e<0?``:v.current[e])},[]);return(0,Z.jsxs)(`div`,{className:`terminal-composer`,children:[(0,Z.jsxs)(`div`,{className:`terminal-composer-toolbar`,children:[Ie.map(t=>(0,Z.jsxs)(l,{open:h===t.section,onOpenChange:e=>g(e?t.section:null),children:[(0,Z.jsx)(f,{asChild:!0,children:(0,Z.jsxs)(`button`,{type:`button`,className:`terminal-toolbar-btn`,title:t.title,"aria-label":t.title,children:[(0,Z.jsx)(`svg`,{width:`14`,height:`14`,viewBox:`0 0 16 16`,"aria-hidden":`true`,focusable:`false`,children:t.icon}),t.label]})}),(0,Z.jsx)(u,{className:`terminal-commands-popover`,side:`top`,align:`start`,onCloseAutoFocus:e=>{e.preventDefault(),_.current?.focus()},children:(0,Z.jsx)(R,{projectId:e,section:t.section,onStageCommand:b})})]},t.section)),r]}),n,(0,Z.jsx)(`div`,{className:`terminal-composer-fire-row`,children:(0,Z.jsx)(`button`,{type:`button`,className:`terminal-fire-btn`,"aria-label":`Fire`,title:`Fire — run this command (Enter)`,onClick:S,children:(0,Z.jsx)(d,{})})}),(0,Z.jsxs)(`div`,{className:`terminal-composer-input-wrap`,children:[(0,Z.jsx)(`span`,{className:`terminal-prompt-sigil`,children:`>`}),(0,Z.jsx)(B.Suspense,{fallback:(0,Z.jsx)(`div`,{className:`terminal-composer-input`,"aria-busy":`true`}),children:(0,Z.jsx)(Pe,{ref:_,projectId:e,initialValue:s,placeholder:Fe,onSubmit:e=>void x(e),onHistoryPrev:C,onHistoryNext:w,onChatEscape:o})})]}),p&&(0,Z.jsx)(`div`,{className:`terminal-error-banner`,children:p})]})}var Re=`project`;function ze(e,t){return M(e?.lastHumanActivityAt,t)}function Be({project:e,compact:t=!1}){let[n,r]=(0,B.useState)([]),[i,a]=(0,B.useState)(!1),[o,s]=(0,B.useState)(``);(0,B.useEffect)(()=>{c.listGezels().then(e=>{r(e.gezels),a(!0)}).catch(()=>a(!0))},[e.id,e.voormanGezelId,(e.gezelIds??[]).join(`,`)]),(0,B.useEffect)(()=>{s(``),f(null)},[e.id]);let[l,u]=(0,B.useState)(void 0);(0,B.useEffect)(()=>{u(void 0);let t=!1;return c.listChatSessions({projectId:e.id}).then(e=>{if(t)return;let n=e.sessions.filter(e=>!e.archived&&!e.taskRef)[0];u(n?{gezelId:n.gezelId,...n.lastHumanActivityAt?{lastHumanActivityAt:n.lastHumanActivityAt}:{}}:null)}).catch(()=>{t||u(null)}),()=>{t=!0}},[e.id]);let[d,f]=(0,B.useState)(null),p=(0,B.useCallback)(e=>{f(null),s(e)},[]);(0,B.useEffect)(()=>{if(o)return;let t=se(L(e.id))?.gezelId;if(t&&n.some(e=>e.id===t)){s(t),f(null);return}if(l===void 0)return;let r=ze(l,Date.now())&&l&&n.some(e=>e.id===l.gezelId)?l.gezelId:``,i=n.find(t=>t.id===e.voormanGezelId)?.id??``,a=(e.gezelIds??[]).map(e=>n.find(t=>t.id===e)?.id).find(Boolean)??``,c=r||i||a||n[0]?.id||``;c&&(s(c),f(r?null:c))},[o,l,n,e.id,e.voormanGezelId,e.gezelIds]),(0,B.useEffect)(()=>{o&&ce(L(e.id),{gezelId:o})},[e.id,o]);let m=n.find(e=>e.id===o);return!i||n.length>0&&!m?(0,Z.jsx)(Me,{}):n.length===0?(0,Z.jsx)(`p`,{className:`muted project-chat-empty`,children:`No gezellen available to chat with yet. Create one from the Gezellen tab.`}):(0,Z.jsx)(`div`,{className:`project-chat`,children:o&&m&&(0,Z.jsx)(Ve,{project:e,selectedGezel:m,recipientGezels:n,isVoorman:m.id===e.voormanGezelId,startFreshThread:m.id===d,onSelectGezel:p,compact:t})})}function Ve({project:e,selectedGezel:t,recipientGezels:n,isVoorman:a,startFreshThread:s,onSelectGezel:l,compact:u}){let[d,f]=(0,B.useState)(``),[p,m]=(0,B.useState)(``),[h,g]=(0,B.useState)(null),[_,v]=(0,B.useState)(!1),[y,b]=(0,B.useState)(0),x=T(),S=r({name:t.name,roleBasedName:t.roleBasedName},x),[C,w]=(0,B.useState)(0),[E,O]=(0,B.useState)([]),[k,A]=(0,B.useState)(`chat`),[j,M]=(0,B.useState)(0),N=(0,B.useCallback)(()=>{M(e=>e+1),A(`chat`)},[]),P=D()&&o(e);(0,B.useEffect)(()=>{!P&&k===`terminal`&&N()},[P,k,N]);let[F,re]=(0,B.useState)(``),[L,R]=(0,B.useState)(``),[le,z]=(0,B.useState)(``),V=(0,B.useCallback)(e=>{z(``),re(e),R(e)},[]),[H,ue]=(0,B.useState)(``);(0,B.useEffect)(()=>{k!==`terminal`&&H!==``&&ue(``)},[k,H]);let[de,fe]=(0,B.useState)(0),[U,pe]=(0,B.useState)(null),[W,me]=(0,B.useState)(null),G=(0,B.useRef)(null),K=(0,B.useRef)(null),q=(0,B.useCallback)((e,n,r)=>{n===t.id?g(r):(G.current=e||null,K.current=r,l(n)),f(e)},[t.id,l]),[J,Y]=(0,B.useState)(null),X=(0,B.useCallback)(e=>{e&&Y(t=>({sessionId:e,requestKey:(t?.requestKey??0)+1}))},[]),he=(0,B.useCallback)(async e=>{let t={ref:e.ref,...e.activeStepId?{stepId:e.activeStepId}:{}};try{let{sessions:n}=await c.listTaskSessions(e.projectId,e.num),r=n.find(e=>!e.archived);if(r){q(r.id,r.gezelId,t),X(r.id);return}}catch{}e.assignee.kind===`gezel`&&e.assignee.gezelId?q(``,e.assignee.gezelId,t):g(t)},[q,X]),ge=(0,B.useCallback)(e=>{b(e=>e+1),(e.status===`complete`||e.status===`canceled`)&&g(t=>t?.ref===e.ref?null:t)},[]);(0,B.useEffect)(()=>{let n=G.current;G.current=null,f(n??se(ie(e.id,t.id))?.sessionId??``),g(K.current),K.current=null},[t.id,e.id]),(0,B.useEffect)(()=>{ce(ie(e.id,t.id),{sessionId:d})},[e.id,t.id,d]);let _e=(0,B.useMemo)(()=>ae({role:a?`voorman`:`other`,gezelName:S,gezelGender:t.gender,projectName:e.name,fixedFunctionTool:t.fixedFunction?.tool}),[a,S,t.gender,e.name,t.fixedFunction?.tool]),ve=i(t.gender),ye=P?(0,Z.jsxs)(`div`,{className:`compose-mode-tabs`,role:`tablist`,"aria-label":`Compose surface`,children:[(0,Z.jsxs)(`button`,{type:`button`,role:`tab`,"aria-selected":k===`chat`,"aria-label":`AI chat`,className:`compose-mode-tab`,onClick:N,title:`AI chat (@-mention to talk to a gezel)`,children:[(0,Z.jsx)(`span`,{className:`compose-mode-tab-glyph`,"aria-hidden":`true`,children:`@`}),`Chat`]}),(0,Z.jsxs)(`button`,{type:`button`,role:`tab`,"aria-selected":k===`terminal`,className:`compose-mode-tab`,onClick:()=>A(`terminal`),title:`Terminal (run shell commands in this project's workspace)`,children:[(0,Z.jsx)(`span`,{className:`compose-mode-tab-glyph`,"aria-hidden":`true`,children:`>`}),`Terminal`]})]}):null;return(0,Z.jsx)(oe,{projectId:e.id,skillsProjectId:e.id,compact:u,chatKey:`${e.id}:timeline`,onTaskChanged:ge,banner:({onTaskReference:t})=>(0,Z.jsx)(xe,{projectId:e.id,gezels:n,activeSessionId:k===`chat`&&d||void 0,activeTaskRef:k===`chat`?h?.ref??null:null,activeTerminalThreadId:k===`terminal`?le:null,refreshKey:y,terminalRefreshKey:de,onFocusThread:e=>{q(e.sessionId,e.gezelId,e.taskRef?{ref:e.taskRef}:null),X(e.sessionId)},onFocusTask:e=>{t(e.ref,{focus:!0}),he(e)},onFocusTerminal:P?t=>{V(t.workingDir),z(t.id),A(`terminal`),pe(e=>({threadId:t.id,requestKey:(e?.requestKey??0)+1})),c.getTerminalThread(e.id,t.id).then(e=>{let t=[...e.messages].reverse().find(e=>e.cwd!==void 0)?.cwd;t!==void 0&&R(t)}).catch(()=>{})}:void 0,onNewTask:()=>v(!0)}),children:({onToolActivity:r,onArtifactReference:i,onArtifactSeen:o,onWorkspaceReference:c,onWorkspaceSeen:u,recentReferences:g,onOpenReference:y,onTaskReference:x})=>(0,Z.jsxs)(Z.Fragment,{children:[(0,Z.jsx)(I,{projectId:e.id,activeSessionId:d||void 0,onFocusSession:(e,t)=>q(e,t,null),onToolActivity:r,onArtifactReference:i,onArtifactSeen:o,onWorkspaceReference:c,onWorkspaceSeen:u,onOpenReference:y,onTaskReference:x,onTerminalWorkingDirChanged:(e,t)=>{R(t)},terminalRefreshKey:de,...W?{terminalSubmission:W}:{},...U?{terminalFocusRequest:U}:{},...J?{sessionFocusRequest:J}:{},emptyPlaceholder:a?`Talk to ${S} about running "${e.name}" — planning tasks, delegating, or checking progress.`:`Chat with ${S} about what ${ve.subject} ${ve.presentBe} working on in "${e.name}".`}),(0,Z.jsx)(`div`,{className:`project-chat-compose-shell`,children:(0,Z.jsx)(`div`,{className:`project-chat-compose-main${k===`terminal`?` project-chat-compose-main-terminal`:``}`,children:k===`chat`?(0,Z.jsx)(te,{gezelId:t.id,gezelName:t.name,gezelRoleBasedName:t.roleBasedName,gezelRole:t.role,gezelIcon:t.icon??null,gezelPoppetje:t.poppetje,gezelIconOverride:t.iconOverride,recipientGezels:n,onPrimaryRecipientChange:l,focusRequestKey:j,projectId:e.id,sessionId:d||void 0,...h?{taskRef:h.ref}:{},...h?.stepId?{stepId:h.stepId}:{},onSessionCreated:e=>{f(e),w(e=>e+1)},onToolActivity:r,recentReferences:g,onOpenReference:y,placeholder:_e,draftScope:Re,onPivotToMention:e=>{e!==t.id&&(O(e=>e.includes(t.id)?e:[...e,t.id]),l(e))},passiveCcGezelIds:E,onPassiveCcConsumed:()=>O([]),onTerminalEscape:P?e=>{ue(e),A(`terminal`)}:void 0,addressLineTrailing:ye,draftId:p||void 0,onDraftIdChange:e=>m(e??``),belowAddressLine:(0,Z.jsx)(ne,{gezelId:t.id,projectId:e.id,sessionId:d||void 0,...h?{taskRef:h.ref}:{},...h?.stepId?{stepId:h.stepId}:{},onSessionIdChange:e=>f(e??``),onFreshThread:()=>M(e=>e+1),refreshKey:C,activeDraftId:p||void 0,onDraftSelect:e=>m(e??``),draftScope:Re,autoPickNewest:!s||!!h})}):(0,Z.jsx)(Le,{projectId:e.id,workingDir:F,contextRow:(0,Z.jsx)(je,{projectId:e.id,workingDir:L,onChangeWorkingDir:V}),toolbarTrailing:ye,initialInput:H,onSent:(e,t)=>{z(t.threadId),me({runId:t.runId,threadId:t.threadId,input:e}),fe(e=>e+1)},onChatEscape:N},`terminal:${e.id}`)})}),(0,Z.jsx)(ee,{open:_,defaultProjectId:e.id,projects:[e],gezels:n,projectLocked:!0,onClose:()=>v(!1),onCreated:()=>{v(!1),b(e=>e+1)}})]})})}export{Be as ProjectChat};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{t as r}from"./api-CmrgM5Rf.js";import{n as i,t as a}from"./relative-time-B2kBaekd.js";import{t as o}from"./ConfirmDialog-Dt1ed4Fh.js";import{r as s}from"./new-project-meta-5Y9Blozr.js";import{at as c}from"./index-DivKnJyx.js";var l=e(t(),1),u=n();function d(e,t){return`connector-${e}-${t}`.replace(/[^a-zA-Z0-9_-]/g,`-`)}function f(e){return e&&/^https:\/\//i.test(e)?e:void 0}function p({required:e}){return e?(0,u.jsx)(`span`,{className:`gz-connector-field-requirement`,"aria-hidden":`true`,children:`Required`}):null}function m({id:e,description:t,helpUrl:n,helpLabel:r}){let i=f(n);return!t&&!i?null:(0,u.jsxs)(`span`,{id:e,className:`gz-connector-field-help`,children:[t,t&&i?` `:``,i&&(0,u.jsx)(`a`,{href:i,target:`_blank`,rel:`noreferrer`,children:r??`Learn more`})]})}function h({connectorId:e,fieldKey:t,property:n,required:r,value:i,onChange:a}){let o=d(e,t),s=`${o}-label`,c=`${o}-help`,l=n.title??t,f=n.description?c:void 0;return(0,u.jsxs)(`div`,{className:`gz-connector-field`,children:[(0,u.jsxs)(`label`,{id:s,className:`gz-connector-field-label`,htmlFor:o,children:[(0,u.jsx)(`span`,{children:l}),(0,u.jsx)(p,{required:r})]}),(0,u.jsxs)(`span`,{className:`gz-connector-field-control`,children:[n.type===`boolean`?(0,u.jsx)(`input`,{id:o,type:`checkbox`,"aria-label":l,checked:i===!0,onChange:e=>a(e.target.checked),"aria-describedby":f}):(0,u.jsx)(`input`,{id:o,type:n.type===`integer`||n.type===`number`?`number`:`text`,value:typeof i==`string`?i:``,onChange:e=>a(e.target.value),placeholder:n.type===`array`?`comma,separated`:``,min:n.minimum,max:n.maximum,step:n.type===`integer`?1:void 0,required:r,"aria-label":l,"aria-describedby":f}),(0,u.jsx)(m,{id:c,description:n.description})]})]})}function g({connectorId:e,fieldKey:t,label:n,value:r,onChange:i,required:a=!1,secret:o=!1,description:s,helpUrl:c,helpLabel:l,placeholder:h}){let g=d(e,t),_=`${g}-help`,v=!!(s||f(c));return(0,u.jsxs)(`div`,{className:`gz-connector-field`,children:[(0,u.jsxs)(`label`,{className:`gz-connector-field-label`,htmlFor:g,children:[(0,u.jsx)(`span`,{children:n}),(0,u.jsx)(p,{required:a})]}),(0,u.jsxs)(`span`,{className:`gz-connector-field-control`,children:[(0,u.jsx)(`input`,{id:g,type:o?`password`:`text`,value:r,onChange:e=>i(e.target.value),required:a,autoComplete:o?`off`:void 0,placeholder:h,"aria-label":n,"aria-describedby":v?_:void 0}),(0,u.jsx)(m,{id:_,description:s,helpUrl:c,helpLabel:l})]})]})}function _({connectorId:e,fieldKey:t,label:n,checked:r,onChange:i}){let a=d(e,t);return(0,u.jsxs)(`div`,{className:`gz-connector-field`,children:[(0,u.jsx)(`label`,{className:`gz-connector-field-label`,htmlFor:a,children:(0,u.jsx)(`span`,{children:n})}),(0,u.jsx)(`span`,{className:`gz-connector-field-control gz-connector-checkbox-control`,children:(0,u.jsx)(`input`,{id:a,type:`checkbox`,"aria-label":n,checked:r,onChange:e=>i(e.target.checked)})})]})}function v({title:e,children:t}){return(0,u.jsxs)(`section`,{className:`gz-connector-field-group`,"aria-label":e,children:[(0,u.jsx)(`div`,{className:`gz-connector-field-group-heading`,children:e}),t]})}function y(e){let t={};for(let[n,r]of Object.entries(e.configSchema?.properties??{}))r.default!==void 0&&(t[n]=r.type===`boolean`?r.default===!0:String(r.default));return t}function b({connector:e,config:t,onConfigChange:n,displayName:r,onDisplayNameChange:i,credential:a,onCredentialChange:o,imapHost:s,onImapHostChange:c,imapPort:l,onImapPortChange:d,imapSecure:p,onImapSecureChange:m}){let y=e.secretShape?.kind,b=new Set(e.configSchema?.required??[]),x=Object.entries(e.configSchema?.properties??{}).filter(([,e])=>e.const===void 0),S=([e,t])=>b.has(e)||t[`x-gezel-priority`]===`primary`,C=x.filter(S),w=x.filter(e=>!S(e)),T=e.secretShape?.required===!0||e.secretShape?.[`x-gezel-priority`]===`primary`,E=([r,i])=>(0,u.jsx)(h,{connectorId:e.id,fieldKey:r,property:i,required:b.has(r),value:t[r],onChange:e=>n(r,e)},r),D=y!==`oauth2`&&y!==`imap`&&(0,u.jsx)(g,{connectorId:e.id,fieldKey:`credential`,label:e.secretShape?.label??`API key / token`,value:a,onChange:o,required:e.secretShape?.required===!0,secret:!0,description:e.secretShape?.description,helpUrl:e.secretShape?.helpUrl,helpLabel:e.secretShape?.helpLabel},`credential`),O=y===`imap`&&(0,u.jsxs)(u.Fragment,{children:[(0,u.jsx)(g,{connectorId:e.id,fieldKey:`imap-host`,label:`IMAP host`,value:s,onChange:c,required:!0,placeholder:`imap.example.com`}),(0,u.jsx)(g,{connectorId:e.id,fieldKey:`credential`,label:`Password / app password`,value:a,onChange:o,required:!0,secret:!0,description:e.secretShape?.description,helpUrl:e.secretShape?.helpUrl,helpLabel:e.secretShape?.helpLabel})]}),k=C.length>0||T||y===`imap`||y===`oauth2`;return(0,u.jsxs)(u.Fragment,{children:[e.setupInstructions&&(0,u.jsxs)(`aside`,{className:`gz-connector-setup-instructions`,children:[(0,u.jsx)(`strong`,{children:e.setupInstructions.title}),e.setupInstructions.description&&(0,u.jsx)(`p`,{children:e.setupInstructions.description}),e.setupInstructions.steps&&e.setupInstructions.steps.length>0&&(0,u.jsx)(`ol`,{children:e.setupInstructions.steps.map(e=>(0,u.jsx)(`li`,{children:e},e))}),f(e.setupInstructions.url)&&(0,u.jsx)(`a`,{href:e.setupInstructions.url,target:`_blank`,rel:`noreferrer`,children:e.setupInstructions.urlLabel??`Open setup instructions`})]}),(0,u.jsxs)(`div`,{className:`gz-connector-config-fields`,children:[k&&(0,u.jsxs)(v,{title:`Connection details`,children:[C.map(E),y===`oauth2`?(0,u.jsx)(`p`,{className:`muted small gz-connector-oauth-note`,children:`You'll authorize this connector in your browser after you click Connect.`}):y===`imap`?O:T?D:null]}),(0,u.jsxs)(v,{title:`Additional settings`,children:[w.map(E),y===`imap`&&(0,u.jsxs)(u.Fragment,{children:[(0,u.jsx)(g,{connectorId:e.id,fieldKey:`imap-port`,label:`Port`,value:l,onChange:d,placeholder:`993`}),(0,u.jsx)(_,{connectorId:e.id,fieldKey:`imap-tls`,label:`Use TLS`,checked:p,onChange:m})]}),!T&&D,(0,u.jsx)(g,{connectorId:e.id,fieldKey:`display-name`,label:`Display name`,value:r,onChange:i})]})]})]})}var x=/^GEZEL_[A-Z0-9_]{1,120}$/,S=8;function C(e,t){if(!t||typeof t!=`object`)return null;let n=t;if(n.kind!==`oauth2`)return null;let r=typeof n.clientIdEnv==`string`?n.clientIdEnv:``;if(!x.test(r))return null;let i=typeof n.clientSecretEnv==`string`&&n.clientSecretEnv.length>0,a=n.clientSetup&&typeof n.clientSetup==`object`?n.clientSetup:{},o=typeof a.providerLabel==`string`&&a.providerLabel.trim()?a.providerLabel.trim():e,s=typeof a.docsUrl==`string`&&/^https:\/\//.test(a.docsUrl)?a.docsUrl:void 0,c=typeof a.redirectPort==`number`&&Number.isInteger(a.redirectPort)&&a.redirectPort>=1024&&a.redirectPort<=65535?a.redirectPort:void 0,l=typeof a.appTypeNote==`string`&&a.appTypeNote.trim()?a.appTypeNote.trim():void 0,u=typeof a.redirectNote==`string`&&a.redirectNote.trim()?a.redirectNote.trim():void 0,d=Array.isArray(a.steps)?a.steps.filter(e=>typeof e==`string`&&e.trim().length>0).map(e=>e.trim()).slice(0,S):[];return{clientKey:r,hasSecretField:i,secretRequired:i&&a.secretRequired===!0,providerLabel:o,...s?{docsUrl:s}:{},...l?{appTypeNote:l}:{},...c===void 0?{}:{redirectPort:c},...u?{redirectNote:u}:{},...d.length>0?{steps:d}:{}}}function w(e){return`http://127.0.0.1:${e}/callback`}function T(e){let t=e instanceof Error?e.message:typeof e==`string`?e:``;return/oauth is not configured/i.test(t)}function E({requirement:e,registered:t,forceOpenNonce:n,busy:r,onSave:i}){let[a,o]=(0,l.useState)(!1),[s,c]=(0,l.useState)(``),[d,f]=(0,l.useState)(``),[p,m]=(0,l.useState)(``),[h,g]=(0,l.useState)(!1),_=(0,l.useRef)(t);_.current=t;let v=()=>{c(_.current?.clientId??``),f(``),m(``),o(!0)};(0,l.useEffect)(()=>{n&&v()},[n]);let y=e.redirectPort===void 0?null:w(e.redirectPort),b=async()=>{if(y)try{await navigator.clipboard.writeText(y),g(!0),setTimeout(()=>g(!1),1500)}catch{}},x=async()=>{let n=s.trim(),r=d.trim();if(!n){m(`Client ID is required.`);return}if(e.secretRequired&&!r&&!t?.hasSecret){m(`${e.providerLabel} requires a client secret.`);return}m(``);try{await i({clientId:n,...r?{clientSecret:r}:{}})}catch{return}f(``),o(!1)};return a?(0,u.jsxs)(`div`,{className:`gz-oauth-app`,"aria-label":`${e.providerLabel} OAuth app setup`,children:[(0,u.jsxs)(`strong`,{className:`gz-oauth-app-heading`,children:[`Your `,e.providerLabel,` app`]}),(0,u.jsx)(`p`,{className:`muted small`,children:e.appTypeNote??`Create an OAuth app in your ${e.providerLabel} developer settings and paste its client ID here. It is stored on this machine only.`}),e.steps&&(0,u.jsx)(`ol`,{className:`gz-oauth-app-steps`,children:e.steps.map(e=>(0,u.jsx)(`li`,{children:e},e))}),e.docsUrl&&(0,u.jsxs)(`a`,{className:`gz-oauth-app-docs`,href:e.docsUrl,target:`_blank`,rel:`noreferrer`,children:[`Open the `,e.providerLabel,` developer console`]}),(0,u.jsxs)(`div`,{className:`gz-oauth-app-redirect`,children:[(0,u.jsx)(`span`,{children:`Redirect URI to register`}),y?(0,u.jsxs)(u.Fragment,{children:[(0,u.jsxs)(`span`,{className:`gz-oauth-app-redirect-row`,children:[(0,u.jsx)(`code`,{children:y}),(0,u.jsx)(`button`,{type:`button`,onClick:()=>void b(),title:`Copy the redirect URI`,children:h?`Copied`:`Copy`})]}),e.redirectNote&&(0,u.jsx)(`span`,{className:`muted small`,children:e.redirectNote})]}):(0,u.jsx)(`span`,{className:`muted small`,children:e.redirectNote??`${e.providerLabel} accepts any 127.0.0.1 port, so there is no fixed URI to register — Gezel picks a free port when you connect.`})]}),(0,u.jsxs)(`div`,{className:`gz-oauth-app-fields`,children:[(0,u.jsxs)(`label`,{children:[`Client ID`,(0,u.jsx)(`input`,{value:s,onChange:e=>c(e.target.value),autoComplete:`off`,spellCheck:!1})]}),e.hasSecretField&&(0,u.jsxs)(`label`,{children:[`Client secret`,` `,!e.secretRequired&&(0,u.jsx)(`span`,{className:`muted`,children:`(optional — PKCE public clients don't need one)`}),(0,u.jsx)(`input`,{type:`password`,value:d,onChange:e=>f(e.target.value),autoComplete:`off`,placeholder:t?.hasSecret?`leave blank to keep the saved secret`:``})]})]}),p&&(0,u.jsx)(`p`,{className:`error small`,children:p}),(0,u.jsxs)(`div`,{className:`gz-oauth-app-actions`,children:[(0,u.jsx)(`button`,{type:`button`,onClick:()=>o(!1),disabled:r,children:`Cancel`}),(0,u.jsx)(`button`,{type:`button`,className:`primary`,onClick:()=>void x(),disabled:r,children:r?`Working…`:`Save & connect`})]})]}):(0,u.jsxs)(`div`,{className:`gz-oauth-app gz-oauth-app-summary`,children:[(0,u.jsx)(`div`,{className:`gz-oauth-app-summary-text`,children:t?(0,u.jsxs)(u.Fragment,{children:[(0,u.jsxs)(`span`,{children:[`Connects through your `,e.providerLabel,` app`]}),(0,u.jsx)(`code`,{title:t.clientId,children:t.clientId}),t.hasSecret&&(0,u.jsx)(`span`,{children:`· secret saved`})]}):(0,u.jsxs)(`span`,{children:[`Gezel ships no built-in `,e.providerLabel,` client — connecting uses an app you register once on this machine.`]})}),(0,u.jsx)(`button`,{type:`button`,onClick:v,disabled:r,children:t?`Edit`:`Use your own ${e.providerLabel} app`})]})}async function D(e,t,n,i,a){let o=window.__GEZEL__;if(!o?.mailOAuthListen||!o.mailOAuthAwait)throw Error(`Connecting this source needs the Gezel desktop app.`);let{requestId:s,redirectUri:c}=await o.mailOAuthListen(a?.redirectPort===void 0?void 0:{port:a.redirectPort}),{authUrl:l,state:u}=await r.startConnectorOAuth(e,{type:t,redirectUri:c,config:n,...i?{displayName:i}:{}}),d=await o.mailOAuthAwait(s,l);if(`error`in d)throw Error(d.error);await r.completeConnectorOAuth(e,{state:d.state||u,code:d.code})}function O(e){let t=`${e.id} ${(e.tags??[]).join(` `)}`.toLowerCase();return t.includes(`wiki`)?`sheet`:t.includes(`calendar`)?`calendar`:/(mail|gmail|imap|email)/.test(t)?`envelope`:/(github|git)/.test(t)?`branch`:/(issue|linear)/.test(t)?`bubbles`:/(airtable|record|data)/.test(t)?`chart`:`dots`}function k(e){let t=e.secretShape?.kind;return t===`oauth2`?`OAuth`:t===`imap`?`Mail login`:e.secretShape?.required?e.secretShape?.label??`API token`:`Optional token`}function ee({tables:e}){return(0,u.jsx)(`ul`,{className:`gz-connector-tables`,children:e.map(e=>{let t=e.earliestPartition&&e.latestPartition?e.earliestPartition===e.latestPartition?e.earliestPartition:`${e.earliestPartition} → ${e.latestPartition}`:null;return(0,u.jsxs)(`li`,{className:`small muted`,children:[(0,u.jsx)(`strong`,{children:e.table}),` · `,e.rows.toLocaleString(),` `,e.rows===1?`row`:`rows`,t?` · ${t}`:``,e.retentionDays?` · keeps ${e.retentionDays} days`:``,e.schemaInferred?` · schema inferred`:``,e.pendingParts>0?` · tidying up tonight`:``]},e.table)})})}function A(e){return e.completeness===`window`?`Recent window`:`Full mirror`}function j({project:e,onProjectChange:t}){let[n,d]=(0,l.useState)(null),[f,p]=(0,l.useState)(null),[m,h]=(0,l.useState)(``),[g,_]=(0,l.useState)(``),[v,x]=(0,l.useState)(null),[S,w]=(0,l.useState)([]),[j,te]=(0,l.useState)(!1),[ne,re]=(0,l.useState)(!1),[M,N]=(0,l.useState)([]),[P,F]=(0,l.useState)(null),[I,L]=(0,l.useState)({}),[R,z]=(0,l.useState)(``),[B,V]=(0,l.useState)(``),[H,U]=(0,l.useState)(``),[W,G]=(0,l.useState)(``),[K,q]=(0,l.useState)(!0),[ie,ae]=(0,l.useState)({}),[oe,J]=(0,l.useState)(0),Y=(0,l.useCallback)(async()=>{try{let[t,n]=await Promise.all([r.listConnectors(e.id),r.listConnectorActions(e.id)]);d(t),w(n.pending)}catch(e){h(e instanceof Error?e.message:String(e))}},[e.id]),se=(0,l.useCallback)(async t=>{p(t),h(``),_(``);try{let n=await r.commitConnectorAction(e.id,t);_(n.status===`queued-night-shift`?`Held for daytime approval (night shift).`:`Action committed.`),await Y()}catch(e){h(e instanceof Error?e.message:String(e))}finally{p(null)}},[e.id,Y]),ce=(0,l.useCallback)(async t=>{p(t);try{await r.discardConnectorAction(e.id,t),await Y()}catch(e){h(e instanceof Error?e.message:String(e))}finally{p(null)}},[e.id,Y]);(0,l.useEffect)(()=>{Y()},[Y]);let X=(0,l.useCallback)(()=>{te(!1),F(null),L({}),z(``),V(``),U(``),G(``),q(!0),J(0)},[]),Z=(0,l.useCallback)(async()=>{let e=await r.listOAuthClients();ae(Object.fromEntries((e.clients??[]).map(e=>[e.key,{clientId:e.clientId,hasSecret:e.hasSecret}])))},[]),le=(0,l.useCallback)(async()=>{te(!0),re(!0),N([]),F(null),h(``),_(``),Z().catch(()=>{});try{let e=await r.listConnectorTypes();N(e.items.map(e=>({...e.manifest,...e.iconSvg?{iconSvg:e.iconSvg}:{},...e.logoUrl?{logoUrl:e.logoUrl}:{}})))}catch(e){h(e instanceof Error?e.message:String(e))}finally{re(!1)}},[Z]),ue=(0,l.useCallback)(async t=>{p(t),h(``),_(``);try{let n=(await r.syncConnector(e.id,t)).result;_(n.error?`Sync error: ${n.error}`:`Synced ${(n.written??0)+(n.quarantined??0)} new record(s).`),await Y()}catch(e){h(e instanceof Error?e.message:String(e))}finally{p(null)}},[e.id,Y]),de=(0,l.useCallback)(async t=>{p(t);try{await r.unbindConnector(e.id,t),await Y()}catch(e){h(e instanceof Error?e.message:String(e))}finally{p(null),x(null)}},[e.id,Y]),fe=(0,l.useCallback)(()=>{let e=P?.configSchema?.properties??{},t={};for(let[n,r]of Object.entries(e))if(r.const!==void 0)t[n]=r.const;else if(r.type===`array`){let e=typeof I[n]==`string`?I[n].trim():``;e&&(t[n]=e.split(`,`).map(e=>e.trim()).filter(Boolean))}else if(r.type===`boolean`)typeof I[n]==`boolean`&&(t[n]=I[n]);else if(r.type===`integer`||r.type===`number`){let e=typeof I[n]==`string`?I[n].trim():``;e&&(t[n]=Number(e))}else{let e=typeof I[n]==`string`?I[n].trim():``;e&&(t[n]=e)}return t},[P,I]),Q=(0,l.useMemo)(()=>P?.secretShape?.kind===`oauth2`?C(P.name,P.secretShape):null,[P]),$=(0,l.useCallback)(async()=>{if(!P)return;h(``),_(``);let n=fe(),i=P.secretShape?.kind,a=(P.configSchema?.required??[]).find(e=>{let t=n[e];return t===void 0||t===``||Array.isArray(t)&&t.length===0});if(a){let e=P.configSchema?.properties?.[a]?.title??a;h(`${e} is required.`);return}if(i!==`oauth2`&&i!==`imap`&&P.secretShape?.required&&!B.trim()){h(`${P.secretShape.label??`API key / token`} is required.`);return}p(`add`);try{if(i===`oauth2`)await D(e.id,P.id,n,R.trim()||void 0,Q?.redirectPort===void 0?void 0:{redirectPort:Q.redirectPort});else{let t;i===`imap`?t={host:H.trim(),...W.trim()?{port:Number(W.trim())}:{},secure:K,user:String(n.address??``),pass:B}:B.trim()&&(t=B.trim()),await r.bindConnector(e.id,{type:P.id,...R.trim()?{displayName:R.trim()}:{},config:n,...t===void 0?{}:{credential:t}})}_(`Connector added.`),X(),await Y();try{let n=await r.getProject(e.id);n&&t?.(n)}catch{}}catch(e){let t=e instanceof Error?e.message:String(e);T(t)&&J(e=>e+1),h(t)}finally{p(null)}},[P,e.id,fe,R,B,H,W,K,X,Y,t,Q]),pe=(0,l.useCallback)(async e=>{if(Q){h(``),p(`oauth-app`);try{await r.putOAuthClient(Q.clientKey,e),await Z().catch(()=>{ae(t=>({...t,[Q.clientKey]:{clientId:e.clientId,hasSecret:!!e.clientSecret||(t[Q.clientKey]?.hasSecret??!1)}}))}),J(0)}catch(e){throw h(e instanceof Error?e.message:String(e)),e}finally{p(null)}await $()}},[Q,Z,$]),me=n?.bindings??[],he=P?.secretShape?.kind,ge=e=>{e.id!==P?.id&&(F(e),L(y(e)),z(``),V(``),U(``),G(``),q(!0),h(``),J(0))};return(0,u.jsxs)(`div`,{className:`settings-section`,children:[(0,u.jsxs)(`div`,{className:`gz-mail-header`,children:[(0,u.jsx)(`h3`,{children:`Connections`}),!j&&(0,u.jsx)(`button`,{type:`button`,onClick:()=>void le(),children:`Add connection`})]}),me.length===0&&!j?(0,u.jsx)(`p`,{className:`muted`,children:`No connectors yet. Add one to mirror an external source (email, issues, a data source) into this project as searchable files.`}):(0,u.jsx)(`ul`,{className:`settings-list`,children:me.map(e=>(0,u.jsxs)(`li`,{children:[(0,u.jsxs)(`div`,{children:[(0,u.jsx)(`strong`,{children:e.displayName||e.type}),(0,u.jsxs)(`span`,{className:`muted small`,children:[` · `,e.type]}),(0,u.jsx)(`div`,{className:`small`,children:e.lastError?(0,u.jsxs)(`span`,{className:`error`,children:[`Error: `,e.lastError]}):e.lastSyncedAt?(0,u.jsxs)(`span`,{className:`muted`,title:a(e.lastSyncedAt),children:[`Last synced `,i(e.lastSyncedAt)]}):(0,u.jsx)(`span`,{className:`muted`,children:`Not synced yet`})}),e.tables&&e.tables.length>0?(0,u.jsx)(ee,{tables:e.tables}):null]}),(0,u.jsxs)(`div`,{className:`gz-mail-link-actions`,children:[(0,u.jsx)(`button`,{type:`button`,onClick:()=>void ue(e.id),disabled:f===e.id,children:f===e.id?`Working…`:`Sync now`}),(0,u.jsx)(`button`,{type:`button`,className:`danger`,onClick:()=>x(e.id),disabled:f===e.id,children:`Remove`})]})]},e.id))}),S.length>0&&(0,u.jsxs)(`div`,{className:`settings-subsection`,children:[(0,u.jsx)(`h4`,{children:`Pending actions`}),(0,u.jsx)(`p`,{className:`muted small`,children:`Drafted by a gezel — review, then commit (the live write). You commit; the gezel can't.`}),(0,u.jsx)(`ul`,{className:`settings-list`,children:S.map(e=>(0,u.jsxs)(`li`,{children:[(0,u.jsxs)(`div`,{children:[(0,u.jsx)(`strong`,{children:e.action}),(0,u.jsxs)(`span`,{className:`muted small`,children:[` · `,e.connectorType]}),e.status===`queued`&&(0,u.jsx)(`span`,{className:`badge`,children:` held for daytime`})]}),(0,u.jsxs)(`div`,{className:`gz-mail-link-actions`,children:[(0,u.jsx)(`button`,{type:`button`,className:`primary`,onClick:()=>void se(e.draftId),disabled:f===e.draftId,children:f===e.draftId?`Working…`:`Commit`}),(0,u.jsx)(`button`,{type:`button`,onClick:()=>void ce(e.draftId),disabled:f===e.draftId,children:`Discard`})]})]},e.draftId))})]}),j&&(0,u.jsxs)(`div`,{className:`gz-connector-picker`,children:[(0,u.jsxs)(`div`,{className:`gz-connector-picker-heading`,children:[(0,u.jsxs)(`div`,{children:[(0,u.jsx)(`strong`,{children:`Choose a connector`}),(0,u.jsx)(`p`,{className:`muted small`,children:`Pick a source to mirror into this project's searchable files.`})]}),(0,u.jsx)(`span`,{className:`gz-connector-picker-count`,children:ne?`Loading…`:`${M.length} available`})]}),ne?(0,u.jsx)(`div`,{className:`gz-connector-picker-empty muted small`,children:`Gathering connectors…`}):M.length===0?(0,u.jsx)(`div`,{className:`gz-connector-picker-empty muted small`,children:`No connector types are available.`}):(0,u.jsx)(`div`,{className:`gz-connector-grid`,role:`radiogroup`,"aria-label":`Connector type`,children:M.map((e,t)=>(0,u.jsxs)(`button`,{type:`button`,role:`radio`,"aria-checked":P?.id===e.id,"aria-label":e.name,className:`gz-npd-card gz-connector-card${P?.id===e.id?` active`:``}`,onClick:()=>ge(e),style:{"--card-i":Math.min(t,11)},children:[(0,u.jsx)(`span`,{className:`gz-npd-card-mark`,children:(0,u.jsx)(c,{iconSvg:e.iconSvg,logoUrl:e.logoUrl,svgClassName:`gz-npd-card-mark-svg`,fallback:(0,u.jsx)(s,{glyph:O(e),size:19})})}),(0,u.jsx)(`span`,{className:`gz-npd-card-name`,children:e.name}),(0,u.jsx)(`span`,{className:`gz-npd-card-description`,children:e.description}),(0,u.jsxs)(`span`,{className:`gz-connector-card-meta`,"aria-hidden":`true`,children:[(0,u.jsx)(`span`,{children:k(e)}),(0,u.jsx)(`span`,{children:A(e)})]})]},e.id))}),P&&(0,u.jsxs)(`div`,{className:`gz-mail-link-form gz-connector-config`,"aria-label":`${P.name} setup`,children:[(0,u.jsxs)(`div`,{className:`gz-connector-config-heading`,children:[(0,u.jsx)(`span`,{className:`gz-connector-config-mark`,children:(0,u.jsx)(c,{iconSvg:P.iconSvg,logoUrl:P.logoUrl,svgClassName:`gz-npd-card-mark-svg`,fallback:(0,u.jsx)(s,{glyph:O(P),size:19})})}),(0,u.jsxs)(`div`,{children:[(0,u.jsxs)(`strong`,{children:[`Set up `,P.name]}),(0,u.jsxs)(`div`,{className:`small muted`,children:[k(P),` · `,A(P)]})]})]}),(0,u.jsx)(b,{connector:P,config:I,onConfigChange:(e,t)=>L(n=>({...n,[e]:t})),displayName:R,onDisplayNameChange:z,credential:B,onCredentialChange:V,imapHost:H,onImapHostChange:U,imapPort:W,onImapPortChange:G,imapSecure:K,onImapSecureChange:q}),Q&&(0,u.jsx)(E,{requirement:Q,registered:ie[Q.clientKey]??null,forceOpenNonce:oe,busy:f===`oauth-app`||f===`add`,onSave:pe},P.id)]}),(0,u.jsxs)(`div`,{className:`gz-mail-link-actions gz-connector-picker-actions`,children:[(0,u.jsx)(`button`,{type:`button`,onClick:X,disabled:f===`add`,children:`Cancel`}),P&&(0,u.jsx)(`button`,{type:`button`,className:`primary`,onClick:()=>void $(),disabled:f===`add`,children:f===`add`?`Working…`:he===`oauth2`?`Connect`:`Add`})]})]}),m&&(0,u.jsx)(`p`,{className:`error small`,children:m}),g&&(0,u.jsx)(`p`,{className:`muted small`,children:g}),(0,u.jsx)(o,{open:v!==null,title:`Remove connector?`,message:`This removes the binding and its stored credential. Synced files stay on disk.`,confirmLabel:`Remove`,danger:!0,onConfirm:()=>{v&&de(v)},onCancel:()=>x(null)})]})}export{j as ProjectConnectionsTab};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{t as r}from"./api-C0I7spBl.js";import{_ as i,a,d as o,g as ee,i as s,l as c,m as l,p as u,r as d,s as f,t as te,v as ne,y as re}from"./primitives-CWrGZpPI.js";import{n as ie,t as ae}from"./relative-time-B2kBaekd.js";import{s as oe}from"./gitCopy-Dcjz17cJ.js";import{r as se,t as ce}from"./useGitSync-DOt-ODiw.js";var p=e(t(),1),m=n(),le=`Active — the Meester nudges the voorman, phase handoffs auto-start, and scheduled tasks tick. Read-only or Inactive — ambient gezel work pauses. Chat still works.`,ue=`Whether Gezel-managed tools and background work may create, edit, and delete files in this project's workspace. Internal workspaces default to on; a project opened from an existing folder defaults to off (turning it on asks for confirmation first). Provider-native access such as Codex is shown separately.`,h=[{value:`plan`,label:`Plan`,hint:`Read and reason without changing workspace files.`},{value:`edit`,label:`Edit`,hint:`Edit inside the workspace; deny boundary crossings.`},{value:`reviewed`,label:`Reviewed`,hint:`Edit in the workspace; send boundary crossings to an independent Codex reviewer.`},{value:`full`,label:`Full`,hint:`Run without Codex sandboxing or approvals. Gezel still blocks a narrow set of unmistakably destructive commands.`}],de=[{value:`plan`,label:`Plan`,hint:`Read and reason without changing workspace files.`},{value:`default`,label:`Ask`,hint:`Let Claude request permission for tool use.`},{value:`acceptEdits`,label:`Edit`,hint:`Auto-approve file edits; gate shell commands.`},{value:`bypassPermissions`,label:`Full`,hint:`Bypass Claude permission prompts, including for shell commands.`}];function fe(e){let t=h.find(t=>t.value===e);return`Codex ${t?.label??e}: ${t?.hint??``}`}function pe(e){if(e===`mixed`)return`Claude: assigned gezels currently use different permission modes.`;let t=de.find(t=>t.value===e);return`Claude ${t?.label??e}: ${t?.hint??``}`}var me=[{value:`active`,label:`Active`},{value:`stable`,label:`Stable`},{value:`readonly`,label:`Read-only`},{value:`inactive`,label:`Inactive`}];function g({unlocked:e=!1}){return(0,m.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsx)(`rect`,{x:`3`,y:`7`,width:`10`,height:`7`,rx:`1.25`,stroke:`currentColor`,strokeWidth:`1.5`}),e?(0,m.jsx)(`path`,{d:`M5 7V5a3 3 0 0 1 5.75-1.2`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`}):(0,m.jsx)(`path`,{d:`M5 7V5a3 3 0 0 1 6 0v2`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`})]})}function he(){return(0,m.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsx)(`rect`,{x:`3`,y:`1.75`,width:`10`,height:`12.5`,rx:`1.5`,stroke:`currentColor`,strokeWidth:`1.1`}),(0,m.jsx)(`line`,{x1:`5.2`,y1:`5`,x2:`10.8`,y2:`5`,stroke:`currentColor`,strokeWidth:`1`,strokeLinecap:`round`,opacity:`0.35`}),(0,m.jsx)(`line`,{x1:`5.2`,y1:`7.5`,x2:`10.8`,y2:`7.5`,stroke:`currentColor`,strokeWidth:`1`,strokeLinecap:`round`,opacity:`0.35`}),(0,m.jsx)(`line`,{x1:`5.2`,y1:`10`,x2:`9.4`,y2:`10`,stroke:`currentColor`,strokeWidth:`1`,strokeLinecap:`round`,opacity:`0.35`}),(0,m.jsx)(`line`,{className:`project-index-scanline`,x1:`4.4`,y1:`4.2`,x2:`11.6`,y2:`4.2`,strokeWidth:`1.3`,strokeLinecap:`round`})]})}function ge(){return(0,m.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsxs)(`g`,{className:`project-index-quill-feather`,children:[(0,m.jsx)(`path`,{d:`M13 2.5C10.2 3.4 7.4 5.7 6 8.7L5.1 10.9L7.3 10C10.3 8.6 12.1 5.4 13 2.5Z`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinejoin:`round`}),(0,m.jsx)(`path`,{d:`M11.6 3.9L6.6 9.4`,stroke:`currentColor`,strokeWidth:`0.9`,opacity:`0.45`}),(0,m.jsx)(`path`,{d:`M5.1 10.9L4.2 12.1`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`})]}),(0,m.jsx)(`path`,{className:`project-index-quill-line`,d:`M3.4 13.9H12.4`,strokeWidth:`1.3`,strokeLinecap:`round`})]})}function _e({projectStatus:e,statusLocked:t,onStatusChange:n,managedWritesOn:r,onManagedWorkspaceWritesChange:a,codexMode:o,onCodexModeChange:s,claudeMode:c,onClaudeModeChange:l}){let[u,d]=(0,p.useState)(!1);return!n&&!s&&!l&&(!a||r)?null:(0,m.jsx)(`div`,{className:`project-controls-overflow`,children:(0,m.jsxs)(i,{open:u,onOpenChange:d,children:[(0,m.jsx)(ne,{asChild:!0,children:(0,m.jsx)(`button`,{type:`button`,className:`project-controls-overflow-trigger`,title:`More project controls`,"aria-label":`More project controls`,children:`…`})}),(0,m.jsx)(ee,{className:`project-controls-overflow-popover`,side:`top`,align:`end`,children:(0,m.jsxs)(`fieldset`,{className:`project-controls-overflow-fieldset`,children:[(0,m.jsx)(`legend`,{className:`sr-only`,children:`Project controls overflow`}),n&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Project status`}),(0,m.jsx)(`div`,{className:`project-controls-overflow-options`,children:me.map(r=>(0,m.jsxs)(`button`,{type:`button`,className:`project-controls-overflow-item project-status-select-${r.value}`,"aria-pressed":e===r.value,disabled:t,onClick:()=>{n(r.value),d(!1)},children:[(0,m.jsx)(`span`,{className:`project-status-select-dot`,"aria-hidden":!0}),(0,m.jsx)(`span`,{children:r.label})]},r.value))})]}),a&&!r&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Built-in tools`}),(0,m.jsxs)(`button`,{type:`button`,className:`project-controls-overflow-item`,onClick:()=>{a(!0),d(!1)},children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:!0})}),(0,m.jsx)(`span`,{children:`Allow workspace edits`})]})]}),o&&s&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Codex access`}),(0,m.jsx)(`div`,{className:`project-controls-overflow-options`,children:h.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-controls-overflow-item`,"aria-pressed":o===e.value,title:e.hint,onClick:()=>{s(e.value),d(!1)},children:e.label},e.value))})]}),c&&l&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Claude access`}),(0,m.jsx)(`div`,{className:`project-controls-overflow-options`,children:de.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-controls-overflow-item`,"aria-pressed":c===e.value,title:e.hint,onClick:()=>{l(e.value),d(!1)},children:e.label},e.value))})]})]})})]})})}function _({projectId:e,compact:t=!1,managedWorkspaceWritable:n=!0,onManagedWorkspaceWritesChange:_,codexMode:v,onCodexModeChange:Se,claudeMode:y,onClaudeModeChange:b,onOpenGitHub:x,onAddBoekwachter:S,status:C,statusLocked:w=!1,onStatusChange:T}){let[E,Ce]=(0,p.useState)(null),[D,we]=(0,p.useState)(null),[O,Te]=(0,p.useState)(null),[k,A]=(0,p.useState)(!1),[Ee,De]=(0,p.useState)(!1),[Oe,ke]=(0,p.useState)(``),[Ae,j]=(0,p.useState)(``),[M,je]=(0,p.useState)(null),[Me,Ne]=(0,p.useState)(!1),[N,Pe]=(0,p.useState)(!1),[Fe,P]=(0,p.useState)(null),[F,I]=(0,p.useState)(`idle`),[L,R]=(0,p.useState)(`idle`),[z,B]=(0,p.useState)(null),[V,Ie]=(0,p.useState)(!1),H=(0,p.useRef)(null),U=n,W=(0,p.useCallback)(async()=>{try{let t=await r.getProjectGitStatus(e);Ce(t)}catch{}},[e]),G=(0,p.useCallback)(async()=>{try{we(await r.getProjectIndexStatus(e))}catch{}},[e]);(0,p.useEffect)(()=>{W(),G();let e=window.setInterval(()=>{W(),G()},3e4);return()=>window.clearInterval(e)},[W,G]);let Le=D?.aiDrive!=null||F!==`idle`;(0,p.useEffect)(()=>{if(!Le)return;let e=window.setInterval(()=>void G(),5e3);return()=>window.clearInterval(e)},[Le,G]),(0,p.useEffect)(()=>{let t=t=>{t.detail?.projectId===e&&W()};return window.addEventListener(ce,t),()=>window.removeEventListener(ce,t)},[e,W]);let K=(0,p.useRef)(null),[Re,ze]=(0,p.useState)(!1);(0,p.useEffect)(()=>{let e=D?.enrichment?.pending;if(e===void 0||e<=0||D?.aiDrive){K.current=null,ze(!1);return}let t=K.current;if(K.current={pending:e,at:Date.now()},!t)return;let n=Date.now()-t.at;if(n<2e4)return;let r=t.pending-e,i=r>0?r/n:5/12e4;ze(e/i>1440*60*1e3)},[D]);let Be=(0,p.useCallback)(async()=>{if(!(N||D===null||D.state===`disabled`||D.state===`indexing`)){Pe(!0),P(null);try{await r.refreshProjectIndex(e),we(e=>e?{...e,state:`indexing`}:{state:`indexing`}),window.setTimeout(()=>void G(),800)}catch{P(`Couldn’t start the index update. Try again.`)}finally{Pe(!1)}}},[N,D,e,G]),Ve=(0,p.useRef)(null),He=(0,p.useCallback)(async()=>{if(!(F!==`idle`||D===null||D.state===`disabled`||D.aiDrive!=null)){I(`starting`),B(null),Ve.current=D;try{let t=await r.driveIndexEnrichment(e,{intensity:`full`});if(t.mode===`embed-only`){B({code:`boekwachter-required`,message:t.hint??``}),I(`idle`),window.setTimeout(()=>void G(),800);return}I(`running`),window.setTimeout(()=>void G(),800)}catch(e){let t=e&&typeof e==`object`&&`details`in e?e.details:void 0;B({code:t?.error,message:t?.message??`Couldn’t start the full scan. Try again.`}),I(`idle`)}}},[F,D,e,G]),Ue=(0,p.useCallback)(async()=>{if(L===`idle`){R(`requesting`),B(null);try{await r.stopIndexEnrichment(e),R(`stopping`),window.setTimeout(()=>void G(),800)}catch{R(`idle`),B({message:`Couldn’t stop the scan. Try again.`})}}},[L,e,G]),We=(0,p.useCallback)(async()=>{if(!(!S||V)){Ie(!0);try{await S(),B(null)}catch(e){B({message:e instanceof Error?e.message:`Couldn’t add the Boekwachter. Try again.`})}finally{Ie(!1)}}},[V,S]);(0,p.useEffect)(()=>{F===`running`&&D!==Ve.current&&D!==null&&D.aiDrive==null&&I(`idle`)},[F,D]),(0,p.useEffect)(()=>{L!==`idle`&&D!==null&&D.aiDrive==null&&R(`idle`)},[L,D]),(0,p.useEffect)(()=>{if(!k)return;let e=e=>{H.current&&!H.current.contains(e.target)&&(A(!1),De(!1))};return document.addEventListener(`mousedown`,e),()=>document.removeEventListener(`mousedown`,e)},[k]),(0,p.useEffect)(()=>{!k||O||r.listProjectGitBranches(e).then(Te).catch(()=>Te({local:[],remote:[]}))},[k,O,e]);let q=(0,p.useCallback)((e,t)=>{je({kind:e,text:t}),window.setTimeout(()=>je(null),4e3)},[]),{sync:Ge,syncing:Ke}=se(e,{onToast:q,onNeedsSave:()=>{q(`err`,`Save your changes first — they’re waiting in the GitHub tab.`),x?.()},onConflicts:()=>x?.(),onAuth:()=>x?.()}),qe=(0,p.useCallback)(async()=>{await Ge(),await W()},[Ge,W]),Je=(0,p.useCallback)(async t=>{A(!1),j(`branch`);try{await r.setProjectGitBranch(e,t),await W(),q(`ok`,`Switched to ${t}.`)}catch(e){q(`err`,`Couldn’t switch: ${e instanceof Error?e.message:String(e)}`)}finally{j(``)}},[e,W,q]),Ye=(0,p.useCallback)(async t=>{t.preventDefault();let n=Oe.trim();if(n){A(!1),De(!1),ke(``),j(`branch`);try{await r.createProjectGitBranch(e,n),Te(null),await W(),q(`ok`,`Created and switched to ${n}.`)}catch(e){q(`err`,`Couldn’t create: ${e instanceof Error?e.message:String(e)}`)}finally{j(``)}}},[Oe,e,W,q]),Xe=!!E?.github,Ze=E?.branch,J=E?.github?.lastSyncedAt,Y=D?.state??`never`,X=D?.aiScanPending===!0,Qe=D?.embeddings?.status,$e=Qe===`disabled`||Qe===`unavailable`||D?.enrichment?.vectorsAvailable===!1,et=D?.embeddings?.reason??(D?.enrichment?.vectorsAvailable===!1?`the vector extension failed to load`:`the embedding model could not be loaded`),tt=Y===`disabled`?`disabled`:Y===`indexing`?`indexing`:Y===`fresh`?X||$e?`scan`:`fresh`:`stale`,Z=D?.enrichment,nt=Z?.searchReady??Z?.embedded??0;Z&&ve(nt,Z.eligible);let rt=Z?.skipped??0,it=Z?.skippedFiles??[],at=Math.max(0,rt-it.length),ot=Z?`${Z.summarized} of ${Z.eligible} files${rt>0?` · ${rt} skipped after repeated failures`:``}`:``,Q=Z?ye(Z):null,$=D?.aiDrive??null,st=D===null?`Checking workspace index`:Y===`disabled`?`Workspace indexing is off`:Y===`indexing`?`Scanning workspace`:Y===`never`?`Workspace not indexed`:Y===`stale`?`Workspace scan is out of date`:X?Q===null?`AI indexing is pending`:`AI indexing ${Q}% complete`:`Workspace index is ready`,ct=`Indexing status: ${st}`,lt=D===null||Y===`disabled`||Y===`indexing`||N,ut=E?oe({mergeInProgress:E.mergeInProgress,changesCount:E.changesCount,ahead:E.ahead,behind:E.behind,syncStale:E.syncStale}):``,dt=E?.mergeInProgress===!0||(E?.changesCount??0)>0||(E?.ahead??0)>0||(E?.behind??0)>0||E?.syncStale===!0,ft=E?.syncStale===!0||(E?.ahead??0)>0||(E?.behind??0)>0;return(0,m.jsxs)(`div`,{className:`project-git-status-bar${t?` is-compact`:``}`,children:[(0,m.jsxs)(`div`,{className:`project-git-status-bar-left`,children:[Xe&&(0,m.jsxs)(m.Fragment,{children:[(0,m.jsxs)(`div`,{className:`project-git-branch-picker`,ref:H,children:[(0,m.jsxs)(`button`,{type:`button`,className:`project-git-branch-chip`,onClick:()=>A(e=>!e),disabled:!E?.exists,title:`Switch branch`,children:[(0,m.jsx)(`span`,{className:`project-git-icon`,"aria-hidden":!0,children:`⎇`}),(0,m.jsx)(`span`,{className:`project-git-branch-name`,children:Ze??`(detached)`}),(0,m.jsx)(re,{className:`project-git-chevron`})]}),k&&(0,m.jsxs)(`div`,{className:`project-git-branch-menu`,role:`menu`,children:[O===null?(0,m.jsx)(`div`,{className:`project-git-branch-loading muted small`,children:`Loading branches…`}):(0,m.jsxs)(m.Fragment,{children:[O.local.length>0&&(0,m.jsxs)(`div`,{className:`project-git-branch-group`,children:[(0,m.jsx)(`div`,{className:`project-git-branch-group-label muted small`,children:`Local`}),O.local.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-git-branch-item${e===Ze?` is-current`:``}`,onClick:()=>void Je(e),children:e},`local-${e}`))]}),O.remote.length>0&&(0,m.jsxs)(`div`,{className:`project-git-branch-group`,children:[(0,m.jsx)(`div`,{className:`project-git-branch-group-label muted small`,children:`Remote`}),O.remote.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-git-branch-item`,onClick:()=>void Je(e),children:e},`remote-${e}`))]})]}),(0,m.jsx)(`div`,{className:`project-git-branch-divider`}),Ee?(0,m.jsxs)(`form`,{className:`project-git-new-branch-form`,onSubmit:Ye,children:[(0,m.jsx)(`input`,{value:Oe,onChange:e=>ke(e.target.value),placeholder:`new-branch-name`,autoFocus:!0}),(0,m.jsx)(`button`,{type:`submit`,className:`primary`,children:`Create`})]}):(0,m.jsx)(`button`,{type:`button`,className:`project-git-branch-item project-git-new-branch-trigger`,onClick:()=>De(!0),children:`+ new branch`})]})]}),E&&!t&&(0,m.jsxs)(`button`,{type:`button`,className:`project-git-status-chip${dt?` has-attention`:``}${E.mergeInProgress?` has-conflict`:``}`,onClick:x,title:`Open the GitHub tab`,children:[ut,!dt&&J&&(0,m.jsxs)(`span`,{className:`muted small`,title:ae(J),children:[` `,`· synced `,ie(J,{seconds:!0})]})]})]}),(0,m.jsxs)(i,{open:Me,onOpenChange:e=>{Ne(e),e&&(P(null),G())},children:[(0,m.jsx)(ne,{asChild:!0,children:(0,m.jsxs)(`button`,{type:`button`,className:`project-index-chip project-index-chip-${tt}`,"aria-label":ct,title:`Open indexing status`,children:[(0,m.jsxs)(`svg`,{className:`project-index-icon`,width:`14`,height:`14`,viewBox:`0 0 16 16`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsx)(`rect`,{x:`3`,y:`2`,width:`10.5`,height:`12`,rx:`1.3`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.2`}),(0,m.jsx)(`line`,{x1:`6`,y1:`2`,x2:`6`,y2:`14`,stroke:`currentColor`,strokeWidth:`1.2`}),(0,m.jsx)(`line`,{x1:`8`,y1:`5.5`,x2:`11.5`,y2:`5.5`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`}),(0,m.jsx)(`line`,{x1:`8`,y1:`8`,x2:`11.5`,y2:`8`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`}),(0,m.jsx)(`line`,{x1:`8`,y1:`10.5`,x2:`10.5`,y2:`10.5`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`})]}),(0,m.jsx)(`span`,{className:`project-index-dot`,"aria-hidden":!0})]})}),(0,m.jsx)(ee,{className:`project-index-popover`,side:`top`,align:`center`,"aria-label":`Indexing status`,children:(0,m.jsxs)(`div`,{className:`project-index-panel`,children:[(0,m.jsxs)(`div`,{className:`project-index-panel-heading`,children:[(0,m.jsx)(`span`,{className:`project-index-panel-dot project-index-panel-dot-${tt}`,"aria-hidden":!0}),(0,m.jsx)(`strong`,{children:st}),Y===`indexing`||N?(0,m.jsx)(`span`,{className:`project-index-phase-spinner`,role:`img`,"aria-label":`File scan running`,title:`Reading the workspace file by file`,children:(0,m.jsx)(he,{})}):$!==null||F===`running`?(0,m.jsx)(`span`,{className:`project-index-phase-spinner`,role:`img`,"aria-label":`AI scan running`,title:`Studying files — summaries, reviews, and media`,children:(0,m.jsx)(ge,{})}):null]}),$e&&(0,m.jsxs)(`p`,{className:`project-index-panel-warning`,children:[`Semantic search is off — `,et,`. Results are keyword-only`,Qe===`unavailable`?`; retrying automatically`:``,`.`]}),Z&&Z.eligible>0&&Q!==null&&(0,m.jsxs)(`div`,{className:`project-index-panel-progress`,children:[(0,m.jsxs)(`div`,{className:`project-index-panel-progress-label`,children:[(0,m.jsx)(`span`,{children:`Indexing progress`}),(0,m.jsxs)(`strong`,{children:[Q,`%`]})]}),(0,m.jsx)(`div`,{className:`project-index-panel-progress-track`,role:`progressbar`,"aria-label":`Indexing progress`,"aria-valuemin":0,"aria-valuemax":100,"aria-valuenow":Q,tabIndex:-1,children:(0,m.jsx)(`span`,{style:{width:`${Q}%`}})}),(0,m.jsxs)(`span`,{className:`project-index-panel-caption`,children:[nt,` of `,Z.eligible,` files searchable`,Z.pending>0?` · ${Z.pending} waiting`:``]})]}),(0,m.jsxs)(`dl`,{className:`project-index-panel-details`,children:[(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`File scan`}),(0,m.jsx)(`dd`,{children:be(Y)})]}),D?.meta&&(0,m.jsxs)(m.Fragment,{children:[(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Indexed`}),(0,m.jsxs)(`dd`,{children:[D.meta.fileCount,` file`,D.meta.fileCount===1?``:`s`]})]}),(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Last scan`}),(0,m.jsxs)(`dd`,{title:ae(D.meta.scannedAt),children:[ie(D.meta.scannedAt,{seconds:!0}),` ·`,` `,xe(D.meta.durationMs)]})]})]}),$&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`AI scan`}),(0,m.jsx)(`dd`,{children:$===`full`?`Running at full speed`:`Running quietly in background`})]}),Z&&(Z.shadowsPending??0)>0&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Media scan`}),(0,m.jsxs)(`dd`,{children:[Z.shadowsPending,` waiting`]})]}),Z&&Z.eligible>0&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`AI summaries`}),(0,m.jsx)(`dd`,{children:it.length>0?(0,m.jsx)(d,{delayDuration:150,children:(0,m.jsxs)(s,{children:[(0,m.jsx)(a,{asChild:!0,children:(0,m.jsx)(`button`,{type:`button`,className:`project-index-skipped-trigger`,children:ot})}),(0,m.jsx)(te,{side:`left`,children:(0,m.jsxs)(`div`,{className:`project-index-skipped-tip`,children:[(0,m.jsx)(`strong`,{children:`Skipped after repeated failures`}),(0,m.jsx)(`ul`,{children:it.map(e=>(0,m.jsxs)(`li`,{children:[(0,m.jsx)(`span`,{className:`project-index-skipped-path`,children:e.path}),e.reason&&(0,m.jsx)(`span`,{className:`project-index-skipped-reason`,children:e.reason})]},e.path))}),at>0&&(0,m.jsxs)(`span`,{className:`project-index-skipped-more`,children:[`and `,at,` more`]}),(0,m.jsx)(`span`,{className:`project-index-skipped-note`,children:`Each retries once its content changes.`})]})})]})}):ot})]}),Z?.reviews&&Z.reviews.eligible>0&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Quality review`}),(0,m.jsxs)(`dd`,{children:[Z.reviews.reviewed,` of `,Z.reviews.eligible,Z.reviews.pending>0?` · ${Z.reviews.pending} waiting`:``,Z.reviews.stale>0?` · ${Z.reviews.stale} to refresh`:``]})]})]}),(0,m.jsxs)(`div`,{className:`project-index-panel-footer`,children:[(0,m.jsx)(`span`,{className:`project-index-panel-note`,children:Y===`disabled`?(0,m.jsxs)(m.Fragment,{children:[`Workspace indexing is off.`,` `,(0,m.jsx)(`button`,{type:`button`,className:`project-index-panel-link`,onClick:()=>window.dispatchEvent(new CustomEvent(`gezel:open-project-settings`,{detail:{projectId:e}})),children:`Turn it on in Project Settings`}),`.`]}):$===`full`?`Full scan in progress — it shares the model with chat, so counts move as calls finish.`:$===`background`?`Background scan in progress — it politely waits while you chat.`:Y===`indexing`?`The status updates automatically while the scan runs.`:X&&Re?(0,m.jsxs)(m.Fragment,{children:[`At the idle pace this will take more than a day.`,` `,(0,m.jsx)(`button`,{type:`button`,className:`project-index-panel-link`,onClick:()=>window.dispatchEvent(new CustomEvent(`gezel:open-night-shift`)),children:`Set up Night Shift`}),` `,`or use “Start full AI scan” to finish sooner.`]}):X?`AI indexing continues while the app is idle.`:`Refresh the index whenever you need the latest workspace state.`}),(0,m.jsxs)(`div`,{className:`project-index-panel-actions`,children:[$!==null||F===`running`?(0,m.jsx)(`button`,{type:`button`,className:`project-index-update-button`,disabled:L!==`idle`,onClick:()=>void Ue(),title:`Stop the running scan at its next step. Everything indexed so far is kept.`,children:L===`idle`?`Stop updating index`:`Stopping…`}):(0,m.jsx)(`button`,{type:`button`,className:`project-index-update-button`,disabled:lt,onClick:()=>void Be(),children:Y===`indexing`||N?`Updating index…`:`Update index`}),Y!==`disabled`&&(0,m.jsx)(`button`,{type:`button`,className:`project-index-update-button project-index-full-scan-button`,disabled:F!==`idle`||$!==null||D===null,onClick:()=>void He(),title:`Bring the whole index up to date at full speed — file scan plus AI summaries, rollups, and reviews, run to completion. Shares the model with chat while it works.`,children:F===`starting`?`Starting full scan…`:F===`running`||$===`full`?`Full scan running…`:$===`background`?`Background scan running…`:`Start full AI scan`})]}),Fe&&(0,m.jsx)(`span`,{className:`project-index-panel-error`,role:`alert`,children:Fe}),z&&(0,m.jsx)(`span`,{className:`project-index-panel-error`,role:`alert`,children:z.code===`boekwachter-required`&&S?(0,m.jsxs)(m.Fragment,{children:[(0,m.jsx)(`button`,{type:`button`,className:`project-index-panel-error-link`,disabled:V,onClick:()=>void We(),children:V?`Adding Boekwachter…`:`Add a Boekwachter to this project crew`}),` `,`to enable AI summaries, reviews, and semantic enrichment.`]}):z.message})]})]})})]}),(0,m.jsxs)(`div`,{className:`project-controls-inline`,children:[T&&(0,m.jsxs)(o,{value:C??`active`,disabled:w,onValueChange:e=>T(e),children:[(0,m.jsxs)(u,{className:`project-status-select project-status-select-${C??`active`}`,title:w?`Archived projects are inactive. Restore this project to change its status.`:le,"aria-label":`Project status`,children:[(0,m.jsx)(`span`,{className:`project-status-select-dot`,"aria-hidden":!0}),(0,m.jsx)(l,{})]}),(0,m.jsx)(f,{children:me.map(e=>(0,m.jsx)(c,{value:e.value,children:e.label},e.value))})]}),_&&(!t||!U)&&(0,m.jsxs)(o,{value:U?`on`:`off`,onValueChange:e=>_(e===`on`),children:[(0,m.jsxs)(u,{className:`project-writes-select project-writes-select-${U?`on`:`off`}`,title:ue,"aria-label":`Built-in tool workspace access for this project`,children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:U})}),(0,m.jsx)(l,{})]}),(0,m.jsxs)(f,{children:[(0,m.jsx)(c,{value:`on`,children:`Can edit`}),(0,m.jsx)(c,{value:`off`,children:`Read-only`})]})]}),v&&Se&&(0,m.jsxs)(o,{value:v,onValueChange:e=>Se(e),children:[(0,m.jsxs)(u,{className:`project-writes-select project-codex-mode project-codex-mode-${v}`,title:fe(v),"aria-label":`Codex execution mode for this project`,children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:v!==`plan`})}),(0,m.jsx)(`span`,{className:`project-permission-scope`,children:`Codex:`}),(0,m.jsx)(l,{})]}),(0,m.jsx)(f,{children:h.map(e=>(0,m.jsx)(c,{value:e.value,textValue:e.label,children:e.label},e.value))})]}),y&&b&&(0,m.jsxs)(o,{value:y,onValueChange:e=>{e!==`mixed`&&b(e)},children:[(0,m.jsxs)(u,{className:`project-writes-select project-claude-mode project-claude-mode-${y}`,title:pe(y),"aria-label":`Claude execution mode for this project`,children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:y!==`plan`&&y!==`mixed`})}),(0,m.jsx)(`span`,{className:`project-permission-scope`,children:`Claude:`}),(0,m.jsx)(l,{})]}),(0,m.jsxs)(f,{children:[y===`mixed`&&(0,m.jsx)(c,{value:`mixed`,disabled:!0,children:`Mixed`}),de.map(e=>(0,m.jsx)(c,{value:e.value,textValue:e.label,children:e.label},e.value))]})]})]}),t&&(0,m.jsx)(_e,{projectStatus:C??`active`,statusLocked:w,onStatusChange:T,managedWritesOn:U,onManagedWorkspaceWritesChange:_,codexMode:v,onCodexModeChange:Se,claudeMode:y,onClaudeModeChange:b}),!_&&!U&&(0,m.jsxs)(`span`,{className:`project-lockdown-chip`,title:`Managed workspace edits are off for this project. Enable "Allow built-in tools and background work to modify the workspace" in Project → Settings.`,"aria-label":`Built-in tool workspace access is read-only for this project.`,children:[(0,m.jsx)(`span`,{className:`project-lockdown-chip-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{})}),(0,m.jsx)(`span`,{className:`project-lockdown-chip-label`,children:`edits off`})]})]}),!t&&(0,m.jsx)(`div`,{className:`project-git-status-bar-right`,children:Xe&&(0,m.jsx)(`button`,{type:`button`,className:`project-git-action${ft?` primary`:``}`,onClick:()=>void qe(),disabled:Ke||Ae!==``,title:`Get new changes from GitHub and send yours`,children:Ke?`Syncing…`:`Sync`})}),M&&(0,m.jsx)(`output`,{className:`project-git-toast project-git-toast-${M.kind}`,children:M.text})]})}function ve(e,t){return t<=0?null:Math.round(Math.min(Math.max(e,0),t)/t*100)}function ye(e){let t=[[e.summarized,e.eligible],[e.embedded,e.eligible]];e.reviews&&t.push([e.reviews.reviewed,e.reviews.eligible]);let n=0,r=0;for(let[e,i]of t)i<=0||(n+=Math.min(Math.max(e,0),i),r+=i);return r>0?Math.round(n/r*100):null}function be(e){switch(e){case`fresh`:return`Up to date`;case`stale`:return`Needs a rescan`;case`indexing`:return`Scanning now`;case`never`:return`Not scanned yet`;case`disabled`:return`Off for this project`}}function xe(e){if(e<1e3)return`${Math.max(1,Math.round(e))}ms`;if(e<6e4)return`${(e/1e3).toFixed(+(e<1e4))}s`;let t=Math.floor(e/6e4),n=Math.round(e%6e4/1e3);return n>0?`${t}m ${n}s`:`${t}m`}export{_ as t};
|
|
1
|
+
import{i as e}from"./rolldown-runtime-aKtaBQYM.js";import{n as t,t as n}from"./jsx-runtime-CEpd2cAX.js";import{t as r}from"./api-CmrgM5Rf.js";import{_ as i,a,d as o,g as ee,i as s,l as c,m as l,p as u,r as d,s as f,t as te,v as ne,y as re}from"./primitives-CWrGZpPI.js";import{n as ie,t as ae}from"./relative-time-B2kBaekd.js";import{s as oe}from"./gitCopy-Dcjz17cJ.js";import{r as se,t as ce}from"./useGitSync-7m9YA7h5.js";var p=e(t(),1),m=n(),le=`Active — the Meester nudges the voorman, phase handoffs auto-start, and scheduled tasks tick. Read-only or Inactive — ambient gezel work pauses. Chat still works.`,ue=`Whether Gezel-managed tools and background work may create, edit, and delete files in this project's workspace. Internal workspaces default to on; a project opened from an existing folder defaults to off (turning it on asks for confirmation first). Provider-native access such as Codex is shown separately.`,h=[{value:`plan`,label:`Plan`,hint:`Read and reason without changing workspace files.`},{value:`edit`,label:`Edit`,hint:`Edit inside the workspace; deny boundary crossings.`},{value:`reviewed`,label:`Reviewed`,hint:`Edit in the workspace; send boundary crossings to an independent Codex reviewer.`},{value:`full`,label:`Full`,hint:`Run without Codex sandboxing or approvals. Gezel still blocks a narrow set of unmistakably destructive commands.`}],de=[{value:`plan`,label:`Plan`,hint:`Read and reason without changing workspace files.`},{value:`default`,label:`Ask`,hint:`Let Claude request permission for tool use.`},{value:`acceptEdits`,label:`Edit`,hint:`Auto-approve file edits; gate shell commands.`},{value:`bypassPermissions`,label:`Full`,hint:`Bypass Claude permission prompts, including for shell commands.`}];function fe(e){let t=h.find(t=>t.value===e);return`Codex ${t?.label??e}: ${t?.hint??``}`}function pe(e){if(e===`mixed`)return`Claude: assigned gezels currently use different permission modes.`;let t=de.find(t=>t.value===e);return`Claude ${t?.label??e}: ${t?.hint??``}`}var me=[{value:`active`,label:`Active`},{value:`stable`,label:`Stable`},{value:`readonly`,label:`Read-only`},{value:`inactive`,label:`Inactive`}];function g({unlocked:e=!1}){return(0,m.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsx)(`rect`,{x:`3`,y:`7`,width:`10`,height:`7`,rx:`1.25`,stroke:`currentColor`,strokeWidth:`1.5`}),e?(0,m.jsx)(`path`,{d:`M5 7V5a3 3 0 0 1 5.75-1.2`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`}):(0,m.jsx)(`path`,{d:`M5 7V5a3 3 0 0 1 6 0v2`,stroke:`currentColor`,strokeWidth:`1.5`,strokeLinecap:`round`})]})}function he(){return(0,m.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsx)(`rect`,{x:`3`,y:`1.75`,width:`10`,height:`12.5`,rx:`1.5`,stroke:`currentColor`,strokeWidth:`1.1`}),(0,m.jsx)(`line`,{x1:`5.2`,y1:`5`,x2:`10.8`,y2:`5`,stroke:`currentColor`,strokeWidth:`1`,strokeLinecap:`round`,opacity:`0.35`}),(0,m.jsx)(`line`,{x1:`5.2`,y1:`7.5`,x2:`10.8`,y2:`7.5`,stroke:`currentColor`,strokeWidth:`1`,strokeLinecap:`round`,opacity:`0.35`}),(0,m.jsx)(`line`,{x1:`5.2`,y1:`10`,x2:`9.4`,y2:`10`,stroke:`currentColor`,strokeWidth:`1`,strokeLinecap:`round`,opacity:`0.35`}),(0,m.jsx)(`line`,{className:`project-index-scanline`,x1:`4.4`,y1:`4.2`,x2:`11.6`,y2:`4.2`,strokeWidth:`1.3`,strokeLinecap:`round`})]})}function ge(){return(0,m.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsxs)(`g`,{className:`project-index-quill-feather`,children:[(0,m.jsx)(`path`,{d:`M13 2.5C10.2 3.4 7.4 5.7 6 8.7L5.1 10.9L7.3 10C10.3 8.6 12.1 5.4 13 2.5Z`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinejoin:`round`}),(0,m.jsx)(`path`,{d:`M11.6 3.9L6.6 9.4`,stroke:`currentColor`,strokeWidth:`0.9`,opacity:`0.45`}),(0,m.jsx)(`path`,{d:`M5.1 10.9L4.2 12.1`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`})]}),(0,m.jsx)(`path`,{className:`project-index-quill-line`,d:`M3.4 13.9H12.4`,strokeWidth:`1.3`,strokeLinecap:`round`})]})}function _e({projectStatus:e,statusLocked:t,onStatusChange:n,managedWritesOn:r,onManagedWorkspaceWritesChange:a,codexMode:o,onCodexModeChange:s,claudeMode:c,onClaudeModeChange:l}){let[u,d]=(0,p.useState)(!1);return!n&&!s&&!l&&(!a||r)?null:(0,m.jsx)(`div`,{className:`project-controls-overflow`,children:(0,m.jsxs)(i,{open:u,onOpenChange:d,children:[(0,m.jsx)(ne,{asChild:!0,children:(0,m.jsx)(`button`,{type:`button`,className:`project-controls-overflow-trigger`,title:`More project controls`,"aria-label":`More project controls`,children:`…`})}),(0,m.jsx)(ee,{className:`project-controls-overflow-popover`,side:`top`,align:`end`,children:(0,m.jsxs)(`fieldset`,{className:`project-controls-overflow-fieldset`,children:[(0,m.jsx)(`legend`,{className:`sr-only`,children:`Project controls overflow`}),n&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Project status`}),(0,m.jsx)(`div`,{className:`project-controls-overflow-options`,children:me.map(r=>(0,m.jsxs)(`button`,{type:`button`,className:`project-controls-overflow-item project-status-select-${r.value}`,"aria-pressed":e===r.value,disabled:t,onClick:()=>{n(r.value),d(!1)},children:[(0,m.jsx)(`span`,{className:`project-status-select-dot`,"aria-hidden":!0}),(0,m.jsx)(`span`,{children:r.label})]},r.value))})]}),a&&!r&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Built-in tools`}),(0,m.jsxs)(`button`,{type:`button`,className:`project-controls-overflow-item`,onClick:()=>{a(!0),d(!1)},children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:!0})}),(0,m.jsx)(`span`,{children:`Allow workspace edits`})]})]}),o&&s&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Codex access`}),(0,m.jsx)(`div`,{className:`project-controls-overflow-options`,children:h.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-controls-overflow-item`,"aria-pressed":o===e.value,title:e.hint,onClick:()=>{s(e.value),d(!1)},children:e.label},e.value))})]}),c&&l&&(0,m.jsxs)(`section`,{className:`project-controls-overflow-section`,children:[(0,m.jsx)(`span`,{className:`project-controls-overflow-label`,children:`Claude access`}),(0,m.jsx)(`div`,{className:`project-controls-overflow-options`,children:de.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-controls-overflow-item`,"aria-pressed":c===e.value,title:e.hint,onClick:()=>{l(e.value),d(!1)},children:e.label},e.value))})]})]})})]})})}function _({projectId:e,compact:t=!1,managedWorkspaceWritable:n=!0,onManagedWorkspaceWritesChange:_,codexMode:v,onCodexModeChange:Se,claudeMode:y,onClaudeModeChange:b,onOpenGitHub:x,onAddBoekwachter:S,status:C,statusLocked:w=!1,onStatusChange:T}){let[E,Ce]=(0,p.useState)(null),[D,we]=(0,p.useState)(null),[O,Te]=(0,p.useState)(null),[k,A]=(0,p.useState)(!1),[Ee,De]=(0,p.useState)(!1),[Oe,ke]=(0,p.useState)(``),[Ae,j]=(0,p.useState)(``),[M,je]=(0,p.useState)(null),[Me,Ne]=(0,p.useState)(!1),[N,Pe]=(0,p.useState)(!1),[Fe,P]=(0,p.useState)(null),[F,I]=(0,p.useState)(`idle`),[L,R]=(0,p.useState)(`idle`),[z,B]=(0,p.useState)(null),[V,Ie]=(0,p.useState)(!1),H=(0,p.useRef)(null),U=n,W=(0,p.useCallback)(async()=>{try{let t=await r.getProjectGitStatus(e);Ce(t)}catch{}},[e]),G=(0,p.useCallback)(async()=>{try{we(await r.getProjectIndexStatus(e))}catch{}},[e]);(0,p.useEffect)(()=>{W(),G();let e=window.setInterval(()=>{W(),G()},3e4);return()=>window.clearInterval(e)},[W,G]);let Le=D?.aiDrive!=null||F!==`idle`;(0,p.useEffect)(()=>{if(!Le)return;let e=window.setInterval(()=>void G(),5e3);return()=>window.clearInterval(e)},[Le,G]),(0,p.useEffect)(()=>{let t=t=>{t.detail?.projectId===e&&W()};return window.addEventListener(ce,t),()=>window.removeEventListener(ce,t)},[e,W]);let K=(0,p.useRef)(null),[Re,ze]=(0,p.useState)(!1);(0,p.useEffect)(()=>{let e=D?.enrichment?.pending;if(e===void 0||e<=0||D?.aiDrive){K.current=null,ze(!1);return}let t=K.current;if(K.current={pending:e,at:Date.now()},!t)return;let n=Date.now()-t.at;if(n<2e4)return;let r=t.pending-e,i=r>0?r/n:5/12e4;ze(e/i>1440*60*1e3)},[D]);let Be=(0,p.useCallback)(async()=>{if(!(N||D===null||D.state===`disabled`||D.state===`indexing`)){Pe(!0),P(null);try{await r.refreshProjectIndex(e),we(e=>e?{...e,state:`indexing`}:{state:`indexing`}),window.setTimeout(()=>void G(),800)}catch{P(`Couldn’t start the index update. Try again.`)}finally{Pe(!1)}}},[N,D,e,G]),Ve=(0,p.useRef)(null),He=(0,p.useCallback)(async()=>{if(!(F!==`idle`||D===null||D.state===`disabled`||D.aiDrive!=null)){I(`starting`),B(null),Ve.current=D;try{let t=await r.driveIndexEnrichment(e,{intensity:`full`});if(t.mode===`embed-only`){B({code:`boekwachter-required`,message:t.hint??``}),I(`idle`),window.setTimeout(()=>void G(),800);return}I(`running`),window.setTimeout(()=>void G(),800)}catch(e){let t=e&&typeof e==`object`&&`details`in e?e.details:void 0;B({code:t?.error,message:t?.message??`Couldn’t start the full scan. Try again.`}),I(`idle`)}}},[F,D,e,G]),Ue=(0,p.useCallback)(async()=>{if(L===`idle`){R(`requesting`),B(null);try{await r.stopIndexEnrichment(e),R(`stopping`),window.setTimeout(()=>void G(),800)}catch{R(`idle`),B({message:`Couldn’t stop the scan. Try again.`})}}},[L,e,G]),We=(0,p.useCallback)(async()=>{if(!(!S||V)){Ie(!0);try{await S(),B(null)}catch(e){B({message:e instanceof Error?e.message:`Couldn’t add the Boekwachter. Try again.`})}finally{Ie(!1)}}},[V,S]);(0,p.useEffect)(()=>{F===`running`&&D!==Ve.current&&D!==null&&D.aiDrive==null&&I(`idle`)},[F,D]),(0,p.useEffect)(()=>{L!==`idle`&&D!==null&&D.aiDrive==null&&R(`idle`)},[L,D]),(0,p.useEffect)(()=>{if(!k)return;let e=e=>{H.current&&!H.current.contains(e.target)&&(A(!1),De(!1))};return document.addEventListener(`mousedown`,e),()=>document.removeEventListener(`mousedown`,e)},[k]),(0,p.useEffect)(()=>{!k||O||r.listProjectGitBranches(e).then(Te).catch(()=>Te({local:[],remote:[]}))},[k,O,e]);let q=(0,p.useCallback)((e,t)=>{je({kind:e,text:t}),window.setTimeout(()=>je(null),4e3)},[]),{sync:Ge,syncing:Ke}=se(e,{onToast:q,onNeedsSave:()=>{q(`err`,`Save your changes first — they’re waiting in the GitHub tab.`),x?.()},onConflicts:()=>x?.(),onAuth:()=>x?.()}),qe=(0,p.useCallback)(async()=>{await Ge(),await W()},[Ge,W]),Je=(0,p.useCallback)(async t=>{A(!1),j(`branch`);try{await r.setProjectGitBranch(e,t),await W(),q(`ok`,`Switched to ${t}.`)}catch(e){q(`err`,`Couldn’t switch: ${e instanceof Error?e.message:String(e)}`)}finally{j(``)}},[e,W,q]),Ye=(0,p.useCallback)(async t=>{t.preventDefault();let n=Oe.trim();if(n){A(!1),De(!1),ke(``),j(`branch`);try{await r.createProjectGitBranch(e,n),Te(null),await W(),q(`ok`,`Created and switched to ${n}.`)}catch(e){q(`err`,`Couldn’t create: ${e instanceof Error?e.message:String(e)}`)}finally{j(``)}}},[Oe,e,W,q]),Xe=!!E?.github,Ze=E?.branch,J=E?.github?.lastSyncedAt,Y=D?.state??`never`,X=D?.aiScanPending===!0,Qe=D?.embeddings?.status,$e=Qe===`disabled`||Qe===`unavailable`||D?.enrichment?.vectorsAvailable===!1,et=D?.embeddings?.reason??(D?.enrichment?.vectorsAvailable===!1?`the vector extension failed to load`:`the embedding model could not be loaded`),tt=Y===`disabled`?`disabled`:Y===`indexing`?`indexing`:Y===`fresh`?X||$e?`scan`:`fresh`:`stale`,Z=D?.enrichment,nt=Z?.searchReady??Z?.embedded??0;Z&&ve(nt,Z.eligible);let rt=Z?.skipped??0,it=Z?.skippedFiles??[],at=Math.max(0,rt-it.length),ot=Z?`${Z.summarized} of ${Z.eligible} files${rt>0?` · ${rt} skipped after repeated failures`:``}`:``,Q=Z?ye(Z):null,$=D?.aiDrive??null,st=D===null?`Checking workspace index`:Y===`disabled`?`Workspace indexing is off`:Y===`indexing`?`Scanning workspace`:Y===`never`?`Workspace not indexed`:Y===`stale`?`Workspace scan is out of date`:X?Q===null?`AI indexing is pending`:`AI indexing ${Q}% complete`:`Workspace index is ready`,ct=`Indexing status: ${st}`,lt=D===null||Y===`disabled`||Y===`indexing`||N,ut=E?oe({mergeInProgress:E.mergeInProgress,changesCount:E.changesCount,ahead:E.ahead,behind:E.behind,syncStale:E.syncStale}):``,dt=E?.mergeInProgress===!0||(E?.changesCount??0)>0||(E?.ahead??0)>0||(E?.behind??0)>0||E?.syncStale===!0,ft=E?.syncStale===!0||(E?.ahead??0)>0||(E?.behind??0)>0;return(0,m.jsxs)(`div`,{className:`project-git-status-bar${t?` is-compact`:``}`,children:[(0,m.jsxs)(`div`,{className:`project-git-status-bar-left`,children:[Xe&&(0,m.jsxs)(m.Fragment,{children:[(0,m.jsxs)(`div`,{className:`project-git-branch-picker`,ref:H,children:[(0,m.jsxs)(`button`,{type:`button`,className:`project-git-branch-chip`,onClick:()=>A(e=>!e),disabled:!E?.exists,title:`Switch branch`,children:[(0,m.jsx)(`span`,{className:`project-git-icon`,"aria-hidden":!0,children:`⎇`}),(0,m.jsx)(`span`,{className:`project-git-branch-name`,children:Ze??`(detached)`}),(0,m.jsx)(re,{className:`project-git-chevron`})]}),k&&(0,m.jsxs)(`div`,{className:`project-git-branch-menu`,role:`menu`,children:[O===null?(0,m.jsx)(`div`,{className:`project-git-branch-loading muted small`,children:`Loading branches…`}):(0,m.jsxs)(m.Fragment,{children:[O.local.length>0&&(0,m.jsxs)(`div`,{className:`project-git-branch-group`,children:[(0,m.jsx)(`div`,{className:`project-git-branch-group-label muted small`,children:`Local`}),O.local.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-git-branch-item${e===Ze?` is-current`:``}`,onClick:()=>void Je(e),children:e},`local-${e}`))]}),O.remote.length>0&&(0,m.jsxs)(`div`,{className:`project-git-branch-group`,children:[(0,m.jsx)(`div`,{className:`project-git-branch-group-label muted small`,children:`Remote`}),O.remote.map(e=>(0,m.jsx)(`button`,{type:`button`,className:`project-git-branch-item`,onClick:()=>void Je(e),children:e},`remote-${e}`))]})]}),(0,m.jsx)(`div`,{className:`project-git-branch-divider`}),Ee?(0,m.jsxs)(`form`,{className:`project-git-new-branch-form`,onSubmit:Ye,children:[(0,m.jsx)(`input`,{value:Oe,onChange:e=>ke(e.target.value),placeholder:`new-branch-name`,autoFocus:!0}),(0,m.jsx)(`button`,{type:`submit`,className:`primary`,children:`Create`})]}):(0,m.jsx)(`button`,{type:`button`,className:`project-git-branch-item project-git-new-branch-trigger`,onClick:()=>De(!0),children:`+ new branch`})]})]}),E&&!t&&(0,m.jsxs)(`button`,{type:`button`,className:`project-git-status-chip${dt?` has-attention`:``}${E.mergeInProgress?` has-conflict`:``}`,onClick:x,title:`Open the GitHub tab`,children:[ut,!dt&&J&&(0,m.jsxs)(`span`,{className:`muted small`,title:ae(J),children:[` `,`· synced `,ie(J,{seconds:!0})]})]})]}),(0,m.jsxs)(i,{open:Me,onOpenChange:e=>{Ne(e),e&&(P(null),G())},children:[(0,m.jsx)(ne,{asChild:!0,children:(0,m.jsxs)(`button`,{type:`button`,className:`project-index-chip project-index-chip-${tt}`,"aria-label":ct,title:`Open indexing status`,children:[(0,m.jsxs)(`svg`,{className:`project-index-icon`,width:`14`,height:`14`,viewBox:`0 0 16 16`,"aria-hidden":`true`,focusable:`false`,children:[(0,m.jsx)(`rect`,{x:`3`,y:`2`,width:`10.5`,height:`12`,rx:`1.3`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.2`}),(0,m.jsx)(`line`,{x1:`6`,y1:`2`,x2:`6`,y2:`14`,stroke:`currentColor`,strokeWidth:`1.2`}),(0,m.jsx)(`line`,{x1:`8`,y1:`5.5`,x2:`11.5`,y2:`5.5`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`}),(0,m.jsx)(`line`,{x1:`8`,y1:`8`,x2:`11.5`,y2:`8`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`}),(0,m.jsx)(`line`,{x1:`8`,y1:`10.5`,x2:`10.5`,y2:`10.5`,stroke:`currentColor`,strokeWidth:`1.1`,strokeLinecap:`round`})]}),(0,m.jsx)(`span`,{className:`project-index-dot`,"aria-hidden":!0})]})}),(0,m.jsx)(ee,{className:`project-index-popover`,side:`top`,align:`center`,"aria-label":`Indexing status`,children:(0,m.jsxs)(`div`,{className:`project-index-panel`,children:[(0,m.jsxs)(`div`,{className:`project-index-panel-heading`,children:[(0,m.jsx)(`span`,{className:`project-index-panel-dot project-index-panel-dot-${tt}`,"aria-hidden":!0}),(0,m.jsx)(`strong`,{children:st}),Y===`indexing`||N?(0,m.jsx)(`span`,{className:`project-index-phase-spinner`,role:`img`,"aria-label":`File scan running`,title:`Reading the workspace file by file`,children:(0,m.jsx)(he,{})}):$!==null||F===`running`?(0,m.jsx)(`span`,{className:`project-index-phase-spinner`,role:`img`,"aria-label":`AI scan running`,title:`Studying files — summaries, reviews, and media`,children:(0,m.jsx)(ge,{})}):null]}),$e&&(0,m.jsxs)(`p`,{className:`project-index-panel-warning`,children:[`Semantic search is off — `,et,`. Results are keyword-only`,Qe===`unavailable`?`; retrying automatically`:``,`.`]}),Z&&Z.eligible>0&&Q!==null&&(0,m.jsxs)(`div`,{className:`project-index-panel-progress`,children:[(0,m.jsxs)(`div`,{className:`project-index-panel-progress-label`,children:[(0,m.jsx)(`span`,{children:`Indexing progress`}),(0,m.jsxs)(`strong`,{children:[Q,`%`]})]}),(0,m.jsx)(`div`,{className:`project-index-panel-progress-track`,role:`progressbar`,"aria-label":`Indexing progress`,"aria-valuemin":0,"aria-valuemax":100,"aria-valuenow":Q,tabIndex:-1,children:(0,m.jsx)(`span`,{style:{width:`${Q}%`}})}),(0,m.jsxs)(`span`,{className:`project-index-panel-caption`,children:[nt,` of `,Z.eligible,` files searchable`,Z.pending>0?` · ${Z.pending} waiting`:``]})]}),(0,m.jsxs)(`dl`,{className:`project-index-panel-details`,children:[(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`File scan`}),(0,m.jsx)(`dd`,{children:be(Y)})]}),D?.meta&&(0,m.jsxs)(m.Fragment,{children:[(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Indexed`}),(0,m.jsxs)(`dd`,{children:[D.meta.fileCount,` file`,D.meta.fileCount===1?``:`s`]})]}),(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Last scan`}),(0,m.jsxs)(`dd`,{title:ae(D.meta.scannedAt),children:[ie(D.meta.scannedAt,{seconds:!0}),` ·`,` `,xe(D.meta.durationMs)]})]})]}),$&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`AI scan`}),(0,m.jsx)(`dd`,{children:$===`full`?`Running at full speed`:`Running quietly in background`})]}),Z&&(Z.shadowsPending??0)>0&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Media scan`}),(0,m.jsxs)(`dd`,{children:[Z.shadowsPending,` waiting`]})]}),Z&&Z.eligible>0&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`AI summaries`}),(0,m.jsx)(`dd`,{children:it.length>0?(0,m.jsx)(d,{delayDuration:150,children:(0,m.jsxs)(s,{children:[(0,m.jsx)(a,{asChild:!0,children:(0,m.jsx)(`button`,{type:`button`,className:`project-index-skipped-trigger`,children:ot})}),(0,m.jsx)(te,{side:`left`,children:(0,m.jsxs)(`div`,{className:`project-index-skipped-tip`,children:[(0,m.jsx)(`strong`,{children:`Skipped after repeated failures`}),(0,m.jsx)(`ul`,{children:it.map(e=>(0,m.jsxs)(`li`,{children:[(0,m.jsx)(`span`,{className:`project-index-skipped-path`,children:e.path}),e.reason&&(0,m.jsx)(`span`,{className:`project-index-skipped-reason`,children:e.reason})]},e.path))}),at>0&&(0,m.jsxs)(`span`,{className:`project-index-skipped-more`,children:[`and `,at,` more`]}),(0,m.jsx)(`span`,{className:`project-index-skipped-note`,children:`Each retries once its content changes.`})]})})]})}):ot})]}),Z?.reviews&&Z.reviews.eligible>0&&(0,m.jsxs)(`div`,{children:[(0,m.jsx)(`dt`,{children:`Quality review`}),(0,m.jsxs)(`dd`,{children:[Z.reviews.reviewed,` of `,Z.reviews.eligible,Z.reviews.pending>0?` · ${Z.reviews.pending} waiting`:``,Z.reviews.stale>0?` · ${Z.reviews.stale} to refresh`:``]})]})]}),(0,m.jsxs)(`div`,{className:`project-index-panel-footer`,children:[(0,m.jsx)(`span`,{className:`project-index-panel-note`,children:Y===`disabled`?(0,m.jsxs)(m.Fragment,{children:[`Workspace indexing is off.`,` `,(0,m.jsx)(`button`,{type:`button`,className:`project-index-panel-link`,onClick:()=>window.dispatchEvent(new CustomEvent(`gezel:open-project-settings`,{detail:{projectId:e}})),children:`Turn it on in Project Settings`}),`.`]}):$===`full`?`Full scan in progress — it shares the model with chat, so counts move as calls finish.`:$===`background`?`Background scan in progress — it politely waits while you chat.`:Y===`indexing`?`The status updates automatically while the scan runs.`:X&&Re?(0,m.jsxs)(m.Fragment,{children:[`At the idle pace this will take more than a day.`,` `,(0,m.jsx)(`button`,{type:`button`,className:`project-index-panel-link`,onClick:()=>window.dispatchEvent(new CustomEvent(`gezel:open-night-shift`)),children:`Set up Night Shift`}),` `,`or use “Start full AI scan” to finish sooner.`]}):X?`AI indexing continues while the app is idle.`:`Refresh the index whenever you need the latest workspace state.`}),(0,m.jsxs)(`div`,{className:`project-index-panel-actions`,children:[$!==null||F===`running`?(0,m.jsx)(`button`,{type:`button`,className:`project-index-update-button`,disabled:L!==`idle`,onClick:()=>void Ue(),title:`Stop the running scan at its next step. Everything indexed so far is kept.`,children:L===`idle`?`Stop updating index`:`Stopping…`}):(0,m.jsx)(`button`,{type:`button`,className:`project-index-update-button`,disabled:lt,onClick:()=>void Be(),children:Y===`indexing`||N?`Updating index…`:`Update index`}),Y!==`disabled`&&(0,m.jsx)(`button`,{type:`button`,className:`project-index-update-button project-index-full-scan-button`,disabled:F!==`idle`||$!==null||D===null,onClick:()=>void He(),title:`Bring the whole index up to date at full speed — file scan plus AI summaries, rollups, and reviews, run to completion. Shares the model with chat while it works.`,children:F===`starting`?`Starting full scan…`:F===`running`||$===`full`?`Full scan running…`:$===`background`?`Background scan running…`:`Start full AI scan`})]}),Fe&&(0,m.jsx)(`span`,{className:`project-index-panel-error`,role:`alert`,children:Fe}),z&&(0,m.jsx)(`span`,{className:`project-index-panel-error`,role:`alert`,children:z.code===`boekwachter-required`&&S?(0,m.jsxs)(m.Fragment,{children:[(0,m.jsx)(`button`,{type:`button`,className:`project-index-panel-error-link`,disabled:V,onClick:()=>void We(),children:V?`Adding Boekwachter…`:`Add a Boekwachter to this project crew`}),` `,`to enable AI summaries, reviews, and semantic enrichment.`]}):z.message})]})]})})]}),(0,m.jsxs)(`div`,{className:`project-controls-inline`,children:[T&&(0,m.jsxs)(o,{value:C??`active`,disabled:w,onValueChange:e=>T(e),children:[(0,m.jsxs)(u,{className:`project-status-select project-status-select-${C??`active`}`,title:w?`Archived projects are inactive. Restore this project to change its status.`:le,"aria-label":`Project status`,children:[(0,m.jsx)(`span`,{className:`project-status-select-dot`,"aria-hidden":!0}),(0,m.jsx)(l,{})]}),(0,m.jsx)(f,{children:me.map(e=>(0,m.jsx)(c,{value:e.value,children:e.label},e.value))})]}),_&&(!t||!U)&&(0,m.jsxs)(o,{value:U?`on`:`off`,onValueChange:e=>_(e===`on`),children:[(0,m.jsxs)(u,{className:`project-writes-select project-writes-select-${U?`on`:`off`}`,title:ue,"aria-label":`Built-in tool workspace access for this project`,children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:U})}),(0,m.jsx)(l,{})]}),(0,m.jsxs)(f,{children:[(0,m.jsx)(c,{value:`on`,children:`Can edit`}),(0,m.jsx)(c,{value:`off`,children:`Read-only`})]})]}),v&&Se&&(0,m.jsxs)(o,{value:v,onValueChange:e=>Se(e),children:[(0,m.jsxs)(u,{className:`project-writes-select project-codex-mode project-codex-mode-${v}`,title:fe(v),"aria-label":`Codex execution mode for this project`,children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:v!==`plan`})}),(0,m.jsx)(`span`,{className:`project-permission-scope`,children:`Codex:`}),(0,m.jsx)(l,{})]}),(0,m.jsx)(f,{children:h.map(e=>(0,m.jsx)(c,{value:e.value,textValue:e.label,children:e.label},e.value))})]}),y&&b&&(0,m.jsxs)(o,{value:y,onValueChange:e=>{e!==`mixed`&&b(e)},children:[(0,m.jsxs)(u,{className:`project-writes-select project-claude-mode project-claude-mode-${y}`,title:pe(y),"aria-label":`Claude execution mode for this project`,children:[(0,m.jsx)(`span`,{className:`project-writes-select-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{unlocked:y!==`plan`&&y!==`mixed`})}),(0,m.jsx)(`span`,{className:`project-permission-scope`,children:`Claude:`}),(0,m.jsx)(l,{})]}),(0,m.jsxs)(f,{children:[y===`mixed`&&(0,m.jsx)(c,{value:`mixed`,disabled:!0,children:`Mixed`}),de.map(e=>(0,m.jsx)(c,{value:e.value,textValue:e.label,children:e.label},e.value))]})]})]}),t&&(0,m.jsx)(_e,{projectStatus:C??`active`,statusLocked:w,onStatusChange:T,managedWritesOn:U,onManagedWorkspaceWritesChange:_,codexMode:v,onCodexModeChange:Se,claudeMode:y,onClaudeModeChange:b}),!_&&!U&&(0,m.jsxs)(`span`,{className:`project-lockdown-chip`,title:`Managed workspace edits are off for this project. Enable "Allow built-in tools and background work to modify the workspace" in Project → Settings.`,"aria-label":`Built-in tool workspace access is read-only for this project.`,children:[(0,m.jsx)(`span`,{className:`project-lockdown-chip-icon`,"aria-hidden":!0,children:(0,m.jsx)(g,{})}),(0,m.jsx)(`span`,{className:`project-lockdown-chip-label`,children:`edits off`})]})]}),!t&&(0,m.jsx)(`div`,{className:`project-git-status-bar-right`,children:Xe&&(0,m.jsx)(`button`,{type:`button`,className:`project-git-action${ft?` primary`:``}`,onClick:()=>void qe(),disabled:Ke||Ae!==``,title:`Get new changes from GitHub and send yours`,children:Ke?`Syncing…`:`Sync`})}),M&&(0,m.jsx)(`output`,{className:`project-git-toast project-git-toast-${M.kind}`,children:M.text})]})}function ve(e,t){return t<=0?null:Math.round(Math.min(Math.max(e,0),t)/t*100)}function ye(e){let t=[[e.summarized,e.eligible],[e.embedded,e.eligible]];e.reviews&&t.push([e.reviews.reviewed,e.reviews.eligible]);let n=0,r=0;for(let[e,i]of t)i<=0||(n+=Math.min(Math.max(e,0),i),r+=i);return r>0?Math.round(n/r*100):null}function be(e){switch(e){case`fresh`:return`Up to date`;case`stale`:return`Needs a rescan`;case`indexing`:return`Scanning now`;case`never`:return`Not scanned yet`;case`disabled`:return`Off for this project`}}function xe(e){if(e<1e3)return`${Math.max(1,Math.round(e))}ms`;if(e<6e4)return`${(e/1e3).toFixed(+(e<1e4))}s`;let t=Math.floor(e/6e4),n=Math.round(e%6e4/1e3);return n>0?`${t}m ${n}s`:`${t}m`}export{_ as t};
|