@drscrewdriver/dsh-better-display 0.3.3-fork.1
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/CHANGELOG.md +259 -0
- package/DESIGN.md +72 -0
- package/LICENSE +24 -0
- package/README.en.md +55 -0
- package/README.md +55 -0
- package/THIRD_PARTY_NOTICES.md +65 -0
- package/compat/harness-rc2.json +99 -0
- package/cordis.patch.yml +5 -0
- package/cordis.yml +4 -0
- package/docs/official-rendering-bridge.md +65 -0
- package/dshx.yml +5 -0
- package/lib/client.js +49292 -0
- package/lib/client.js.map +1 -0
- package/lib/dsh-better-display.js +101 -0
- package/lib/types/client/Blocks.d.ts +49 -0
- package/lib/types/client/Blocks.d.ts.map +1 -0
- package/lib/types/client/Blocks.js +143 -0
- package/lib/types/client/Blocks.js.map +1 -0
- package/lib/types/client/ChoreographedFlow.d.ts +22 -0
- package/lib/types/client/ChoreographedFlow.d.ts.map +1 -0
- package/lib/types/client/ChoreographedFlow.js +218 -0
- package/lib/types/client/ChoreographedFlow.js.map +1 -0
- package/lib/types/client/ClosedProcessSummary.d.ts +9 -0
- package/lib/types/client/ClosedProcessSummary.d.ts.map +1 -0
- package/lib/types/client/ClosedProcessSummary.js +16 -0
- package/lib/types/client/ClosedProcessSummary.js.map +1 -0
- package/lib/types/client/DiffPanel.d.ts +13 -0
- package/lib/types/client/DiffPanel.d.ts.map +1 -0
- package/lib/types/client/DiffPanel.js +115 -0
- package/lib/types/client/DiffPanel.js.map +1 -0
- package/lib/types/client/LiveFold.d.ts +10 -0
- package/lib/types/client/LiveFold.d.ts.map +1 -0
- package/lib/types/client/LiveFold.js +39 -0
- package/lib/types/client/LiveFold.js.map +1 -0
- package/lib/types/client/McpAppFrame.d.ts +32 -0
- package/lib/types/client/McpAppFrame.d.ts.map +1 -0
- package/lib/types/client/McpAppFrame.js +193 -0
- package/lib/types/client/McpAppFrame.js.map +1 -0
- package/lib/types/client/OfficialContent.d.ts +25 -0
- package/lib/types/client/OfficialContent.d.ts.map +1 -0
- package/lib/types/client/OfficialContent.js +53 -0
- package/lib/types/client/OfficialContent.js.map +1 -0
- package/lib/types/client/Reader.d.ts +3 -0
- package/lib/types/client/Reader.d.ts.map +1 -0
- package/lib/types/client/Reader.js +603 -0
- package/lib/types/client/Reader.js.map +1 -0
- package/lib/types/client/ReasoningCard.d.ts +11 -0
- package/lib/types/client/ReasoningCard.d.ts.map +1 -0
- package/lib/types/client/ReasoningCard.js +322 -0
- package/lib/types/client/ReasoningCard.js.map +1 -0
- package/lib/types/client/SettingsSection.d.ts +37 -0
- package/lib/types/client/SettingsSection.d.ts.map +1 -0
- package/lib/types/client/SettingsSection.js +63 -0
- package/lib/types/client/SettingsSection.js.map +1 -0
- package/lib/types/client/StickyLane.d.ts +8 -0
- package/lib/types/client/StickyLane.d.ts.map +1 -0
- package/lib/types/client/StickyLane.js +39 -0
- package/lib/types/client/StickyLane.js.map +1 -0
- package/lib/types/client/TimelineRail.d.ts +10 -0
- package/lib/types/client/TimelineRail.d.ts.map +1 -0
- package/lib/types/client/TimelineRail.js +168 -0
- package/lib/types/client/TimelineRail.js.map +1 -0
- package/lib/types/client/ToolActivity.d.ts +17 -0
- package/lib/types/client/ToolActivity.d.ts.map +1 -0
- package/lib/types/client/ToolActivity.js +244 -0
- package/lib/types/client/ToolActivity.js.map +1 -0
- package/lib/types/client/TurnMetrics.d.ts +11 -0
- package/lib/types/client/TurnMetrics.d.ts.map +1 -0
- package/lib/types/client/TurnMetrics.js +44 -0
- package/lib/types/client/TurnMetrics.js.map +1 -0
- package/lib/types/client/WaitClock.d.ts +16 -0
- package/lib/types/client/WaitClock.d.ts.map +1 -0
- package/lib/types/client/WaitClock.js +29 -0
- package/lib/types/client/WaitClock.js.map +1 -0
- package/lib/types/client/WaitingClock.d.ts +15 -0
- package/lib/types/client/WaitingClock.d.ts.map +1 -0
- package/lib/types/client/WaitingClock.js +30 -0
- package/lib/types/client/WaitingClock.js.map +1 -0
- package/lib/types/client/WaitingStatus.d.ts +6 -0
- package/lib/types/client/WaitingStatus.d.ts.map +1 -0
- package/lib/types/client/WaitingStatus.js +9 -0
- package/lib/types/client/WaitingStatus.js.map +1 -0
- package/lib/types/client/conversation-scroll.d.ts +19 -0
- package/lib/types/client/conversation-scroll.d.ts.map +1 -0
- package/lib/types/client/conversation-scroll.js +25 -0
- package/lib/types/client/conversation-scroll.js.map +1 -0
- package/lib/types/client/deliverables.d.ts +24 -0
- package/lib/types/client/deliverables.d.ts.map +1 -0
- package/lib/types/client/deliverables.js +104 -0
- package/lib/types/client/deliverables.js.map +1 -0
- package/lib/types/client/entry-policy.d.ts +10 -0
- package/lib/types/client/entry-policy.d.ts.map +1 -0
- package/lib/types/client/entry-policy.js +24 -0
- package/lib/types/client/entry-policy.js.map +1 -0
- package/lib/types/client/entry.d.ts +4 -0
- package/lib/types/client/entry.d.ts.map +1 -0
- package/lib/types/client/entry.js +34 -0
- package/lib/types/client/entry.js.map +1 -0
- package/lib/types/client/fold-choreography.d.ts +40 -0
- package/lib/types/client/fold-choreography.d.ts.map +1 -0
- package/lib/types/client/fold-choreography.js +48 -0
- package/lib/types/client/fold-choreography.js.map +1 -0
- package/lib/types/client/fold-intensity.d.ts +11 -0
- package/lib/types/client/fold-intensity.d.ts.map +1 -0
- package/lib/types/client/fold-intensity.js +32 -0
- package/lib/types/client/fold-intensity.js.map +1 -0
- package/lib/types/client/index.d.ts +7 -0
- package/lib/types/client/index.d.ts.map +1 -0
- package/lib/types/client/index.js +195 -0
- package/lib/types/client/index.js.map +1 -0
- package/lib/types/client/live-turn.d.ts +58 -0
- package/lib/types/client/live-turn.d.ts.map +1 -0
- package/lib/types/client/live-turn.js +190 -0
- package/lib/types/client/live-turn.js.map +1 -0
- package/lib/types/client/markdown/MarkdownText.d.ts +41 -0
- package/lib/types/client/markdown/MarkdownText.d.ts.map +1 -0
- package/lib/types/client/markdown/MarkdownText.js +178 -0
- package/lib/types/client/markdown/MarkdownText.js.map +1 -0
- package/lib/types/client/markdown/cjkFriendlyStrong.d.ts +9 -0
- package/lib/types/client/markdown/cjkFriendlyStrong.d.ts.map +1 -0
- package/lib/types/client/markdown/cjkFriendlyStrong.js +73 -0
- package/lib/types/client/markdown/cjkFriendlyStrong.js.map +1 -0
- package/lib/types/client/markdown/incremental.d.ts +69 -0
- package/lib/types/client/markdown/incremental.d.ts.map +1 -0
- package/lib/types/client/markdown/incremental.js +108 -0
- package/lib/types/client/markdown/incremental.js.map +1 -0
- package/lib/types/client/markdown/katex.d.ts +27 -0
- package/lib/types/client/markdown/katex.d.ts.map +1 -0
- package/lib/types/client/markdown/katex.js +88 -0
- package/lib/types/client/markdown/katex.js.map +1 -0
- package/lib/types/client/markdown/mathCompatibility.d.ts +11 -0
- package/lib/types/client/markdown/mathCompatibility.d.ts.map +1 -0
- package/lib/types/client/markdown/mathCompatibility.js +293 -0
- package/lib/types/client/markdown/mathCompatibility.js.map +1 -0
- package/lib/types/client/markdown/parse.d.ts +25 -0
- package/lib/types/client/markdown/parse.d.ts.map +1 -0
- package/lib/types/client/markdown/parse.js +42 -0
- package/lib/types/client/markdown/parse.js.map +1 -0
- package/lib/types/client/markdown/render.d.ts +121 -0
- package/lib/types/client/markdown/render.d.ts.map +1 -0
- package/lib/types/client/markdown/render.js +452 -0
- package/lib/types/client/markdown/render.js.map +1 -0
- package/lib/types/client/mcp-app.d.ts +50 -0
- package/lib/types/client/mcp-app.d.ts.map +1 -0
- package/lib/types/client/mcp-app.js +328 -0
- package/lib/types/client/mcp-app.js.map +1 -0
- package/lib/types/client/message-chrome.d.ts +19 -0
- package/lib/types/client/message-chrome.d.ts.map +1 -0
- package/lib/types/client/message-chrome.js +42 -0
- package/lib/types/client/message-chrome.js.map +1 -0
- package/lib/types/client/motion.d.ts +38 -0
- package/lib/types/client/motion.d.ts.map +1 -0
- package/lib/types/client/motion.js +453 -0
- package/lib/types/client/motion.js.map +1 -0
- package/lib/types/client/native/ContextBody.d.ts +130 -0
- package/lib/types/client/native/ContextBody.d.ts.map +1 -0
- package/lib/types/client/native/ContextBody.js +398 -0
- package/lib/types/client/native/ContextBody.js.map +1 -0
- package/lib/types/client/native/ContextInjectionRow.d.ts +35 -0
- package/lib/types/client/native/ContextInjectionRow.d.ts.map +1 -0
- package/lib/types/client/native/ContextInjectionRow.js +42 -0
- package/lib/types/client/native/ContextInjectionRow.js.map +1 -0
- package/lib/types/client/native/ReferenceIcon.d.ts +16 -0
- package/lib/types/client/native/ReferenceIcon.d.ts.map +1 -0
- package/lib/types/client/native/ReferenceIcon.js +16 -0
- package/lib/types/client/native/ReferenceIcon.js.map +1 -0
- package/lib/types/client/native/tool-call-model.d.ts +58 -0
- package/lib/types/client/native/tool-call-model.d.ts.map +1 -0
- package/lib/types/client/native/tool-call-model.js +219 -0
- package/lib/types/client/native/tool-call-model.js.map +1 -0
- package/lib/types/client/native/tool-update.d.ts +23 -0
- package/lib/types/client/native/tool-update.d.ts.map +1 -0
- package/lib/types/client/native/tool-update.js +22 -0
- package/lib/types/client/native/tool-update.js.map +1 -0
- package/lib/types/client/official-slots.d.ts +71 -0
- package/lib/types/client/official-slots.d.ts.map +1 -0
- package/lib/types/client/official-slots.js +183 -0
- package/lib/types/client/official-slots.js.map +1 -0
- package/lib/types/client/open-file.d.ts +29 -0
- package/lib/types/client/open-file.d.ts.map +1 -0
- package/lib/types/client/open-file.js +71 -0
- package/lib/types/client/open-file.js.map +1 -0
- package/lib/types/client/pending-submission.d.ts +28 -0
- package/lib/types/client/pending-submission.d.ts.map +1 -0
- package/lib/types/client/pending-submission.js +28 -0
- package/lib/types/client/pending-submission.js.map +1 -0
- package/lib/types/client/platform-media.d.ts +6 -0
- package/lib/types/client/platform-media.d.ts.map +1 -0
- package/lib/types/client/platform-media.js +18 -0
- package/lib/types/client/platform-media.js.map +1 -0
- package/lib/types/client/primitive-labels.d.ts +10 -0
- package/lib/types/client/primitive-labels.d.ts.map +1 -0
- package/lib/types/client/primitive-labels.js +38 -0
- package/lib/types/client/primitive-labels.js.map +1 -0
- package/lib/types/client/projection.d.ts +41 -0
- package/lib/types/client/projection.d.ts.map +1 -0
- package/lib/types/client/projection.js +112 -0
- package/lib/types/client/projection.js.map +1 -0
- package/lib/types/client/reasoning-follow.d.ts +10 -0
- package/lib/types/client/reasoning-follow.d.ts.map +1 -0
- package/lib/types/client/reasoning-follow.js +21 -0
- package/lib/types/client/reasoning-follow.js.map +1 -0
- package/lib/types/client/resource-address.d.ts +3 -0
- package/lib/types/client/resource-address.d.ts.map +1 -0
- package/lib/types/client/resource-address.js +33 -0
- package/lib/types/client/resource-address.js.map +1 -0
- package/lib/types/client/settings-copy.d.ts +7 -0
- package/lib/types/client/settings-copy.d.ts.map +1 -0
- package/lib/types/client/settings-copy.js +53 -0
- package/lib/types/client/settings-copy.js.map +1 -0
- package/lib/types/client/settings-slots.d.ts +23 -0
- package/lib/types/client/settings-slots.d.ts.map +1 -0
- package/lib/types/client/settings-slots.js +2 -0
- package/lib/types/client/settings-slots.js.map +1 -0
- package/lib/types/client/settings.d.ts +4 -0
- package/lib/types/client/settings.d.ts.map +1 -0
- package/lib/types/client/settings.js +60 -0
- package/lib/types/client/settings.js.map +1 -0
- package/lib/types/client/skill-status.d.ts +25 -0
- package/lib/types/client/skill-status.d.ts.map +1 -0
- package/lib/types/client/skill-status.js +44 -0
- package/lib/types/client/skill-status.js.map +1 -0
- package/lib/types/client/store.d.ts +35 -0
- package/lib/types/client/store.d.ts.map +1 -0
- package/lib/types/client/store.js +37 -0
- package/lib/types/client/store.js.map +1 -0
- package/lib/types/client/stream-buffer.d.ts +37 -0
- package/lib/types/client/stream-buffer.d.ts.map +1 -0
- package/lib/types/client/stream-buffer.js +150 -0
- package/lib/types/client/stream-buffer.js.map +1 -0
- package/lib/types/client/streaming.d.ts +18 -0
- package/lib/types/client/streaming.d.ts.map +1 -0
- package/lib/types/client/streaming.js +84 -0
- package/lib/types/client/streaming.js.map +1 -0
- package/lib/types/client/timeline.d.ts +26 -0
- package/lib/types/client/timeline.d.ts.map +1 -0
- package/lib/types/client/timeline.js +48 -0
- package/lib/types/client/timeline.js.map +1 -0
- package/lib/types/client/tool-activity.d.ts +98 -0
- package/lib/types/client/tool-activity.d.ts.map +1 -0
- package/lib/types/client/tool-activity.js +301 -0
- package/lib/types/client/tool-activity.js.map +1 -0
- package/lib/types/client/types.d.ts +91 -0
- package/lib/types/client/types.d.ts.map +1 -0
- package/lib/types/client/types.js +2 -0
- package/lib/types/client/types.js.map +1 -0
- package/lib/types/client/waiting-clock.d.ts +49 -0
- package/lib/types/client/waiting-clock.d.ts.map +1 -0
- package/lib/types/client/waiting-clock.js +80 -0
- package/lib/types/client/waiting-clock.js.map +1 -0
- package/lib/types/client/word-motion.d.ts +16 -0
- package/lib/types/client/word-motion.d.ts.map +1 -0
- package/lib/types/client/word-motion.js +90 -0
- package/lib/types/client/word-motion.js.map +1 -0
- package/lib/types/client/word-timeline.d.ts +32 -0
- package/lib/types/client/word-timeline.d.ts.map +1 -0
- package/lib/types/client/word-timeline.js +119 -0
- package/lib/types/client/word-timeline.js.map +1 -0
- package/lib/types/dsh-better-display.d.ts +17 -0
- package/lib/types/dsh-better-display.d.ts.map +1 -0
- package/lib/types/dsh-better-display.js +93 -0
- package/lib/types/dsh-better-display.js.map +1 -0
- package/lib/types/skill-roots.d.ts +22 -0
- package/lib/types/skill-roots.d.ts.map +1 -0
- package/lib/types/skill-roots.js +126 -0
- package/lib/types/skill-roots.js.map +1 -0
- package/lib/types/skill-status.d.ts +36 -0
- package/lib/types/skill-status.d.ts.map +1 -0
- package/lib/types/skill-status.js +51 -0
- package/lib/types/skill-status.js.map +1 -0
- package/package.json +133 -0
- package/scripts/build-motion-fixture.mjs +26 -0
- package/scripts/check-harness-compat.mjs +71 -0
- package/scripts/link-harness-dependencies.mjs +54 -0
- package/scripts/verify-auto-fold.mjs +114 -0
- package/scripts/verify-official-bridge.mjs +121 -0
- package/scripts/verify-tool-shimmer.mjs +62 -0
- package/skills/generative-mcpapps/SKILL.md +47 -0
- package/skills/generative-mcpapps/examples/interactive_quiz.html +153 -0
- package/skills/generative-mcpapps/references/html_boilerplate.md +122 -0
- package/skills/generative-mcpapps/references/sep1865_protocol.md +54 -0
- package/src/client/Blocks.tsx +213 -0
- package/src/client/ChoreographedFlow.tsx +232 -0
- package/src/client/ClosedProcessSummary.tsx +23 -0
- package/src/client/DiffPanel.tsx +124 -0
- package/src/client/LiveFold.tsx +43 -0
- package/src/client/McpAppFrame.module.css +210 -0
- package/src/client/McpAppFrame.tsx +317 -0
- package/src/client/OfficialContent.tsx +69 -0
- package/src/client/Reader.module.css +692 -0
- package/src/client/Reader.tsx +878 -0
- package/src/client/ReasoningCard.tsx +306 -0
- package/src/client/SettingsSection.module.css +184 -0
- package/src/client/SettingsSection.tsx +194 -0
- package/src/client/StickyLane.tsx +34 -0
- package/src/client/TimelineRail.module.css +170 -0
- package/src/client/TimelineRail.tsx +262 -0
- package/src/client/ToolActivity.tsx +274 -0
- package/src/client/TurnMetrics.module.css +139 -0
- package/src/client/TurnMetrics.tsx +160 -0
- package/src/client/WaitClock.tsx +33 -0
- package/src/client/WaitingStatus.tsx +13 -0
- package/src/client/conversation-scroll.ts +28 -0
- package/src/client/deliverables.ts +122 -0
- package/src/client/entry-policy.ts +20 -0
- package/src/client/entry.tsx +40 -0
- package/src/client/fold-choreography.ts +55 -0
- package/src/client/fold-intensity.ts +36 -0
- package/src/client/index.tsx +222 -0
- package/src/client/live-turn.ts +198 -0
- package/src/client/markdown/MarkdownText.module.css +304 -0
- package/src/client/markdown/MarkdownText.tsx +195 -0
- package/src/client/markdown/cjkFriendlyStrong.ts +84 -0
- package/src/client/markdown/incremental.ts +131 -0
- package/src/client/markdown/katex.tsx +91 -0
- package/src/client/markdown/mathCompatibility.ts +350 -0
- package/src/client/markdown/parse.ts +45 -0
- package/src/client/markdown/render.tsx +647 -0
- package/src/client/markdown/upstream.json +14 -0
- package/src/client/mcp-app.ts +323 -0
- package/src/client/message-chrome.ts +47 -0
- package/src/client/motion.tsx +410 -0
- package/src/client/native/ContextBody.module.css +161 -0
- package/src/client/native/ContextBody.tsx +591 -0
- package/src/client/native/ContextInjectionRow.module.css +66 -0
- package/src/client/native/ContextInjectionRow.tsx +106 -0
- package/src/client/native/ReferenceIcon.tsx +35 -0
- package/src/client/native/tool-call-model.ts +248 -0
- package/src/client/native/tool-update.ts +32 -0
- package/src/client/native/upstream.json +41 -0
- package/src/client/official-slots.tsx +211 -0
- package/src/client/open-file.ts +94 -0
- package/src/client/pending-submission.ts +49 -0
- package/src/client/platform-media.ts +17 -0
- package/src/client/primitive-labels.ts +54 -0
- package/src/client/projection.ts +118 -0
- package/src/client/reasoning-follow.ts +28 -0
- package/src/client/settings-copy.ts +80 -0
- package/src/client/settings-slots.ts +20 -0
- package/src/client/settings.tsx +73 -0
- package/src/client/skill-status.ts +78 -0
- package/src/client/store.ts +75 -0
- package/src/client/stream-buffer.ts +136 -0
- package/src/client/streaming.tsx +70 -0
- package/src/client/style.d.ts +4 -0
- package/src/client/timeline.ts +77 -0
- package/src/client/tool-activity.ts +298 -0
- package/src/client/types.ts +89 -0
- package/src/client/waiting-clock.ts +83 -0
- package/src/client/word-motion.tsx +92 -0
- package/src/client/word-timeline.ts +113 -0
- package/src/dsh-better-display.ts +108 -0
- package/src/skill-roots.ts +138 -0
- package/src/skill-status.ts +81 -0
- package/tests/browser-auto-fold.tsx +64 -0
- package/tests/browser-closed-gap.tsx +20 -0
- package/tests/browser-motion.tsx +65 -0
- package/tests/browser-official-bridge.tsx +152 -0
- package/tests/browser-sticky-lanes.tsx +22 -0
- package/tests/browser-waiting-clock.tsx +14 -0
- package/tests/chat-flow-hook.test.ts +66 -0
- package/tests/cloud-gate.test.ts +34 -0
- package/tests/context-tool-update.test.ts +33 -0
- package/tests/conversation-scroll.test.ts +47 -0
- package/tests/deliverables.test.ts +128 -0
- package/tests/entry.test.ts +42 -0
- package/tests/fixtures/maid-composer-hide.html +31 -0
- package/tests/fold-choreography.test.ts +54 -0
- package/tests/fold-intensity.test.ts +94 -0
- package/tests/footer-precedence.test.ts +129 -0
- package/tests/history-word-regression.test.ts +16 -0
- package/tests/live-turn.test.ts +218 -0
- package/tests/mcp-apps.test.ts +157 -0
- package/tests/message-chrome.test.ts +29 -0
- package/tests/official-slots.test.ts +112 -0
- package/tests/open-file.test.ts +114 -0
- package/tests/pending-submission.test.ts +45 -0
- package/tests/platform-media.test.ts +23 -0
- package/tests/projection.test.ts +184 -0
- package/tests/reasoning-follow.test.ts +34 -0
- package/tests/settings-copy.test.ts +63 -0
- package/tests/skill-status.test.ts +137 -0
- package/tests/stock-install.test.ts +58 -0
- package/tests/stream-buffer.test.ts +102 -0
- package/tests/timeline.test.ts +59 -0
- package/tests/tool-diff.test.ts +57 -0
- package/tests/waiting-clock.test.ts +83 -0
- package/tests/word-timeline.test.ts +146 -0
- package/tsconfig.json +11 -0
- package/tsdown.config.ts +51 -0
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
const timestamp = (value) => typeof value === 'number' && Number.isFinite(value) && value >= 0 ? value : null;
|
|
2
|
+
/**
|
|
3
|
+
* Chat-layer kinds that hand the turn back to the model unconditionally.
|
|
4
|
+
*
|
|
5
|
+
* These are `ChatNodeDataMap` keys, NOT conversation-layer `ConversationNode` kinds.
|
|
6
|
+
* The two layers name the same idea differently: a returned tool is `tool-result`
|
|
7
|
+
* in the conversation contract, but the row the reader sees is the `tool-call` node.
|
|
8
|
+
* A name copied from the wrong layer silently disables the branch it guards, so
|
|
9
|
+
* the `satisfies` below makes the compiler reject any name that is not a real kind.
|
|
10
|
+
*/
|
|
11
|
+
export const WAIT_AFTER = new Set(['context', 'model-retry']);
|
|
12
|
+
/**
|
|
13
|
+
* Every chat-kind the handover logic reasons about, checked against the host's own
|
|
14
|
+
* kind union at compile time. Adding a name here that the host does not register
|
|
15
|
+
* fails `tsc` instead of failing silently at runtime.
|
|
16
|
+
*/
|
|
17
|
+
export const HANDOVER_KINDS = [
|
|
18
|
+
'user', 'steering', 'context', 'model-retry', 'tool-call', 'command',
|
|
19
|
+
];
|
|
20
|
+
/**
|
|
21
|
+
* Mirrors the host's `isSettledTool`: a running call has no `kind`, a settled one
|
|
22
|
+
* carries `kind: 'tool-result'`. Kept local so this module stays dependency-free,
|
|
23
|
+
* and pinned by a test against the host's own helper contract.
|
|
24
|
+
*/
|
|
25
|
+
function toolSettled(data) {
|
|
26
|
+
const root = data?.root;
|
|
27
|
+
return typeof root === 'object' && root !== null && root.kind === 'tool-result';
|
|
28
|
+
}
|
|
29
|
+
/** A command that is still executing has no outcome yet; only a settled one hands over. */
|
|
30
|
+
function commandSettled(data) {
|
|
31
|
+
return data?.outcome != null;
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Does this node leave the model on the hook for the next move?
|
|
35
|
+
*
|
|
36
|
+
* A tool or command that is *still running* is not a wait — the tool is the one
|
|
37
|
+
* working. Only its returned form hands control back, which is exactly the moment
|
|
38
|
+
* the model can stall.
|
|
39
|
+
*/
|
|
40
|
+
export function handsBackToModel(node) {
|
|
41
|
+
if (node.kind === 'user' || node.kind === 'steering')
|
|
42
|
+
return true;
|
|
43
|
+
if (node.kind === 'tool-call')
|
|
44
|
+
return toolSettled(node.data);
|
|
45
|
+
if (node.kind === 'command')
|
|
46
|
+
return commandSettled(node.data);
|
|
47
|
+
return WAIT_AFTER.has(node.kind);
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* The moment the current wait began.
|
|
51
|
+
*
|
|
52
|
+
* This is the time of the **last** node that handed control to the model — a
|
|
53
|
+
* returned tool, an injected context, or the user's own message. Anchoring on the
|
|
54
|
+
* user's message alone made the readout count the entire turn, so a wait that had
|
|
55
|
+
* only just begun showed the minutes the tools had already spent.
|
|
56
|
+
*/
|
|
57
|
+
export function waitingAnchor(order, get, pending = []) {
|
|
58
|
+
let anchor = { key: 'unresolved', time: null };
|
|
59
|
+
for (let i = order.length - 1; i >= 0; i--) {
|
|
60
|
+
const node = get(order[i]);
|
|
61
|
+
if (!node)
|
|
62
|
+
continue;
|
|
63
|
+
if (!handsBackToModel(node))
|
|
64
|
+
continue;
|
|
65
|
+
const time = node.data && typeof node.data === 'object' && 'time' in node.data && typeof node.data.time === 'number' ? node.data.time : undefined;
|
|
66
|
+
anchor = { key: order[i], time: timestamp(time) };
|
|
67
|
+
break;
|
|
68
|
+
}
|
|
69
|
+
for (let i = pending.length - 1; i >= 0; i--) {
|
|
70
|
+
const input = pending[i];
|
|
71
|
+
if (input.placement === 'queued')
|
|
72
|
+
continue;
|
|
73
|
+
const time = timestamp(input.time);
|
|
74
|
+
if (time === null || anchor.time === null || time >= anchor.time)
|
|
75
|
+
return { key: `pending:${input.requestId}`, time };
|
|
76
|
+
break;
|
|
77
|
+
}
|
|
78
|
+
return anchor;
|
|
79
|
+
}
|
|
80
|
+
//# sourceMappingURL=waiting-clock.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"waiting-clock.js","sourceRoot":"","sources":["../../../src/client/waiting-clock.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { MarkdownFileMentions } from '@deepseek-ai/dsh-client-ui-primitives';
|
|
2
|
+
/** Native Think is literal text, not Markdown. Spans never alter its bytes. */
|
|
3
|
+
export declare function MotionPlainText({ text, enabled, revision }: {
|
|
4
|
+
text: string;
|
|
5
|
+
enabled: boolean;
|
|
6
|
+
revision: number;
|
|
7
|
+
}): import("react").JSX.Element;
|
|
8
|
+
/** Native DSH Markdown semantics with a stable text-leaf animation hook. */
|
|
9
|
+
export declare function MotionMarkdown({ text, streaming, enabled, revision, fileMentions }: {
|
|
10
|
+
text: string;
|
|
11
|
+
streaming: boolean;
|
|
12
|
+
enabled: boolean;
|
|
13
|
+
revision: number;
|
|
14
|
+
fileMentions?: MarkdownFileMentions;
|
|
15
|
+
}): import("react").JSX.Element;
|
|
16
|
+
//# sourceMappingURL=word-motion.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"word-motion.d.ts","sourceRoot":"","sources":["../../../src/client/word-motion.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,uCAAuC,CAAC;AAmDlF,+EAA+E;AAC/E,wBAAgB,eAAe,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,OAAO,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,+BAYhH;AAED,4EAA4E;AAC5E,wBAAgB,cAAc,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,QAAQ,EAAE,YAAY,EAAE,EAAE;IACnF,IAAI,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,OAAO,CAAC;IAAC,OAAO,EAAE,OAAO,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAC;IAAC,YAAY,CAAC,EAAE,oBAAoB,CAAC;CAC3G,+BAoBA"}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { createContext, useContext, useLayoutEffect, useMemo, useRef } from 'react';
|
|
3
|
+
import { MarkdownText } from './markdown/MarkdownText.js';
|
|
4
|
+
import { readerPathImages } from './platform-media.js';
|
|
5
|
+
import { WORD_MOTION, WordTimeline } from './word-timeline.js';
|
|
6
|
+
import css from './Reader.module.css';
|
|
7
|
+
const WordScope = createContext({ enabled: false, generation: 0 });
|
|
8
|
+
const CODE_LABELS = { copyLabel: '复制代码', copiedLabel: '已复制' };
|
|
9
|
+
function useSourceReveal(element, born, generation) {
|
|
10
|
+
const scope = useContext(WordScope);
|
|
11
|
+
const cancelled = useRef(false);
|
|
12
|
+
useLayoutEffect(() => {
|
|
13
|
+
const target = element.current;
|
|
14
|
+
if (!target)
|
|
15
|
+
return;
|
|
16
|
+
target.dataset.wordState = 'settled';
|
|
17
|
+
if (!scope.enabled || scope.generation !== generation) {
|
|
18
|
+
cancelled.current = true;
|
|
19
|
+
return;
|
|
20
|
+
}
|
|
21
|
+
if (cancelled.current || born === null || document.hidden)
|
|
22
|
+
return;
|
|
23
|
+
const age = Number(document.timeline.currentTime ?? performance.now()) - born;
|
|
24
|
+
if (age >= WORD_MOTION.duration || typeof target.animate !== 'function')
|
|
25
|
+
return;
|
|
26
|
+
// The reference opacity + blur frames, applied only to this new word.
|
|
27
|
+
// No color interpolation, stylesheet mutation, or whole-paragraph wipe.
|
|
28
|
+
const animation = target.animate([
|
|
29
|
+
{ opacity: 0, filter: `blur(${WORD_MOTION.blur}px)` },
|
|
30
|
+
{ opacity: 1, filter: 'blur(0px)' },
|
|
31
|
+
], { duration: WORD_MOTION.duration, easing: WORD_MOTION.easing, fill: 'backwards' });
|
|
32
|
+
// One absolute clock prevents newly mounted/resegmented leaves from getting
|
|
33
|
+
// a fresh delay or running ahead because their layout effects ran later.
|
|
34
|
+
animation.startTime = born;
|
|
35
|
+
target.dataset.wordState = 'resolving';
|
|
36
|
+
const finish = () => { animation.cancel(); target.dataset.wordState = 'settled'; document.removeEventListener('visibilitychange', hidden); };
|
|
37
|
+
animation.onfinish = finish;
|
|
38
|
+
const hidden = () => { if (document.hidden) {
|
|
39
|
+
cancelled.current = true;
|
|
40
|
+
finish();
|
|
41
|
+
} };
|
|
42
|
+
document.addEventListener('visibilitychange', hidden);
|
|
43
|
+
return () => { animation.cancel(); document.removeEventListener('visibilitychange', hidden); target.dataset.wordState = 'settled'; };
|
|
44
|
+
}, [element, born, generation, scope.enabled, scope.generation]);
|
|
45
|
+
}
|
|
46
|
+
function Word({ children, born, generation, offset, inline }) {
|
|
47
|
+
const element = useRef(null);
|
|
48
|
+
useSourceReveal(element, born, generation);
|
|
49
|
+
return _jsx("span", { ref: element, className: inline ? css.streamInlineWord : css.streamWord, "data-reader-word": true, "data-source-start": offset, "data-source-birth": born ?? undefined, children: children });
|
|
50
|
+
}
|
|
51
|
+
/** A native code block enters on the same clock, without rebuilding its text. */
|
|
52
|
+
function MotionAtom({ children, born, generation, offset }) {
|
|
53
|
+
const element = useRef(null);
|
|
54
|
+
useSourceReveal(element, born, generation);
|
|
55
|
+
return _jsx("div", { ref: element, className: css.streamAtom, "data-reader-atom": true, "data-source-start": offset, "data-source-birth": born ?? undefined, children: children });
|
|
56
|
+
}
|
|
57
|
+
/** Native Think is literal text, not Markdown. Spans never alter its bytes. */
|
|
58
|
+
export function MotionPlainText({ text, enabled, revision }) {
|
|
59
|
+
const timeline = useRef();
|
|
60
|
+
timeline.current ??= new WordTimeline();
|
|
61
|
+
timeline.current.begin(text, enabled, revision, Number(document.timeline.currentTime ?? performance.now()));
|
|
62
|
+
const current = timeline.current;
|
|
63
|
+
const generation = current.generation;
|
|
64
|
+
const scope = useMemo(() => ({ enabled, generation }), [enabled, generation]);
|
|
65
|
+
return _jsx(WordScope.Provider, { value: scope, children: _jsx("div", { className: css.reasonPlain, children: current.hasLiveText ? current.words(text, 0).map(word => word.text.trim()
|
|
66
|
+
? _jsx(Word, { born: word.born, generation: generation, offset: word.key, inline: true, children: word.text }, word.key)
|
|
67
|
+
: word.text) : text }) });
|
|
68
|
+
}
|
|
69
|
+
/** Native DSH Markdown semantics with a stable text-leaf animation hook. */
|
|
70
|
+
export function MotionMarkdown({ text, streaming, enabled, revision, fileMentions }) {
|
|
71
|
+
const timeline = useRef();
|
|
72
|
+
timeline.current ??= new WordTimeline();
|
|
73
|
+
timeline.current.begin(text, enabled, revision, Number(document.timeline.currentTime ?? performance.now()));
|
|
74
|
+
const generation = timeline.current.generation;
|
|
75
|
+
const scope = useMemo(() => ({ enabled, generation }), [enabled, generation]);
|
|
76
|
+
const renderText = useMemo(() => (value, offset, inline = false) => {
|
|
77
|
+
const current = timeline.current;
|
|
78
|
+
if (!current.hasLiveText)
|
|
79
|
+
return value;
|
|
80
|
+
return current.words(value, offset).map(word => word.text.trim()
|
|
81
|
+
? _jsx(Word, { born: word.born, generation: current.generation, offset: word.key, inline: inline || /^\p{P}+$/u.test(word.text), children: word.text }, word.key)
|
|
82
|
+
: word.text);
|
|
83
|
+
}, []);
|
|
84
|
+
const renderAtom = useMemo(() => (children, offset) => {
|
|
85
|
+
const current = timeline.current;
|
|
86
|
+
return current.hasLiveText ? _jsx(MotionAtom, { born: current.bornAt(offset), generation: current.generation, offset: offset, children: children }) : children;
|
|
87
|
+
}, []);
|
|
88
|
+
return _jsx(WordScope.Provider, { value: scope, children: _jsx(MarkdownText, { text: text, streaming: streaming, codeLabels: CODE_LABELS, fileMentions: fileMentions, pathImages: readerPathImages, renderText: renderText, renderAtom: renderAtom }) });
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=word-motion.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"word-motion.js","sourceRoot":"","sources":["../../../src/client/word-motion.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
/** Motion parameters from the public transitions.dev streaming-text recipe. */
|
|
2
|
+
export declare const WORD_MOTION: {
|
|
3
|
+
readonly duration: 350;
|
|
4
|
+
readonly gap: 60;
|
|
5
|
+
readonly blur: 1;
|
|
6
|
+
readonly easing: "cubic-bezier(0.22, 1, 0.36, 1)";
|
|
7
|
+
readonly maxDelay: 240;
|
|
8
|
+
/** Floor for the per-word cadence once a batch is compressed. */
|
|
9
|
+
readonly minGap: 3;
|
|
10
|
+
/** One paint's words should land inside this window, however many arrive. */
|
|
11
|
+
readonly batchMs: 90;
|
|
12
|
+
};
|
|
13
|
+
export interface RevealingWord {
|
|
14
|
+
key: number;
|
|
15
|
+
text: string;
|
|
16
|
+
born: number | null;
|
|
17
|
+
}
|
|
18
|
+
/** Source-offset identity survives reparsing, frozen blocks, and final formatting. */
|
|
19
|
+
export declare class WordTimeline {
|
|
20
|
+
generation: number;
|
|
21
|
+
hasLiveText: boolean;
|
|
22
|
+
private source;
|
|
23
|
+
private enabled;
|
|
24
|
+
private revision;
|
|
25
|
+
private floor;
|
|
26
|
+
private lastBirth;
|
|
27
|
+
private readonly births;
|
|
28
|
+
begin(source: string, enabled: boolean, revision: number, now: number): void;
|
|
29
|
+
bornAt(offset: number): number | null;
|
|
30
|
+
words(value: string, offset: number): RevealingWord[];
|
|
31
|
+
}
|
|
32
|
+
//# sourceMappingURL=word-timeline.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"word-timeline.d.ts","sourceRoot":"","sources":["../../../src/client/word-timeline.ts"],"names":[],"mappings":"AAAA,+EAA+E;AAC/E,eAAO,MAAM,WAAW;;;;;;IAMtB,iEAAiE;;IAEjE,6EAA6E;;CAErE,CAAC;AAKX,MAAM,WAAW,aAAa;IAAG,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAAA;CAAE;AAGjF,sFAAsF;AACtF,qBAAa,YAAY;IACvB,UAAU,SAAK;IACf,WAAW,UAAS;IACpB,OAAO,CAAC,MAAM,CAAuB;IACrC,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,QAAQ,CAAK;IACrB,OAAO,CAAC,KAAK,CAAK;IAClB,OAAO,CAAC,SAAS,CAAa;IAC9B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAqB;IAE5C,KAAK,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,IAAI;IA+C5E,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI;IAYrC,KAAK,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,aAAa,EAAE;CAuBtD"}
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
/** Motion parameters from the public transitions.dev streaming-text recipe. */
|
|
2
|
+
export const WORD_MOTION = {
|
|
3
|
+
duration: 350,
|
|
4
|
+
gap: 60,
|
|
5
|
+
blur: 1,
|
|
6
|
+
easing: 'cubic-bezier(0.22, 1, 0.36, 1)',
|
|
7
|
+
maxDelay: 240,
|
|
8
|
+
/** Floor for the per-word cadence once a batch is compressed. */
|
|
9
|
+
minGap: 3,
|
|
10
|
+
/** One paint's words should land inside this window, however many arrive. */
|
|
11
|
+
batchMs: 90,
|
|
12
|
+
};
|
|
13
|
+
const segmenter = new Intl.Segmenter(undefined, { granularity: 'word' });
|
|
14
|
+
const closingPunctuation = /^[\p{Pe}\p{Pf},.!?:;,。!?、;:%‰…·]+$/u;
|
|
15
|
+
const openingPunctuation = /^[\p{Ps}\p{Pi}]+$/u;
|
|
16
|
+
/** Source-offset identity survives reparsing, frozen blocks, and final formatting. */
|
|
17
|
+
export class WordTimeline {
|
|
18
|
+
generation = 0;
|
|
19
|
+
hasLiveText = false;
|
|
20
|
+
source = null;
|
|
21
|
+
enabled = false;
|
|
22
|
+
revision = 0;
|
|
23
|
+
floor = 0;
|
|
24
|
+
lastBirth = -Infinity;
|
|
25
|
+
births = [];
|
|
26
|
+
begin(source, enabled, revision, now) {
|
|
27
|
+
if (this.source === source && this.enabled === enabled && this.revision === revision)
|
|
28
|
+
return;
|
|
29
|
+
const replaced = revision !== this.revision || (this.source !== null && !source.startsWith(this.source));
|
|
30
|
+
if (replaced || !enabled) {
|
|
31
|
+
this.births.length = 0;
|
|
32
|
+
this.lastBirth = -Infinity;
|
|
33
|
+
this.generation++;
|
|
34
|
+
this.floor = source.length;
|
|
35
|
+
}
|
|
36
|
+
else if (this.source === null) {
|
|
37
|
+
// A mounted historical prefix must not replay; a fresh live buffer mounts empty.
|
|
38
|
+
this.floor = source.length;
|
|
39
|
+
}
|
|
40
|
+
else {
|
|
41
|
+
// Allocate in source order, before Markdown can split/reorder text leaves.
|
|
42
|
+
// Intervals cover every offset, so resegmented CJK words inherit the time
|
|
43
|
+
// of their characters rather than falling through as instant "history".
|
|
44
|
+
const from = this.source.length;
|
|
45
|
+
const added = source.slice(from);
|
|
46
|
+
// The cadence follows the batch, not a constant. A fixed per-word gap caps
|
|
47
|
+
// the reveal at ~16 words/second however fast the model actually wrote, so
|
|
48
|
+
// a 500 tok/s answer still dripped out one word at a time. A batch of many
|
|
49
|
+
// words is compressed into one short window instead; a lone word keeps the
|
|
50
|
+
// original typing rhythm.
|
|
51
|
+
let arriving = 0;
|
|
52
|
+
for (const part of segmenter.segment(added))
|
|
53
|
+
if (part.segment.trim())
|
|
54
|
+
arriving++;
|
|
55
|
+
const gap = arriving > 1
|
|
56
|
+
? Math.max(WORD_MOTION.minGap, Math.min(WORD_MOTION.gap, WORD_MOTION.batchMs / arriving))
|
|
57
|
+
: WORD_MOTION.gap;
|
|
58
|
+
for (const part of segmenter.segment(added)) {
|
|
59
|
+
let born = Number.isFinite(this.lastBirth) ? this.lastBirth : null;
|
|
60
|
+
if (part.segment.trim()) {
|
|
61
|
+
// Capping at the batch window is what stops a queue from forming: the
|
|
62
|
+
// clock can never run further ahead than one window past the newest text.
|
|
63
|
+
born = Math.min(now + WORD_MOTION.batchMs, Math.max(now, this.lastBirth + gap));
|
|
64
|
+
this.lastBirth = born;
|
|
65
|
+
}
|
|
66
|
+
const end = from + part.index + part.segment.length;
|
|
67
|
+
const previous = this.births.at(-1);
|
|
68
|
+
if (previous && previous.born === born)
|
|
69
|
+
previous.end = end;
|
|
70
|
+
else
|
|
71
|
+
this.births.push({ end, born });
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
this.source = source;
|
|
75
|
+
this.enabled = enabled;
|
|
76
|
+
this.revision = revision;
|
|
77
|
+
this.hasLiveText = enabled && this.births.length > 0;
|
|
78
|
+
}
|
|
79
|
+
bornAt(offset) {
|
|
80
|
+
if (!this.enabled || offset < this.floor || this.births.length === 0)
|
|
81
|
+
return null;
|
|
82
|
+
let low = 0;
|
|
83
|
+
let high = this.births.length - 1;
|
|
84
|
+
while (low < high) {
|
|
85
|
+
const middle = (low + high) >>> 1;
|
|
86
|
+
if (this.births[middle].end <= offset)
|
|
87
|
+
low = middle + 1;
|
|
88
|
+
else
|
|
89
|
+
high = middle;
|
|
90
|
+
}
|
|
91
|
+
return this.births[low].born;
|
|
92
|
+
}
|
|
93
|
+
words(value, offset) {
|
|
94
|
+
// Atomic inline animation boxes must not turn commas into legal line starts
|
|
95
|
+
// or strand opening quotes at a line end. Keep source-offset identities when
|
|
96
|
+
// punctuation arrives in a later chunk, so the preceding word never replays.
|
|
97
|
+
// Already received text is one inert leaf, not thousands of React Words.
|
|
98
|
+
// Only the newly appended suffix needs word identities and birth times.
|
|
99
|
+
const prefixLength = Math.min(value.length, Math.max(0, this.floor - offset));
|
|
100
|
+
const prefix = prefixLength > 0
|
|
101
|
+
? [{ key: offset, text: value.slice(0, prefixLength), born: null }]
|
|
102
|
+
: [];
|
|
103
|
+
const parts = [];
|
|
104
|
+
for (const segment of segmenter.segment(value.slice(prefixLength))) {
|
|
105
|
+
const part = { index: prefixLength + segment.index, segment: segment.segment };
|
|
106
|
+
const previous = parts.at(-1);
|
|
107
|
+
if (previous?.segment.trim() && (closingPunctuation.test(part.segment) || openingPunctuation.test(previous.segment))) {
|
|
108
|
+
previous.segment += part.segment;
|
|
109
|
+
}
|
|
110
|
+
else
|
|
111
|
+
parts.push({ index: part.index, segment: part.segment });
|
|
112
|
+
}
|
|
113
|
+
return prefix.concat(parts.map(part => {
|
|
114
|
+
const key = offset + part.index;
|
|
115
|
+
return { key, text: part.segment, born: this.bornAt(key) };
|
|
116
|
+
}));
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
//# sourceMappingURL=word-timeline.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"word-timeline.js","sourceRoot":"","sources":["../../../src/client/word-timeline.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { IncomingMessage, ServerResponse } from 'node:http';
|
|
2
|
+
import type { Context } from '@deepseek-ai/cordis';
|
|
3
|
+
declare module '@deepseek-ai/cordis' {
|
|
4
|
+
interface Context {
|
|
5
|
+
webServer?: {
|
|
6
|
+
register: (route: {
|
|
7
|
+
kind: 'exact' | 'prefix';
|
|
8
|
+
path: string;
|
|
9
|
+
handler: (req: IncomingMessage, res: ServerResponse) => void | Promise<void>;
|
|
10
|
+
}) => () => void;
|
|
11
|
+
};
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
export declare const name = "@drscrewdriver/dsh-better-display";
|
|
15
|
+
export declare const inject: string[];
|
|
16
|
+
export declare function apply(ctx: Context): void;
|
|
17
|
+
//# sourceMappingURL=dsh-better-display.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dsh-better-display.d.ts","sourceRoot":"","sources":["../../src/dsh-better-display.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AACjE,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAC;AAInD,OAAO,QAAQ,qBAAqB,CAAC;IACnC,UAAU,OAAO;QACf,SAAS,CAAC,EAAE;YACV,QAAQ,EAAE,CAAC,KAAK,EAAE;gBAChB,IAAI,EAAE,OAAO,GAAG,QAAQ,CAAC;gBACzB,IAAI,EAAE,MAAM,CAAC;gBACb,OAAO,EAAE,CAAC,GAAG,EAAE,eAAe,EAAE,GAAG,EAAE,cAAc,KAAK,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;aAC9E,KAAK,MAAM,IAAI,CAAC;SAClB,CAAC;KACH;CACF;AAED,eAAO,MAAM,IAAI,sCAAsC,CAAC;AACxD,eAAO,MAAM,MAAM,UAAgB,CAAC;AAcpC,wBAAgB,KAAK,CAAC,GAAG,EAAE,OAAO,GAAG,IAAI,CA0ExC"}
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import { spawn } from 'node:child_process';
|
|
2
|
+
import { scanGenerativeMcpappsStatus } from './skill-roots.js';
|
|
3
|
+
import { skillsFromListResult, toPublicSkillStatus } from './skill-status.js';
|
|
4
|
+
export const name = '@drscrewdriver/dsh-better-display';
|
|
5
|
+
export const inject = ['webServer'];
|
|
6
|
+
function writeJson(res, status, body) {
|
|
7
|
+
res.setHeader('Content-Type', 'application/json');
|
|
8
|
+
res.statusCode = status;
|
|
9
|
+
res.end(JSON.stringify(body));
|
|
10
|
+
}
|
|
11
|
+
function skillLister(ctx) {
|
|
12
|
+
const skills = ctx.get?.('skills');
|
|
13
|
+
if (typeof skills?.list !== 'function')
|
|
14
|
+
return undefined;
|
|
15
|
+
return async () => skillsFromListResult(await skills.list({}));
|
|
16
|
+
}
|
|
17
|
+
export function apply(ctx) {
|
|
18
|
+
console.log('[my-plugins/dsh-better-display] loaded');
|
|
19
|
+
if (ctx.webServer) {
|
|
20
|
+
ctx.effect(() => {
|
|
21
|
+
const disposeReveal = ctx.webServer.register({
|
|
22
|
+
kind: 'exact',
|
|
23
|
+
path: '/better-display/reveal',
|
|
24
|
+
handler: async (req, res) => {
|
|
25
|
+
if (req.method !== 'POST') {
|
|
26
|
+
res.statusCode = 405;
|
|
27
|
+
res.end();
|
|
28
|
+
return;
|
|
29
|
+
}
|
|
30
|
+
let body = '';
|
|
31
|
+
req.on('data', chunk => { body += chunk; });
|
|
32
|
+
req.on('end', () => {
|
|
33
|
+
try {
|
|
34
|
+
const data = JSON.parse(body);
|
|
35
|
+
const targetPath = typeof data.path === 'string' ? data.path.trim() : '';
|
|
36
|
+
if (!targetPath) {
|
|
37
|
+
res.statusCode = 400;
|
|
38
|
+
res.end(JSON.stringify({ ok: false, error: 'Empty path' }));
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
if (process.platform === 'darwin') {
|
|
42
|
+
// Exact file reveal in macOS Finder with selection highlight
|
|
43
|
+
spawn('open', ['-R', targetPath], { detached: true, stdio: 'ignore' });
|
|
44
|
+
}
|
|
45
|
+
else if (process.platform === 'win32') {
|
|
46
|
+
// Exact file selection in Windows Explorer
|
|
47
|
+
spawn('explorer.exe', [`/select,${targetPath}`], { detached: true, stdio: 'ignore' });
|
|
48
|
+
}
|
|
49
|
+
else {
|
|
50
|
+
spawn('xdg-open', [targetPath], { detached: true, stdio: 'ignore' });
|
|
51
|
+
}
|
|
52
|
+
res.setHeader('Content-Type', 'application/json');
|
|
53
|
+
res.statusCode = 200;
|
|
54
|
+
res.end(JSON.stringify({ ok: true }));
|
|
55
|
+
}
|
|
56
|
+
catch (err) {
|
|
57
|
+
res.statusCode = 400;
|
|
58
|
+
res.end(JSON.stringify({ ok: false, error: String(err) }));
|
|
59
|
+
}
|
|
60
|
+
});
|
|
61
|
+
},
|
|
62
|
+
});
|
|
63
|
+
const disposeSkill = ctx.webServer.register({
|
|
64
|
+
kind: 'exact',
|
|
65
|
+
path: '/better-display/skill-status',
|
|
66
|
+
handler: async (req, res) => {
|
|
67
|
+
if (req.method !== 'GET') {
|
|
68
|
+
res.statusCode = 405;
|
|
69
|
+
res.end();
|
|
70
|
+
return;
|
|
71
|
+
}
|
|
72
|
+
try {
|
|
73
|
+
const url = new URL(req.url ?? '', 'http://127.0.0.1');
|
|
74
|
+
const cwd = url.searchParams.get('cwd') ?? undefined;
|
|
75
|
+
const status = await scanGenerativeMcpappsStatus({
|
|
76
|
+
cwd,
|
|
77
|
+
listSkills: skillLister(ctx),
|
|
78
|
+
});
|
|
79
|
+
writeJson(res, 200, toPublicSkillStatus(status));
|
|
80
|
+
}
|
|
81
|
+
catch (err) {
|
|
82
|
+
writeJson(res, 500, { ok: false, error: String(err) });
|
|
83
|
+
}
|
|
84
|
+
},
|
|
85
|
+
});
|
|
86
|
+
return () => {
|
|
87
|
+
disposeReveal();
|
|
88
|
+
disposeSkill();
|
|
89
|
+
};
|
|
90
|
+
}, 'dsh-better-display: reveal and skill-status routes');
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
//# sourceMappingURL=dsh-better-display.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dsh-better-display.js","sourceRoot":"","sources":["../../src/dsh-better-display.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { type HostSkillStatus, type SkillRootInfo } from './skill-status.js';
|
|
2
|
+
export declare function expandHomePath(path: string, home?: string): string;
|
|
3
|
+
/** `$DSH_HOME` or `~/.dsh`, matching official `resolveDshHome`. */
|
|
4
|
+
export declare function resolveDshHome(env?: Record<string, string | undefined>, home?: string): string;
|
|
5
|
+
/** `$DSH_AGENTS_HOME` or `~/.agents`. */
|
|
6
|
+
export declare function resolveAgentsHome(env?: Record<string, string | undefined>, home?: string): string;
|
|
7
|
+
export declare function userSkillRoots(env?: Record<string, string | undefined>, home?: string): readonly SkillRootInfo[];
|
|
8
|
+
export declare function projectSkillRoots(projectRoot: string): readonly SkillRootInfo[];
|
|
9
|
+
export declare function findProjectRoot(cwd: string): Promise<string>;
|
|
10
|
+
export declare function rootHasGenerativeMcpapps(rootPath: string): Promise<boolean>;
|
|
11
|
+
/** Resolve the plugin-shipped pack. This path is never treated as a skill root. */
|
|
12
|
+
export declare function pluginSkillPackPath(moduleUrl?: string): string | undefined;
|
|
13
|
+
export declare function scanGenerativeMcpappsStatus(options?: {
|
|
14
|
+
cwd?: string;
|
|
15
|
+
env?: Record<string, string | undefined>;
|
|
16
|
+
home?: string;
|
|
17
|
+
packPath?: string;
|
|
18
|
+
listSkills?: () => Promise<readonly {
|
|
19
|
+
readonly name?: string;
|
|
20
|
+
}[] | undefined>;
|
|
21
|
+
}): Promise<HostSkillStatus>;
|
|
22
|
+
//# sourceMappingURL=skill-roots.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"skill-roots.d.ts","sourceRoot":"","sources":["../../src/skill-roots.ts"],"names":[],"mappings":"AAKA,OAAO,EAIL,KAAK,eAAe,EACpB,KAAK,aAAa,EACnB,MAAM,mBAAmB,CAAC;AAE3B,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,SAAY,GAAG,MAAM,CAIrE;AAED,mEAAmE;AACnE,wBAAgB,cAAc,CAAC,GAAG,GAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAe,EAAE,IAAI,SAAY,GAAG,MAAM,CAI9G;AAED,yCAAyC;AACzC,wBAAgB,iBAAiB,CAAC,GAAG,GAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAe,EAAE,IAAI,SAAY,GAAG,MAAM,CAIjH;AAED,wBAAgB,cAAc,CAC5B,GAAG,GAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAe,EACrD,IAAI,SAAY,GACf,SAAS,aAAa,EAAE,CAK1B;AAED,wBAAgB,iBAAiB,CAAC,WAAW,EAAE,MAAM,GAAG,SAAS,aAAa,EAAE,CAK/E;AAED,wBAAsB,eAAe,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAQlE;AAED,wBAAsB,wBAAwB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAqBjF;AAED,mFAAmF;AACnF,wBAAgB,mBAAmB,CAAC,SAAS,SAAkB,GAAG,MAAM,GAAG,SAAS,CAQnF;AAED,wBAAsB,2BAA2B,CAAC,OAAO,GAAE;IACzD,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,GAAG,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,CAAC;IACzC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,OAAO,CAAC,SAAS;QAAE,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAA;KAAE,EAAE,GAAG,SAAS,CAAC,CAAC;CAC1E,GAAG,OAAO,CAAC,eAAe,CAAC,CAqChC"}
|