@lmzhen/dsh-evolution-merge 0.0.0 → 0.29.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/README.md +27 -1
- package/lib/index.js +3814 -0
- package/lib/types/adapters/channel.d.ts +42 -0
- package/lib/types/adapters/engine-screen.d.ts +55 -0
- package/lib/types/adapters/library.d.ts +8 -0
- package/lib/types/adapters/model-runner.d.ts +28 -0
- package/lib/types/adapters/undo.d.ts +9 -0
- package/lib/types/approve-command.d.ts +22 -0
- package/lib/types/authoring-flow.d.ts +40 -0
- package/lib/types/channel-port.d.ts +61 -0
- package/lib/types/commands.d.ts +55 -0
- package/lib/types/commit-assembly.d.ts +27 -0
- package/lib/types/commit-execute.d.ts +29 -0
- package/lib/types/commit-plan.d.ts +45 -0
- package/lib/types/commit-receipt.d.ts +17 -0
- package/lib/types/contracts.d.ts +141 -0
- package/lib/types/coordinator.d.ts +65 -0
- package/lib/types/decision.d.ts +18 -0
- package/lib/types/doctor.d.ts +10 -0
- package/lib/types/gate-cache.d.ts +12 -0
- package/lib/types/index.d.ts +81 -0
- package/lib/types/ladder.d.ts +65 -0
- package/lib/types/merge-command.d.ts +39 -0
- package/lib/types/merge-routes.d.ts +24 -0
- package/lib/types/merge-tool.d.ts +22 -0
- package/lib/types/new-child-authoring.d.ts +29 -0
- package/lib/types/pair-command.d.ts +20 -0
- package/lib/types/params.d.ts +14 -0
- package/lib/types/pending-actions.d.ts +17 -0
- package/lib/types/prompts.d.ts +15 -0
- package/lib/types/read-commands.d.ts +9 -0
- package/lib/types/report.d.ts +10 -0
- package/lib/types/resume-command.d.ts +24 -0
- package/lib/types/round2-outcome.d.ts +13 -0
- package/lib/types/routes.d.ts +64 -0
- package/lib/types/rules.d.ts +24 -0
- package/lib/types/run-shell.d.ts +65 -0
- package/lib/types/runtime.d.ts +37 -0
- package/lib/types/scan-command.d.ts +21 -0
- package/lib/types/scan-ports.d.ts +32 -0
- package/lib/types/scan-run.d.ts +46 -0
- package/lib/types/skill-card.d.ts +12 -0
- package/lib/types/skipped.d.ts +8 -0
- package/lib/types/stage-tool-registry.d.ts +14 -0
- package/lib/types/stage-tool.d.ts +45 -0
- package/lib/types/staged-tree.d.ts +4 -0
- package/lib/types/staging-files.d.ts +15 -0
- package/lib/types/staging.d.ts +49 -0
- package/lib/types/state.d.ts +29 -0
- package/lib/types/status.d.ts +14 -0
- package/lib/types/supersede.d.ts +8 -0
- package/lib/types/undo-merge.d.ts +13 -0
- package/package.json +31 -3
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { type EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
2
|
+
export declare const MERGE_DOCTOR_SCHEMA_VERSION = 3;
|
|
3
|
+
export interface MergeDoctorRow {
|
|
4
|
+
readonly key: string;
|
|
5
|
+
readonly label: string;
|
|
6
|
+
readonly status: 'ok' | 'warn' | 'unknown';
|
|
7
|
+
readonly detail: string;
|
|
8
|
+
}
|
|
9
|
+
export declare function mergeDoctor(io: EvolutionIoLike, home: string, configuredRoot?: string): Promise<readonly MergeDoctorRow[]>;
|
|
10
|
+
//# sourceMappingURL=doctor.d.ts.map
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { type EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
2
|
+
import { GateCache } from './ladder.ts';
|
|
3
|
+
export declare const GATE_CACHE_VERSION = 1;
|
|
4
|
+
export declare function gateCachePath(home: string): string;
|
|
5
|
+
export interface LoadGateCacheResult {
|
|
6
|
+
readonly cache: GateCache;
|
|
7
|
+
readonly note?: string;
|
|
8
|
+
}
|
|
9
|
+
export declare function loadGateCache(io: EvolutionIoLike, home: string): Promise<LoadGateCacheResult>;
|
|
10
|
+
export declare function saveGateCache(io: EvolutionIoLike, home: string, cache: GateCache): Promise<void>;
|
|
11
|
+
export declare function hasGateCache(cache: GateCache): boolean;
|
|
12
|
+
//# sourceMappingURL=gate-cache.d.ts.map
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import z from '@deepseek-ai/schemastery';
|
|
2
|
+
import type { Context } from '@deepseek-ai/cordis';
|
|
3
|
+
/** E3 knobs are volatile (user layer); the E2 pair timeout is deployment-only. */
|
|
4
|
+
export declare const Config: z<Schemastery.ObjectS<NoInfer<{
|
|
5
|
+
mergeApproval: z<boolean, boolean, "volatile-defined">;
|
|
6
|
+
mergeSkippedTtlDays: z<number, number, "volatile-defined">;
|
|
7
|
+
mergeRunTimeoutMinutes: z<number, number, "volatile-defined">;
|
|
8
|
+
mergePairTimeoutMinutes: z<number, number, "defined">;
|
|
9
|
+
mergeModelsRoot: z<string, string, "defined">;
|
|
10
|
+
}>>, Schemastery.ObjectT<NoInfer<{
|
|
11
|
+
mergeApproval: z<boolean, boolean, "volatile-defined">;
|
|
12
|
+
mergeSkippedTtlDays: z<number, number, "volatile-defined">;
|
|
13
|
+
mergeRunTimeoutMinutes: z<number, number, "volatile-defined">;
|
|
14
|
+
mergePairTimeoutMinutes: z<number, number, "defined">;
|
|
15
|
+
mergeModelsRoot: z<string, string, "defined">;
|
|
16
|
+
}>>, "plain">;
|
|
17
|
+
export interface MergePresentationScope {
|
|
18
|
+
effect(run: () => () => void, label?: string): unknown;
|
|
19
|
+
settings?: {
|
|
20
|
+
configure?: (presentation: {
|
|
21
|
+
auto?: boolean;
|
|
22
|
+
}, owner?: unknown) => unknown;
|
|
23
|
+
};
|
|
24
|
+
}
|
|
25
|
+
export declare function engineConfigFromEnv(configuredRoot?: string): Record<string, unknown> | undefined;
|
|
26
|
+
export interface MergePresentationContext {
|
|
27
|
+
inject(names: string[], run: (scope: MergePresentationScope) => void): void;
|
|
28
|
+
readonly fiber?: unknown;
|
|
29
|
+
}
|
|
30
|
+
/** Suppress the platform auto form; the registry renders the merge card instead. */
|
|
31
|
+
export declare function configureMergePresentation(ctx: MergePresentationContext): void;
|
|
32
|
+
export * from './contracts.ts';
|
|
33
|
+
export * from './skill-card.ts';
|
|
34
|
+
export * from './state.ts';
|
|
35
|
+
export * from './coordinator.ts';
|
|
36
|
+
export * from './report.ts';
|
|
37
|
+
export * from './staging.ts';
|
|
38
|
+
export * from './staging-files.ts';
|
|
39
|
+
export * from './rules.ts';
|
|
40
|
+
export * from './commit-plan.ts';
|
|
41
|
+
export * from './stage-tool.ts';
|
|
42
|
+
export * from './stage-tool-registry.ts';
|
|
43
|
+
export * from './staged-tree.ts';
|
|
44
|
+
export * from './commit-assembly.ts';
|
|
45
|
+
export * from './commit-receipt.ts';
|
|
46
|
+
export * from './commit-execute.ts';
|
|
47
|
+
export * from './undo-merge.ts';
|
|
48
|
+
export * from './adapters/library.ts';
|
|
49
|
+
export * from './adapters/model-runner.ts';
|
|
50
|
+
export * from './adapters/channel.ts';
|
|
51
|
+
export * from './adapters/engine-screen.ts';
|
|
52
|
+
export * from './adapters/undo.ts';
|
|
53
|
+
export * from './run-shell.ts';
|
|
54
|
+
export * from './scan-run.ts';
|
|
55
|
+
export * from './pending-actions.ts';
|
|
56
|
+
export * from './scan-command.ts';
|
|
57
|
+
export * from './round2-outcome.ts';
|
|
58
|
+
export * from './approve-command.ts';
|
|
59
|
+
export * from './pair-command.ts';
|
|
60
|
+
export * from './resume-command.ts';
|
|
61
|
+
export * from './decision.ts';
|
|
62
|
+
export * from './prompts.ts';
|
|
63
|
+
export * from './channel-port.ts';
|
|
64
|
+
export * from './authoring-flow.ts';
|
|
65
|
+
export * from './merge-tool.ts';
|
|
66
|
+
export * from './commands.ts';
|
|
67
|
+
export * from './scan-ports.ts';
|
|
68
|
+
export * from './new-child-authoring.ts';
|
|
69
|
+
export * from './status.ts';
|
|
70
|
+
export * from './skipped.ts';
|
|
71
|
+
export * from './read-commands.ts';
|
|
72
|
+
export * from './routes.ts';
|
|
73
|
+
export * from './merge-routes.ts';
|
|
74
|
+
export * from './merge-command.ts';
|
|
75
|
+
export * from './params.ts';
|
|
76
|
+
export * from './doctor.ts';
|
|
77
|
+
export * from './supersede.ts';
|
|
78
|
+
export * from './runtime.ts';
|
|
79
|
+
export declare const inject: string[];
|
|
80
|
+
export declare function apply(ctx: Context, rawConfig?: Record<string, unknown>): void;
|
|
81
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
export type GateLevel = 'L0' | 'L1' | 'L2';
|
|
2
|
+
export type GateVerdictValue = 1 | 0 | -1;
|
|
3
|
+
export interface GateFacts {
|
|
4
|
+
readonly name: string;
|
|
5
|
+
readonly description: string;
|
|
6
|
+
readonly body: string;
|
|
7
|
+
}
|
|
8
|
+
export interface GateCandidate {
|
|
9
|
+
readonly a: string;
|
|
10
|
+
readonly b: string;
|
|
11
|
+
readonly score?: number;
|
|
12
|
+
}
|
|
13
|
+
export interface GateEvidence {
|
|
14
|
+
readonly path: string;
|
|
15
|
+
readonly line: number;
|
|
16
|
+
readonly quote: string;
|
|
17
|
+
}
|
|
18
|
+
export interface GateVerdict {
|
|
19
|
+
readonly level: GateLevel;
|
|
20
|
+
readonly verdict: GateVerdictValue;
|
|
21
|
+
readonly reason: string;
|
|
22
|
+
readonly evidence: readonly GateEvidence[];
|
|
23
|
+
readonly cached: boolean;
|
|
24
|
+
}
|
|
25
|
+
export interface GateModelPort {
|
|
26
|
+
callJson(request: {
|
|
27
|
+
readonly system: string;
|
|
28
|
+
readonly user: string;
|
|
29
|
+
readonly maxTokens: number;
|
|
30
|
+
readonly signal: AbortSignal;
|
|
31
|
+
}): Promise<unknown>;
|
|
32
|
+
}
|
|
33
|
+
export type LadderRoute = 'merge' | 'undecided' | 'keep' | 'error';
|
|
34
|
+
export interface LadderResult {
|
|
35
|
+
readonly route: LadderRoute;
|
|
36
|
+
readonly verdicts: readonly GateVerdict[];
|
|
37
|
+
readonly calls: number;
|
|
38
|
+
readonly droppedAt?: GateLevel;
|
|
39
|
+
readonly error?: string;
|
|
40
|
+
}
|
|
41
|
+
export declare class GateCache {
|
|
42
|
+
private readonly entries;
|
|
43
|
+
get(key: string): GateVerdict | undefined;
|
|
44
|
+
put(key: string, value: GateVerdict): void;
|
|
45
|
+
get size(): number;
|
|
46
|
+
toObject(): Record<string, GateVerdict>;
|
|
47
|
+
static fromObject(value: unknown): GateCache;
|
|
48
|
+
}
|
|
49
|
+
export declare function gateCacheKey(level: GateLevel, payload: string, model: string): string;
|
|
50
|
+
export declare function parseVerdict(level: GateLevel, raw: unknown, cached?: boolean): GateVerdict | undefined;
|
|
51
|
+
export interface RunLadderOptions {
|
|
52
|
+
readonly level: GateLevel;
|
|
53
|
+
readonly candidate: GateCandidate;
|
|
54
|
+
readonly facts: readonly GateFacts[];
|
|
55
|
+
readonly model: GateModelPort;
|
|
56
|
+
readonly modelName: string;
|
|
57
|
+
readonly signal: AbortSignal;
|
|
58
|
+
readonly cache?: GateCache;
|
|
59
|
+
/** Audit path starts at L2 after an L0 keep. */
|
|
60
|
+
readonly startLevel?: GateLevel;
|
|
61
|
+
}
|
|
62
|
+
/** Deterministic 10% L0 audit selection from the run seed + pair key. */
|
|
63
|
+
export declare function selectedForAudit(pairKey: string, seed: string, rate?: number): boolean;
|
|
64
|
+
export declare function runLadder(options: RunLadderOptions): Promise<LadderResult>;
|
|
65
|
+
//# sourceMappingURL=ladder.d.ts.map
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Model/CLI-facing /merge command definition. The host shell registers it; this module owns
|
|
3
|
+
* parsing, read-only verb dispatch and the uniform error/success envelope.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import { type MergeCliCommand } from './commands.ts';
|
|
7
|
+
export interface MergeCommandResult {
|
|
8
|
+
readonly ok: boolean;
|
|
9
|
+
readonly text: string;
|
|
10
|
+
}
|
|
11
|
+
export interface MergeCommandContext {
|
|
12
|
+
/** The invoking agent, when a command (not a route) initiated the run. */
|
|
13
|
+
readonly parent?: unknown;
|
|
14
|
+
}
|
|
15
|
+
export interface MergeCommandService {
|
|
16
|
+
execute(command: MergeCliCommand, context?: MergeCommandContext): Promise<MergeCommandResult>;
|
|
17
|
+
}
|
|
18
|
+
export interface CommandInvocationLike {
|
|
19
|
+
readonly rawInput: string;
|
|
20
|
+
readonly agent?: unknown;
|
|
21
|
+
}
|
|
22
|
+
export interface CommandResultLike {
|
|
23
|
+
readonly kind: 'success' | 'error';
|
|
24
|
+
readonly text: string;
|
|
25
|
+
}
|
|
26
|
+
export interface MergeCommandDefinitionLike {
|
|
27
|
+
readonly name: string;
|
|
28
|
+
readonly description: string;
|
|
29
|
+
readonly input: {
|
|
30
|
+
readonly hint: string;
|
|
31
|
+
};
|
|
32
|
+
readonly handler: (invocation: CommandInvocationLike) => Promise<CommandResultLike>;
|
|
33
|
+
}
|
|
34
|
+
export declare function createReadOnlyMergeService(io: EvolutionIoLike, home: string): MergeCommandService;
|
|
35
|
+
export declare function runMergeCommand(service: MergeCommandService, rawInput: string, invocation?: {
|
|
36
|
+
readonly agent?: unknown;
|
|
37
|
+
}): Promise<MergeCommandResult>;
|
|
38
|
+
export declare function createMergeCommand(service: MergeCommandService): MergeCommandDefinitionLike;
|
|
39
|
+
//# sourceMappingURL=merge-command.d.ts.map
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Four read-only merge routes: view / rows / run / runs. The host loads rows and runs; these
|
|
3
|
+
* handlers only project. A missing merge service answers 503 instead of pretending empty.
|
|
4
|
+
*/
|
|
5
|
+
import type { RunRecord } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import { type ConnectionFetchRouteLike, type DecisionAudit } from '@lmzhen/dsh-evolution-core/http-routes';
|
|
7
|
+
import type { MergeRow } from './contracts.ts';
|
|
8
|
+
export declare const MERGE_ROUTES: {
|
|
9
|
+
readonly view: "/api/dsh-evolution/merge/view";
|
|
10
|
+
readonly rows: "/api/dsh-evolution/merge/rows";
|
|
11
|
+
readonly run: "/api/dsh-evolution/merge/run";
|
|
12
|
+
readonly runs: "/api/dsh-evolution/merge/runs";
|
|
13
|
+
};
|
|
14
|
+
export interface MergeRouteSource {
|
|
15
|
+
rows(): Promise<readonly MergeRow[]>;
|
|
16
|
+
run(id: string): Promise<RunRecord | undefined>;
|
|
17
|
+
runs(cursor?: string, limit?: number): Promise<readonly RunRecord[]>;
|
|
18
|
+
commands(): readonly string[];
|
|
19
|
+
approval?(): boolean;
|
|
20
|
+
}
|
|
21
|
+
export declare function makeMergeRoutes(deps: {
|
|
22
|
+
getSource: () => MergeRouteSource | undefined;
|
|
23
|
+
}, _audit: DecisionAudit): ConnectionFetchRouteLike[];
|
|
24
|
+
//# sourceMappingURL=merge-routes.d.ts.map
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Model-facing merge_stage tool definition. The plugin shell supplies the context factory;
|
|
3
|
+
* this module owns the argument schema and the JSON result. All policy remains in applyStageTool.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import { type StageToolContext } from './stage-tool.ts';
|
|
7
|
+
export declare const MERGE_STAGE_TOOL_NAME = "merge_stage";
|
|
8
|
+
export interface ToolDefinitionLike {
|
|
9
|
+
readonly name: string;
|
|
10
|
+
readonly description: string;
|
|
11
|
+
readonly parameters: Record<string, unknown>;
|
|
12
|
+
readonly output: {
|
|
13
|
+
readonly schema: Record<string, unknown>;
|
|
14
|
+
readonly render: (args: unknown, value: string) => readonly {
|
|
15
|
+
readonly type: 'text';
|
|
16
|
+
readonly text: string;
|
|
17
|
+
}[];
|
|
18
|
+
};
|
|
19
|
+
readonly execute: (args: Record<string, unknown>, exec: unknown) => Promise<string>;
|
|
20
|
+
}
|
|
21
|
+
export declare function createMergeStageTool(io: EvolutionIoLike, home: string, context: (exec: unknown) => StageToolContext | undefined): ToolDefinitionLike;
|
|
22
|
+
//# sourceMappingURL=merge-tool.d.ts.map
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Round2 with a NEW child (approval after the pending window). The child gets the round2
|
|
3
|
+
* prompt and writes the staging tree; the plugin then runs the same gate/commit path.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import type { MergeDecision, MergeRow } from './contracts.ts';
|
|
7
|
+
import type { SkillCard } from './skill-card.ts';
|
|
8
|
+
import type { ConversationChannelLike } from './channel-port.ts';
|
|
9
|
+
import { type CommitPort } from './commit-execute.ts';
|
|
10
|
+
import type { StageToolContext } from './stage-tool.ts';
|
|
11
|
+
import type { ScanRound2Outcome } from './scan-run.ts';
|
|
12
|
+
export interface NewChildAuthoringOptions {
|
|
13
|
+
readonly io: EvolutionIoLike;
|
|
14
|
+
readonly home: string;
|
|
15
|
+
readonly runId: string;
|
|
16
|
+
readonly cards: readonly SkillCard[];
|
|
17
|
+
readonly channel: ConversationChannelLike;
|
|
18
|
+
readonly parent: unknown;
|
|
19
|
+
readonly allow: readonly string[];
|
|
20
|
+
readonly cwd?: string;
|
|
21
|
+
readonly timeoutMs: number;
|
|
22
|
+
readonly commitPort: CommitPort;
|
|
23
|
+
readonly now: () => number;
|
|
24
|
+
readonly onChild?: (context: StageToolContext) => void;
|
|
25
|
+
readonly onChildClosed?: (childId: string) => void;
|
|
26
|
+
}
|
|
27
|
+
export declare function runNewChildAuthoring(options: NewChildAuthoringOptions, row: MergeRow, decision: MergeDecision, signal: AbortSignal): Promise<ScanRound2Outcome>;
|
|
28
|
+
export declare function createNewChildRound2(options: Omit<NewChildAuthoringOptions, 'runId'>): (row: MergeRow, decision: MergeDecision, signal: AbortSignal, runId: string) => Promise<ScanRound2Outcome>;
|
|
29
|
+
//# sourceMappingURL=new-child-authoring.d.ts.map
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* pair command: one explicit candidate through the same scan shell.
|
|
3
|
+
*/
|
|
4
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
5
|
+
import type { ScanPorts } from './scan-run.ts';
|
|
6
|
+
import type { MergeRegistryPort, WithMergeRunResult } from './run-shell.ts';
|
|
7
|
+
export interface RunPairCommandOptions {
|
|
8
|
+
readonly io: EvolutionIoLike;
|
|
9
|
+
readonly home: string;
|
|
10
|
+
readonly registry: MergeRegistryPort;
|
|
11
|
+
readonly ports: ScanPorts;
|
|
12
|
+
readonly a: string;
|
|
13
|
+
readonly b: string;
|
|
14
|
+
readonly approval: boolean;
|
|
15
|
+
readonly platformWrite: boolean;
|
|
16
|
+
readonly timeoutMinutes?: number;
|
|
17
|
+
readonly now: () => number;
|
|
18
|
+
}
|
|
19
|
+
export declare function runPairCommand(options: RunPairCommandOptions): Promise<WithMergeRunResult>;
|
|
20
|
+
//# sourceMappingURL=pair-command.d.ts.map
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Merge parameter resolution. E2/E3 values arrive as one JSON object; this is the only
|
|
3
|
+
* validator. Invalid values throw loudly (no silent clamp), matching the screening contract.
|
|
4
|
+
*/
|
|
5
|
+
export interface MergeParams {
|
|
6
|
+
readonly mergeApproval: boolean;
|
|
7
|
+
readonly mergeSkippedTtlDays: number;
|
|
8
|
+
readonly mergeRunTimeoutMinutes: number;
|
|
9
|
+
readonly mergePairTimeoutMinutes: number;
|
|
10
|
+
readonly mergeModelsRoot: string;
|
|
11
|
+
}
|
|
12
|
+
export declare const MERGE_PARAM_DEFAULTS: MergeParams;
|
|
13
|
+
export declare function resolveMergeParams(input?: unknown): MergeParams;
|
|
14
|
+
//# sourceMappingURL=params.d.ts.map
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Pending approval actions. The row lookup and the transition happen in one
|
|
3
|
+
* mutateMergeState transaction, so two clients approving the same row cannot both win.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import type { MergeRow } from './contracts.ts';
|
|
7
|
+
export type PendingActionResult = {
|
|
8
|
+
readonly ok: true;
|
|
9
|
+
readonly row: MergeRow;
|
|
10
|
+
} | {
|
|
11
|
+
readonly ok: false;
|
|
12
|
+
readonly reason: 'not-found' | 'not-pending' | 'invalid';
|
|
13
|
+
readonly message: string;
|
|
14
|
+
};
|
|
15
|
+
export declare function approvePending(io: EvolutionIoLike, home: string, now: () => number, id: string): Promise<PendingActionResult>;
|
|
16
|
+
export declare function rejectPending(io: EvolutionIoLike, home: string, now: () => number, id: string): Promise<PendingActionResult>;
|
|
17
|
+
//# sourceMappingURL=pending-actions.d.ts.map
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Round-1/round-2 prompt builders. B draft body, with only the file-tool ->
|
|
3
|
+
* merge_stage substitution and the fresh-mode bridge sentence.
|
|
4
|
+
*/
|
|
5
|
+
import type { MergeDecision, MergeRow } from './contracts.ts';
|
|
6
|
+
import type { SkillCard } from './skill-card.ts';
|
|
7
|
+
export declare const MERGE_PROMPT_VERSION = "merge-b/v1";
|
|
8
|
+
export declare const STANDBY_PROMPT = "You are a merge worker. Wait for instructions.";
|
|
9
|
+
export declare function buildRound1Prompt(candidate: {
|
|
10
|
+
readonly a: string;
|
|
11
|
+
readonly b: string;
|
|
12
|
+
}, cards: readonly SkillCard[]): string;
|
|
13
|
+
export declare function buildRound2Prompt(row: MergeRow, decision: MergeDecision, mode?: 'continue' | 'fresh'): string;
|
|
14
|
+
export declare function buildStandbyPrompt(): string;
|
|
15
|
+
//# sourceMappingURL=prompts.d.ts.map
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Read-only command handlers: status/pending/skipped are served from merge-state.
|
|
3
|
+
* Mutating verbs return null so the host shell can route them to the run engine.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import type { MergeCliCommand } from './commands.ts';
|
|
7
|
+
export declare function handleReadOnlyMergeCommand(command: MergeCliCommand, io: EvolutionIoLike, home: string): Promise<string | null>;
|
|
8
|
+
export declare function mergeCommandHelp(): string;
|
|
9
|
+
//# sourceMappingURL=read-commands.d.ts.map
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { type EvolutionIoLike, type Probe } from '@lmzhen/dsh-evolution-core';
|
|
2
|
+
import type { MergeReport, MergeReportPair } from './contracts.ts';
|
|
3
|
+
export declare function mergeReportPath(home: string, runId: string): string;
|
|
4
|
+
export declare function mergeReportDigestPath(home: string, runId: string): string;
|
|
5
|
+
/** Write JSON first, then the digest; returns the JSON path (the registry resultRef). */
|
|
6
|
+
export declare function writeMergeReport(io: EvolutionIoLike, home: string, report: MergeReport): Promise<string>;
|
|
7
|
+
export declare function readMergeReport(io: EvolutionIoLike, home: string, runId: string): Promise<Probe<MergeReport>>;
|
|
8
|
+
/** Pairs this run actually merged (for merge undo / reports). */
|
|
9
|
+
export declare function committedPairs(io: EvolutionIoLike, home: string, runId: string): Promise<readonly MergeReportPair[]>;
|
|
10
|
+
//# sourceMappingURL=report.d.ts.map
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* resume command: verify rows re-enter round1; fuse rows re-enter round2 with the persisted
|
|
3
|
+
* decision. pending/skipped rows are not resumable.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import { type MergeRegistryPort, type WithMergeRunResult } from './run-shell.ts';
|
|
7
|
+
import type { ScanPorts, ScanRound2Outcome } from './scan-run.ts';
|
|
8
|
+
import type { MergeDecision, MergeRow } from './contracts.ts';
|
|
9
|
+
export interface RunResumeCommandOptions {
|
|
10
|
+
readonly io: EvolutionIoLike;
|
|
11
|
+
readonly home: string;
|
|
12
|
+
readonly registry: MergeRegistryPort;
|
|
13
|
+
readonly ports: ScanPorts;
|
|
14
|
+
/** Per-run ports for the verify branch (staging needs the new runId). */
|
|
15
|
+
readonly makePorts?: (runId: string) => ScanPorts;
|
|
16
|
+
/** Optional new-child authoring port (approve-after-pending path). */
|
|
17
|
+
readonly round2WithRun?: (row: MergeRow, decision: MergeDecision, signal: AbortSignal, runId: string) => Promise<ScanRound2Outcome>;
|
|
18
|
+
readonly rowId: string;
|
|
19
|
+
readonly platformWrite: boolean;
|
|
20
|
+
readonly timeoutMinutes?: number;
|
|
21
|
+
readonly now: () => number;
|
|
22
|
+
}
|
|
23
|
+
export declare function runResumeCommand(options: RunResumeCommandOptions): Promise<WithMergeRunResult>;
|
|
24
|
+
//# sourceMappingURL=resume-command.d.ts.map
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared round2 outcome recorder for approve and resume: one place decides whether the
|
|
3
|
+
* row is dropped (commit landed) or kept in fuse with a failure. No report/registry logic.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import type { MergeReportPair, MergeRow } from './contracts.ts';
|
|
7
|
+
import type { ScanRound2Outcome } from './scan-run.ts';
|
|
8
|
+
export interface Round2Record {
|
|
9
|
+
readonly pair: MergeReportPair;
|
|
10
|
+
readonly merged: boolean;
|
|
11
|
+
}
|
|
12
|
+
export declare function recordRound2Outcome(io: EvolutionIoLike, home: string, now: () => number, row: MergeRow, outcome: ScanRound2Outcome): Promise<Round2Record>;
|
|
13
|
+
//# sourceMappingURL=round2-outcome.d.ts.map
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Read-only view models for the four merge routes. Pure functions; the host loads rows and
|
|
3
|
+
* runs, the client renders these shapes. No io, no write paths.
|
|
4
|
+
*/
|
|
5
|
+
import type { RunRecord } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import type { MergeQueue, MergeRow } from './contracts.ts';
|
|
7
|
+
import { type MergeCounts } from './status.ts';
|
|
8
|
+
export interface MergeRowView {
|
|
9
|
+
readonly id: string;
|
|
10
|
+
readonly pairKey: string;
|
|
11
|
+
readonly a: string;
|
|
12
|
+
readonly b: string;
|
|
13
|
+
readonly state: MergeRow['state'];
|
|
14
|
+
readonly queue: MergeQueue;
|
|
15
|
+
readonly stage: string | null;
|
|
16
|
+
readonly label: string;
|
|
17
|
+
readonly updatedAt: string;
|
|
18
|
+
readonly createdAt: string;
|
|
19
|
+
readonly target?: string;
|
|
20
|
+
readonly confidence?: number;
|
|
21
|
+
readonly failure?: {
|
|
22
|
+
readonly stage: string;
|
|
23
|
+
readonly code: string;
|
|
24
|
+
readonly message: string;
|
|
25
|
+
readonly retryable: boolean;
|
|
26
|
+
};
|
|
27
|
+
readonly attempts?: number;
|
|
28
|
+
readonly origin?: 'agent' | 'human';
|
|
29
|
+
readonly stagingExpiresAt?: number;
|
|
30
|
+
readonly actions: readonly string[];
|
|
31
|
+
}
|
|
32
|
+
export declare function toRowView(row: MergeRow): MergeRowView;
|
|
33
|
+
export interface MergeView {
|
|
34
|
+
readonly schemaVersion: 1;
|
|
35
|
+
readonly counts: MergeCounts;
|
|
36
|
+
readonly tabs: readonly {
|
|
37
|
+
readonly queue: MergeQueue;
|
|
38
|
+
readonly count: number;
|
|
39
|
+
}[];
|
|
40
|
+
readonly commands: readonly string[];
|
|
41
|
+
readonly latestRun?: MergeRunFact;
|
|
42
|
+
readonly approval?: boolean;
|
|
43
|
+
}
|
|
44
|
+
export declare function buildMergeView(rows: readonly MergeRow[], commands: readonly string[], latestRun?: MergeRunFact, approval?: boolean): MergeView;
|
|
45
|
+
export interface QueuePage {
|
|
46
|
+
readonly queue: MergeQueue;
|
|
47
|
+
readonly items: readonly MergeRowView[];
|
|
48
|
+
readonly nextCursor?: string;
|
|
49
|
+
}
|
|
50
|
+
export declare function pageQueue(rows: readonly MergeRow[], queue: MergeQueue, cursor?: number, limit?: number): QueuePage;
|
|
51
|
+
export interface MergeRunFact {
|
|
52
|
+
readonly id: string;
|
|
53
|
+
readonly state: RunRecord['state'];
|
|
54
|
+
readonly command?: RunRecord['command'];
|
|
55
|
+
readonly stage?: RunRecord['stage'];
|
|
56
|
+
readonly progress?: RunRecord['progress'];
|
|
57
|
+
readonly startedAt: number;
|
|
58
|
+
readonly endedAt?: number;
|
|
59
|
+
readonly resultRef?: string;
|
|
60
|
+
readonly failure?: string;
|
|
61
|
+
readonly supersededAt?: number;
|
|
62
|
+
}
|
|
63
|
+
export declare function toRunFact(run: RunRecord): MergeRunFact;
|
|
64
|
+
//# sourceMappingURL=routes.d.ts.map
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Deterministic gate for a staged merge tree. No io, no model.
|
|
3
|
+
*
|
|
4
|
+
* block = commit must not proceed; warn = report only. The path and reference checks reuse
|
|
5
|
+
* the skill-store's own `validateSupportPath` / `supportRefs`, so there is one whitelist.
|
|
6
|
+
*/
|
|
7
|
+
import { type SkillLimits } from '@lmzhen/dsh-evolution-core';
|
|
8
|
+
export interface StagedTree {
|
|
9
|
+
readonly target: string;
|
|
10
|
+
readonly body: string;
|
|
11
|
+
readonly files: readonly {
|
|
12
|
+
readonly path: string;
|
|
13
|
+
readonly content: string;
|
|
14
|
+
}[];
|
|
15
|
+
}
|
|
16
|
+
export interface RuleFinding {
|
|
17
|
+
readonly rule: string;
|
|
18
|
+
readonly path: string;
|
|
19
|
+
readonly severity: 'block' | 'warn';
|
|
20
|
+
readonly message: string;
|
|
21
|
+
}
|
|
22
|
+
export declare function validateStagedTree(tree: StagedTree, limits?: SkillLimits): readonly RuleFinding[];
|
|
23
|
+
export declare function hasBlockingFinding(findings: readonly RuleFinding[]): boolean;
|
|
24
|
+
//# sourceMappingURL=rules.d.ts.map
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Merge run shell: registry lifecycle + report-before-settle.
|
|
3
|
+
*
|
|
4
|
+
* The pair executor is injected. This module owns the invariants every command shares:
|
|
5
|
+
* begin a merge run, publish stage/progress, write the report, then settle with resultRef.
|
|
6
|
+
* A body failure still produces a failed report (unless the report itself cannot be written).
|
|
7
|
+
*/
|
|
8
|
+
import type { EvolutionIoLike, RunHandle, RunKind, RunStage } from '@lmzhen/dsh-evolution-core';
|
|
9
|
+
import type { MergeReport, MergeReportPair, MergeRunCommand } from './contracts.ts';
|
|
10
|
+
export interface MergeRegistryPort {
|
|
11
|
+
begin(kind: RunKind, seed?: {
|
|
12
|
+
command?: MergeRunCommand;
|
|
13
|
+
total?: number;
|
|
14
|
+
parentRunId?: string;
|
|
15
|
+
}): Promise<Pick<RunHandle, 'id' | 'signal' | 'startedAt'>>;
|
|
16
|
+
stage(id: string, stage: RunStage, progress?: {
|
|
17
|
+
done: number;
|
|
18
|
+
total: number;
|
|
19
|
+
}): Promise<void>;
|
|
20
|
+
settle(id: string, outcome: {
|
|
21
|
+
state: 'succeeded' | 'failed' | 'cancelled';
|
|
22
|
+
resultRef?: string;
|
|
23
|
+
failure?: string;
|
|
24
|
+
}): Promise<void>;
|
|
25
|
+
}
|
|
26
|
+
export interface MergeRunBodyContext {
|
|
27
|
+
readonly runId: string;
|
|
28
|
+
readonly startedAt: number;
|
|
29
|
+
readonly signal: AbortSignal;
|
|
30
|
+
readonly stage: (stage: RunStage, progress?: {
|
|
31
|
+
done: number;
|
|
32
|
+
total: number;
|
|
33
|
+
}) => Promise<void>;
|
|
34
|
+
}
|
|
35
|
+
export interface MergeRunReportDraft {
|
|
36
|
+
readonly stopReason: MergeReport['stopReason'];
|
|
37
|
+
readonly scope: MergeReport['scope'];
|
|
38
|
+
readonly pairs: readonly MergeReportPair[];
|
|
39
|
+
readonly totals: MergeReport['totals'];
|
|
40
|
+
readonly notes: readonly string[];
|
|
41
|
+
readonly remaining?: MergeReport['remaining'];
|
|
42
|
+
}
|
|
43
|
+
export interface WithMergeRunOptions {
|
|
44
|
+
readonly io: EvolutionIoLike;
|
|
45
|
+
readonly home: string;
|
|
46
|
+
readonly registry: MergeRegistryPort;
|
|
47
|
+
readonly command: MergeRunCommand;
|
|
48
|
+
readonly approval: MergeReport['approval'];
|
|
49
|
+
readonly now: () => number;
|
|
50
|
+
readonly total?: number;
|
|
51
|
+
readonly body: (ctx: MergeRunBodyContext) => Promise<MergeRunReportDraft>;
|
|
52
|
+
}
|
|
53
|
+
export type WithMergeRunResult = {
|
|
54
|
+
readonly ok: true;
|
|
55
|
+
readonly runId: string;
|
|
56
|
+
readonly reportPath: string;
|
|
57
|
+
readonly report: MergeReport;
|
|
58
|
+
} | {
|
|
59
|
+
readonly ok: false;
|
|
60
|
+
readonly runId?: string;
|
|
61
|
+
readonly message: string;
|
|
62
|
+
readonly reportPath?: string;
|
|
63
|
+
};
|
|
64
|
+
export declare function withMergeRun(options: WithMergeRunOptions): Promise<WithMergeRunResult>;
|
|
65
|
+
//# sourceMappingURL=run-shell.d.ts.map
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The merge command runtime: cards -> screening -> channel ports -> scan/approve.
|
|
3
|
+
* Plugin wiring supplies the channel, model and library; this module keeps the orchestration
|
|
4
|
+
* out of apply() and makes the mutating verbs testable with fakes.
|
|
5
|
+
*/
|
|
6
|
+
import { type EvolutionIoLike, type SkillLibrary } from '@lmzhen/dsh-evolution-core';
|
|
7
|
+
import { type MergeCandidate } from './contracts.ts';
|
|
8
|
+
import type { MergeParams } from './params.ts';
|
|
9
|
+
import type { SkillCard } from './skill-card.ts';
|
|
10
|
+
import type { MergeRegistryPort } from './run-shell.ts';
|
|
11
|
+
import type { MergeCommandService } from './merge-command.ts';
|
|
12
|
+
import type { StageToolContext } from './stage-tool.ts';
|
|
13
|
+
import type { ConversationChannelLike } from './channel-port.ts';
|
|
14
|
+
export interface MergeStageBindingPort {
|
|
15
|
+
bind(context: StageToolContext): void;
|
|
16
|
+
unbind(childId: string): void;
|
|
17
|
+
}
|
|
18
|
+
export interface MergeRuntimeDeps {
|
|
19
|
+
readonly io: EvolutionIoLike;
|
|
20
|
+
readonly home: string;
|
|
21
|
+
readonly registry: MergeRegistryPort;
|
|
22
|
+
readonly skills: SkillLibrary;
|
|
23
|
+
readonly now: () => number;
|
|
24
|
+
readonly params: MergeParams;
|
|
25
|
+
readonly platformWrite: boolean;
|
|
26
|
+
readonly channel: ConversationChannelLike;
|
|
27
|
+
readonly parent: unknown;
|
|
28
|
+
readonly allow: readonly string[];
|
|
29
|
+
readonly cwd?: string;
|
|
30
|
+
readonly timeoutMinutes: number;
|
|
31
|
+
readonly cards: (signal: AbortSignal) => Promise<readonly SkillCard[]>;
|
|
32
|
+
/** Run-scoped engine screening. */
|
|
33
|
+
readonly screeningForRun: (cards: readonly SkillCard[], runId: string, signal: AbortSignal) => Promise<readonly MergeCandidate[]>;
|
|
34
|
+
readonly stage?: MergeStageBindingPort;
|
|
35
|
+
}
|
|
36
|
+
export declare function createMergeRuntime(deps: MergeRuntimeDeps): MergeCommandService;
|
|
37
|
+
//# sourceMappingURL=runtime.d.ts.map
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* scan command wiring: the registry/report shell around runScan.
|
|
3
|
+
* Pair/approve/resume commands get their own thin wrappers on the same shell.
|
|
4
|
+
*/
|
|
5
|
+
import type { EvolutionIoLike } from '@lmzhen/dsh-evolution-core';
|
|
6
|
+
import { type ScanPorts } from './scan-run.ts';
|
|
7
|
+
import { type MergeRegistryPort, type WithMergeRunResult } from './run-shell.ts';
|
|
8
|
+
export interface RunScanCommandOptions {
|
|
9
|
+
readonly io: EvolutionIoLike;
|
|
10
|
+
readonly home: string;
|
|
11
|
+
readonly registry: MergeRegistryPort;
|
|
12
|
+
readonly ports?: ScanPorts;
|
|
13
|
+
/** Build per-run ports when staging needs the runId (channel authoring). */
|
|
14
|
+
readonly makePorts?: (runId: string) => ScanPorts;
|
|
15
|
+
readonly approval: boolean;
|
|
16
|
+
readonly platformWrite: boolean;
|
|
17
|
+
readonly timeoutMinutes?: number;
|
|
18
|
+
readonly now: () => number;
|
|
19
|
+
}
|
|
20
|
+
export declare function runScanCommand(options: RunScanCommandOptions): Promise<WithMergeRunResult>;
|
|
21
|
+
//# sourceMappingURL=scan-command.d.ts.map
|