@nklisch/pi-enhanced 0.1.2 → 0.1.4
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 +7 -0
- package/README.md +3 -2
- package/node_modules/@nklisch/pi-clearance/README.md +10 -5
- package/node_modules/@nklisch/pi-clearance/docs/ARCHITECTURE.md +12 -7
- package/node_modules/@nklisch/pi-clearance/docs/CONFIGURATION.md +25 -35
- package/node_modules/@nklisch/pi-clearance/docs/DEVELOPER_GUIDE.md +30 -30
- package/node_modules/@nklisch/pi-clearance/docs/PACK_AUTHORING.md +5 -4
- package/node_modules/@nklisch/pi-clearance/docs/PRINCIPLES.md +14 -10
- package/node_modules/@nklisch/pi-clearance/docs/REFERENCE_PATTERNS.md +1 -1
- package/node_modules/@nklisch/pi-clearance/docs/REVIEWER_PROMPTS.md +12 -8
- package/node_modules/@nklisch/pi-clearance/docs/RULE_PACKS.md +1 -1
- package/node_modules/@nklisch/pi-clearance/docs/SPEC.md +7 -6
- package/node_modules/@nklisch/pi-clearance/docs/TUNE.md +2 -2
- package/node_modules/@nklisch/pi-clearance/docs/USER_GUIDE.md +7 -3
- package/node_modules/@nklisch/pi-clearance/docs/VISION.md +3 -3
- package/node_modules/@nklisch/pi-clearance/native/clearance-core.darwin-arm64.node +0 -0
- package/node_modules/@nklisch/pi-clearance/native/clearance-core.darwin-x64.node +0 -0
- package/node_modules/@nklisch/pi-clearance/native/clearance-core.linux-arm64-gnu.node +0 -0
- package/node_modules/@nklisch/pi-clearance/native/clearance-core.linux-x64-gnu.node +0 -0
- package/node_modules/@nklisch/pi-clearance/native/clearance-core.win32-arm64-msvc.node +0 -0
- package/node_modules/@nklisch/pi-clearance/native/clearance-core.win32-x64-msvc.node +0 -0
- package/node_modules/@nklisch/pi-clearance/package.json +9 -5
- package/node_modules/@nklisch/pi-clearance/src/config/config-command-plans.ts +79 -3
- package/node_modules/@nklisch/pi-clearance/src/config/config-command-writer.ts +7 -1
- package/node_modules/@nklisch/pi-clearance/src/config/defaults.ts +42 -0
- package/node_modules/@nklisch/pi-clearance/src/config/gated-tools.ts +7 -0
- package/node_modules/@nklisch/pi-clearance/src/config/loader.ts +7 -1
- package/node_modules/@nklisch/pi-clearance/src/config/pack-enablement-writer.ts +1 -0
- package/node_modules/@nklisch/pi-clearance/src/config/paths.ts +14 -3
- package/node_modules/@nklisch/pi-clearance/src/config/persistence.ts +135 -0
- package/node_modules/@nklisch/pi-clearance/src/config/schema.ts +74 -26
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialCase.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialCaseCategory.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialCaseExpectation.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialCaseResult.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialCaseResultOutcome.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialCaseSource.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialValidationReport.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/AdversarialValidationStatus.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashBlock.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashCommandShape.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashConditionalArm.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashControlConstruct.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashFlag.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashForLoopKeywordSpans.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashIteratorEntry.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashIteratorEntryKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashListOperator.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashLoopVariableReference.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashPathFact.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashPathFactContext.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashPathFactProvenance.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashPathFactProvenanceEntry.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashPathFacts.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashPipeline.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashStage.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BashStageProgram.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/BlockOperator.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CapturedOutcome.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CommandFamilyKey.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CommandFamilySummary.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CompileError.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CompositionOperator.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CompoundBodyReason.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CompoundFeatureReason.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CompoundForm.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CompoundIteratorReason.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusEntry.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusExpectedLabel.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusFidelity.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusQueryModel.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusQuerySummary.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusQuerySummarySnapshot.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusRecord.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CorpusSource.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/CountByLabel.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/Decision.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/DecisionEffect.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/DecisionProvenance.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/DecisionSource.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/DiagnosticSeverity.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/EffectivePolicy.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/EmbeddedShellProjection.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/EnvironmentAssignment.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/IteratorSourceKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/LoopQuoteKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/LoopVariableUnknownReason.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/MatcherExpr.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/MutationShapeKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/MutationTrustBoundaryClassification.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/MutationTrustBoundaryKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PackCompileResult.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PackWarningLevel.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ParsedEvidence.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ParsedShapeSummary.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathAccess.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathFactProjectScope.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathFactsRequirement.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathFactsResolvedConfig.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathNormalization.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathScope.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathScopeMatcherExpr.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathScopeMatcherMode.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathUnknownReason.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PathUsageKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PiBuiltinToolOperation.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PiBuiltinToolPathInput.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PiBuiltinToolShape.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PiBuiltinToolSpec.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PiFileMutationToolName.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PiToolMutationFacts.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PolicyPack.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PolicyPackDocLink.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PolicyPackExample.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PolicyPackMetadata.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PolicyPackWarning.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/PolicyRule.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ProposalNotRunReason.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ProposalNotRunSeverity.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/QuoteKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/Redirect.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/RedirectStream.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/RedirectTargetKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayCorpus.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDelta.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaBlockedSummary.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaChangedRecord.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaFamily.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaImprovement.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaRegression.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaStatus.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayDeltaTransitionCount.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayPathFacts.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayReviewerMode.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayReviewerOutcome.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayStatus.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ReplayedDecision.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ShapeDiagnostic.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/SourceFidelity.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/SourceSpan.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/Substitution.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/SubstitutionKind.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolCallIdentity.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolPathAccess.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolPathFact.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolPathFactContext.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolPathFacts.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolPathUsage.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/ToolShape.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/UnknownPathBehavior.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/UnknownToolShape.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/contracts/index.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/index.ts +33 -2
- package/node_modules/@nklisch/pi-clearance/src/native/loader.ts +29 -42
- package/node_modules/@nklisch/pi-clearance/src/replay/reviewer-config-proposals.ts +7 -4
- package/node_modules/@nklisch/pi-clearance/src/runtime/allow-request-message.ts +21 -0
- package/node_modules/@nklisch/pi-clearance/src/runtime/auto-reviewer-read-models.ts +165 -8
- package/node_modules/@nklisch/pi-clearance/src/runtime/command-registry.ts +1 -1
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/allow.ts +26 -2
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/packs.ts +6 -6
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/scope.ts +5 -5
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/actions.ts +11 -0
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/dispatcher.ts +274 -1
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/model-options.ts +52 -0
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/native-ui.ts +54 -67
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/panels/reviewer.ts +19 -3
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/panels/scope.ts +2 -11
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/panels.ts +10 -1
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings/read-model.ts +47 -13
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/settings.ts +32 -37
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/status.ts +3 -0
- package/node_modules/@nklisch/pi-clearance/src/runtime/config-commands/types.ts +14 -5
- package/node_modules/@nklisch/pi-clearance/src/runtime/handler.ts +36 -0
- package/node_modules/@nklisch/pi-clearance/src/runtime/mode-prompt.ts +0 -1
- package/node_modules/@nklisch/pi-clearance/src/runtime/model-adapter.ts +5 -1
- package/node_modules/@nklisch/pi-clearance/src/runtime/reviewer-context.ts +73 -10
- package/node_modules/@nklisch/pi-clearance/src/runtime/reviewer-prompts.ts +186 -175
- package/node_modules/@nklisch/pi-clearance/src/runtime/reviewer.ts +26 -6
- package/node_modules/@nklisch/pi-plugins/dist/infrastructure/state/local-lock-filesystem.d.ts +23 -1
- package/node_modules/@nklisch/pi-plugins/dist/infrastructure/state/local-lock-filesystem.js +46 -50
- package/node_modules/@nklisch/pi-plugins/dist/infrastructure/state/local-lock-filesystem.js.map +1 -1
- package/node_modules/@nklisch/pi-plugins/dist/runtime/mcp/pi-mcp-adapter-package.js +2 -2
- package/node_modules/@nklisch/pi-plugins/dist/runtime/mcp/pi-mcp-adapter-runtime.js +2 -2
- package/node_modules/@nklisch/pi-plugins/dist/runtime/subagents/pi-subagents-lifecycle.js +1 -1
- package/node_modules/@nklisch/pi-plugins/dist/runtime/subagents/pi-subagents-package.js +2 -2
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/README.md +41 -31
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/dist/public.d.ts +2 -1
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/docs/FORK-MAINTENANCE.md +17 -11
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/docs/VISION.md +14 -7
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/docs/architecture/architecture.md +11 -19
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/docs/comparison-with-upstream.md +58 -53
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/package.json +2 -2
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/config/agent-type-resolution.ts +43 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/config/agent-types.ts +11 -6
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/config/custom-agents.ts +13 -6
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/config/default-agents.ts +0 -52
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/config/thinking-levels.ts +12 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/handlers/interrupt.ts +5 -2
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/handlers/lifecycle.ts +3 -3
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/index.ts +7 -6
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/lifecycle/create-subagent-session.ts +7 -2
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/lifecycle/parent-snapshot.ts +11 -3
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/lifecycle/subagent-manager.ts +26 -56
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/lifecycle/subagent-session.ts +48 -9
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/lifecycle/subagent-state.ts +32 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/lifecycle/subagent.ts +105 -17
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/observation/composite-subagent-observer.ts +4 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/observation/notification.ts +50 -46
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/observation/renderer.ts +1 -1
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/observation/subagent-events-observer.ts +15 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/runtime.ts +2 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/service/service-adapter.ts +35 -6
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/service/service.ts +1 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/session/model-label.ts +19 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/session/prompts.ts +24 -1
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/session/session-config.ts +11 -6
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/settings.ts +70 -3
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/agent-tool.ts +27 -10
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/background-spawner.ts +6 -2
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/foreground-runner.ts +12 -3
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/get-result-report.ts +17 -3
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/get-result-tool.ts +13 -20
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/result-renderer.ts +6 -1
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/spawn-config.ts +16 -16
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/tools/steer-tool.ts +12 -4
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/types.ts +2 -2
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/agent-widget.ts +24 -11
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/display.ts +10 -7
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/glyphs.ts +7 -0
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/session-navigation.ts +34 -25
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/session-navigator.ts +30 -10
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/subagents-settings.ts +58 -13
- package/node_modules/@nklisch/pi-plugins/node_modules/@nklisch/pi-subagents/src/ui/widget-renderer.ts +32 -19
- package/node_modules/@nklisch/pi-plugins/package.json +3 -3
- package/package.json +1 -1
- package/test/verify-bundle.mjs +28 -1
|
@@ -14,7 +14,6 @@
|
|
|
14
14
|
|
|
15
15
|
import { buildSessionContext, parseSessionEntries, type SessionEntry, type ToolDefinition } from "@earendil-works/pi-coding-agent";
|
|
16
16
|
import type { AgentConfigLookup } from "#src/config/agent-types";
|
|
17
|
-
import type { EvictedSubagent } from "#src/lifecycle/subagent-manager";
|
|
18
17
|
import type { SubagentStatus } from "#src/lifecycle/subagent-state";
|
|
19
18
|
import type { AgentSessionEvent, SessionMessage, SubagentType } from "#src/types";
|
|
20
19
|
import { formatDuration, getDisplayName } from "#src/ui/display";
|
|
@@ -26,12 +25,14 @@ export interface NavigableSubagent {
|
|
|
26
25
|
readonly id: string;
|
|
27
26
|
readonly type: SubagentType;
|
|
28
27
|
readonly description: string;
|
|
28
|
+
readonly modelLabel: string;
|
|
29
29
|
readonly status: SubagentStatus;
|
|
30
30
|
readonly startedAt: number;
|
|
31
31
|
readonly completedAt: number | undefined;
|
|
32
32
|
readonly toolUses: number;
|
|
33
33
|
readonly activeTools: ReadonlyMap<string, string>;
|
|
34
34
|
readonly responseText: string;
|
|
35
|
+
readonly outputFile: string | undefined;
|
|
35
36
|
readonly agentMessages: readonly SessionMessage[];
|
|
36
37
|
isSessionReady(): boolean;
|
|
37
38
|
subscribeToUpdates(fn: (event: AgentSessionEvent) => void): (() => void) | undefined;
|
|
@@ -41,17 +42,24 @@ export interface NavigableSubagent {
|
|
|
41
42
|
/**
|
|
42
43
|
* A navigable entry plus the label shown in the picker.
|
|
43
44
|
*
|
|
44
|
-
* A `live` entry sources its transcript from the in-memory
|
|
45
|
-
* entry
|
|
45
|
+
* A `live` entry sources its transcript from the in-memory session; an
|
|
46
|
+
* `evicted`-kind entry is a persisted snapshot for a released live session.
|
|
46
47
|
*/
|
|
48
|
+
export interface RunDisplayMetadata {
|
|
49
|
+
readonly modelLabel: string;
|
|
50
|
+
readonly startedAt: number;
|
|
51
|
+
readonly completedAt: () => number | undefined;
|
|
52
|
+
}
|
|
53
|
+
|
|
47
54
|
export type NavigationEntry =
|
|
48
|
-
| { readonly kind: "live"; readonly label: string; readonly record: NavigableSubagent }
|
|
49
|
-
| { readonly kind: "evicted"; readonly label: string; readonly outputFile: string };
|
|
55
|
+
| { readonly kind: "live"; readonly label: string; readonly record: NavigableSubagent; readonly run: RunDisplayMetadata }
|
|
56
|
+
| { readonly kind: "evicted"; readonly label: string; readonly outputFile: string; readonly run: RunDisplayMetadata };
|
|
50
57
|
|
|
51
58
|
/** The fields `buildLabel` reads — shared by a live record and an evicted descriptor. */
|
|
52
59
|
interface LabelFields {
|
|
53
60
|
readonly type: SubagentType;
|
|
54
61
|
readonly description: string;
|
|
62
|
+
readonly modelLabel: string;
|
|
55
63
|
readonly status: SubagentStatus;
|
|
56
64
|
readonly startedAt: number;
|
|
57
65
|
readonly completedAt: number | undefined;
|
|
@@ -77,34 +85,35 @@ export interface TranscriptSource {
|
|
|
77
85
|
}
|
|
78
86
|
|
|
79
87
|
/**
|
|
80
|
-
* Label every navigable subagent
|
|
81
|
-
*
|
|
88
|
+
* Label every navigable subagent: live sessions first, then persisted snapshots
|
|
89
|
+
* for released records and any legacy evicted descriptors.
|
|
82
90
|
*/
|
|
83
91
|
export function listNavigableAgents(
|
|
84
92
|
agents: readonly NavigableSubagent[],
|
|
85
|
-
evicted: readonly EvictedSubagent[],
|
|
86
93
|
registry: AgentConfigLookup,
|
|
87
94
|
): NavigationEntry[] {
|
|
88
|
-
const live = agents
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
.
|
|
95
|
-
kind: "
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
95
|
+
const live = agents.flatMap((record): NavigationEntry[] => {
|
|
96
|
+
const run = {
|
|
97
|
+
modelLabel: record.modelLabel,
|
|
98
|
+
startedAt: record.startedAt,
|
|
99
|
+
completedAt: () => record.completedAt,
|
|
100
|
+
};
|
|
101
|
+
if (record.isSessionReady()) {
|
|
102
|
+
return [{ kind: "live", record, label: buildLabel(record, registry), run }];
|
|
103
|
+
}
|
|
104
|
+
return record.outputFile
|
|
105
|
+
? [{ kind: "evicted", outputFile: record.outputFile, label: buildLabel(record, registry, true), run }]
|
|
106
|
+
: [];
|
|
107
|
+
});
|
|
108
|
+
return live;
|
|
100
109
|
}
|
|
101
110
|
|
|
102
111
|
/**
|
|
103
112
|
* Source a transcript from a persisted child-session JSONL snapshot.
|
|
104
113
|
*
|
|
105
|
-
* For an agent
|
|
106
|
-
* the
|
|
107
|
-
*
|
|
114
|
+
* For an agent whose live session was released, the in-memory message history is
|
|
115
|
+
* gone but the terminal record and session file survive. Reads the file, drops
|
|
116
|
+
* the `SessionHeader`, and resolves the
|
|
108
117
|
* message list via Pi's own parser. A static snapshot — no subscription, no
|
|
109
118
|
* streaming, no live tool registry. `readFile` is injected so this module makes
|
|
110
119
|
* no `fs` calls.
|
|
@@ -140,6 +149,6 @@ export function liveSource(record: NavigableSubagent): TranscriptSource {
|
|
|
140
149
|
function buildLabel(fields: LabelFields, registry: AgentConfigLookup, evicted = false): string {
|
|
141
150
|
const name = getDisplayName(fields.type, registry);
|
|
142
151
|
const duration = formatDuration(fields.startedAt, fields.completedAt);
|
|
143
|
-
const marker = evicted ? " ·
|
|
144
|
-
return `${name} (${fields.description}) · ${fields.toolUses} tools · ${fields.status} · ${duration}${marker}`;
|
|
152
|
+
const marker = evicted ? " · released (snapshot)" : "";
|
|
153
|
+
return `${name} (${fields.description}) · ${fields.modelLabel} · ${fields.toolUses} tools · ${fields.status} · ${duration}${marker}`;
|
|
145
154
|
}
|
|
@@ -38,10 +38,9 @@ import {
|
|
|
38
38
|
visibleWidth,
|
|
39
39
|
} from "@earendil-works/pi-tui";
|
|
40
40
|
import type { AgentConfigLookup } from "#src/config/agent-types";
|
|
41
|
-
import type { EvictedSubagent } from "#src/lifecycle/subagent-manager";
|
|
42
41
|
import type { SessionMessage } from "#src/types";
|
|
43
|
-
import { describeActivity, type Theme } from "#src/ui/display";
|
|
44
|
-
import { fileSnapshotSource, listNavigableAgents, liveSource, type NavigableSubagent, type TranscriptSource } from "#src/ui/session-navigation";
|
|
42
|
+
import { describeActivity, formatDuration, type Theme } from "#src/ui/display";
|
|
43
|
+
import { fileSnapshotSource, listNavigableAgents, liveSource, type NavigableSubagent, type RunDisplayMetadata, type TranscriptSource } from "#src/ui/session-navigation";
|
|
45
44
|
|
|
46
45
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
47
46
|
|
|
@@ -69,8 +68,6 @@ export interface SessionNavigatorUI {
|
|
|
69
68
|
export interface SessionNavigatorParams {
|
|
70
69
|
ui: SessionNavigatorUI;
|
|
71
70
|
agents: readonly NavigableSubagent[];
|
|
72
|
-
/** Descriptors of agents evicted by the cleanup sweep, sourced from disk when picked. */
|
|
73
|
-
evicted: readonly EvictedSubagent[];
|
|
74
71
|
registry: AgentConfigLookup;
|
|
75
72
|
/** Working directory for tool-call rendering (relative path display). */
|
|
76
73
|
cwd: string;
|
|
@@ -83,6 +80,7 @@ export interface TranscriptOverlayOptions {
|
|
|
83
80
|
tui: TUI;
|
|
84
81
|
theme: Theme;
|
|
85
82
|
source: TranscriptSource;
|
|
83
|
+
run: RunDisplayMetadata;
|
|
86
84
|
done: (result: undefined) => void;
|
|
87
85
|
cwd: string;
|
|
88
86
|
markdownTheme: MarkdownTheme;
|
|
@@ -96,8 +94,8 @@ export interface TranscriptOverlayOptions {
|
|
|
96
94
|
* manager, so it stays a reactive consumer with no inbound call into the core.
|
|
97
95
|
*/
|
|
98
96
|
export class SessionNavigatorHandler {
|
|
99
|
-
async handle({ ui, agents,
|
|
100
|
-
const entries = listNavigableAgents(agents,
|
|
97
|
+
async handle({ ui, agents, registry, cwd, readFile }: SessionNavigatorParams): Promise<void> {
|
|
98
|
+
const entries = listNavigableAgents(agents, registry);
|
|
101
99
|
if (entries.length === 0) {
|
|
102
100
|
ui.notify("No subagent sessions to view.", "info");
|
|
103
101
|
return;
|
|
@@ -120,7 +118,7 @@ export class SessionNavigatorHandler {
|
|
|
120
118
|
const markdownTheme = getMarkdownTheme();
|
|
121
119
|
await ui.custom<undefined>(
|
|
122
120
|
(tui, theme, _keybindings, done) =>
|
|
123
|
-
new TranscriptOverlay({ tui, theme, source, done, cwd, markdownTheme }),
|
|
121
|
+
new TranscriptOverlay({ tui, theme, source, run: entry.run, done, cwd, markdownTheme }),
|
|
124
122
|
{
|
|
125
123
|
overlay: true,
|
|
126
124
|
overlayOptions: { anchor: "center", width: "90%", maxHeight: `${VIEWPORT_HEIGHT_PCT}%` },
|
|
@@ -142,20 +140,23 @@ export class TranscriptOverlay implements Component {
|
|
|
142
140
|
private scrollOffset = 0;
|
|
143
141
|
private autoScroll = true;
|
|
144
142
|
private unsubscribe: (() => void) | undefined;
|
|
143
|
+
private runtimeInterval: ReturnType<typeof setInterval> | undefined;
|
|
145
144
|
private closed = false;
|
|
146
145
|
|
|
147
146
|
private readonly tui: TUI;
|
|
148
147
|
private readonly theme: Theme;
|
|
149
148
|
private readonly source: TranscriptSource;
|
|
149
|
+
private readonly run: RunDisplayMetadata;
|
|
150
150
|
private readonly done: (result: undefined) => void;
|
|
151
151
|
private readonly cwd: string;
|
|
152
152
|
private readonly markdownTheme: MarkdownTheme;
|
|
153
153
|
private content: Container;
|
|
154
154
|
|
|
155
|
-
constructor({ tui, theme, source, done, cwd, markdownTheme }: TranscriptOverlayOptions) {
|
|
155
|
+
constructor({ tui, theme, source, run, done, cwd, markdownTheme }: TranscriptOverlayOptions) {
|
|
156
156
|
this.tui = tui;
|
|
157
157
|
this.theme = theme;
|
|
158
158
|
this.source = source;
|
|
159
|
+
this.run = run;
|
|
159
160
|
this.done = done;
|
|
160
161
|
this.cwd = cwd;
|
|
161
162
|
this.markdownTheme = markdownTheme;
|
|
@@ -165,11 +166,21 @@ export class TranscriptOverlay implements Component {
|
|
|
165
166
|
this.content = this.rebuild();
|
|
166
167
|
this.tui.requestRender();
|
|
167
168
|
});
|
|
169
|
+
if (run.completedAt() === undefined) {
|
|
170
|
+
this.runtimeInterval = setInterval(() => {
|
|
171
|
+
if (this.closed || this.run.completedAt() !== undefined) {
|
|
172
|
+
this.clearRuntimeInterval();
|
|
173
|
+
return;
|
|
174
|
+
}
|
|
175
|
+
this.tui.requestRender();
|
|
176
|
+
}, 100);
|
|
177
|
+
}
|
|
168
178
|
}
|
|
169
179
|
|
|
170
180
|
handleInput(data: string): void {
|
|
171
181
|
if (matchesKey(data, "escape") || matchesKey(data, "q")) {
|
|
172
182
|
this.closed = true;
|
|
183
|
+
this.clearRuntimeInterval();
|
|
173
184
|
this.done(undefined);
|
|
174
185
|
return;
|
|
175
186
|
}
|
|
@@ -213,7 +224,8 @@ export class TranscriptOverlay implements Component {
|
|
|
213
224
|
const hrMid = row(th.fg("dim", "─".repeat(innerW)));
|
|
214
225
|
|
|
215
226
|
lines.push(hrTop);
|
|
216
|
-
|
|
227
|
+
const runtime = formatDuration(this.run.startedAt, this.run.completedAt());
|
|
228
|
+
lines.push(row(th.bold(`Subagent session · ${this.run.modelLabel} · ${runtime}`)));
|
|
217
229
|
lines.push(hrMid);
|
|
218
230
|
|
|
219
231
|
const contentLines = this.buildContentLines(innerW);
|
|
@@ -249,10 +261,18 @@ export class TranscriptOverlay implements Component {
|
|
|
249
261
|
this.unsubscribe();
|
|
250
262
|
this.unsubscribe = undefined;
|
|
251
263
|
}
|
|
264
|
+
this.clearRuntimeInterval();
|
|
252
265
|
}
|
|
253
266
|
|
|
254
267
|
// ---- Private ----
|
|
255
268
|
|
|
269
|
+
private clearRuntimeInterval(): void {
|
|
270
|
+
if (this.runtimeInterval) {
|
|
271
|
+
clearInterval(this.runtimeInterval);
|
|
272
|
+
this.runtimeInterval = undefined;
|
|
273
|
+
}
|
|
274
|
+
}
|
|
275
|
+
|
|
256
276
|
private innerWidth(): number {
|
|
257
277
|
return Math.max(0, this.tui.terminal.columns - 4);
|
|
258
278
|
}
|
|
@@ -5,9 +5,17 @@ export interface SubagentsSettingsManager {
|
|
|
5
5
|
readonly maxConcurrent: number;
|
|
6
6
|
readonly defaultMaxTurns: number | undefined;
|
|
7
7
|
readonly graceTurns: number;
|
|
8
|
+
readonly consumedSessionRetentionMinutes: number;
|
|
9
|
+
readonly unconsumedSessionRetentionMinutes: number;
|
|
10
|
+
readonly abortAllOnInterrupt: boolean;
|
|
11
|
+
readonly fallbackSubagent: string | false | undefined;
|
|
8
12
|
applyMaxConcurrent(n: number): { message: string; level: "info" | "warning" };
|
|
9
13
|
applyDefaultMaxTurns(n: number): { message: string; level: "info" | "warning" };
|
|
10
14
|
applyGraceTurns(n: number): { message: string; level: "info" | "warning" };
|
|
15
|
+
applyConsumedSessionRetention(n: number): { message: string; level: "info" | "warning" };
|
|
16
|
+
applyUnconsumedSessionRetention(n: number): { message: string; level: "info" | "warning" };
|
|
17
|
+
applyAbortAllOnInterrupt(value: boolean): { message: string; level: "info" | "warning" };
|
|
18
|
+
applyFallbackSubagent(value: string | false | undefined): { message: string; level: "info" | "warning" };
|
|
11
19
|
}
|
|
12
20
|
|
|
13
21
|
/** Narrow UI interface — only the ctx.ui methods the settings handler calls. */
|
|
@@ -17,6 +25,12 @@ export interface SubagentsSettingsUI {
|
|
|
17
25
|
notify(message: string, level: "info" | "warning" | "error"): void;
|
|
18
26
|
}
|
|
19
27
|
|
|
28
|
+
/** Registry operations needed to offer only valid fallback agents. */
|
|
29
|
+
export interface SubagentsSettingsAgentRegistry {
|
|
30
|
+
reload(): void;
|
|
31
|
+
getAvailableTypes(): string[];
|
|
32
|
+
}
|
|
33
|
+
|
|
20
34
|
// ---- Class ----
|
|
21
35
|
|
|
22
36
|
/**
|
|
@@ -26,13 +40,20 @@ export interface SubagentsSettingsUI {
|
|
|
26
40
|
* settings list. Lifted from `AgentsMenuHandler.showSettings`.
|
|
27
41
|
*/
|
|
28
42
|
export class SubagentsSettingsHandler {
|
|
29
|
-
constructor(
|
|
43
|
+
constructor(
|
|
44
|
+
private readonly settings: SubagentsSettingsManager,
|
|
45
|
+
private readonly agentRegistry: SubagentsSettingsAgentRegistry,
|
|
46
|
+
) {}
|
|
30
47
|
|
|
31
48
|
async handle({ ui }: { ui: SubagentsSettingsUI }): Promise<void> {
|
|
32
49
|
const choice = await ui.select("Settings", [
|
|
33
50
|
`Max concurrency (current: ${this.settings.maxConcurrent})`,
|
|
34
51
|
`Default max turns (current: ${this.settings.defaultMaxTurns ?? "unlimited"})`,
|
|
35
52
|
`Grace turns (current: ${this.settings.graceTurns})`,
|
|
53
|
+
`Consumed session retention (current: ${this.settings.consumedSessionRetentionMinutes}m)`,
|
|
54
|
+
`Unconsumed session retention (current: ${this.settings.unconsumedSessionRetentionMinutes}m)`,
|
|
55
|
+
`Abort all on ESC (current: ${this.settings.abortAllOnInterrupt ? "yes" : "no"})`,
|
|
56
|
+
`Unknown agent fallback (current: ${this.settings.fallbackSubagent === false ? "none" : this.settings.fallbackSubagent ?? "general-purpose"})`,
|
|
36
57
|
]);
|
|
37
58
|
if (!choice) return;
|
|
38
59
|
|
|
@@ -65,19 +86,43 @@ export class SubagentsSettingsHandler {
|
|
|
65
86
|
}
|
|
66
87
|
}
|
|
67
88
|
} else if (choice.startsWith("Grace turns")) {
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
89
|
+
await this.applyNonNegativeInput(ui, "Grace turns after wrap-up steer", this.settings.graceTurns, 1, (n) => this.settings.applyGraceTurns(n));
|
|
90
|
+
} else if (choice.startsWith("Consumed session retention")) {
|
|
91
|
+
await this.applyNonNegativeInput(ui, "Minutes to retain a consumed live session", this.settings.consumedSessionRetentionMinutes, 0, (n) => this.settings.applyConsumedSessionRetention(n));
|
|
92
|
+
} else if (choice.startsWith("Unconsumed session retention")) {
|
|
93
|
+
await this.applyNonNegativeInput(ui, "Minutes to retain an unconsumed live session", this.settings.unconsumedSessionRetentionMinutes, 0, (n) => this.settings.applyUnconsumedSessionRetention(n));
|
|
94
|
+
} else if (choice.startsWith("Abort all on ESC")) {
|
|
95
|
+
const toast = this.settings.applyAbortAllOnInterrupt(!this.settings.abortAllOnInterrupt);
|
|
96
|
+
ui.notify(toast.message, toast.level);
|
|
97
|
+
} else if (choice.startsWith("Unknown agent fallback")) {
|
|
98
|
+
this.agentRegistry.reload();
|
|
99
|
+
const failClosed = "Fail closed (no fallback)";
|
|
100
|
+
const selected = await ui.select("Fallback for unknown agent types", [
|
|
101
|
+
failClosed,
|
|
102
|
+
...this.agentRegistry.getAvailableTypes(),
|
|
103
|
+
]);
|
|
104
|
+
if (selected) {
|
|
105
|
+
const toast = this.settings.applyFallbackSubagent(selected === failClosed ? false : selected);
|
|
106
|
+
ui.notify(toast.message, toast.level);
|
|
80
107
|
}
|
|
81
108
|
}
|
|
82
109
|
}
|
|
110
|
+
|
|
111
|
+
private async applyNonNegativeInput(
|
|
112
|
+
ui: SubagentsSettingsUI,
|
|
113
|
+
title: string,
|
|
114
|
+
current: number,
|
|
115
|
+
minimum: number,
|
|
116
|
+
apply: (value: number) => { message: string; level: "info" | "warning" },
|
|
117
|
+
): Promise<void> {
|
|
118
|
+
const val = await ui.input(title, String(current));
|
|
119
|
+
if (!val) return;
|
|
120
|
+
const n = Number(val);
|
|
121
|
+
if (!Number.isInteger(n) || n < minimum) {
|
|
122
|
+
ui.notify(minimum === 0 ? "Must be a non-negative integer." : "Must be a positive integer.", "warning");
|
|
123
|
+
return;
|
|
124
|
+
}
|
|
125
|
+
const toast = apply(n);
|
|
126
|
+
ui.notify(toast.message, toast.level);
|
|
127
|
+
}
|
|
83
128
|
}
|
|
@@ -29,6 +29,7 @@ export interface WidgetAgent {
|
|
|
29
29
|
readonly type: SubagentType;
|
|
30
30
|
readonly status: string;
|
|
31
31
|
readonly description: string;
|
|
32
|
+
readonly modelLabel: string;
|
|
32
33
|
readonly toolUses: number;
|
|
33
34
|
readonly startedAt: number;
|
|
34
35
|
readonly completedAt?: number;
|
|
@@ -77,7 +78,7 @@ export function renderFinishedLine(
|
|
|
77
78
|
statusText = theme.fg("warning", " aborted");
|
|
78
79
|
}
|
|
79
80
|
|
|
80
|
-
const parts: string[] = [];
|
|
81
|
+
const parts: string[] = [agent.modelLabel];
|
|
81
82
|
parts.push(formatTurns(agent.turnCount, agent.maxTurns));
|
|
82
83
|
if (agent.toolUses > 0) parts.push(`${agent.toolUses} tool use${agent.toolUses === 1 ? "" : "s"}`);
|
|
83
84
|
parts.push(duration);
|
|
@@ -101,7 +102,7 @@ export function renderRunningLines(
|
|
|
101
102
|
const tokens = getLifetimeTotal(agent.lifetimeUsage);
|
|
102
103
|
const tokenText = tokens > 0 ? formatSessionTokens(tokens, agent.contextPercent, theme, agent.compactionCount) : "";
|
|
103
104
|
|
|
104
|
-
const parts: string[] = [];
|
|
105
|
+
const parts: string[] = [agent.modelLabel];
|
|
105
106
|
parts.push(formatTurns(agent.turnCount, agent.maxTurns));
|
|
106
107
|
if (agent.toolUses > 0) parts.push(`${agent.toolUses} tool use${agent.toolUses === 1 ? "" : "s"}`);
|
|
107
108
|
if (tokenText) parts.push(tokenText);
|
|
@@ -146,7 +147,7 @@ function categorizeAgents(
|
|
|
146
147
|
interface WidgetSections {
|
|
147
148
|
finishedLines: string[];
|
|
148
149
|
runningLines: [string, string][];
|
|
149
|
-
|
|
150
|
+
queuedLines: string[];
|
|
150
151
|
}
|
|
151
152
|
|
|
152
153
|
/** Render each agent bucket into pre-formatted lines with ├─ tree connectors. */
|
|
@@ -171,11 +172,17 @@ function buildSections(
|
|
|
171
172
|
]);
|
|
172
173
|
}
|
|
173
174
|
|
|
174
|
-
const
|
|
175
|
-
|
|
176
|
-
|
|
175
|
+
const queuedLines = categories.queued.map((agent) =>
|
|
176
|
+
truncate(
|
|
177
|
+
theme.fg("dim", "\u251C\u2500")
|
|
178
|
+
+ ` ${theme.fg("muted", "\u25E6")} ${theme.fg("dim", getDisplayName(agent.type, registry))}`
|
|
179
|
+
+ ` ${theme.fg("dim", "·")} ${theme.fg("dim", agent.modelLabel)}`
|
|
180
|
+
+ ` ${theme.fg("dim", "·")} ${theme.fg("dim", agent.description)}`
|
|
181
|
+
+ ` ${theme.fg("dim", "· queued")}`,
|
|
182
|
+
),
|
|
183
|
+
);
|
|
177
184
|
|
|
178
|
-
return { finishedLines, runningLines,
|
|
185
|
+
return { finishedLines, runningLines, queuedLines };
|
|
179
186
|
}
|
|
180
187
|
|
|
181
188
|
/**
|
|
@@ -183,16 +190,16 @@ function buildSections(
|
|
|
183
190
|
* Fixes the last tree connector: ├─ → └─, and │ → space for the running-agent activity line.
|
|
184
191
|
*/
|
|
185
192
|
function assembleWithinBudget(heading: string, sections: WidgetSections): string[] {
|
|
186
|
-
const { finishedLines, runningLines,
|
|
193
|
+
const { finishedLines, runningLines, queuedLines } = sections;
|
|
187
194
|
const lines: string[] = [heading, ...finishedLines];
|
|
188
195
|
for (const pair of runningLines) lines.push(...pair);
|
|
189
|
-
|
|
196
|
+
lines.push(...queuedLines);
|
|
190
197
|
|
|
191
198
|
// Fix last connector: swap \u251C\u2500 \u2192 \u2514\u2500.
|
|
192
199
|
if (lines.length > 1) {
|
|
193
200
|
const last = lines.length - 1;
|
|
194
201
|
lines[last] = lines[last].replace("\u251C\u2500", "\u2514\u2500");
|
|
195
|
-
if (runningLines.length > 0 &&
|
|
202
|
+
if (runningLines.length > 0 && queuedLines.length === 0) {
|
|
196
203
|
if (last >= 2) {
|
|
197
204
|
lines[last - 1] = lines[last - 1].replace("\u251C\u2500", "\u2514\u2500");
|
|
198
205
|
lines[last] = lines[last].replace("\u2502 ", " ");
|
|
@@ -213,10 +220,11 @@ function assembleOverflow(
|
|
|
213
220
|
truncate: (line: string) => string,
|
|
214
221
|
theme: Theme,
|
|
215
222
|
): string[] {
|
|
216
|
-
const { finishedLines, runningLines,
|
|
223
|
+
const { finishedLines, runningLines, queuedLines } = sections;
|
|
217
224
|
const lines: string[] = [heading];
|
|
218
225
|
let budget = maxBody - 1;
|
|
219
226
|
let hiddenRunning = 0;
|
|
227
|
+
let hiddenQueued = 0;
|
|
220
228
|
let hiddenFinished = 0;
|
|
221
229
|
|
|
222
230
|
for (const pair of runningLines) {
|
|
@@ -228,9 +236,13 @@ function assembleOverflow(
|
|
|
228
236
|
}
|
|
229
237
|
}
|
|
230
238
|
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
239
|
+
for (const queuedLine of queuedLines) {
|
|
240
|
+
if (budget >= 1) {
|
|
241
|
+
lines.push(queuedLine);
|
|
242
|
+
budget--;
|
|
243
|
+
} else {
|
|
244
|
+
hiddenQueued++;
|
|
245
|
+
}
|
|
234
246
|
}
|
|
235
247
|
|
|
236
248
|
for (const fl of finishedLines) {
|
|
@@ -244,9 +256,10 @@ function assembleOverflow(
|
|
|
244
256
|
|
|
245
257
|
const overflowParts: string[] = [];
|
|
246
258
|
if (hiddenRunning > 0) overflowParts.push(`${hiddenRunning} running`);
|
|
259
|
+
if (hiddenQueued > 0) overflowParts.push(`${hiddenQueued} queued`);
|
|
247
260
|
if (hiddenFinished > 0) overflowParts.push(`${hiddenFinished} finished`);
|
|
248
261
|
const overflowText = overflowParts.join(", ");
|
|
249
|
-
lines.push(truncate(theme.fg("dim", "\u2514\u2500") + ` ${theme.fg("dim", `+${hiddenRunning + hiddenFinished} more (${overflowText})`)}`));
|
|
262
|
+
lines.push(truncate(theme.fg("dim", "\u2514\u2500") + ` ${theme.fg("dim", `+${hiddenRunning + hiddenQueued + hiddenFinished} more (${overflowText})`)}`));
|
|
250
263
|
return lines;
|
|
251
264
|
}
|
|
252
265
|
|
|
@@ -272,7 +285,7 @@ export function renderWidgetLines(params: {
|
|
|
272
285
|
const headingColor = hasActive ? "accent" : "dim";
|
|
273
286
|
const headingIcon = hasActive ? "\u25CF" : "\u25CB";
|
|
274
287
|
|
|
275
|
-
const { finishedLines, runningLines,
|
|
288
|
+
const { finishedLines, runningLines, queuedLines } = buildSections(
|
|
276
289
|
{ running, queued, finished },
|
|
277
290
|
registry,
|
|
278
291
|
spinnerFrame,
|
|
@@ -282,11 +295,11 @@ export function renderWidgetLines(params: {
|
|
|
282
295
|
|
|
283
296
|
// Assemble with overflow cap (heading takes 1 line).
|
|
284
297
|
const maxBody = MAX_WIDGET_LINES - 1;
|
|
285
|
-
const totalBody = finishedLines.length + runningLines.length * 2 +
|
|
298
|
+
const totalBody = finishedLines.length + runningLines.length * 2 + queuedLines.length;
|
|
286
299
|
const heading = truncate(theme.fg(headingColor, headingIcon) + " " + theme.fg(headingColor, "Agents"));
|
|
287
300
|
|
|
288
301
|
if (totalBody <= maxBody) {
|
|
289
|
-
return assembleWithinBudget(heading, { finishedLines, runningLines,
|
|
302
|
+
return assembleWithinBudget(heading, { finishedLines, runningLines, queuedLines });
|
|
290
303
|
}
|
|
291
|
-
return assembleOverflow(heading, { finishedLines, runningLines,
|
|
304
|
+
return assembleOverflow(heading, { finishedLines, runningLines, queuedLines }, maxBody, truncate, theme);
|
|
292
305
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nklisch/pi-plugins",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.4",
|
|
4
4
|
"private": false,
|
|
5
5
|
"description": "Native marketplace and plugin lifecycle management for Pi, with Claude Code and Codex compatibility.",
|
|
6
6
|
"license": "MIT",
|
|
@@ -67,8 +67,8 @@
|
|
|
67
67
|
"@nklisch/pi-subagents"
|
|
68
68
|
],
|
|
69
69
|
"dependencies": {
|
|
70
|
-
"@nklisch/pi-mcp-adapter": "2.
|
|
71
|
-
"@nklisch/pi-subagents": "18.0
|
|
70
|
+
"@nklisch/pi-mcp-adapter": "2.20.1-nklisch.0",
|
|
71
|
+
"@nklisch/pi-subagents": "18.1.0-nklisch.0",
|
|
72
72
|
"jiti": "2.7.0",
|
|
73
73
|
"semver": "7.8.1",
|
|
74
74
|
"smol-toml": "^1.7.0",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nklisch/pi-enhanced",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.4",
|
|
4
4
|
"description": "Pi, enhanced — one install for nklisch's full harness: policy-gated command review, plugin marketplace, subagents, background tasks, research tools, search, model modes, and a curated UX set.",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "nklisch"
|
package/test/verify-bundle.mjs
CHANGED
|
@@ -7,12 +7,15 @@
|
|
|
7
7
|
* resource path actually land in the pack?"
|
|
8
8
|
*/
|
|
9
9
|
import { execFileSync } from "node:child_process";
|
|
10
|
-
import { readFileSync } from "node:fs";
|
|
10
|
+
import { existsSync, readFileSync } from "node:fs";
|
|
11
11
|
import { dirname, join } from "node:path";
|
|
12
12
|
import { fileURLToPath } from "node:url";
|
|
13
13
|
|
|
14
14
|
const root = join(dirname(fileURLToPath(import.meta.url)), "..");
|
|
15
15
|
const manifest = JSON.parse(readFileSync(join(root, "package.json"), "utf8"));
|
|
16
|
+
const clearanceManifest = JSON.parse(
|
|
17
|
+
readFileSync(join(root, "../pi-clearance/package.json"), "utf8"),
|
|
18
|
+
);
|
|
16
19
|
|
|
17
20
|
// Pack through the repo's bundle-aware packer; npm pack alone drops
|
|
18
21
|
// bundleDependencies inside workspaces.
|
|
@@ -45,6 +48,30 @@ for (const dep of manifest.bundledDependencies ?? []) {
|
|
|
45
48
|
if (!hit) failures.push(`node_modules/${dep}/package.json (bundled dependency missing)`);
|
|
46
49
|
}
|
|
47
50
|
|
|
51
|
+
const clearancePrefix = "node_modules/@nklisch/pi-clearance/";
|
|
52
|
+
const targetSuffix = new Map([
|
|
53
|
+
["x86_64-unknown-linux-gnu", "linux-x64-gnu"],
|
|
54
|
+
["aarch64-unknown-linux-gnu", "linux-arm64-gnu"],
|
|
55
|
+
["x86_64-apple-darwin", "darwin-x64"],
|
|
56
|
+
["aarch64-apple-darwin", "darwin-arm64"],
|
|
57
|
+
["x86_64-pc-windows-msvc", "win32-x64-msvc"],
|
|
58
|
+
["aarch64-pc-windows-msvc", "win32-arm64-msvc"],
|
|
59
|
+
]);
|
|
60
|
+
const nativeArtifacts = clearanceManifest.napi.targets.map((target) => {
|
|
61
|
+
const suffix = targetSuffix.get(target);
|
|
62
|
+
if (suffix === undefined) throw new Error(`Unknown Pi Clearance native target: ${target}`);
|
|
63
|
+
return `${clearanceManifest.napi.binaryName}.${suffix}.node`;
|
|
64
|
+
});
|
|
65
|
+
for (const artifact of nativeArtifacts) {
|
|
66
|
+
const staged = existsSync(join(root, "../pi-clearance/native", artifact));
|
|
67
|
+
if (process.env.PI_NATIVE_RELEASE_ARTIFACTS === "1" && !staged) {
|
|
68
|
+
failures.push(`release artifact was not staged: ${artifact}`);
|
|
69
|
+
}
|
|
70
|
+
if (staged && !files.has(`${clearancePrefix}native/${artifact}`)) {
|
|
71
|
+
failures.push(`bundled pi-clearance is missing native/${artifact}`);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
48
75
|
if (failures.length > 0) {
|
|
49
76
|
console.error(`Bundle verification failed:\n- ${failures.join("\n- ")}`);
|
|
50
77
|
process.exit(1);
|