chainlesschain 0.162.95 → 0.162.96

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (217) hide show
  1. package/README.md +1 -1
  2. package/bin/chainlesschain.js +8 -18
  3. package/package.json +1 -1
  4. package/src/assets/web-panel/assets/{AIOps-DLvvkb9x.js → AIOps-Bo9Ux24z.js} +1 -1
  5. package/src/assets/web-panel/assets/{ActionButton-BxhQTwqd.js → ActionButton-CExgXSQT.js} +1 -1
  6. package/src/assets/web-panel/assets/{Analytics-C4oUXzhG.js → Analytics-BNnZhRTZ.js} +3 -3
  7. package/src/assets/web-panel/assets/{AppLayout-CjzKJdv3.js → AppLayout-D9xfqFCT.js} +5 -5
  8. package/src/assets/web-panel/assets/{Audit-B-MrugUs.js → Audit-Cpgu8uCw.js} +1 -1
  9. package/src/assets/web-panel/assets/{Backup-ecIfEpIZ.js → Backup-CHdEJnNE.js} +1 -1
  10. package/src/assets/web-panel/assets/{BaseInput-BUcSfWnx.js → BaseInput-Cbw-PxBq.js} +1 -1
  11. package/src/assets/web-panel/assets/{Chat-DIc1n_Lk.js → Chat-ChHTZK_6.js} +5 -5
  12. package/src/assets/web-panel/assets/{ChatBubbleRenderer-BGzg7oVA.js → ChatBubbleRenderer-Dl6z6ZH7.js} +1 -1
  13. package/src/assets/web-panel/assets/{Checkbox-BQ3Ueff-.js → Checkbox-Cj8d9bru.js} +1 -1
  14. package/src/assets/web-panel/assets/{Codegen-CvSGLnqE.js → Codegen-C2YobW4j.js} +1 -1
  15. package/src/assets/web-panel/assets/{Col-Br9IXZcE.js → Col-CxfV5FGT.js} +1 -1
  16. package/src/assets/web-panel/assets/{Community-tPuLOf0r.js → Community-CiwOASMj.js} +1 -1
  17. package/src/assets/web-panel/assets/{Compact-vMWH73BE.js → Compact-CTg_2iKW.js} +1 -1
  18. package/src/assets/web-panel/assets/{Compliance-Ct9z699x.js → Compliance-HMbsTmtw.js} +1 -1
  19. package/src/assets/web-panel/assets/{Cowork-Bxs1kL1y.js → Cowork-DyNDqGR2.js} +3 -3
  20. package/src/assets/web-panel/assets/{Cron-QEpr2k4U.js → Cron-9-x5M7qy.js} +2 -2
  21. package/src/assets/web-panel/assets/{Crosschain-u4xbUw6O.js → Crosschain-4msgDaYJ.js} +1 -1
  22. package/src/assets/web-panel/assets/{DID-DXTEvyrW.js → DID--2Beb5Po.js} +2 -2
  23. package/src/assets/web-panel/assets/{Dashboard-C4pZgzkg.js → Dashboard-T6nq0Lzs.js} +2 -2
  24. package/src/assets/web-panel/assets/{Dropdown-LRuqREGe.js → Dropdown-D_Q6T10v.js} +1 -1
  25. package/src/assets/web-panel/assets/{EmailListRenderer-D7XI1yBM.js → EmailListRenderer-TnN21bJx.js} +1 -1
  26. package/src/assets/web-panel/assets/{FamilyGuardDashboard-3y_SuAMQ.js → FamilyGuardDashboard-kky_uIij.js} +1 -1
  27. package/src/assets/web-panel/assets/{Federation-DbjbJJCW.js → Federation-C1GkNY4B.js} +1 -1
  28. package/src/assets/web-panel/assets/{FormItemContext-WPpMZcUw.js → FormItemContext-5-_Fc5YV.js} +1 -1
  29. package/src/assets/web-panel/assets/{GenericCardRenderer-nNT9Tn4E.js → GenericCardRenderer-CmHiB7sr.js} +1 -1
  30. package/src/assets/web-panel/assets/{Git-DqDaVzwV.js → Git-Cuci_BPI.js} +2 -2
  31. package/src/assets/web-panel/assets/{Governance-BquBZpcg.js → Governance-BU0cO2LD.js} +1 -1
  32. package/src/assets/web-panel/assets/{Inference-RcPPYijs.js → Inference-BDFNgEcx.js} +1 -1
  33. package/src/assets/web-panel/assets/{KnowledgeGraph-ByXfZV13.js → KnowledgeGraph-DITXUzHz.js} +1 -1
  34. package/src/assets/web-panel/assets/{Logs-CHT3DUcq.js → Logs-Ea-07CRd.js} +2 -2
  35. package/src/assets/web-panel/assets/{Marketplace-Bi0HJ9pN.js → Marketplace-D6OBbRVG.js} +1 -1
  36. package/src/assets/web-panel/assets/{McpTools-QCBxPRRc.js → McpTools-eiKpIJMi.js} +4 -4
  37. package/src/assets/web-panel/assets/{Memory-D4RlxGXn.js → Memory-M-X-T8UF.js} +2 -2
  38. package/src/assets/web-panel/assets/{MobileBridge-CU_PV7e-.js → MobileBridge-xcZb9Ekv.js} +2 -2
  39. package/src/assets/web-panel/assets/{MobileProjects-c1CMFD8z.js → MobileProjects-DCfoTPRC.js} +1 -1
  40. package/src/assets/web-panel/assets/{Mtc-BezDB1-s.js → Mtc-BWfGDzD8.js} +5 -5
  41. package/src/assets/web-panel/assets/{MtcAudit-CgLpiHpE.js → MtcAudit-imBuld-U.js} +2 -2
  42. package/src/assets/web-panel/assets/{Multisig-vx6bz-bA.js → Multisig-C2kcsq7I.js} +3 -3
  43. package/src/assets/web-panel/assets/{NLProgramming-CGOagg3-.js → NLProgramming-DObvXSXP.js} +1 -1
  44. package/src/assets/web-panel/assets/{Notes-BcuDGYRS.js → Notes-C-6OGJMe.js} +4 -4
  45. package/src/assets/web-panel/assets/{NotificationSettings-ZAGCDUpc.js → NotificationSettings-ub7Ozxci.js} +1 -1
  46. package/src/assets/web-panel/assets/{OrderTableRenderer-B5onE0eX.js → OrderTableRenderer-CR2W89Vk.js} +1 -1
  47. package/src/assets/web-panel/assets/{Organization-y_y20-5Y.js → Organization-DNA_Wty7.js} +4 -4
  48. package/src/assets/web-panel/assets/{Overflow-BEICS31D.js → Overflow-rT4Wb4rQ.js} +1 -1
  49. package/src/assets/web-panel/assets/{P2P-D_WRMzh4.js → P2P-CK-hARKv.js} +2 -2
  50. package/src/assets/web-panel/assets/PdhVaultBrowser-C2pbtNbT.js +7 -0
  51. package/src/assets/web-panel/assets/{Permissions-3aqCc_4f.js → Permissions-B8EIEqGJ.js} +4 -4
  52. package/src/assets/web-panel/assets/{PersonalDataHub-DT3R9g9Y.js → PersonalDataHub-BxNVNU3s.js} +2 -2
  53. package/src/assets/web-panel/assets/{Pipeline-MiMWIhw0.js → Pipeline-CT9pbkyY.js} +1 -1
  54. package/src/assets/web-panel/assets/{Privacy-C3JsLuDa.js → Privacy-DhCNd2CS.js} +1 -1
  55. package/src/assets/web-panel/assets/{ProjectInit-EhHVi1ff.js → ProjectInit-Qngnx-vQ.js} +2 -2
  56. package/src/assets/web-panel/assets/{ProjectSettings-D_dNEA37.js → ProjectSettings-Dfn-nQc1.js} +2 -2
  57. package/src/assets/web-panel/assets/Projects-BKdiSaPR.js +1 -0
  58. package/src/assets/web-panel/assets/{Providers-CPEhi2iZ.js → Providers-4o9B_n-X.js} +1 -1
  59. package/src/assets/web-panel/assets/{QuickAsk-BFQpMleX.js → QuickAsk-bs1qvF30.js} +1 -1
  60. package/src/assets/web-panel/assets/{Recommend-DzbovRC8.js → Recommend-CuEnKA2K.js} +1 -1
  61. package/src/assets/web-panel/assets/{Reputation-DoBeV3TD.js → Reputation-DbfvmRb2.js} +1 -1
  62. package/src/assets/web-panel/assets/{Row-DthhwX_B.js → Row-DvMJGAI3.js} +1 -1
  63. package/src/assets/web-panel/assets/{RssFeed-Dsf5U0lP.js → RssFeed-oJ0BZvmA.js} +2 -2
  64. package/src/assets/web-panel/assets/{Search-CJPB8kKl.js → Search-DnIVrY9O.js} +1 -1
  65. package/src/assets/web-panel/assets/{Security-DI9MfpdD.js → Security-CIWhI_Tc.js} +3 -3
  66. package/src/assets/web-panel/assets/{Services-BdG0TFGf.js → Services-DLrnpjwm.js} +2 -2
  67. package/src/assets/web-panel/assets/{Skeleton-DSYazY_B.js → Skeleton-CYmqgtVb.js} +1 -1
  68. package/src/assets/web-panel/assets/{Skills-BD309VTT.js → Skills-BUzCkoeu.js} +1 -1
  69. package/src/assets/web-panel/assets/{Sla-CaUlw4_6.js → Sla-DYRE4bnS.js} +1 -1
  70. package/src/assets/web-panel/assets/{SpeechSettings-CZAPkR7H.js → SpeechSettings-_6MurdOg.js} +1 -1
  71. package/src/assets/web-panel/assets/{SyncSettings-CFRSowN3.js → SyncSettings-UIdnF5Li.js} +2 -2
  72. package/src/assets/web-panel/assets/{Tasks-Di8EOluc.js → Tasks-COx2CjT8.js} +1 -1
  73. package/src/assets/web-panel/assets/{Templates-B5FTziwi.js → Templates-BcHAmkZo.js} +1 -1
  74. package/src/assets/web-panel/assets/{Tenant-Dj3XYfBg.js → Tenant-CjYQS8yZ.js} +1 -1
  75. package/src/assets/web-panel/assets/{Terminal-CznH_rJT.js → Terminal-BmfOPcWt.js} +2 -2
  76. package/src/assets/web-panel/assets/{TimelineRenderer-DTHzaXPt.js → TimelineRenderer-D5HuarNQ.js} +1 -1
  77. package/src/assets/web-panel/assets/{Tokens-Bo56nuML.js → Tokens-C_fbProA.js} +1 -1
  78. package/src/assets/web-panel/assets/{Trigger-pyVUVBwb.js → Trigger-JPulpRx8.js} +1 -1
  79. package/src/assets/web-panel/assets/{Trust-Cp7jMkKN.js → Trust-CnO-062O.js} +1 -1
  80. package/src/assets/web-panel/assets/{UkeySign-aPcZCdpz.js → UkeySign-HpNovvau.js} +1 -1
  81. package/src/assets/web-panel/assets/{VideoEditing-DAv5j--w.js → VideoEditing-yMncxH7y.js} +1 -1
  82. package/src/assets/web-panel/assets/{Wallet-DRhK7IDR.js → Wallet-Cug-t7Np.js} +4 -4
  83. package/src/assets/web-panel/assets/{WebAuthn-B2yQJuq8.js → WebAuthn--U1-NR-3.js} +2 -2
  84. package/src/assets/web-panel/assets/{WorkflowEditor-D98DhR54.js → WorkflowEditor-R-XvSJ3S.js} +1 -1
  85. package/src/assets/web-panel/assets/{chat-BXrRNi8C.js → chat-CCI1i6Rp.js} +1 -1
  86. package/src/assets/web-panel/assets/{colors-jQ94T_qn.js → colors-C-mqoaLt.js} +1 -1
  87. package/src/assets/web-panel/assets/{compact-item-KqUJLlF2.js → compact-item-De_N2iRR.js} +1 -1
  88. package/src/assets/web-panel/assets/{createContext-DxM3zuQW.js → createContext-DbTM6sjZ.js} +1 -1
  89. package/src/assets/web-panel/assets/devWarning-OcLPHSl5.js +1 -0
  90. package/src/assets/web-panel/assets/{hasIn-BGm946KV.js → hasIn-D0Adylyc.js} +1 -1
  91. package/src/assets/web-panel/assets/index-7E_mHkDU.js +1 -0
  92. package/src/assets/web-panel/assets/{index-Dib0FsTT.js → index-AY937BxS.js} +1 -1
  93. package/src/assets/web-panel/assets/{index-C5NQai7O.js → index-B6hgy5VC.js} +1 -1
  94. package/src/assets/web-panel/assets/{index-LWTZAud0.js → index-B7XnpLHk.js} +1 -1
  95. package/src/assets/web-panel/assets/{index-BXMZLfd8.js → index-B7gw-tDm.js} +1 -1
  96. package/src/assets/web-panel/assets/{index-DTUs9t5F.js → index-BBgDgkwW.js} +1 -1
  97. package/src/assets/web-panel/assets/{index-Ce-YoL4x.js → index-BMmeiw88.js} +1 -1
  98. package/src/assets/web-panel/assets/{index-BaU_fSK7.js → index-BU6XtnSx.js} +1 -1
  99. package/src/assets/web-panel/assets/{index-BMp41Q1Y.js → index-Bi7VUG0R.js} +1 -1
  100. package/src/assets/web-panel/assets/{index-CbQvgx2e.js → index-BtE3cw9m.js} +1 -1
  101. package/src/assets/web-panel/assets/{index-DWcd5zDG.js → index-C9ej-MF0.js} +3 -3
  102. package/src/assets/web-panel/assets/{index-BbS0cBU9.js → index-CIEiQl1j.js} +1 -1
  103. package/src/assets/web-panel/assets/{index-D1VWL6Lc.js → index-CKgaW9E5.js} +1 -1
  104. package/src/assets/web-panel/assets/{index-DRzsaWQy.js → index-CY0KKR5f.js} +1 -1
  105. package/src/assets/web-panel/assets/index-CbV3-WlB.js +1 -0
  106. package/src/assets/web-panel/assets/{index-DSzb9VOG.js → index-Co1UkcFX.js} +1 -1
  107. package/src/assets/web-panel/assets/{index-B-2HpfWo.js → index-CzP5d5LW.js} +1 -1
  108. package/src/assets/web-panel/assets/{index-DboUBf6R.js → index-D0NJ5lRi.js} +1 -1
  109. package/src/assets/web-panel/assets/{index-DZMzj4ay.js → index-D0gBsqTX.js} +1 -1
  110. package/src/assets/web-panel/assets/{index-CghRL1dh.js → index-D5F6shtn.js} +1 -1
  111. package/src/assets/web-panel/assets/{index-Cz_SFSix.js → index-DVtamtlm.js} +1 -1
  112. package/src/assets/web-panel/assets/{index-T4UJiTi3.js → index-DWT18hDG.js} +1 -1
  113. package/src/assets/web-panel/assets/{index-CreXAr5Y.js → index-DaXb4B9P.js} +1 -1
  114. package/src/assets/web-panel/assets/{index-C7Z2m28C.js → index-DjQA0Vez.js} +1 -1
  115. package/src/assets/web-panel/assets/{index-Crw76vIF.js → index-Ds8NJVEL.js} +1 -1
  116. package/src/assets/web-panel/assets/{index-mZNLT2SP.js → index-DuP-8HWu.js} +1 -1
  117. package/src/assets/web-panel/assets/{index-BnEZfi5D.js → index-DwLTiJ31.js} +1 -1
  118. package/src/assets/web-panel/assets/{index-1P0sXNhG.js → index-T3VhH8cO.js} +1 -1
  119. package/src/assets/web-panel/assets/{index-B4b7KjRq.js → index-TDY1o0w3.js} +1 -1
  120. package/src/assets/web-panel/assets/{index-DOYcemym.js → index-TRy2Gc3V.js} +1 -1
  121. package/src/assets/web-panel/assets/{index-BAPk6ntc.js → index-W1OMxCmI.js} +1 -1
  122. package/src/assets/web-panel/assets/{index-Dgzw6eKr.js → index-ftFRZbuc.js} +1 -1
  123. package/src/assets/web-panel/assets/{index-C7sBLech.js → index-iGPGaORA.js} +1 -1
  124. package/src/assets/web-panel/assets/{index-FSYz5aww.js → index-jhy5KQvg.js} +1 -1
  125. package/src/assets/web-panel/assets/{index-DZpVYD4j.js → index-qUSZJcgw.js} +1 -1
  126. package/src/assets/web-panel/assets/{index-yavsyHif.js → index-w3f6lqkD.js} +1 -1
  127. package/src/assets/web-panel/assets/{index-CfE3jxrT.js → index-xdMc71Kh.js} +1 -1
  128. package/src/assets/web-panel/assets/{index-aOLXuHpG.js → index-xhX5eg2Z.js} +1 -1
  129. package/src/assets/web-panel/assets/{index-BGjCjsf1.js → index-zkTiW6d6.js} +1 -1
  130. package/src/assets/web-panel/assets/{initDefaultProps-BDoZJI7g.js → initDefaultProps-CIHqouWk.js} +1 -1
  131. package/src/assets/web-panel/assets/{motion-sceLjgp-.js → motion-D1iUKftk.js} +1 -1
  132. package/src/assets/web-panel/assets/{move-CTWQpFa7.js → move-YOpWjmjL.js} +1 -1
  133. package/src/assets/web-panel/assets/{omit-dr-NCrHZ.js → omit-C_1357UY.js} +1 -1
  134. package/src/assets/web-panel/assets/{pickAttrs-DK-GX_Z2.js → pickAttrs-CDb4dq6o.js} +1 -1
  135. package/src/assets/web-panel/assets/{placementArrow-BIPf--18.js → placementArrow-D-OGYyhd.js} +1 -1
  136. package/src/assets/web-panel/assets/{responsiveObserve-BzrWT5tV.js → responsiveObserve-hS-j69A0.js} +1 -1
  137. package/src/assets/web-panel/assets/{slide-D5XhxlET.js → slide-tnjuvphU.js} +1 -1
  138. package/src/assets/web-panel/assets/{statusUtils-6DI-k-9E.js → statusUtils-BERfMMcU.js} +1 -1
  139. package/src/assets/web-panel/assets/{styleChecker-DMw-eyn9.js → styleChecker-DKpl2K9E.js} +1 -1
  140. package/src/assets/web-panel/assets/{useFlexGapSupport-D4oVdliM.js → useFlexGapSupport-C_sX4D3N.js} +1 -1
  141. package/src/assets/web-panel/assets/{useFs-D3PPZnvy.js → useFs-DBcxC1vK.js} +1 -1
  142. package/src/assets/web-panel/assets/{usePersonalDataHub-Gh5ba4KP.js → usePersonalDataHub-CeoDf2XI.js} +1 -1
  143. package/src/assets/web-panel/assets/{vnode-CVEM1u4x.js → vnode-DC9Pmj_u.js} +1 -1
  144. package/src/assets/web-panel/assets/{zoom-ClT_-9RZ.js → zoom-CZA58J7M.js} +1 -1
  145. package/src/assets/web-panel/index.html +1 -1
  146. package/src/commands/activitypub.js +19 -3
  147. package/src/commands/agent.js +25 -0
  148. package/src/commands/ask.js +13 -0
  149. package/src/commands/config.js +17 -1
  150. package/src/commands/cost.js +6 -1
  151. package/src/commands/dao.js +16 -3
  152. package/src/commands/dlp.js +7 -1
  153. package/src/commands/hub.js +13 -0
  154. package/src/commands/mtc.js +37 -1
  155. package/src/gateways/discord/discord-formatter.js +18 -1
  156. package/src/gateways/telegram/telegram-formatter.js +6 -3
  157. package/src/gateways/ws/ws-server.js +19 -1
  158. package/src/harness/plugin-manager.js +20 -0
  159. package/src/harness/worktree-isolator.js +17 -1
  160. package/src/lib/__tests__/model-deprecation.test.js +194 -0
  161. package/src/lib/a2a-protocol.js +23 -9
  162. package/src/lib/agent-core.js +2 -5
  163. package/src/lib/audit-mtc.js +40 -2
  164. package/src/lib/chat-core.js +141 -18
  165. package/src/lib/cli-anything-bridge.js +5 -0
  166. package/src/lib/cli-numeric.js +38 -0
  167. package/src/lib/config-manager.js +37 -6
  168. package/src/lib/cowork/ab-comparator-cli.js +6 -2
  169. package/src/lib/cowork-cron.js +45 -34
  170. package/src/lib/cowork-learning.js +31 -1
  171. package/src/lib/cowork-share.js +39 -3
  172. package/src/lib/cowork-template-marketplace.js +54 -2
  173. package/src/lib/cowork-workflow.js +33 -6
  174. package/src/lib/cross-chain-mtc.js +41 -12
  175. package/src/lib/crypto-manager.js +12 -2
  176. package/src/lib/dbevo.js +19 -8
  177. package/src/lib/downloader.js +24 -9
  178. package/src/lib/evomap-governance.js +4 -4
  179. package/src/lib/evomap-manager.js +54 -7
  180. package/src/lib/fatal-handler.js +48 -0
  181. package/src/lib/file-checkpoint.js +26 -0
  182. package/src/lib/git-integration.js +28 -0
  183. package/src/lib/goal-store.js +36 -10
  184. package/src/lib/hierarchical-memory.js +6 -0
  185. package/src/lib/llm-pricing.js +52 -2
  186. package/src/lib/mcp-oauth.js +37 -7
  187. package/src/lib/memory-manager.js +23 -2
  188. package/src/lib/model-deprecation.js +249 -0
  189. package/src/lib/pdh-feedback-ledger.js +131 -0
  190. package/src/lib/permanent-memory.js +30 -2
  191. package/src/lib/permission-rules.cjs +11 -3
  192. package/src/lib/personal-data-hub-aichat-wizard.js +33 -3
  193. package/src/lib/personal-data-hub-wiring.js +36 -13
  194. package/src/lib/project-instructions.js +10 -4
  195. package/src/lib/runnable-provider.js +62 -31
  196. package/src/lib/session-usage.js +34 -1
  197. package/src/lib/skill-loader.js +4 -1
  198. package/src/lib/skill-packs/generator.js +25 -2
  199. package/src/lib/stream-retry.js +56 -0
  200. package/src/lib/sync-credentials.js +53 -17
  201. package/src/lib/token-tracker.js +12 -2
  202. package/src/lib/with-file-lock.js +87 -0
  203. package/src/repl/agent-repl.js +39 -7
  204. package/src/repl/chat-repl.js +10 -0
  205. package/src/repl/session-cost.js +31 -3
  206. package/src/runtime/agent-core.js +474 -53
  207. package/src/runtime/coding-agent-contract-shared.cjs +58 -1
  208. package/src/runtime/coding-agent-policy.cjs +10 -0
  209. package/src/runtime/file-ref-expander.js +29 -1
  210. package/src/runtime/headless-runner.js +12 -1
  211. package/src/runtime/headless-stream.js +131 -5
  212. package/src/skills/video-editing/tools/commit.js +15 -1
  213. package/src/assets/web-panel/assets/PdhVaultBrowser-C8f5NbbI.js +0 -7
  214. package/src/assets/web-panel/assets/Projects-CXydUXp8.js +0 -1
  215. package/src/assets/web-panel/assets/devWarning-Bo1r5_zX.js +0 -1
  216. package/src/assets/web-panel/assets/index-BCU6dVQ-.js +0 -1
  217. package/src/assets/web-panel/assets/index-N_oOFphx.js +0 -1
