@pellux/goodvibes-agent 0.1.116 → 1.0.0
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 +48 -661
- package/README.md +64 -57
- package/bin/goodvibes-agent.ts +16 -2
- package/dist/package/main.js +199180 -192185
- package/docs/README.md +15 -8
- package/docs/channels-remote-and-api.md +50 -0
- package/docs/connected-host.md +59 -0
- package/docs/getting-started.md +61 -50
- package/docs/knowledge-artifacts-and-multimodal.md +91 -0
- package/docs/project-planning.md +79 -0
- package/docs/providers-and-routing.md +46 -0
- package/docs/release-and-publishing.md +48 -11
- package/docs/tools-and-commands.md +123 -0
- package/docs/voice-and-live-tts.md +51 -0
- package/package.json +3 -6
- package/src/agent/behavior-discovery-summary.ts +1 -3
- package/src/agent/channel-delivery.ts +201 -0
- package/src/agent/media-generation.ts +159 -0
- package/src/agent/memory-prompt.ts +0 -1
- package/src/agent/note-registry.ts +329 -0
- package/src/agent/operator-actions.ts +343 -0
- package/src/agent/persona-discovery.ts +1 -3
- package/src/agent/persona-registry.ts +19 -16
- package/src/agent/record-labels.ts +107 -0
- package/src/agent/reminder-schedule-format.ts +33 -24
- package/src/agent/reminder-schedule.ts +27 -26
- package/src/agent/routine-registry.ts +54 -14
- package/src/agent/routine-schedule-args.ts +2 -1
- package/src/agent/routine-schedule-format.ts +77 -53
- package/src/agent/routine-schedule-promotion.ts +35 -33
- package/src/agent/routine-schedule-receipts.ts +29 -27
- package/src/agent/runtime-profile-starters.ts +5 -5
- package/src/agent/runtime-profile.ts +91 -12
- package/src/agent/skill-registry.ts +210 -32
- package/src/cli/agent-knowledge-args.ts +5 -1
- package/src/cli/agent-knowledge-command.ts +40 -34
- package/src/cli/agent-knowledge-format.ts +80 -67
- package/src/cli/agent-knowledge-methods.ts +1 -1
- package/src/cli/agent-knowledge-runtime.ts +32 -26
- package/src/cli/bundle-command.ts +14 -9
- package/src/cli/config-overrides.ts +37 -36
- package/src/cli/entrypoint.ts +16 -7
- package/src/cli/external-runtime.ts +10 -4
- package/src/cli/help.ts +54 -29
- package/src/cli/local-library-command.ts +203 -83
- package/src/cli/management-commands.ts +105 -68
- package/src/cli/management.ts +55 -74
- package/src/cli/memory-command.ts +66 -32
- package/src/cli/parser.ts +37 -3
- package/src/cli/profiles-command.ts +166 -31
- package/src/cli/provider-auth-routes.ts +2 -1
- package/src/cli/routines-command.ts +176 -40
- package/src/cli/service-posture.ts +16 -16
- package/src/cli/status.ts +56 -135
- package/src/core/conversation-message-snapshot.ts +131 -0
- package/src/input/agent-workspace-access-command-editor-submission.ts +149 -0
- package/src/input/agent-workspace-access-command-editors.ts +170 -0
- package/src/input/agent-workspace-activation.ts +35 -8
- package/src/input/agent-workspace-basic-command-editor-submission.ts +351 -94
- package/src/input/agent-workspace-basic-command-editors.ts +502 -9
- package/src/input/agent-workspace-categories.ts +423 -51
- package/src/input/agent-workspace-channel-command-editor-submission.ts +83 -0
- package/src/input/agent-workspace-channel-command-editors.ts +65 -0
- package/src/input/agent-workspace-channels.ts +35 -2
- package/src/input/agent-workspace-command-editor.ts +41 -3
- package/src/input/agent-workspace-config-reader.ts +16 -0
- package/src/input/agent-workspace-delegation-editor-submission.ts +55 -0
- package/src/input/agent-workspace-editors.ts +166 -1
- package/src/input/agent-workspace-knowledge-command-editor-submission.ts +132 -0
- package/src/input/agent-workspace-knowledge-command-editors.ts +110 -0
- package/src/input/agent-workspace-knowledge-query-editor.ts +1 -1
- package/src/input/agent-workspace-learned-behavior.ts +67 -0
- package/src/input/agent-workspace-library-command-editor-submission.ts +50 -0
- package/src/input/agent-workspace-library-command-editors.ts +35 -0
- package/src/input/agent-workspace-local-operations.ts +218 -0
- package/src/input/agent-workspace-local-selection.ts +75 -0
- package/src/input/agent-workspace-mcp-command-editor-submission.ts +95 -0
- package/src/input/agent-workspace-media-command-editor-submission.ts +62 -0
- package/src/input/agent-workspace-media-command-editors.ts +27 -0
- package/src/input/agent-workspace-memory-command-editor-submission.ts +232 -0
- package/src/input/agent-workspace-memory-command-editors.ts +180 -0
- package/src/input/agent-workspace-memory-editor.ts +2 -2
- package/src/input/agent-workspace-navigation.ts +81 -0
- package/src/input/agent-workspace-notify-editor-submission.ts +121 -0
- package/src/input/agent-workspace-operations-command-editor-submission.ts +208 -0
- package/src/input/agent-workspace-operations-command-editors.ts +196 -0
- package/src/input/agent-workspace-panel-route.ts +43 -0
- package/src/input/agent-workspace-provider-command-editor-submission.ts +155 -0
- package/src/input/agent-workspace-provider-command-editors.ts +93 -0
- package/src/input/agent-workspace-reminder-schedule-editor.ts +1 -1
- package/src/input/agent-workspace-requirements.ts +11 -0
- package/src/input/agent-workspace-routine-schedule-editor.ts +2 -2
- package/src/input/agent-workspace-search.ts +169 -0
- package/src/input/agent-workspace-secret-editor-submission.ts +153 -0
- package/src/input/agent-workspace-session-command-editor-submission.ts +199 -0
- package/src/input/agent-workspace-session-command-editors.ts +249 -0
- package/src/input/agent-workspace-setup.ts +37 -16
- package/src/input/agent-workspace-skill-bundle-command-editor-submission.ts +101 -0
- package/src/input/agent-workspace-skill-bundle-command-editors.ts +110 -0
- package/src/input/agent-workspace-snapshot.ts +162 -21
- package/src/input/agent-workspace-task-command-editor-submission.ts +61 -0
- package/src/input/agent-workspace-task-command-editors.ts +47 -0
- package/src/input/agent-workspace-token.ts +18 -2
- package/src/input/agent-workspace-types.ts +212 -4
- package/src/input/agent-workspace-voice-media.ts +4 -7
- package/src/input/agent-workspace-web-research-editor.ts +104 -0
- package/src/input/agent-workspace-workplan-editor-submission.ts +153 -0
- package/src/input/agent-workspace.ts +178 -240
- package/src/input/command-registry.ts +5 -2
- package/src/input/commands/agent-runtime-profile-runtime.ts +126 -37
- package/src/input/commands/agent-skills-runtime.ts +149 -72
- package/src/input/commands/agent-workspace-runtime.ts +23 -6
- package/src/input/commands/brief-runtime.ts +55 -25
- package/src/input/commands/channels-runtime.ts +147 -33
- package/src/input/commands/compat-runtime.ts +32 -0
- package/src/input/commands/delegation-runtime.ts +29 -23
- package/src/input/commands/experience-runtime.ts +6 -4
- package/src/input/commands/guidance-runtime.ts +4 -4
- package/src/input/commands/health-runtime.ts +149 -126
- package/src/input/commands/knowledge.ts +82 -60
- package/src/input/commands/local-provider-runtime.ts +43 -21
- package/src/input/commands/local-runtime.ts +138 -16
- package/src/input/commands/local-setup-review.ts +10 -20
- package/src/input/commands/mcp-runtime.ts +63 -46
- package/src/input/commands/notify-runtime.ts +38 -9
- package/src/input/commands/operator-actions-runtime.ts +138 -0
- package/src/input/commands/operator-runtime.ts +6 -76
- package/src/input/commands/personas-runtime.ts +46 -31
- package/src/input/commands/planning-runtime.ts +1 -1
- package/src/input/commands/platform-access-runtime.ts +35 -98
- package/src/input/commands/product-runtime.ts +2 -2
- package/src/input/commands/provider-accounts-runtime.ts +60 -39
- package/src/input/commands/qrcode-runtime.ts +50 -9
- package/src/input/commands/recall-bundle.ts +11 -11
- package/src/input/commands/recall-capture.ts +13 -11
- package/src/input/commands/recall-query.ts +29 -21
- package/src/input/commands/recall-review.ts +2 -1
- package/src/input/commands/routines-runtime.ts +99 -45
- package/src/input/commands/runtime-services.ts +1 -14
- package/src/input/commands/schedule-runtime.ts +33 -20
- package/src/input/commands/security-runtime.ts +6 -11
- package/src/input/commands/session-content.ts +80 -78
- package/src/input/commands/session-workflow.ts +134 -104
- package/src/input/commands/session.ts +3 -174
- package/src/input/commands/shell-core.ts +38 -17
- package/src/input/commands/subscription-runtime.ts +54 -185
- package/src/input/commands/support-bundle-runtime.ts +53 -0
- package/src/input/commands/tasks-runtime.ts +21 -21
- package/src/input/commands/work-plan-runtime.ts +33 -8
- package/src/input/commands.ts +6 -2
- package/src/input/feed-context-factory.ts +2 -2
- package/src/input/file-picker.ts +3 -2
- package/src/input/handler-command-route.ts +4 -7
- package/src/input/handler-content-actions.ts +89 -26
- package/src/input/handler-feed-routes.ts +19 -12
- package/src/input/handler-feed.ts +6 -5
- package/src/input/handler-interactions.ts +9 -36
- package/src/input/handler-modal-stack.ts +3 -3
- package/src/input/handler-onboarding.ts +52 -91
- package/src/input/handler-shortcuts.ts +16 -7
- package/src/input/handler.ts +50 -23
- package/src/input/input-history.ts +5 -6
- package/src/input/keybindings.ts +27 -16
- package/src/input/mcp-workspace.ts +90 -26
- package/src/input/onboarding/handler-onboarding-routes.ts +3 -1
- package/src/input/onboarding/onboarding-wizard-apply.ts +62 -0
- package/src/input/onboarding/onboarding-wizard-constants.ts +1 -0
- package/src/input/onboarding/onboarding-wizard-helpers.ts +1 -1
- package/src/input/onboarding/onboarding-wizard-operator-steps.ts +223 -55
- package/src/input/onboarding/onboarding-wizard-steps.ts +59 -35
- package/src/input/onboarding/onboarding-wizard-types.ts +4 -1
- package/src/input/onboarding/onboarding-wizard.ts +87 -2
- package/src/input/profile-picker-modal.ts +31 -12
- package/src/input/session-picker-modal.ts +21 -4
- package/src/input/settings-modal-agent-policy.ts +6 -6
- package/src/input/settings-modal-behavior.ts +0 -3
- package/src/input/settings-modal-subscriptions.ts +3 -3
- package/src/input/settings-modal-types.ts +2 -13
- package/src/input/settings-modal.ts +20 -66
- package/src/input/submission-intent.ts +0 -1
- package/src/input/submission-router.ts +3 -3
- package/src/main.ts +18 -10
- package/src/panels/approval-panel.ts +8 -8
- package/src/panels/automation-control-panel.ts +4 -4
- package/src/panels/base-panel.ts +1 -1
- package/src/panels/builtin/agent.ts +1 -1
- package/src/panels/builtin/operations.ts +3 -12
- package/src/panels/builtin/session.ts +32 -24
- package/src/panels/builtin/shared.ts +7 -7
- package/src/panels/cost-tracker-panel.ts +1 -1
- package/src/panels/docs-panel.ts +5 -3
- package/src/panels/index.ts +0 -1
- package/src/panels/knowledge-panel.ts +6 -5
- package/src/panels/memory-panel.ts +7 -6
- package/src/panels/panel-list-panel.ts +36 -80
- package/src/panels/project-planning-panel.ts +19 -12
- package/src/panels/provider-account-snapshot.ts +51 -25
- package/src/panels/provider-accounts-panel.ts +33 -18
- package/src/panels/provider-health-domains.ts +48 -7
- package/src/panels/provider-health-panel.ts +5 -4
- package/src/panels/qr-panel.ts +44 -20
- package/src/panels/schedule-panel.ts +9 -17
- package/src/panels/security-panel.ts +8 -8
- package/src/panels/session-browser-panel.ts +10 -10
- package/src/panels/subscription-panel.ts +6 -6
- package/src/panels/system-messages-panel.ts +3 -3
- package/src/panels/tasks-panel.ts +21 -14
- package/src/panels/tool-inspector-panel.ts +19 -12
- package/src/panels/work-plan-panel.ts +5 -5
- package/src/planning/project-planning-coordinator.ts +3 -3
- package/src/provider-auth-route-display.ts +9 -0
- package/src/renderer/agent-workspace-style.ts +34 -0
- package/src/renderer/agent-workspace.ts +254 -57
- package/src/renderer/autocomplete-overlay.ts +25 -6
- package/src/renderer/block-actions.ts +1 -3
- package/src/renderer/bookmark-modal.ts +19 -4
- package/src/renderer/buffer.ts +4 -2
- package/src/renderer/context-inspector.ts +50 -13
- package/src/renderer/diff.ts +1 -1
- package/src/renderer/file-picker-overlay.ts +19 -6
- package/src/renderer/help-overlay.ts +112 -34
- package/src/renderer/history-search-overlay.ts +19 -4
- package/src/renderer/live-tail-modal.ts +27 -5
- package/src/renderer/mcp-workspace.ts +176 -43
- package/src/renderer/model-picker-overlay.ts +58 -3
- package/src/renderer/model-workspace.ts +104 -22
- package/src/renderer/onboarding/onboarding-wizard.ts +20 -4
- package/src/renderer/process-modal.ts +27 -6
- package/src/renderer/profile-picker-modal.ts +21 -5
- package/src/renderer/search-overlay.ts +25 -5
- package/src/renderer/selection-modal-overlay.ts +46 -14
- package/src/renderer/session-picker-modal.ts +18 -1
- package/src/renderer/settings-modal-helpers.ts +2 -40
- package/src/renderer/settings-modal.ts +88 -55
- package/src/renderer/system-message.ts +1 -1
- package/src/renderer/tool-call.ts +20 -11
- package/src/runtime/agent-runtime-events.ts +129 -0
- package/src/runtime/bootstrap-command-context.ts +7 -1
- package/src/runtime/bootstrap-command-parts.ts +11 -8
- package/src/runtime/bootstrap-core.ts +23 -65
- package/src/runtime/bootstrap-hook-bridge.ts +7 -18
- package/src/runtime/bootstrap-shell.ts +46 -8
- package/src/runtime/bootstrap.ts +36 -46
- package/src/runtime/connected-host-auth.ts +47 -0
- package/src/runtime/diagnostics/panels/index.ts +2 -2
- package/src/runtime/diagnostics/panels/panel-resources.ts +1 -1
- package/src/runtime/diagnostics/panels/policy.ts +7 -7
- package/src/runtime/index.ts +2 -5
- package/src/runtime/onboarding/apply-file-helpers.ts +66 -0
- package/src/runtime/onboarding/apply.ts +288 -74
- package/src/runtime/onboarding/derivation.ts +10 -13
- package/src/runtime/onboarding/snapshot.ts +2 -17
- package/src/runtime/onboarding/types.ts +34 -20
- package/src/runtime/onboarding/verify.ts +105 -4
- package/src/runtime/operator-token-cleanup.ts +3 -3
- package/src/runtime/services.ts +95 -11
- package/src/runtime/store/selectors/index.ts +3 -3
- package/src/runtime/store/state.ts +1 -4
- package/src/runtime/surface-feature-flags.ts +41 -6
- package/src/runtime/ui-read-models.ts +3 -4
- package/src/runtime/ui-services.ts +6 -6
- package/src/shell/blocking-input.ts +2 -1
- package/src/shell/service-settings-sync.ts +7 -7
- package/src/shell/ui-openers.ts +17 -38
- package/src/tools/agent-analysis-registry-policy.ts +0 -1
- package/src/tools/agent-channel-send-tool.ts +133 -0
- package/src/tools/agent-context-policy.ts +1 -1
- package/src/tools/agent-knowledge-ingest-tool.ts +405 -0
- package/src/tools/agent-knowledge-tool.ts +170 -0
- package/src/tools/agent-local-registry-tool.ts +279 -73
- package/src/tools/agent-media-generate-tool.ts +133 -0
- package/src/tools/agent-notify-tool.ts +143 -0
- package/src/tools/agent-operator-action-tool.ts +137 -0
- package/src/tools/agent-operator-briefing-tool.ts +217 -0
- package/src/tools/agent-reminder-schedule-tool.ts +237 -0
- package/src/tools/agent-tool-policy-guard.ts +13 -15
- package/src/tools/agent-work-plan-tool.ts +256 -0
- package/src/version.ts +1 -1
- package/docs/connected-services.md +0 -51
- package/src/cli/package-verification.ts +0 -274
- package/src/input/commands/policy-dispatch.ts +0 -339
- package/src/input/commands/policy.ts +0 -17
- package/src/panels/panel-picker.ts +0 -105
- package/src/panels/policy-panel.ts +0 -308
- package/src/renderer/panel-picker-overlay.ts +0 -202
|
@@ -10,16 +10,11 @@ export function registerSecurityRuntimeCommands(registry: CommandRegistry): void
|
|
|
10
10
|
description: 'Inspect security posture, attack paths, and review state',
|
|
11
11
|
usage: '[review | attack-paths | tokens]',
|
|
12
12
|
handler(args, ctx) {
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
return;
|
|
17
|
-
}
|
|
18
|
-
ctx.print('Security panel is not available in this runtime.');
|
|
13
|
+
const subcommand = args[0]?.toLowerCase() ?? 'review';
|
|
14
|
+
if (subcommand === 'open' || subcommand === 'panel') {
|
|
15
|
+
ctx.print('Open Agent Workspace -> Tools & MCP -> Security review for the workspace view, or run /security review for compact command output.');
|
|
19
16
|
return;
|
|
20
17
|
}
|
|
21
|
-
|
|
22
|
-
const subcommand = args[0]?.toLowerCase() ?? 'review';
|
|
23
18
|
const audit = requireTokenAuditor(ctx).auditAll(Date.now());
|
|
24
19
|
const securitySnapshot = requireReadModels(ctx).security.getSnapshot();
|
|
25
20
|
const policySnapshot = ctx.extensions.policyRuntimeState?.getSnapshot();
|
|
@@ -34,13 +29,13 @@ export function registerSecurityRuntimeCommands(registry: CommandRegistry): void
|
|
|
34
29
|
|
|
35
30
|
if (subcommand === 'tokens') {
|
|
36
31
|
if (audit.results.length === 0) {
|
|
37
|
-
ctx.print('No registered API tokens are currently
|
|
32
|
+
ctx.print('No registered API tokens are currently available for security review.');
|
|
38
33
|
return;
|
|
39
34
|
}
|
|
40
35
|
ctx.print([
|
|
41
|
-
`Token
|
|
36
|
+
`Token Review (${audit.results.length})`,
|
|
42
37
|
...audit.results.map((result) => (
|
|
43
|
-
` ${result.label} policy
|
|
38
|
+
` ${result.label} policy ${result.scope.policyId} scope ${result.scope.outcome} rotation ${result.rotation.outcome} blocked ${result.blocked ? 'yes' : 'no'}`
|
|
44
39
|
)),
|
|
45
40
|
].join('\n'));
|
|
46
41
|
return;
|
|
@@ -1,12 +1,43 @@
|
|
|
1
1
|
import { join, resolve } from 'path';
|
|
2
2
|
import { existsSync, mkdirSync } from 'node:fs';
|
|
3
3
|
import { writeFile } from 'node:fs/promises';
|
|
4
|
-
import type { CommandRegistry } from '../command-registry.ts';
|
|
4
|
+
import type { CommandContext, CommandRegistry } from '../command-registry.ts';
|
|
5
5
|
import type { SelectionItem } from '../selection-modal.ts';
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
6
|
+
import type { SessionMeta } from '@pellux/goodvibes-sdk/platform/sessions';
|
|
7
|
+
import { exportToMarkdown, extractText } from '@pellux/goodvibes-sdk/platform/export';
|
|
8
|
+
import { requireSessionManager, requireShellPaths } from './runtime-services.ts';
|
|
8
9
|
import { summarizeError } from '@pellux/goodvibes-sdk/platform/utils';
|
|
9
10
|
import { requireYesFlag, stripYesFlag } from './confirmation.ts';
|
|
11
|
+
import { readConversationMessageSnapshots } from '../../core/conversation-message-snapshot.ts';
|
|
12
|
+
|
|
13
|
+
function formatSessionFailure(action: string, error: unknown): string {
|
|
14
|
+
return [
|
|
15
|
+
`Failed to ${action}`,
|
|
16
|
+
` error ${summarizeError(error)}`,
|
|
17
|
+
].join('\n');
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
type ConversationSnapshotReader = {
|
|
21
|
+
readonly getMessageSnapshot?: () => ReturnType<typeof readConversationMessageSnapshots>;
|
|
22
|
+
readonly toJSON?: () => unknown;
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
function isObjectArray(value: unknown): value is readonly object[] {
|
|
26
|
+
return Array.isArray(value) && value.every((entry) => typeof entry === 'object' && entry !== null);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
function getCurrentConversationMessages(ctx: CommandContext): ReturnType<typeof readConversationMessageSnapshots> {
|
|
30
|
+
const manager = ctx.session.conversationManager as unknown as ConversationSnapshotReader;
|
|
31
|
+
if (typeof manager.getMessageSnapshot === 'function') return manager.getMessageSnapshot();
|
|
32
|
+
if (typeof manager.toJSON === 'function') {
|
|
33
|
+
const serialized = manager.toJSON();
|
|
34
|
+
if (serialized && typeof serialized === 'object' && 'messages' in serialized) {
|
|
35
|
+
const messages = (serialized as { readonly messages?: unknown }).messages;
|
|
36
|
+
if (isObjectArray(messages)) return readConversationMessageSnapshots(messages);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
throw new Error('Conversation manager cannot export message snapshots.');
|
|
40
|
+
}
|
|
10
41
|
|
|
11
42
|
export function registerSessionContentCommands(registry: CommandRegistry): void {
|
|
12
43
|
registry.register({
|
|
@@ -32,7 +63,10 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
32
63
|
}
|
|
33
64
|
const resolvedPath = shellPaths.resolveWorkspacePath(outPath);
|
|
34
65
|
if (!shellPaths.isWithinWorkingDirectory(resolvedPath)) {
|
|
35
|
-
ctx.print(
|
|
66
|
+
ctx.print([
|
|
67
|
+
'Error',
|
|
68
|
+
' message Export path must be within the current directory.',
|
|
69
|
+
].join('\n'));
|
|
36
70
|
return;
|
|
37
71
|
}
|
|
38
72
|
if (!yes) {
|
|
@@ -41,23 +75,10 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
41
75
|
}
|
|
42
76
|
|
|
43
77
|
try {
|
|
44
|
-
const
|
|
45
|
-
const msgs = data.messages ?? [];
|
|
78
|
+
const msgs = getCurrentConversationMessages(ctx);
|
|
46
79
|
let fileContent: string;
|
|
47
80
|
if (format === 'markdown') {
|
|
48
|
-
|
|
49
|
-
role: String(m.role ?? 'user') as 'user' | 'assistant' | 'system' | 'tool',
|
|
50
|
-
content: Array.isArray(m.content)
|
|
51
|
-
? m.content as import('@pellux/goodvibes-sdk/platform/providers').ContentPart[]
|
|
52
|
-
: String(m.content ?? ''),
|
|
53
|
-
toolCalls: m.toolCalls as import('@pellux/goodvibes-sdk/platform/types').ToolCall[] | undefined,
|
|
54
|
-
callId: m.callId as string | undefined,
|
|
55
|
-
toolName: m.toolName as string | undefined,
|
|
56
|
-
reasoningContent: m.reasoningContent as string | undefined,
|
|
57
|
-
reasoningSummary: m.reasoningSummary as string | undefined,
|
|
58
|
-
usage: m.usage as { inputTokens: number; outputTokens: number; cacheReadTokens?: number; cacheWriteTokens?: number } | undefined,
|
|
59
|
-
}));
|
|
60
|
-
fileContent = exportToMarkdown(exportMsgs, {
|
|
81
|
+
fileContent = exportToMarkdown(msgs, {
|
|
61
82
|
model: ctx.session.runtime.model,
|
|
62
83
|
provider: ctx.session.runtime.provider,
|
|
63
84
|
sessionId: ctx.session.runtime.sessionId,
|
|
@@ -66,8 +87,8 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
66
87
|
} else {
|
|
67
88
|
const lines: string[] = [];
|
|
68
89
|
for (const m of msgs) {
|
|
69
|
-
const role =
|
|
70
|
-
const content =
|
|
90
|
+
const role = m.role.toUpperCase();
|
|
91
|
+
const content = extractText(m.content);
|
|
71
92
|
if (!content.trim()) continue;
|
|
72
93
|
lines.push(`[${role}]`);
|
|
73
94
|
lines.push(content);
|
|
@@ -79,9 +100,13 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
79
100
|
const dir = dirname(resolvedPath);
|
|
80
101
|
if (!existsSync(dir)) mkdirSync(dir, { recursive: true });
|
|
81
102
|
await writeFile(resolvedPath, fileContent, 'utf-8');
|
|
82
|
-
ctx.print(
|
|
103
|
+
ctx.print([
|
|
104
|
+
'Exported conversation',
|
|
105
|
+
` messages ${msgs.length}`,
|
|
106
|
+
` path ${resolvedPath}`,
|
|
107
|
+
].join('\n'));
|
|
83
108
|
} catch (err) {
|
|
84
|
-
ctx.print(
|
|
109
|
+
ctx.print(formatSessionFailure('export conversation', err));
|
|
85
110
|
}
|
|
86
111
|
},
|
|
87
112
|
});
|
|
@@ -92,10 +117,13 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
92
117
|
usage: '[text]',
|
|
93
118
|
argsHint: '[text]',
|
|
94
119
|
handler(args, ctx) {
|
|
95
|
-
if (args.length === 0) ctx.print(ctx.session.conversationManager.title ? `Conversation title
|
|
120
|
+
if (args.length === 0) ctx.print(ctx.session.conversationManager.title ? `Conversation title\n title ${ctx.session.conversationManager.title}` : 'No title set.');
|
|
96
121
|
else {
|
|
97
122
|
ctx.session.conversationManager.title = args.join(' ');
|
|
98
|
-
ctx.print(
|
|
123
|
+
ctx.print([
|
|
124
|
+
'Title set',
|
|
125
|
+
` title ${ctx.session.conversationManager.title}`,
|
|
126
|
+
].join('\n'));
|
|
99
127
|
ctx.renderRequest();
|
|
100
128
|
}
|
|
101
129
|
},
|
|
@@ -109,19 +137,24 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
109
137
|
handler(args, ctx) {
|
|
110
138
|
const sessionManager = requireSessionManager(ctx);
|
|
111
139
|
const rawName = args[0] || ctx.session.conversationManager.title || `session-${Date.now()}`;
|
|
112
|
-
const
|
|
113
|
-
const
|
|
114
|
-
const meta = {
|
|
140
|
+
const messages = ctx.session.conversationManager.getMessageSnapshot();
|
|
141
|
+
const meta: SessionMeta = {
|
|
115
142
|
title: ctx.session.conversationManager.title,
|
|
116
143
|
model: ctx.session.runtime.model,
|
|
117
144
|
provider: ctx.session.runtime.provider,
|
|
118
145
|
timestamp: Date.now(),
|
|
146
|
+
titleSource: ctx.session.conversationManager.getTitleSource(),
|
|
119
147
|
};
|
|
120
148
|
try {
|
|
121
149
|
const { filePath, sanitizedName } = sessionManager.save(rawName, messages, meta);
|
|
122
|
-
ctx.print(
|
|
150
|
+
ctx.print([
|
|
151
|
+
'Session saved',
|
|
152
|
+
` name ${rawName}`,
|
|
153
|
+
...(sanitizedName !== rawName ? [` saved as ${sanitizedName}`] : []),
|
|
154
|
+
` path ${filePath}`,
|
|
155
|
+
].join('\n'));
|
|
123
156
|
} catch (e) {
|
|
124
|
-
ctx.print(
|
|
157
|
+
ctx.print(formatSessionFailure('save session', e));
|
|
125
158
|
}
|
|
126
159
|
},
|
|
127
160
|
});
|
|
@@ -140,13 +173,18 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
140
173
|
try {
|
|
141
174
|
const { meta, messages, agentRecords } = sessionManager.load(args[0]);
|
|
142
175
|
ctx.session.conversationManager.resetAll();
|
|
143
|
-
ctx.session.conversationManager.fromJSON({ messages: messages
|
|
176
|
+
ctx.session.conversationManager.fromJSON({ messages: readConversationMessageSnapshots(messages) });
|
|
144
177
|
if (meta.title) ctx.session.conversationManager.title = meta.title;
|
|
145
178
|
ctx.session.conversationManager.rebuildHistory();
|
|
146
179
|
ctx.renderRequest();
|
|
147
|
-
ctx.print(
|
|
180
|
+
ctx.print([
|
|
181
|
+
'Session loaded',
|
|
182
|
+
` id ${args[0]}`,
|
|
183
|
+
` messages ${messages.length}`,
|
|
184
|
+
...(agentRecords.length > 0 ? [` ignored connected-host records ${agentRecords.length}`] : []),
|
|
185
|
+
].join('\n'));
|
|
148
186
|
} catch (e) {
|
|
149
|
-
ctx.print(
|
|
187
|
+
ctx.print(formatSessionFailure('load session', e));
|
|
150
188
|
}
|
|
151
189
|
},
|
|
152
190
|
});
|
|
@@ -217,67 +255,31 @@ export function registerSessionContentCommands(registry: CommandRegistry): void
|
|
|
217
255
|
const sessions = sessionManager.list();
|
|
218
256
|
if (ctx.openSelection) {
|
|
219
257
|
const items: SelectionItem[] = sessions.length === 0
|
|
220
|
-
? [{ id: '_empty', label: 'No saved sessions', detail: '
|
|
258
|
+
? [{ id: '_empty', label: 'No saved sessions', detail: 'Open Agent Workspace -> Conversation -> Save current session' }]
|
|
221
259
|
: sessions.map(s => ({ id: s.name, label: s.name, detail: s.title || '(untitled)', actions: 'Enter to load' }));
|
|
222
260
|
ctx.openSelection('Sessions', items, { allowSearch: true }, (result) => {
|
|
223
261
|
if (!result) return;
|
|
224
262
|
try {
|
|
225
263
|
const { meta, messages } = sessionManager.load(result.item.id);
|
|
226
264
|
ctx.session.conversationManager.resetAll();
|
|
227
|
-
ctx.session.conversationManager.fromJSON({ messages: messages
|
|
265
|
+
ctx.session.conversationManager.fromJSON({ messages: readConversationMessageSnapshots(messages) });
|
|
228
266
|
if (meta.title) ctx.session.conversationManager.title = meta.title;
|
|
229
267
|
ctx.session.conversationManager.rebuildHistory();
|
|
230
268
|
ctx.renderRequest();
|
|
231
|
-
ctx.print(
|
|
269
|
+
ctx.print([
|
|
270
|
+
'Session loaded',
|
|
271
|
+
` id ${result.item.id}`,
|
|
272
|
+
` messages ${messages.length}`,
|
|
273
|
+
].join('\n'));
|
|
232
274
|
} catch (e) {
|
|
233
|
-
ctx.print(
|
|
275
|
+
ctx.print(formatSessionFailure('load session', e));
|
|
234
276
|
}
|
|
235
277
|
});
|
|
236
278
|
return;
|
|
237
279
|
}
|
|
238
|
-
const lines = ['Saved sessions
|
|
280
|
+
const lines = ['Saved sessions', ''];
|
|
239
281
|
for (const s of sessions) lines.push(` ${s.name.padEnd(30)} ${(s.title || '(untitled)').padEnd(24)} ${new Date(s.timestamp).toLocaleString()} (${s.messageCount} msgs)`);
|
|
240
282
|
ctx.print(lines.join('\n'));
|
|
241
283
|
},
|
|
242
284
|
});
|
|
243
|
-
|
|
244
|
-
registry.register({
|
|
245
|
-
name: 'session-memory',
|
|
246
|
-
aliases: ['smemory'],
|
|
247
|
-
description: 'Manage conversation-pinned memories used during context compaction',
|
|
248
|
-
usage: '[list|add <text>|remove <id> --yes]',
|
|
249
|
-
argsHint: '[list|add|remove]',
|
|
250
|
-
handler(args, ctx) {
|
|
251
|
-
const sub = args[0] ?? 'list';
|
|
252
|
-
if (sub === 'list' || args.length === 0) {
|
|
253
|
-
const memories = requireSessionMemoryStore(ctx).list();
|
|
254
|
-
ctx.print(memories.length === 0
|
|
255
|
-
? 'No conversation-pinned memories. Use !# prefix or /session-memory add <text> to create one.'
|
|
256
|
-
: [`Conversation-Pinned Memories (${memories.length}):`, ...memories.map(m => ` [${m.id}] ${m.text}`)].join('\n'));
|
|
257
|
-
} else if (sub === 'add') {
|
|
258
|
-
const text = args.slice(1).join(' ').trim();
|
|
259
|
-
if (!text) {
|
|
260
|
-
ctx.print('Usage: /session-memory add <text>');
|
|
261
|
-
return;
|
|
262
|
-
}
|
|
263
|
-
const id = requireSessionMemoryStore(ctx).add(text);
|
|
264
|
-
ctx.print(`Memory added: [${id}] ${text}`);
|
|
265
|
-
} else if (sub === 'remove') {
|
|
266
|
-
const parsed = stripYesFlag(args);
|
|
267
|
-
const id = parsed.rest[1];
|
|
268
|
-
if (!id) {
|
|
269
|
-
ctx.print('Usage: /session-memory remove <id> --yes');
|
|
270
|
-
return;
|
|
271
|
-
}
|
|
272
|
-
if (!parsed.yes) {
|
|
273
|
-
requireYesFlag(ctx, `remove conversation-pinned memory ${id}`, '/session-memory remove <id> --yes');
|
|
274
|
-
return;
|
|
275
|
-
}
|
|
276
|
-
const store = requireSessionMemoryStore(ctx);
|
|
277
|
-
ctx.print(store.remove(id) ? `Memory removed: [${id}]` : `Memory not found: ${id}`);
|
|
278
|
-
} else {
|
|
279
|
-
ctx.print('Usage: /session-memory [list|add <text>|remove <id> --yes]\n /session-memory — list conversation-pinned memories\n /session-memory list — list conversation-pinned memories\n /session-memory add <text> — add a memory without sending a message\n /session-memory remove <id> --yes — remove a specific memory');
|
|
280
|
-
}
|
|
281
|
-
},
|
|
282
|
-
});
|
|
283
285
|
}
|