@@ -27,11 +27,22 @@ const CODING_AGENT_TOOL_CONTRACTS = Object.freeze([
27
27
  title: "Read File",
28
28
  kind: "filesystem",
29
29
  tier: "mvp",
30
- description: "Read a file's content",
30
+ description:
31
+ "Read a file's content. Jupyter notebooks (.ipynb) are rendered as a compact cell listing (index/id/type/source, outputs hidden) for use with notebook_edit — pass raw:true for the underlying JSON.",
31
32
  inputSchema: {
32
33
  type: "object",
33
34
  properties: {
34
35
  path: { type: "string", description: "File path to read" },
36
+ hashed: {
37
+ type: "boolean",
38
+ description:
39
+ "Prefix each line with a 6-char content hash for edit_file_hashed anchoring",
40
+ },
41
+ raw: {
42
+ type: "boolean",
43
+ description:
44
+ "For .ipynb: return the raw notebook JSON instead of the rendered cell listing",
45
+ },
35
46
  },
36
47
  required: ["path"],
37
48
  },
@@ -69,6 +80,52 @@ const CODING_AGENT_TOOL_CONTRACTS = Object.freeze([
69
80
  tags: ["tool:write_file", "contract:coding-agent", "tier:mvp"],
70
81
  },
71
82
  },
83
+ {
84
+ name: "notebook_edit",
85
+ title: "Edit Notebook",
86
+ kind: "filesystem",
87
+ tier: "mvp",
88
+ description:
89
+ "Edit a Jupyter notebook (.ipynb) cell. edit_mode 'replace' (default) overwrites a cell's source; 'insert' adds a new cell (after the target cell, or at the top when no target given); 'delete' removes a cell. Identify the target with cell_id (preferred) or 0-based cell_index. cell_type ('code'|'markdown') is required for 'insert'. Source is plain text with newlines preserved; replacing a code cell clears its previous outputs + execution_count.",
90
+ inputSchema: {
91
+ type: "object",
92
+ properties: {
93
+ path: { type: "string", description: "Path to the .ipynb notebook" },
94
+ new_source: {
95
+ type: "string",
96
+ description: "New cell source text (required for replace/insert)",
97
+ },
98
+ cell_id: {
99
+ type: "string",
100
+ description: "Target cell id (preferred over cell_index)",
101
+ },
102
+ cell_index: {
103
+ type: "number",
104
+ description: "0-based cell index (when cell_id is unknown)",
105
+ },
106
+ cell_type: {
107
+ type: "string",
108
+ enum: ["code", "markdown"],
109
+ description: "Cell type — required for edit_mode 'insert'",
110
+ },
111
+ edit_mode: {
112
+ type: "string",
113
+ enum: ["replace", "insert", "delete"],
114
+ description: "replace (default) | insert | delete",
115
+ },
116
+ },
117
+ required: ["path"],
118
+ },
119
+ ...TOOL_POLICY_METADATA.notebook_edit,
120
+ permissions: {
121
+ level: "elevated",
122
+ scopes: ["filesystem:write"],
123
+ },
124
+ telemetry: {
125
+ category: "filesystem",
126
+ tags: ["tool:notebook_edit", "contract:coding-agent", "tier:mvp"],
127
+ },
128
+ },
72
129
  {
73
130
  name: "edit_file",
74
131
  title: "Edit File",
@@ -94,6 +94,16 @@ const TOOL_POLICY_METADATA = Object.freeze({
94
94
  approvalFlow: "plan",
95
95
  isReadOnly: false,
96
96
  },
97
+ notebook_edit: {
98
+ riskLevel: RISK_LEVELS.MEDIUM,
99
+ category: TOOL_CATEGORIES.WRITE,
100
+ availableInPlanMode: false,
101
+ planModeBehavior: "blocked",
102
+ requiresPlanApproval: true,
103
+ requiresConfirmation: false,
104
+ approvalFlow: "plan",
105
+ isReadOnly: false,
106
+ },
97
107
  run_shell: {
98
108
  riskLevel: RISK_LEVELS.HIGH,
99
109
  category: TOOL_CATEGORIES.EXECUTE,
@@ -110,6 +110,28 @@ function looksBinary(buf) {
110
110
  return false;
111
111
  }
112
112
 
113
+ /**
114
+ * Read at most `limit` bytes from the start of a file. A plain `@file` only
115
+ * ever shows the first `maxBytes`, so reading the whole thing into memory first
116
+ * (readFileSync) would allocate the entire file — pointless for a 300 MB log and
117
+ * a hard failure for files > 2 GB. We read `limit` bytes so truncation can still
118
+ * be detected (caller passes maxBytes + 1). Falls back to readFileSync if the
119
+ * injected fs lacks the lower-level calls.
120
+ */
121
+ function readBoundedFile(fs, abs, limit) {
122
+ if (typeof fs.openSync !== "function" || typeof fs.readSync !== "function") {
123
+ return fs.readFileSync(abs);
124
+ }
125
+ const fd = fs.openSync(abs, "r");
126
+ try {
127
+ const buf = Buffer.alloc(limit);
128
+ const n = fs.readSync(fd, buf, 0, limit, 0);
129
+ return buf.subarray(0, n);
130
+ } finally {
131
+ fs.closeSync(fd);
132
+ }
133
+ }
134
+
113
135
  /**
114
136
  * Resolve a single raw token to an injectable ref descriptor, or null when it
115
137
  * does not resolve to an existing path. Tries the literal path first, then a
@@ -159,9 +181,15 @@ function resolveRef(raw, { cwd, fs, path, maxBytes, maxDirEntries }) {
159
181
  };
160
182
  }
161
183
  if (stat.isFile()) {
184
+ // PDFs (pdf-parse needs the bytes) and line ranges (must reach the end
185
+ // line) need the whole file; a plain inline only ever shows the first
186
+ // maxBytes, so cap the read there instead of slurping the entire file.
187
+ const needsWholeFile = isPdf(fsPath) || range != null;
162
188
  let buf;
163
189
  try {
164
- buf = fs.readFileSync(abs);
190
+ buf = needsWholeFile
191
+ ? fs.readFileSync(abs)
192
+ : readBoundedFile(fs, abs, maxBytes + 1);
165
193
  } catch (err) {
166
194
  return {
167
195
  kind: "error",
@@ -607,6 +607,7 @@ export async function runAgentHeadless(options = {}, deps = {}) {
607
607
  // registered (cc mcp add) + IDE bridge auto-discovery.
608
608
  strict: options.strictMcpConfig === true,
609
609
  ide: options.ide,
610
+ pdh: options.pdh,
610
611
  cwd: options.cwd || process.cwd(),
611
612
  // advertise the session id to spawned stdio MCP servers
612
613
  sessionId,
@@ -760,7 +761,12 @@ export async function runAgentHeadless(options = {}, deps = {}) {
760
761
 
761
762
  const startedAt = deps.now ? deps.now() : Date.now();
762
763
  const toolCalls = [];
763
- const usage = { input_tokens: 0, output_tokens: 0 };
764
+ const usage = {
765
+ input_tokens: 0,
766
+ output_tokens: 0,
767
+ cache_read_input_tokens: 0,
768
+ cache_creation_input_tokens: 0,
769
+ };
764
770
  let finalText = "";
765
771
  let endReason = "complete";
766
772
  let stopForCost = false;
@@ -837,6 +843,11 @@ export async function runAgentHeadless(options = {}, deps = {}) {
837
843
  case "token-usage": {
838
844
  usage.input_tokens += event.usage?.input_tokens || 0;
839
845
  usage.output_tokens += event.usage?.output_tokens || 0;
846
+ // Carry prompt-cache tokens into accumulated usage (cost accuracy).
847
+ usage.cache_read_input_tokens +=
848
+ event.usage?.cache_read_input_tokens || 0;
849
+ usage.cache_creation_input_tokens +=
850
+ event.usage?.cache_creation_input_tokens || 0;
840
851
  emitStream({ type: "token_usage", usage: event.usage });
841
852
  if (costBudget) {
842
853
  costBudget.add({
@@ -114,6 +114,34 @@ export function parseInputEvent(line) {
114
114
  },
115
115
  };
116
116
  }
117
+ // PDH self-learning feedback (design module 101 §3.5.13). The personal-data
118
+ // chat's 纠正卡 sends {"type":"feedback","turn_id":…,"kind":"positive"|
119
+ // "negative"|"correction","comment":…} after a reply. A missing kind → skip.
120
+ if (obj && typeof obj === "object" && obj.type === "feedback") {
121
+ const kind = String(obj.kind || "").toLowerCase();
122
+ if (!kind) return null;
123
+ return {
124
+ feedback: {
125
+ turnId: obj.turn_id != null ? String(obj.turn_id) : null,
126
+ kind,
127
+ comment: typeof obj.comment === "string" ? obj.comment : null,
128
+ },
129
+ };
130
+ }
131
+ // PDH guided-collection resume (design module 101 §3.5.15). When a PDH tool
132
+ // returns assist_required (e.g. "log into the app first") the chat's 引导卡
133
+ // sends {"type":"resume","token":…,"action":"completed"|"skip"} once the user
134
+ // finishes or skips the in-app step. A missing action → skip.
135
+ if (obj && typeof obj === "object" && obj.type === "resume") {
136
+ const action = String(obj.action || "").toLowerCase();
137
+ if (!action) return null;
138
+ return {
139
+ resume: {
140
+ token: obj.token != null ? String(obj.token) : null,
141
+ action,
142
+ },
143
+ };
144
+ }
117
145
  const msg = obj && typeof obj === "object" ? obj.message || obj : {};
118
146
  let content = msg.content ?? obj.text ?? obj.prompt;
119
147
  if (Array.isArray(content)) {
@@ -185,7 +213,12 @@ export async function* readJsonLines(input) {
185
213
  * Returns the turn outcome so the caller can grow history + the result line.
186
214
  */
187
215
  async function runTurn(messages, loopOptions, { runLoop, emit, costBudget }) {
188
- const usage = { input_tokens: 0, output_tokens: 0 };
216
+ const usage = {
217
+ input_tokens: 0,
218
+ output_tokens: 0,
219
+ cache_read_input_tokens: 0,
220
+ cache_creation_input_tokens: 0,
221
+ };
189
222
  const toolCalls = [];
190
223
  let finalText = "";
191
224
  let endReason = "complete";
@@ -213,6 +246,12 @@ async function runTurn(messages, loopOptions, { runLoop, emit, costBudget }) {
213
246
  case "token-usage":
214
247
  usage.input_tokens += event.usage?.input_tokens || 0;
215
248
  usage.output_tokens += event.usage?.output_tokens || 0;
249
+ // Carry prompt-cache tokens into the turn's accumulated usage so the
250
+ // final `result` envelope (read by IDE panels) reflects caching too.
251
+ usage.cache_read_input_tokens +=
252
+ event.usage?.cache_read_input_tokens || 0;
253
+ usage.cache_creation_input_tokens +=
254
+ event.usage?.cache_creation_input_tokens || 0;
216
255
  emit({ type: "token_usage", usage: event.usage });
217
256
  if (costBudget) {
218
257
  costBudget.add({
@@ -463,7 +502,12 @@ export async function runAgentHeadlessStream(options = {}, deps = {}) {
463
502
  e.code = "USER_TIMEOUT"; // handler → user_timeout (model proceeds, not a failure)
464
503
  p.reject(e);
465
504
  };
466
- const interactionAskUser = ({ question, options: qOptions, multiSelect, timeoutMs } = {}) =>
505
+ const interactionAskUser = ({
506
+ question,
507
+ options: qOptions,
508
+ multiSelect,
509
+ timeoutMs,
510
+ } = {}) =>
467
511
  new Promise((resolve, reject) => {
468
512
  const id = `q-${++questionSeq}`;
469
513
  const ms = Number(timeoutMs) > 0 ? Number(timeoutMs) : questionTimeoutMs;
@@ -499,6 +543,27 @@ export async function runAgentHeadlessStream(options = {}, deps = {}) {
499
543
  );
500
544
  const messages = [{ role: "system", content: systemContent }];
501
545
 
546
+ // §3.5.13 flywheel consumption (design module 101): in a PDH session, lead
547
+ // with the user's standing feedback preferences learned ACROSS sessions
548
+ // (corrections + net sentiment) so the agent honours past corrections from
549
+ // the very first turn — the read side of pdh-feedback-ledger.js. Gated to PDH
550
+ // context (the in-APK chat sets CHAINLESSCHAIN_PDH_PORT; `--pdh` forces,
551
+ // `--no-pdh` opts out) so IDE/coding sessions are never polluted. Best-effort.
552
+ try {
553
+ const { isInPdhTerminal } = await import("../lib/pdh-bridge.js");
554
+ const pdhContext =
555
+ options.pdh === true ||
556
+ (options.pdh !== false && isInPdhTerminal(process.env));
557
+ if (pdhContext) {
558
+ const { readFeedback, summarizeFeedback, feedbackSystemNote } =
559
+ await import("../lib/pdh-feedback-ledger.js");
560
+ const note = feedbackSystemNote(summarizeFeedback(readFeedback()));
561
+ if (note) messages.push({ role: "system", content: note });
562
+ }
563
+ } catch {
564
+ /* learned-preference injection must never break the chat */
565
+ }
566
+
502
567
  // settings.json SessionStart hooks → inject session context once (observe-only).
503
568
  if (settingsHooks) {
504
569
  try {
@@ -588,6 +653,7 @@ export async function runAgentHeadlessStream(options = {}, deps = {}) {
588
653
  // registered + IDE bridge) for a reproducible MCP surface.
589
654
  strict: options.strictMcpConfig === true,
590
655
  ide: options.ide,
656
+ pdh: options.pdh,
591
657
  cwd: options.cwd || process.cwd(),
592
658
  // advertise the session id to spawned stdio MCP servers
593
659
  sessionId,
@@ -670,7 +736,9 @@ export async function runAgentHeadlessStream(options = {}, deps = {}) {
670
736
  // ask_user_question round-trip (opt-in via CC_INTERACTIVE_QUESTIONS): give
671
737
  // the tool handler an askUser that emits question_request + blocks on stdin.
672
738
  // Absent → agent-core returns user_not_reachable (graceful proceed).
673
- interaction: interactiveQuestions ? { askUser: interactionAskUser } : undefined,
739
+ interaction: interactiveQuestions
740
+ ? { askUser: interactionAskUser }
741
+ : undefined,
674
742
  prepareCall: goalPrepareCallFn,
675
743
  // --mcp-config wiring (tool defs + dispatch map + live client).
676
744
  mcpClient: mcp?.mcpClient || null,
@@ -767,8 +835,14 @@ export async function runAgentHeadlessStream(options = {}, deps = {}) {
767
835
  if (parsed.answer) {
768
836
  // Answers settle a BLOCKED ask_user_question — never queued. A null
769
837
  // value (user cancelled the QuickPick) → user_timeout (model proceeds).
770
- if (parsed.answer.value == null) failQuestion(parsed.answer.id, "cancelled");
771
- else settleQuestion(parsed.answer.id, parsed.answer.value, "user-answer");
838
+ if (parsed.answer.value == null)
839
+ failQuestion(parsed.answer.id, "cancelled");
840
+ else
841
+ settleQuestion(
842
+ parsed.answer.id,
843
+ parsed.answer.value,
844
+ "user-answer",
845
+ );
772
846
  continue;
773
847
  }
774
848
  queue.push(parsed);
@@ -896,6 +970,58 @@ export async function runAgentHeadlessStream(options = {}, deps = {}) {
896
970
  }
897
971
  }
898
972
 
973
+ // PDH self-learning feedback (design module 101 §3.5.13). Always ack so the
974
+ // chat app can confirm receipt. A `correction` re-drives a turn so the model
975
+ // adapts within the session; `positive`/`negative` are recorded as a
976
+ // lightweight preference note in history without forcing a fresh reply.
977
+ if (parsed.feedback) {
978
+ const { turnId, kind, comment } = parsed.feedback;
979
+ emit({
980
+ type: "feedback_ack",
981
+ turn_id: turnId,
982
+ kind,
983
+ session_id: sessionId,
984
+ });
985
+ // §3.5.13: persist to the cross-session learning ledger so the next
986
+ // session can honour the user's standing preferences ("越用越聪明"
987
+ // flywheel). Best-effort — a learning ledger must never break the chat.
988
+ try {
989
+ const { appendFeedback } =
990
+ await import("../lib/pdh-feedback-ledger.js");
991
+ appendFeedback({ sessionId, turnId, kind, comment });
992
+ } catch {
993
+ /* persistence is best-effort */
994
+ }
995
+ if (kind === "correction") {
996
+ parsed.text = comment
997
+ ? `用户对上一轮回复给出纠正:${comment}\n请据此调整并重新回复。`
998
+ : "用户认为上一轮回复需要纠正,请反思后给出更准确的回复。";
999
+ // fall through into the normal turn machinery with the correction prompt
1000
+ } else {
1001
+ const tag = kind === "positive" ? "认可" : "不满意";
1002
+ messages.push({
1003
+ role: "user",
1004
+ content: `(用户反馈:对上一轮回复表示${tag}。请在后续回复中延续/修正此偏好。)`,
1005
+ });
1006
+ continue;
1007
+ }
1008
+ }
1009
+
1010
+ // PDH guided-collection resume (design module 101 §3.5.15). A PDH tool
1011
+ // returned assist_required (e.g. "log into the app first"); the chat's 引导卡
1012
+ // sends a resume once the user finishes or skips the in-app step. Ack so the
1013
+ // app can dismiss the card, then re-drive the model to retry (completed) or
1014
+ // move on (skip).
1015
+ if (parsed.resume) {
1016
+ const { token, action } = parsed.resume;
1017
+ emit({ type: "resume_ack", token, action, session_id: sessionId });
1018
+ parsed.text =
1019
+ action === "skip"
1020
+ ? "我跳过了刚才需要的引导操作,请不要重试该步骤,继续处理其它事项或做个小结。"
1021
+ : "我已完成刚才需要的引导操作,请重试刚才的采集/操作。";
1022
+ // fall through into the normal turn machinery with the continuation prompt
1023
+ }
1024
+
899
1025
  // --replay-user-messages: echo each accepted user message back on the
900
1026
  // output stream (Claude-Code parity) so a consumer can correlate replies to
901
1027
  // inputs / log the transcript. Echoes the raw user text, before @file or
@@ -96,7 +96,21 @@ export async function execute({ section_idx, shot_idx, clips }, context) {
96
96
  try {
97
97
  const raw = await fs.readFile(context.shotPointPath, "utf-8");
98
98
  existing = JSON.parse(raw);
99
- } catch {}
99
+ if (!Array.isArray(existing)) {
100
+ throw new Error("shot-point log is not a JSON array");
101
+ }
102
+ } catch (err) {
103
+ // A missing file is the normal first-commit case — start fresh. Any other
104
+ // error (parse failure / wrong shape on an existing file, permission)
105
+ // means the log is present but unreadable; appending to a fresh [] would
106
+ // silently discard every previously committed clip, so surface it instead
107
+ // of clobbering.
108
+ if (err.code !== "ENOENT") {
109
+ throw new Error(
110
+ `Refusing to overwrite shot-point log ${context.shotPointPath}: ${err.message}`,
111
+ );
112
+ }
113
+ }
100
114
  existing.push(entry);
101
115
  await fs.writeFile(
102
116
  context.shotPointPath,
@@ -1,7 +0,0 @@
1
- const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./ChatBubbleRenderer-BGzg7oVA.js","./vendor-BvqAck49.js","./index-DWcd5zDG.js","./icons-DP3uiYxy.js","./index-Cq93VfoF.css","./ChatBubbleRenderer-gy5SDGw2.css","./OrderTableRenderer-B5onE0eX.js","./OrderTableRenderer-CfrDjSHT.css","./TimelineRenderer-DTHzaXPt.js","./TimelineRenderer-BlTAtkOc.css","./EmailListRenderer-D7XI1yBM.js","./EmailListRenderer-DTPZPx_S.css","./GenericCardRenderer-nNT9Tn4E.js","./GenericCardRenderer-o85VDYQS.css"])))=>i.map(i=>d[i]);
2
- import{E as ue,r as E,b as w,I as y,P as u,J as O,U as v,c,S as C,V as x,_ as M,F as B,Z as se,a0 as le,R,K as m,Q as b,W as A,o as J}from"./vendor-BvqAck49.js";import{u as U}from"./usePersonalDataHub-Gh5ba4KP.js";import{_ as F,e as L,d as P}from"./index-DWcd5zDG.js";import{a9 as q,af as z,M as Q,aH as G,u as H,aG as K,ap as W,ab as Y,e as de,d as fe,k as pe,ah as me,az as _e,R as ge}from"./icons-DP3uiYxy.js";const D=Object.freeze({q:"",category:null,adapter:null,subtype:null,since:null,until:null}),N=50,Z=300,X=ue("pdhBrowser",()=>{const r=E({...D}),t=E([]),n=E(null),e=E(!1),o=E(!1),l=E(null),a=E(null),s=E(!1),i=E({byCategory:{},byAdapter:{},bySubtype:{},total:0});let d=0,_=null;const j=w(()=>t.value.length>0),T=w(()=>n.value!=null);function h(S={}){const p={},f=r.value;return f.q&&f.q.trim()&&(p.q=f.q.trim()),f.category&&(p.category=f.category),f.adapter&&(p.adapter=f.adapter),f.subtype&&(p.subtype=f.subtype),Number.isFinite(f.since)&&(p.since=f.since),Number.isFinite(f.until)&&(p.until=f.until),{...p,...S}}async function g(){const S=++d;e.value=!0,l.value=null;const p=U();try{const[f,I]=await Promise.all([p.searchEvents(h({limit:N})),p.facetCounts({...r.value.q&&r.value.q.trim()?{q:r.value.q.trim()}:{},...Number.isFinite(r.value.since)?{since:r.value.since}:{},...Number.isFinite(r.value.until)?{until:r.value.until}:{}})]);if(S!==d)return;t.value=f.rows||[],n.value=f.nextCursor||null,a.value=f.mode||"like",s.value=!!f.shortQuery,i.value={byCategory:I.byCategory||{},byAdapter:I.byAdapter||{},bySubtype:I.bySubtype||{},total:I.total||0}}catch(f){if(S!==d)return;l.value=f&&f.message?f.message:String(f),t.value=[],n.value=null}finally{S===d&&(e.value=!1)}}async function k(){if(!n.value||o.value)return;o.value=!0,l.value=null;const S=U();try{const p=await S.searchEvents(h({cursor:n.value,limit:N}));t.value=t.value.concat(p.rows||[]),n.value=p.nextCursor||null,a.value=p.mode||a.value}catch(p){l.value=p&&p.message?p.message:String(p)}finally{o.value=!1}}function ae(S,p){if(!(S in D))throw new Error(`pdhBrowser.setFilter: unknown key "${S}"`);r.value={...r.value,[S]:p},_&&clearTimeout(_),_=setTimeout(()=>{_=null,g()},Z)}function ie(S){return r.value={...D,...S},_&&(clearTimeout(_),_=null),g()}function ce(){r.value={...D},t.value=[],n.value=null,l.value=null,i.value={byCategory:{},byAdapter:{},bySubtype:{},total:0}}return{filters:r,results:t,cursor:n,isLoading:e,isAppending:o,error:l,mode:a,shortQuery:s,facets:i,hasResults:j,canLoadMore:T,search:g,loadMore:k,setFilter:ae,setFilters:ie,reset:ce,PAGE_SIZE:N,SEARCH_DEBOUNCE_MS:Z}}),ye=Object.freeze(["chat","social","email","shopping","travel","system","ai-chat","other"]),ve=Object.freeze({chat:"社交聊天",social:"内容平台",email:"邮件",shopping:"支付订单",travel:"出行",system:"系统数据","ai-chat":"AI 对话",other:"其他"});function V(r){return ve[r]||r||"未知"}const be=Object.freeze([["wechat","chat"],["messaging-","chat"],["social-","social"],["email-","email"],["shopping-","shopping"],["alipay-","shopping"],["travel-","travel"],["system-data","system"],["browser-","system"],["vscode","system"],["win-recent","system"],["git-activity","system"],["shell-history","system"],["local-files","system"],["ai-chat-","ai-chat"]]);function $(r){if(typeof r!="string"||r.length===0)return"other";for(const[t,n]of be)if(t.endsWith("-")||t==="system-data"){if(r.startsWith(t))return n}else if(r===t)return n;return"other"}const he={__name:"CategorySidebar",props:{selected:{type:String,default:null},facets:{type:Object,default:()=>({byCategory:{},total:0})}},emits:["select"],setup(r,{expose:t}){t();const n=r,e=w(()=>n.facets.total||0),o={chat:Y,social:W,email:K,shopping:H,travel:G,system:Q,"ai-chat":z,other:q};function l(i){return o[i]||q}function a(i){return i?{backgroundColor:"#fff",color:"#1677ff"}:{backgroundColor:"#f0f0f0",color:"#666"}}const s={props:n,total:e,ICONS:o,iconFor:l,badgeStyle:a,computed:w,get AppstoreOutlined(){return q},get MessageOutlined(){return Y},get PlayCircleOutlined(){return W},get MailOutlined(){return K},get ShoppingOutlined(){return H},get CarOutlined(){return G},get MobileOutlined(){return Q},get RobotOutlined(){return z},get CATEGORIES(){return ye},get categoryLabel(){return V}};return Object.defineProperty(s,"__isScriptSetup",{enumerable:!1,value:!0}),s}},Se={class:"pdh-sidebar"},Oe=["onClick"],we={class:"label"};function Ce(r,t,n,e,o,l){const a=y("a-badge");return u(),O("div",Se,[t[2]||(t[2]=v("div",{class:"sidebar-title"},"数据类型",-1)),v("div",{class:M(["cat-item",{active:n.selected===null}]),onClick:t[0]||(t[0]=s=>r.$emit("select",null))},[c(e.AppstoreOutlined,{class:"icon"}),t[1]||(t[1]=v("span",{class:"label"},"全部",-1)),e.total>0?(u(),C(a,{key:0,count:e.total,"number-style":e.badgeStyle(n.selected===null),"overflow-count":9999},null,8,["count","number-style"])):x("v-if",!0)],2),(u(!0),O(B,null,se(e.CATEGORIES,s=>(u(),O("div",{key:s,class:M(["cat-item",{active:n.selected===s,dim:!n.facets.byCategory[s]}]),onClick:i=>r.$emit("select",s)},[(u(),C(le(e.iconFor(s)),{class:"icon"})),v("span",we,R(e.categoryLabel(s)),1),n.facets.byCategory[s]?(u(),C(a,{key:0,count:n.facets.byCategory[s],"number-style":e.badgeStyle(n.selected===s),"overflow-count":9999},null,8,["count","number-style"])):x("v-if",!0)],10,Oe))),128))])}const ke=F(he,[["render",Ce],["__scopeId","data-v-6b62a22e"],["__file","/tmp/cc-web-panel-xIdTjN/repo/packages/web-panel/src/components/pdh/CategorySidebar.vue"]]),xe={__name:"SearchFilterBar",props:{filters:{type:Object,required:!0},facets:{type:Object,default:()=>({byAdapter:{}})},isLoading:{type:Boolean,default:!1},mode:{type:String,default:null},shortQuery:{type:Boolean,default:!1}},emits:["set-filter","reset"],setup(r,{expose:t,emit:n}){t();const e=r,o=n,l=w(()=>e.filters.category?`在「${e.filters.category}」类目内搜索…`:"搜索关键词(如:支付宝、罗技、Kotlin)…"),a=w(()=>Object.entries(e.facets.byAdapter||{}).sort((g,k)=>k[1]-g[1]).map(([g,k])=>({value:g,label:`${g} (${k})`}))),s=w(()=>!e.filters.since&&!e.filters.until?null:[e.filters.since?new Date(e.filters.since):null,e.filters.until?new Date(e.filters.until):null]),i=w(()=>!!(e.filters.q||e.filters.adapter||e.filters.subtype||e.filters.since||e.filters.until));function d(h){o("set-filter","q",h||"")}function _(h){o("set-filter","q",h||"")}function j(h){if(!h||h.length===0){o("set-filter","since",null),o("set-filter","until",null);return}const[g,k]=h;o("set-filter","since",g?+g:null),o("set-filter","until",k?+k:null)}const T={props:e,emit:o,placeholderText:l,adapterOptions:a,dateRangeValue:s,hasActiveFilters:i,onQInput:d,onSearch:_,onDateChange:j,computed:w,get SearchOutlined(){return pe},get CloseCircleOutlined(){return fe},get InfoCircleOutlined(){return de}};return Object.defineProperty(T,"__isScriptSetup",{enumerable:!1,value:!0}),T}},Ee={class:"pdh-filter-bar"},Re={key:1,class:"hint"},je={key:2,class:"hint"};function Te(r,t,n,e,o,l){const a=y("a-input-search"),s=y("a-select"),i=y("a-range-picker"),d=y("a-button");return u(),O("div",Ee,[c(a,{value:n.filters.q,placeholder:e.placeholderText,"enter-button":"搜索","allow-clear":"",loading:n.isLoading,style:{flex:"1","max-width":"480px"},"onUpdate:value":e.onQInput,onSearch:e.onSearch},{prefix:m(()=>[c(e.SearchOutlined)]),_:1},8,["value","placeholder","loading"]),c(s,{value:n.filters.adapter,placeholder:"所有 adapter","allow-clear":"",options:e.adapterOptions,style:{width:"200px"},"onUpdate:value":t[0]||(t[0]=_=>r.$emit("set-filter","adapter",_||null))},null,8,["value","options"]),c(i,{value:e.dateRangeValue,placeholder:["开始日期","结束日期"],style:{width:"280px"},"onUpdate:value":e.onDateChange},null,8,["value"]),e.hasActiveFilters?(u(),C(d,{key:0,type:"link",danger:"",onClick:t[1]||(t[1]=_=>r.$emit("reset"))},{icon:m(()=>[c(e.CloseCircleOutlined)]),default:m(()=>[t[2]||(t[2]=b(" 清空筛选 ",-1))]),_:1})):x("v-if",!0),n.shortQuery?(u(),O("span",Re,[c(e.InfoCircleOutlined),t[3]||(t[3]=b(" 关键词需至少 3 字 (FTS5 trigram 限制) ",-1))])):n.mode==="like"?(u(),O("span",je,[c(e.InfoCircleOutlined),t[4]||(t[4]=b(" 当前为 LIKE 兜底模式 ",-1))])):x("v-if",!0)])}const Ae=F(xe,[["render",Te],["__scopeId","data-v-d7cce6e9"],["__file","/tmp/cc-web-panel-xIdTjN/repo/packages/web-panel/src/components/pdh/SearchFilterBar.vue"]]),Le={__name:"RendererDispatcher",props:{event:{type:Object,required:!0}},setup(r,{expose:t}){t();const n=A(()=>L(()=>import("./ChatBubbleRenderer-BGzg7oVA.js"),__vite__mapDeps([0,1,2,3,4,5]),import.meta.url)),e=A(()=>L(()=>import("./OrderTableRenderer-B5onE0eX.js"),__vite__mapDeps([6,1,2,3,4,7]),import.meta.url)),o=A(()=>L(()=>import("./TimelineRenderer-DTHzaXPt.js"),__vite__mapDeps([8,1,2,3,4,9]),import.meta.url)),l=A(()=>L(()=>import("./EmailListRenderer-D7XI1yBM.js"),__vite__mapDeps([10,1,2,3,4,11]),import.meta.url)),a=A(()=>L(()=>import("./GenericCardRenderer-nNT9Tn4E.js"),__vite__mapDeps([12,1,2,3,4,13]),import.meta.url));function s(d){const _=d&&d.source&&d.source.adapter;switch($(_)){case"chat":case"ai-chat":return n;case"shopping":return e;case"travel":return o;case"email":return l;default:return a}}const i={ChatBubbleRenderer:n,OrderTableRenderer:e,TimelineRenderer:o,EmailListRenderer:l,GenericCardRenderer:a,rendererFor:s,defineAsyncComponent:A,get getCategory(){return $}};return Object.defineProperty(i,"__isScriptSetup",{enumerable:!1,value:!0}),i}};function Fe(r,t,n,e,o,l){return u(),C(le(e.rendererFor(n.event)),{event:n.event},null,8,["event"])}const Ie=F(Le,[["render",Fe],["__file","/tmp/cc-web-panel-xIdTjN/repo/packages/web-panel/src/components/pdh/renderers/RendererDispatcher.vue"]]);function ee(r){return JSON.stringify(r,null,2)}function te(r){return r.map(t=>JSON.stringify(t)).join(`
3
- `)+`
4
- `}function ne(r){const n=["id","subtype","occurredAt","occurredAtIso","actor","place","adapter","summary","contentJson","extraJson"].join(","),e=r.map(o=>{const l=Number.isFinite(o.occurredAt)?o.occurredAt:null,a=l?new Date(l).toISOString():"",s=o.source&&o.source.adapter||"",i=o.content&&(o.content.text||o.content.title||o.content.subject)||"";return[o.id||"",o.subtype||"",l!=null?String(l):"",a,o.actor||"",o.place||"",s,i,o.content?JSON.stringify(o.content):"",o.extra?JSON.stringify(o.extra):""].map(De).join(",")});return[n,...e].join(`
5
- `)+`
6
- `}function De(r){const t=String(r??"");return t.includes(",")||t.includes('"')||t.includes(`
7
- `)||t.includes("\r")?'"'+t.replace(/"/g,'""')+'"':t}function re(r,t,n="application/octet-stream"){if(typeof window>"u"||typeof document>"u")return t;const e=new Blob([r],{type:n}),o=URL.createObjectURL(e),l=document.createElement("a");return l.href=o,l.download=t,document.body.appendChild(l),l.click(),document.body.removeChild(l),setTimeout(()=>URL.revokeObjectURL(o),1e3),t}function oe(r,t=null){const n=new Date,e=n.getFullYear(),o=String(n.getMonth()+1).padStart(2,"0"),l=String(n.getDate()).padStart(2,"0"),a=r==="ndjson"?"ndjson":r,s=t?`-${t}`:"";return`pdh-events-${e}-${o}-${l}${s}.${a}`}const Pe={__name:"ExportDropdown",props:{events:{type:Array,required:!0},category:{type:String,default:null}},setup(r,{expose:t}){t();const n=r,e=w(()=>n.events.length>0),o={json:"application/json;charset=utf-8",ndjson:"application/x-ndjson;charset=utf-8",csv:"text/csv;charset=utf-8"};function l(i){switch(i){case"json":return ee(n.events);case"ndjson":return te(n.events);case"csv":return ne(n.events);default:throw new Error(`unknown format: ${i}`)}}function a({key:i}){try{const d=l(i),_=oe(i,n.category);re(d,_,o[i]),P.success(`已导出 ${n.events.length} 条到 ${_}`)}catch(d){P.error(`导出失败: ${d.message||d}`)}}const s={props:n,hasResults:e,MIME:o,serialize:l,onClick:a,computed:w,get DownloadOutlined(){return _e},get DownOutlined(){return me},get message(){return P},get eventsToJson(){return ee},get eventsToNdjson(){return te},get eventsToCsv(){return ne},get downloadAs(){return re},get suggestFilename(){return oe}};return Object.defineProperty(s,"__isScriptSetup",{enumerable:!1,value:!0}),s}};function qe(r,t,n,e,o,l){const a=y("a-button"),s=y("a-menu-item"),i=y("a-menu"),d=y("a-dropdown");return u(),C(d,{disabled:!e.hasResults},{overlay:m(()=>[c(i,{onClick:e.onClick},{default:m(()=>[c(s,{key:"json"},{default:m(()=>[...t[0]||(t[0]=[b("JSON (.json)",-1)])]),_:1}),c(s,{key:"ndjson"},{default:m(()=>[...t[1]||(t[1]=[b("NDJSON (.ndjson)",-1)])]),_:1}),c(s,{key:"csv"},{default:m(()=>[...t[2]||(t[2]=[b("CSV (.csv)",-1)])]),_:1})]),_:1})]),default:m(()=>[c(a,{disabled:!e.hasResults},{icon:m(()=>[c(e.DownloadOutlined)]),default:m(()=>[b(" 导出 ("+R(n.events.length)+") ",1),c(e.DownOutlined)]),_:1},8,["disabled"])]),_:1},8,["disabled"])}const Ne=F(Pe,[["render",qe],["__file","/tmp/cc-web-panel-xIdTjN/repo/packages/web-panel/src/components/pdh/ExportDropdown.vue"]]),Be={__name:"PdhVaultBrowser",setup(r,{expose:t}){t();const n=X(),e=w(()=>n.filters.q?`没有匹配 "${n.filters.q}" 的事件 — 试试更短的关键词或换个类目`:n.filters.category?`「${V(n.filters.category)}」类目下还没有数据 — 去采集页同步对应 adapter`:"Vault 里还没有数据 — 去「个人数据中台」页面同步任意 adapter");function o(s){n.filters.category=s,n.search()}function l(s,i){n.setFilter(s,i)}J(()=>{!n.hasResults&&!n.isLoading&&n.search()});const a={store:n,emptyHint:e,onCategorySelect:o,onSetFilter:l,onMounted:J,computed:w,get ReloadOutlined(){return ge},get usePdhBrowserStore(){return X},get categoryLabel(){return V},CategorySidebar:ke,SearchFilterBar:Ae,RendererDispatcher:Ie,ExportDropdown:Ne};return Object.defineProperty(a,"__isScriptSetup",{enumerable:!1,value:!0}),a}},Ve={class:"pdh-browser-page"},Me={class:"page-header"},Je={class:"main-pane"},Ue={class:"results-summary"},ze={key:0},Qe={key:0},Ge={key:1},He={class:"loaded-of"},Ke={class:"results-list"},We={key:2,class:"load-more"};function Ye(r,t,n,e,o,l){const a=y("a-tag"),s=y("a-button"),i=y("a-space"),d=y("a-col"),_=y("a-spin"),j=y("a-alert"),T=y("a-empty"),h=y("a-row");return u(),O("div",Ve,[v("div",Me,[t[6]||(t[6]=v("div",null,[v("h2",{class:"page-title"},"数据浏览器"),v("p",{class:"page-sub"}," Vault 里所有已采集的数据,按类目浏览 / 全文检索 / 时间窗口筛选。 完全离线,不外传。 ")],-1)),c(i,null,{default:m(()=>[e.store.mode==="fts5"?(u(),C(a,{key:0,color:"green"},{default:m(()=>[...t[3]||(t[3]=[b("FTS5 trigram",-1)])]),_:1})):e.store.mode==="like"?(u(),C(a,{key:1,color:"orange"},{default:m(()=>[...t[4]||(t[4]=[b("LIKE 兜底",-1)])]),_:1})):x("v-if",!0),c(e.ExportDropdown,{events:e.store.results,category:e.store.filters.category},null,8,["events","category"]),c(s,{onClick:t[0]||(t[0]=g=>e.store.search()),loading:e.store.isLoading},{icon:m(()=>[c(e.ReloadOutlined)]),default:m(()=>[t[5]||(t[5]=b(" 刷新 ",-1))]),_:1},8,["loading"])]),_:1})]),c(h,{gutter:16,class:"browser-layout"},{default:m(()=>[c(d,{xs:24,sm:24,md:6,lg:5,xl:4},{default:m(()=>[c(e.CategorySidebar,{selected:e.store.filters.category,facets:e.store.facets,onSelect:e.onCategorySelect},null,8,["selected","facets"])]),_:1}),c(d,{xs:24,sm:24,md:18,lg:19,xl:20},{default:m(()=>[v("div",Je,[c(e.SearchFilterBar,{filters:e.store.filters,facets:e.store.facets,"is-loading":e.store.isLoading,mode:e.store.mode,"short-query":e.store.shortQuery,onSetFilter:e.onSetFilter,onReset:t[1]||(t[1]=g=>{e.store.reset(),e.store.search()})},null,8,["filters","facets","is-loading","mode","short-query"]),v("div",Ue,[e.store.isLoading&&e.store.results.length===0?(u(),O("span",ze,[c(_,{size:"small"}),t[7]||(t[7]=b(" 载入中… ",-1))])):(u(),O(B,{key:1},[v("strong",null,R(e.store.facets.total),1),t[11]||(t[11]=b(" 条事件 ",-1)),e.store.filters.category?(u(),O("span",Qe,[t[8]||(t[8]=b(" / 当前类目 ",-1)),v("strong",null,R(e.categoryLabel(e.store.filters.category)),1),v("strong",null,R(e.store.facets.byCategory[e.store.filters.category]||0),1)])):x("v-if",!0),e.store.filters.q?(u(),O("span",Ge,[t[9]||(t[9]=b(' / 关键词 "',-1)),v("em",null,R(e.store.filters.q),1),t[10]||(t[10]=b('"',-1))])):x("v-if",!0),v("span",He," / 已显示 "+R(e.store.results.length),1)],64))]),e.store.error?(u(),C(j,{key:0,type:"error","show-icon":"",message:e.store.error,closable:"",style:{margin:"12px 0"}},null,8,["message"])):x("v-if",!0),!e.store.isLoading&&e.store.results.length===0&&!e.store.error?(u(),C(T,{key:1,description:e.emptyHint,style:{"margin-top":"40px"}},null,8,["description"])):x("v-if",!0),v("div",Ke,[(u(!0),O(B,null,se(e.store.results,(g,k)=>(u(),C(e.RendererDispatcher,{key:`r-${k}-${g.id}`,event:g},null,8,["event"]))),128))]),e.store.canLoadMore?(u(),O("div",We,[c(s,{loading:e.store.isAppending,onClick:t[2]||(t[2]=g=>e.store.loadMore()),block:""},{default:m(()=>[...t[12]||(t[12]=[b(" 加载下一页 (50 条) ",-1)])]),_:1},8,["loading"])])):x("v-if",!0)])]),_:1})]),_:1})])}const tt=F(Be,[["render",Ye],["__scopeId","data-v-0f7c02cd"],["__file","/tmp/cc-web-panel-xIdTjN/repo/packages/web-panel/src/views/PdhVaultBrowser.vue"]]);export{tt as default};
@@ -1 +0,0 @@
1
- import{I as i,J as A,U,R as s,Q as r,c as t,K as a,V as _,S as x,o as oe,b as ee,r as u,P as p,F as ne,a2 as ge}from"./vendor-BvqAck49.js";import{_ as we,b as re,u as ie,d}from"./index-DWcd5zDG.js";import{u as de}from"./useShellMode-CgR0wCYM.js";import{aM as ke,aN as Fe,aO as be,f as je,a4 as Ce,a7 as xe,as as Oe,R as Se}from"./icons-DP3uiYxy.js";const Pe={__name:"Projects",setup(se,{expose:l}){l();const{t:te}=re(),e=ie(),{isEmbedded:W}=de();async function w(o,f,ye,ae=8e3){if(W){const Z=await e.sendRaw({...f,type:o},ae);if(!Z?.ok){const $=Z?.error;throw new Error(typeof $=="string"?$:$?.message||`${o} failed`)}return Z.result}return e.executeJson(ye,ae)}const B=u(!1),y=u([]),O=u(""),S=u(""),P=u(!1),v=u(null),h=u([]),k=u(!1),E=u(!1),L=u(!1),F=u({name:"",description:"",type:"document",rootPath:""}),z=[{title:"ID",key:"id",width:110},{title:"名称",key:"name"},{title:"类型",key:"project_type",width:120},{title:"状态",key:"status",width:100},{title:"同步",key:"sync_status",width:100},{title:"更新",key:"updated_at",width:160},{title:"操作",key:"actions",width:180,fixed:"right"}],M=ee(()=>{const o={active:0,draft:0,completed:0,archived:0};for(const f of y.value)o[f.status]!==void 0&&(o[f.status]+=1);return o}),J=ee(()=>y.value.filter(o=>!(O.value&&o.status!==O.value||S.value&&!o.name.toLowerCase().includes(S.value.toLowerCase()))));function g(o){switch(o){case"active":return"green";case"draft":return"default";case"completed":return"cyan";case"archived":return"gold";default:return"default"}}function K(o){switch(o){case"synced":return"green";case"pending":return"orange";case"conflict":return"red";case"error":return"red";default:return"default"}}function Q(o){return!o&&o!==0?"-":new Date(typeof o=="number"?o:parseInt(o,10)).toLocaleString("zh-CN",{hour12:!1})}async function C(){B.value=!0;try{const o=await w("project.list",{limit:500},"project list --limit 500 --json",1e4);y.value=Array.isArray(o?.projects)?o.projects:Array.isArray(o)?o:[]}catch(o){d.error("加载失败: "+(o.message||o)),y.value=[]}finally{B.value=!1}}function G(o){return{onClick:()=>V(o)}}async function V(o){v.value=o,P.value=!0,k.value=!0,h.value=[];try{const f=await w("project.listFiles",{projectId:o.id,limit:200},`project list-files ${o.id} --json`,8e3);h.value=Array.isArray(f?.files)?f.files:[]}catch{h.value=[]}finally{k.value=!1}}async function H(o){try{(await w("project.delete",{id:o.id},`project delete ${o.id} --json`,8e3))?.ok?(d.success(`已删除项目 '${o.name}'`),P.value=!1,await C()):d.error("删除失败")}catch(f){d.error(f.message||String(f))}}function X(){F.value={name:"",description:"",type:"document",rootPath:""},E.value=!0}async function T(){if(!F.value.name.trim()){d.warning("请输入项目名称");return}L.value=!0;try{const o=await w("project.init",{name:F.value.name.trim(),description:F.value.description||null,projectType:F.value.type,rootPath:F.value.rootPath||null},`project init "${F.value.name.trim()}" --type ${F.value.type} --json`,8e3);o?.id?(d.success(`已创建项目 '${o.name}'`),E.value=!1,await C()):d.error("创建失败")}catch(o){d.error(o.message||String(o))}finally{L.value=!1}}const b=u(!1),D=u(!1),j=u({path:"",content:""}),I=u(!1),m=u(!1),R=u({path:""}),n=u(!1),c=u(null),N=u(""),Y=u(!1);function ue(){j.value={path:"",content:""},b.value=!0}function ce(){R.value={path:""},I.value=!0}async function q(){if(v.value){k.value=!0;try{const o=await w("project.listFiles",{projectId:v.value.id,limit:200},`project list-files ${v.value.id} --json`,8e3);h.value=Array.isArray(o?.files)?o.files:[]}catch(o){d.error("刷新文件失败: "+(o.message||o))}finally{k.value=!1}}}async function fe(){if(!j.value.path.trim()){d.warning("请输入文件路径");return}if(v.value){D.value=!0;try{const o=await w("project.createFile",{projectId:v.value.id,filePath:j.value.path.trim(),content:j.value.content||""},`project create-file ${v.value.id} "${j.value.path.trim()}" --json`,8e3);o?.id?(d.success(`已创建文件 '${o.file_name}'`),b.value=!1,await q(),await C()):d.error("创建文件失败")}catch(o){d.error(o.message||String(o))}finally{D.value=!1}}}async function pe(){if(!R.value.path.trim()){d.warning("请输入文件夹路径");return}if(v.value){m.value=!0;try{const o=await w("project.createFolder",{projectId:v.value.id,folderPath:R.value.path.trim()},`project create-folder ${v.value.id} "${R.value.path.trim()}" --json`,8e3);o?.id?(d.success(`已创建文件夹 '${o.file_name}'`),I.value=!1,await q(),await C()):d.error("创建文件夹失败")}catch(o){d.error(o.message||String(o))}finally{m.value=!1}}}async function ve(o){try{(await w("project.deleteFile",{fileId:o.id},`project delete-file ${o.id} --json`,8e3))?.deleted?(d.success(`已删除 '${o.file_name}'`),await q(),await C()):d.error("删除失败")}catch(f){d.error(f.message||String(f))}}async function me(o){if(o.is_folder){d.info("文件夹无内容可编辑");return}try{const f=await w("project.getFile",{fileId:o.id},`project get-file ${o.id} --json`,8e3);c.value=o,N.value=f?.content||"",n.value=!0}catch(f){d.error("读取文件失败: "+(f.message||f))}}async function _e(){if(c.value){Y.value=!0;try{(await w("project.writeFile",{fileId:c.value.id,content:N.value},`project write-file ${c.value.id} --json`,8e3))?.id?(d.success("已保存"),n.value=!1,await q()):d.error("保存失败")}catch(o){d.error(o.message||String(o))}finally{Y.value=!1}}}oe(()=>{C()});const le={t:te,ws:e,isEmbedded:W,callProjectTopic:w,loading:B,projects:y,statusFilter:O,nameFilter:S,detailOpen:P,detail:v,files:h,filesLoading:k,createOpen:E,creating:L,newProject:F,columns:z,countByStatus:M,filteredProjects:J,statusColor:g,syncColor:K,formatTime:Q,loadAll:C,onRowClick:G,openDetail:V,onDelete:H,onShowCreate:X,onCreate:T,createFileOpen:b,creatingFile:D,newFile:j,createFolderOpen:I,creatingFolder:m,newFolder:R,editFileOpen:n,editingFile:c,editFileContent:N,savingFile:Y,openCreateFile:ue,openCreateFolder:ce,refreshFiles:q,onCreateFile:fe,onCreateFolder:pe,onDeleteFile:ve,openEditFile:me,onSaveFile:_e,ref:u,computed:ee,onMounted:oe,get ReloadOutlined(){return Se},get PlusOutlined(){return Oe},get FolderOutlined(){return xe},get FileTextOutlined(){return Ce},get CheckCircleOutlined(){return je},get CheckSquareOutlined(){return be},get FileAddOutlined(){return Fe},get FolderAddOutlined(){return ke},get message(){return d},get useI18n(){return re},get useWsStore(){return ie},get useShellMode(){return de}};return Object.defineProperty(le,"__isScriptSetup",{enumerable:!1,value:!0}),le}},ze={style:{display:"flex","align-items":"center","justify-content":"space-between","margin-bottom":"24px"}},Ie={class:"page-title"},Ae={class:"page-sub"},Ue={class:"filter-bar",style:{"margin-bottom":"12px",display:"flex",gap:"12px","align-items":"center"}},he={key:0,style:{"font-size":"12px",color:"#888"}},De={key:0,style:{color:"#888","font-size":"12px"}},Re={key:0},Te={key:1,style:{color:"#888"}},Be=["onClick"],Ee={key:0,style:{color:"#888","font-size":"12px"}};function Le(se,l,te,e,W,w){const B=i("router-link"),y=i("a-button"),O=i("a-space"),S=i("a-statistic"),P=i("a-card"),v=i("a-col"),h=i("a-row"),k=i("a-radio-button"),E=i("a-radio-group"),L=i("a-input-search"),F=i("a-alert"),z=i("a-tag"),M=i("a-popconfirm"),J=i("a-table"),g=i("a-descriptions-item"),K=i("a-descriptions"),Q=i("a-divider"),C=i("a-empty"),G=i("a-list-item"),V=i("a-list"),H=i("a-spin"),X=i("a-drawer"),T=i("a-input"),b=i("a-form-item"),D=i("a-textarea"),j=i("a-form"),I=i("a-modal"),m=i("a-select-option"),R=i("a-select");return p(),A("div",null,[U("div",ze,[U("div",null,[U("h2",Ie,s(e.t("projects.title")),1),U("p",Ae,[l[17]||(l[17]=r("桌面 / CLI / 手机 三端共享同一份项目数据,Phase 3d sync 自动同步 (",-1)),t(B,{to:"/project-init"},{default:a(()=>[...l[16]||(l[16]=[r("项目初始化 / 环境设置",-1)])]),_:1}),l[18]||(l[18]=r(")",-1))])]),t(O,null,{default:a(()=>[t(y,{loading:e.loading,onClick:e.loadAll},{icon:a(()=>[t(e.ReloadOutlined)]),default:a(()=>[l[19]||(l[19]=r(" 刷新 ",-1))]),_:1},8,["loading"]),t(y,{type:"primary",onClick:e.onShowCreate},{icon:a(()=>[t(e.PlusOutlined)]),default:a(()=>[l[20]||(l[20]=r(" 新建项目 ",-1))]),_:1})]),_:1})]),_(" Stats "),t(h,{gutter:[16,16],style:{"margin-bottom":"20px"}},{default:a(()=>[t(v,{xs:12,sm:8,lg:6},{default:a(()=>[t(P,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"}},{default:a(()=>[t(S,{title:"总项目",value:e.projects.length,"value-style":{color:"#1677ff",fontSize:"20px"}},{prefix:a(()=>[t(e.FolderOutlined)]),_:1},8,["value"])]),_:1})]),_:1}),t(v,{xs:12,sm:8,lg:6},{default:a(()=>[t(P,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"}},{default:a(()=>[t(S,{title:"活跃",value:e.countByStatus.active,"value-style":{color:"#52c41a",fontSize:"20px"}},{prefix:a(()=>[t(e.CheckCircleOutlined)]),_:1},8,["value"])]),_:1})]),_:1}),t(v,{xs:12,sm:8,lg:6},{default:a(()=>[t(P,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"}},{default:a(()=>[t(S,{title:"草稿",value:e.countByStatus.draft,"value-style":{color:"#8c8c8c",fontSize:"20px"}},{prefix:a(()=>[t(e.FileTextOutlined)]),_:1},8,["value"])]),_:1})]),_:1}),t(v,{xs:12,sm:8,lg:6},{default:a(()=>[t(P,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"}},{default:a(()=>[t(S,{title:"已完成",value:e.countByStatus.completed,"value-style":{color:"#13c2c2",fontSize:"20px"}},{prefix:a(()=>[t(e.CheckSquareOutlined)]),_:1},8,["value"])]),_:1})]),_:1})]),_:1}),_(" Filter "),U("div",Ue,[t(E,{value:e.statusFilter,"onUpdate:value":l[0]||(l[0]=n=>e.statusFilter=n),size:"small","button-style":"solid"},{default:a(()=>[t(k,{value:""},{default:a(()=>[...l[21]||(l[21]=[r("全部",-1)])]),_:1}),t(k,{value:"active"},{default:a(()=>[...l[22]||(l[22]=[r("活跃",-1)])]),_:1}),t(k,{value:"draft"},{default:a(()=>[...l[23]||(l[23]=[r("草稿",-1)])]),_:1}),t(k,{value:"completed"},{default:a(()=>[...l[24]||(l[24]=[r("已完成",-1)])]),_:1}),t(k,{value:"archived"},{default:a(()=>[...l[25]||(l[25]=[r("已归档",-1)])]),_:1})]),_:1},8,["value"]),t(L,{value:e.nameFilter,"onUpdate:value":l[1]||(l[1]=n=>e.nameFilter=n),placeholder:"按名称过滤",style:{"max-width":"260px"},"allow-clear":""},null,8,["value"])]),!e.projects.length&&!e.loading?(p(),x(F,{key:0,type:"info",message:"还没有项目",description:'运行 `cc project init <name>` 或点击右上角"新建项目"按钮创建。桌面 / CLI / 手机三端共享同一份数据。',"show-icon":"",style:{"margin-bottom":"16px"}})):_("v-if",!0),e.projects.length||e.loading?(p(),x(J,{key:1,columns:e.columns,"data-source":e.filteredProjects,loading:e.loading,pagination:{pageSize:20,showSizeChanger:!0},"row-key":"id","custom-row":e.onRowClick},{bodyCell:a(({column:n,record:c})=>[n.key==="id"?(p(),A("code",he,s(c.id.slice(0,8))+"…",1)):n.key==="name"?(p(),A(ne,{key:1},[U("strong",null,s(c.name),1),c.description?(p(),A("div",De,s(c.description),1)):_("v-if",!0)],64)):n.key==="project_type"?(p(),x(z,{key:2},{default:a(()=>[r(s(c.project_type),1)]),_:2},1024)):n.key==="status"?(p(),x(z,{key:3,color:e.statusColor(c.status)},{default:a(()=>[r(s(c.status),1)]),_:2},1032,["color"])):n.key==="sync_status"?(p(),x(z,{key:4,color:e.syncColor(c.sync_status)},{default:a(()=>[r(s(c.sync_status||"unknown"),1)]),_:2},1032,["color"])):n.key==="updated_at"?(p(),A(ne,{key:5},[r(s(e.formatTime(c.updated_at)),1)],64)):n.key==="actions"?(p(),x(O,{key:6,onClick:l[2]||(l[2]=ge(()=>{},["stop"]))},{default:a(()=>[t(y,{size:"small",onClick:N=>e.openDetail(c)},{default:a(()=>[...l[26]||(l[26]=[r("详情",-1)])]),_:1},8,["onClick"]),t(M,{title:`删除项目 '${c.name}' ?`,"ok-text":"删除","ok-type":"danger","cancel-text":"取消",onConfirm:N=>e.onDelete(c)},{default:a(()=>[t(y,{size:"small",danger:""},{default:a(()=>[...l[27]||(l[27]=[r("删除",-1)])]),_:1})]),_:1},8,["title","onConfirm"])]),_:2},1024)):_("v-if",!0)]),_:1},8,["data-source","loading"])):_("v-if",!0),_(" Detail drawer "),t(X,{open:e.detailOpen,"onUpdate:open":l[3]||(l[3]=n=>e.detailOpen=n),title:e.detail?.name||"项目详情",width:"640",placement:"right"},{default:a(()=>[e.detail?(p(),x(K,{key:0,column:1,bordered:"",size:"small"},{default:a(()=>[t(g,{label:"ID"},{default:a(()=>[U("code",null,s(e.detail.id),1)]),_:1}),t(g,{label:"名称"},{default:a(()=>[r(s(e.detail.name),1)]),_:1}),t(g,{label:"描述"},{default:a(()=>[r(s(e.detail.description||"-"),1)]),_:1}),t(g,{label:"类型"},{default:a(()=>[t(z,null,{default:a(()=>[r(s(e.detail.project_type),1)]),_:1})]),_:1}),t(g,{label:"状态"},{default:a(()=>[t(z,{color:e.statusColor(e.detail.status)},{default:a(()=>[r(s(e.detail.status),1)]),_:1},8,["color"])]),_:1}),t(g,{label:"同步状态"},{default:a(()=>[t(z,{color:e.syncColor(e.detail.sync_status)},{default:a(()=>[r(s(e.detail.sync_status||"unknown"),1)]),_:1},8,["color"])]),_:1}),t(g,{label:"用户"},{default:a(()=>[r(s(e.detail.user_id),1)]),_:1}),t(g,{label:"根路径"},{default:a(()=>[e.detail.root_path?(p(),A("code",Re,s(e.detail.root_path),1)):(p(),A("span",Te,"(无)"))]),_:1}),t(g,{label:"文件数"},{default:a(()=>[r(s(e.detail.file_count||0),1)]),_:1}),t(g,{label:"创建"},{default:a(()=>[r(s(e.formatTime(e.detail.created_at)),1)]),_:1}),t(g,{label:"更新"},{default:a(()=>[r(s(e.formatTime(e.detail.updated_at)),1)]),_:1})]),_:1})):_("v-if",!0),t(Q,null,{default:a(()=>[...l[28]||(l[28]=[r("文件",-1)])]),_:1}),_(" Sub-phase 7.3 (2026-05-17): 文件 CRUD toolbar "),t(O,{style:{"margin-bottom":"12px"}},{default:a(()=>[t(y,{size:"small",type:"primary",disabled:!e.detail,onClick:e.openCreateFile},{default:a(()=>[t(e.FileAddOutlined),l[29]||(l[29]=r(" 新建文件 ",-1))]),_:1},8,["disabled"]),t(y,{size:"small",disabled:!e.detail,onClick:e.openCreateFolder},{default:a(()=>[t(e.FolderAddOutlined),l[30]||(l[30]=r(" 新建文件夹 ",-1))]),_:1},8,["disabled"])]),_:1}),t(H,{spinning:e.filesLoading},{default:a(()=>[!e.files.length&&!e.filesLoading?(p(),x(C,{key:0,description:"无文件 (点上方按钮新建)"})):(p(),x(V,{key:1,size:"small","data-source":e.files},{renderItem:a(({item:n})=>[t(G,null,{extra:a(()=>[t(O,null,{default:a(()=>[n.file_size?(p(),A("span",Ee,s(n.file_size)+" B",1)):_("v-if",!0),t(M,{title:`删除 ${n.is_folder?"文件夹":"文件"} '${n.file_name}' ?`,"ok-text":"删除","ok-type":"danger","cancel-text":"取消",onConfirm:c=>e.onDeleteFile(n)},{default:a(()=>[t(y,{size:"small",danger:""},{default:a(()=>[...l[31]||(l[31]=[r("×",-1)])]),_:1})]),_:1},8,["title","onConfirm"])]),_:2},1024)]),default:a(()=>[U("span",{style:{cursor:"pointer"},onClick:c=>e.openEditFile(n)},s(n.is_folder?"📁":"📄")+" "+s(n.file_path),9,Be)]),_:2},1024)]),_:1},8,["data-source"]))]),_:1},8,["spinning"])]),_:1},8,["open","title"]),_(" Sub-phase 7.3: Create file modal "),t(I,{open:e.createFileOpen,"onUpdate:open":l[6]||(l[6]=n=>e.createFileOpen=n),title:"新建文件","confirm-loading":e.creatingFile,"ok-text":"创建","cancel-text":"取消",onOk:e.onCreateFile},{default:a(()=>[t(j,{layout:"vertical"},{default:a(()=>[t(b,{label:"文件路径(项目内)",required:""},{default:a(()=>[t(T,{value:e.newFile.path,"onUpdate:value":l[4]||(l[4]=n=>e.newFile.path=n),placeholder:"例如 README.md 或 src/main.kt"},null,8,["value"])]),_:1}),t(b,{label:"初始内容(可选)"},{default:a(()=>[t(D,{value:e.newFile.content,"onUpdate:value":l[5]||(l[5]=n=>e.newFile.content=n),rows:6,placeholder:"留空创建空文件"},null,8,["value"])]),_:1})]),_:1})]),_:1},8,["open","confirm-loading"]),_(" Sub-phase 7.3: Create folder modal "),t(I,{open:e.createFolderOpen,"onUpdate:open":l[8]||(l[8]=n=>e.createFolderOpen=n),title:"新建文件夹","confirm-loading":e.creatingFolder,"ok-text":"创建","cancel-text":"取消",onOk:e.onCreateFolder},{default:a(()=>[t(j,{layout:"vertical"},{default:a(()=>[t(b,{label:"文件夹路径(项目内)",required:""},{default:a(()=>[t(T,{value:e.newFolder.path,"onUpdate:value":l[7]||(l[7]=n=>e.newFolder.path=n),placeholder:"例如 src/utils"},null,8,["value"])]),_:1})]),_:1})]),_:1},8,["open","confirm-loading"]),_(" Sub-phase 7.3: Edit file content modal "),t(I,{open:e.editFileOpen,"onUpdate:open":l[10]||(l[10]=n=>e.editFileOpen=n),title:`编辑 ${e.editingFile?.file_name||""}`,"confirm-loading":e.savingFile,"ok-text":"保存","cancel-text":"取消",onOk:e.onSaveFile,width:"720"},{default:a(()=>[t(D,{value:e.editFileContent,"onUpdate:value":l[9]||(l[9]=n=>e.editFileContent=n),rows:18,"auto-size":{minRows:12,maxRows:24},style:{"font-family":"monospace"}},null,8,["value"])]),_:1},8,["open","title","confirm-loading"]),_(" Create modal "),t(I,{open:e.createOpen,"onUpdate:open":l[15]||(l[15]=n=>e.createOpen=n),title:"新建项目","confirm-loading":e.creating,"ok-text":"创建","cancel-text":"取消",onOk:e.onCreate},{default:a(()=>[t(j,{layout:"vertical"},{default:a(()=>[t(b,{label:"项目名称",required:""},{default:a(()=>[t(T,{value:e.newProject.name,"onUpdate:value":l[11]||(l[11]=n=>e.newProject.name=n),placeholder:"例如:旅行计划-上海"},null,8,["value"])]),_:1}),t(b,{label:"描述"},{default:a(()=>[t(D,{value:e.newProject.description,"onUpdate:value":l[12]||(l[12]=n=>e.newProject.description=n),rows:2},null,8,["value"])]),_:1}),t(b,{label:"类型"},{default:a(()=>[t(R,{value:e.newProject.type,"onUpdate:value":l[13]||(l[13]=n=>e.newProject.type=n)},{default:a(()=>[t(m,{value:"document"},{default:a(()=>[...l[32]||(l[32]=[r("文档 (document)",-1)])]),_:1}),t(m,{value:"data"},{default:a(()=>[...l[33]||(l[33]=[r("数据 (data)",-1)])]),_:1}),t(m,{value:"web"},{default:a(()=>[...l[34]||(l[34]=[r("Web",-1)])]),_:1}),t(m,{value:"app"},{default:a(()=>[...l[35]||(l[35]=[r("应用 (app)",-1)])]),_:1}),t(m,{value:"presentation"},{default:a(()=>[...l[36]||(l[36]=[r("演示文稿",-1)])]),_:1}),t(m,{value:"spreadsheet"},{default:a(()=>[...l[37]||(l[37]=[r("表格",-1)])]),_:1}),t(m,{value:"design"},{default:a(()=>[...l[38]||(l[38]=[r("设计",-1)])]),_:1}),t(m,{value:"code"},{default:a(()=>[...l[39]||(l[39]=[r("代码",-1)])]),_:1}),t(m,{value:"workflow"},{default:a(()=>[...l[40]||(l[40]=[r("工作流",-1)])]),_:1}),t(m,{value:"knowledge"},{default:a(()=>[...l[41]||(l[41]=[r("知识库",-1)])]),_:1})]),_:1},8,["value"])]),_:1}),t(b,{label:"根路径 (可选)"},{default:a(()=>[t(T,{value:e.newProject.rootPath,"onUpdate:value":l[14]||(l[14]=n=>e.newProject.rootPath=n),placeholder:"留空则仅元数据"},null,8,["value"])]),_:1})]),_:1})]),_:1},8,["open","confirm-loading"])])}const We=we(Pe,[["render",Le],["__scopeId","data-v-019ac5aa"],["__file","/tmp/cc-web-panel-xIdTjN/repo/packages/web-panel/src/views/Projects.vue"]]);export{We as default};
@@ -1 +0,0 @@
1
- import{O as r}from"./index-DWcd5zDG.js";const o=((n,a,e)=>{r(n,`[ant-design-vue: ${a}] ${e}`)});export{o as d};
@@ -1 +0,0 @@
1
- import{A as o}from"./Row-DthhwX_B.js";import{U as t}from"./index-DWcd5zDG.js";import"./vendor-BvqAck49.js";import"./responsiveObserve-BzrWT5tV.js";import"./useFlexGapSupport-D4oVdliM.js";import"./styleChecker-DMw-eyn9.js";import"./index-BXMZLfd8.js";import"./icons-DP3uiYxy.js";const l=t(o);export{l as default};
@@ -1 +0,0 @@
1
- import{C as o}from"./Col-Br9IXZcE.js";import{U as t}from"./index-DWcd5zDG.js";import"./vendor-BvqAck49.js";import"./index-BXMZLfd8.js";import"./icons-DP3uiYxy.js";const s=t(o);export{s as default};