@xiaoso/dsh-workflow-lite 0.0.0-stage → 0.1.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/LICENSE +24 -0
- package/README.en.md +84 -0
- package/README.md +83 -2
- package/THIRD_PARTY_NOTICES.md +762 -0
- package/assets/icon-full.webp +0 -0
- package/assets/icon.webp +0 -0
- package/assets/wordmark.png +0 -0
- package/cordis.patch.yml +3 -0
- package/lib/client.js +127442 -0
- package/lib/index.mjs +9613 -0
- package/lib/types/client/app/addStep.d.ts +25 -0
- package/lib/types/client/app/desktop.d.ts +52 -0
- package/lib/types/client/app/host.d.ts +29 -0
- package/lib/types/client/app/sessions.d.ts +117 -0
- package/lib/types/client/app/theme.d.ts +27 -0
- package/lib/types/client/app/usePluginConfig.d.ts +59 -0
- package/lib/types/client/app/useRunFile.d.ts +24 -0
- package/lib/types/client/app/useRunGraph.d.ts +51 -0
- package/lib/types/client/app/useRunHistory.d.ts +21 -0
- package/lib/types/client/app/useRuns.d.ts +84 -0
- package/lib/types/client/app/useVersions.d.ts +50 -0
- package/lib/types/client/app/useWorkflow.d.ts +67 -0
- package/lib/types/client/app/viewport.d.ts +14 -0
- package/lib/types/client/i18n.d.ts +930 -0
- package/lib/types/client/index.d.ts +18 -0
- package/lib/types/client/model/connect.d.ts +44 -0
- package/lib/types/client/model/editor.d.ts +252 -0
- package/lib/types/client/model/fileKind.d.ts +15 -0
- package/lib/types/client/model/hostPath.d.ts +15 -0
- package/lib/types/client/model/htmlPreview.d.ts +24 -0
- package/lib/types/client/model/hubRuns.d.ts +45 -0
- package/lib/types/client/model/layout.d.ts +83 -0
- package/lib/types/client/model/library.d.ts +109 -0
- package/lib/types/client/model/nudge.d.ts +43 -0
- package/lib/types/client/model/pathSample.d.ts +26 -0
- package/lib/types/client/model/route.d.ts +121 -0
- package/lib/types/client/model/runDraft.d.ts +68 -0
- package/lib/types/client/model/runGraph.d.ts +15 -0
- package/lib/types/client/model/runHistory.d.ts +40 -0
- package/lib/types/client/model/themes.d.ts +87 -0
- package/lib/types/client/model/time.d.ts +7 -0
- package/lib/types/client/rpc.d.ts +42 -0
- package/lib/types/client/ui/AppearancePicker.d.ts +23 -0
- package/lib/types/client/ui/Canvas.d.ts +76 -0
- package/lib/types/client/ui/Confirm.d.ts +42 -0
- package/lib/types/client/ui/DocViewer.d.ts +67 -0
- package/lib/types/client/ui/Dock.d.ts +13 -0
- package/lib/types/client/ui/FileTag.d.ts +9 -0
- package/lib/types/client/ui/FileViewer.d.ts +30 -0
- package/lib/types/client/ui/FlowStreaks.d.ts +40 -0
- package/lib/types/client/ui/Handoff.d.ts +30 -0
- package/lib/types/client/ui/HostPicker.d.ts +31 -0
- package/lib/types/client/ui/HubDialog.d.ts +38 -0
- package/lib/types/client/ui/HubRunRow.d.ts +22 -0
- package/lib/types/client/ui/HubRuns.d.ts +19 -0
- package/lib/types/client/ui/HubSettings.d.ts +20 -0
- package/lib/types/client/ui/HubStorage.d.ts +18 -0
- package/lib/types/client/ui/HubWorkflowList.d.ts +21 -0
- package/lib/types/client/ui/HubWorkflowRow.d.ts +33 -0
- package/lib/types/client/ui/HubWorkflows.d.ts +26 -0
- package/lib/types/client/ui/HubWorkspacePicker.d.ts +16 -0
- package/lib/types/client/ui/Icon.d.ts +83 -0
- package/lib/types/client/ui/InputPanel.d.ts +37 -0
- package/lib/types/client/ui/InputsDialog.d.ts +22 -0
- package/lib/types/client/ui/Inspector.d.ts +51 -0
- package/lib/types/client/ui/Issues.d.ts +15 -0
- package/lib/types/client/ui/Launch.d.ts +30 -0
- package/lib/types/client/ui/Library.d.ts +23 -0
- package/lib/types/client/ui/LinkRow.d.ts +31 -0
- package/lib/types/client/ui/Markdown.d.ts +21 -0
- package/lib/types/client/ui/NodeHeads.d.ts +47 -0
- package/lib/types/client/ui/NoteDrawer.d.ts +21 -0
- package/lib/types/client/ui/OpenWith.d.ts +21 -0
- package/lib/types/client/ui/Outputs.d.ts +61 -0
- package/lib/types/client/ui/PanelHead.d.ts +21 -0
- package/lib/types/client/ui/PlanDialog.d.ts +18 -0
- package/lib/types/client/ui/PreviewCard.d.ts +38 -0
- package/lib/types/client/ui/QuickAdd.d.ts +30 -0
- package/lib/types/client/ui/ResourceItemDialog.d.ts +33 -0
- package/lib/types/client/ui/ResourceItems.d.ts +30 -0
- package/lib/types/client/ui/ResourcePanel.d.ts +26 -0
- package/lib/types/client/ui/Resources.d.ts +43 -0
- package/lib/types/client/ui/RunDraftBar.d.ts +35 -0
- package/lib/types/client/ui/RunEdge.d.ts +29 -0
- package/lib/types/client/ui/RunFiles.d.ts +24 -0
- package/lib/types/client/ui/RunInput.d.ts +26 -0
- package/lib/types/client/ui/RunItemDialog.d.ts +43 -0
- package/lib/types/client/ui/RunModeSwitch.d.ts +14 -0
- package/lib/types/client/ui/RunNav.d.ts +22 -0
- package/lib/types/client/ui/RunNodeState.d.ts +42 -0
- package/lib/types/client/ui/RunOverview.d.ts +27 -0
- package/lib/types/client/ui/RunPosition.d.ts +24 -0
- package/lib/types/client/ui/RunResource.d.ts +40 -0
- package/lib/types/client/ui/RunStatusMenu.d.ts +28 -0
- package/lib/types/client/ui/RunStep.d.ts +45 -0
- package/lib/types/client/ui/RunTopBar.d.ts +42 -0
- package/lib/types/client/ui/RunView.d.ts +43 -0
- package/lib/types/client/ui/SettingsDialog.d.ts +25 -0
- package/lib/types/client/ui/SettingsFields.d.ts +37 -0
- package/lib/types/client/ui/SkillPicker.d.ts +25 -0
- package/lib/types/client/ui/SkillPreview.d.ts +27 -0
- package/lib/types/client/ui/StepMark.d.ts +16 -0
- package/lib/types/client/ui/StepPanel.d.ts +26 -0
- package/lib/types/client/ui/ThemePicker.d.ts +13 -0
- package/lib/types/client/ui/TipLayer.d.ts +17 -0
- package/lib/types/client/ui/TopBar.d.ts +32 -0
- package/lib/types/client/ui/VersionList.d.ts +19 -0
- package/lib/types/client/ui/VersionRow.d.ts +19 -0
- package/lib/types/client/ui/VersionsDialog.d.ts +18 -0
- package/lib/types/client/ui/WorkflowRow.d.ts +32 -0
- package/lib/types/client/ui/WorkflowSwitcher.d.ts +20 -0
- package/lib/types/client/ui/WorkflowView.d.ts +27 -0
- package/lib/types/client/ui/lines.d.ts +13 -0
- package/lib/types/client/ui/primitives.d.ts +119 -0
- package/lib/types/client/ui/resourceUi.d.ts +49 -0
- package/lib/types/client/ui/stepIcons.d.ts +10 -0
- package/lib/types/host/authoringSkill.d.ts +17 -0
- package/lib/types/host/config.d.ts +54 -0
- package/lib/types/host/hostFs.d.ts +69 -0
- package/lib/types/host/plan.d.ts +68 -0
- package/lib/types/host/pluginConfig.d.ts +57 -0
- package/lib/types/host/rpc.d.ts +45 -0
- package/lib/types/host/runs/files.d.ts +37 -0
- package/lib/types/host/runs/notice.d.ts +21 -0
- package/lib/types/host/runs/service.d.ts +258 -0
- package/lib/types/host/runs/skill.d.ts +16 -0
- package/lib/types/host/runs/storage.d.ts +16 -0
- package/lib/types/host/runs/store.d.ts +56 -0
- package/lib/types/host/skillView.d.ts +22 -0
- package/lib/types/host/store/atomic.d.ts +34 -0
- package/lib/types/host/store/materialize.d.ts +19 -0
- package/lib/types/host/store/merge.d.ts +25 -0
- package/lib/types/host/store/paths.d.ts +86 -0
- package/lib/types/host/store/repository.d.ts +217 -0
- package/lib/types/host/store/versions.d.ts +38 -0
- package/lib/types/host/tool/tool.d.ts +432 -0
- package/lib/types/index.d.ts +35 -0
- package/lib/types/shared/appearance.d.ts +49 -0
- package/lib/types/shared/compile.d.ts +71 -0
- package/lib/types/shared/graph.d.ts +54 -0
- package/lib/types/shared/graphDiff.d.ts +29 -0
- package/lib/types/shared/inputs.d.ts +46 -0
- package/lib/types/shared/limits.d.ts +77 -0
- package/lib/types/shared/model.d.ts +122 -0
- package/lib/types/shared/naming.d.ts +59 -0
- package/lib/types/shared/outputPaths.d.ts +49 -0
- package/lib/types/shared/resources.d.ts +98 -0
- package/lib/types/shared/runCursor.d.ts +54 -0
- package/lib/types/shared/runState.d.ts +221 -0
- package/lib/types/shared/runSync.d.ts +24 -0
- package/lib/types/shared/types.d.ts +488 -0
- package/lib/types/shared/validate.d.ts +54 -0
- package/lib/types/shared/wire.d.ts +600 -0
- package/locale/en.json +6 -0
- package/locale/zh.json +6 -0
- package/package.json +144 -4
|
@@ -0,0 +1,258 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 工作流实例的业务面:建实例、列、读、绑定、删、恢复、保存用户的改动。
|
|
3
|
+
*
|
|
4
|
+
* 工具(`compile` / `resume` / `runs` / `state`)与画布 RPC(`run/*`)共用这一层。状态文件只有插件写:
|
|
5
|
+
* 模型经 `state` 动作改(插件补时间、轮次、流水,改完校验),用户经画布改(逐字段核对冲突)。
|
|
6
|
+
* 同一个实例的写入排队进行,不会互相覆盖。
|
|
7
|
+
*
|
|
8
|
+
* @module @xiaoso/dsh-workflow-lite/host/runs/service
|
|
9
|
+
*/
|
|
10
|
+
import { type CursorStep, type NextStep, type RunCursor } from '../../shared/runCursor.ts';
|
|
11
|
+
import { type EditValue, type InstanceRecord, type InstanceSummary, type InstanceView, type NodeRunState, type NodeStatus, type RunLogEntry, type RunStatus, type StateEdit } from '../../shared/runState.ts';
|
|
12
|
+
import type { InputAnswer, ValidationProblem, WorkflowDocument } from '../../shared/types.ts';
|
|
13
|
+
import type { RunFileResponse } from '../../shared/wire.ts';
|
|
14
|
+
import { type CompileBundle } from '../plan.ts';
|
|
15
|
+
import type { Outcome } from '../store/repository.ts';
|
|
16
|
+
import { type RunFileTarget } from './files.ts';
|
|
17
|
+
import { InstanceStore } from './store.ts';
|
|
18
|
+
/** 把一条通知送进会话(`steer`:空闲就开一轮,正在跑就排进下一步)。送到了回 `true`。 */
|
|
19
|
+
export type Notify = (session: string, text: string, summary: string) => Promise<boolean>;
|
|
20
|
+
export interface RunServiceDeps {
|
|
21
|
+
dataDir: () => string;
|
|
22
|
+
/** 校验一张图(计划的 ⑥ 段「图的注意事项」要它);不给就当没有警告。 */
|
|
23
|
+
validate?: (document: WorkflowDocument, workflow: string) => ValidationProblem[];
|
|
24
|
+
notify?: Notify;
|
|
25
|
+
}
|
|
26
|
+
/** 模型经 `state` 动作对一个步骤的改动。 */
|
|
27
|
+
export interface NodePatch {
|
|
28
|
+
status?: NodeStatus;
|
|
29
|
+
summary?: string;
|
|
30
|
+
outputs?: string[];
|
|
31
|
+
verdict?: string;
|
|
32
|
+
error?: string;
|
|
33
|
+
by?: string;
|
|
34
|
+
}
|
|
35
|
+
/** 模型经 `state` 动作的一次改动;什么都不给 = 只看。 */
|
|
36
|
+
export interface StatePatch {
|
|
37
|
+
status?: RunStatus;
|
|
38
|
+
/** 空串 = 清掉。 */
|
|
39
|
+
note?: string;
|
|
40
|
+
nodes?: Record<string, NodePatch>;
|
|
41
|
+
/** 追加一条说明(流水里记成 `note`)。 */
|
|
42
|
+
log?: string;
|
|
43
|
+
}
|
|
44
|
+
/** `state` 动作回给模型的东西:当前状态的要点。 */
|
|
45
|
+
export interface StateReport {
|
|
46
|
+
instance: string;
|
|
47
|
+
workflow: string;
|
|
48
|
+
status: RunStatus;
|
|
49
|
+
note?: string;
|
|
50
|
+
updatedAt: string;
|
|
51
|
+
progress: {
|
|
52
|
+
done: number;
|
|
53
|
+
total: number;
|
|
54
|
+
running?: string[];
|
|
55
|
+
waiting?: string[];
|
|
56
|
+
failed?: string[];
|
|
57
|
+
};
|
|
58
|
+
nodes: Record<string, NodeRunState>;
|
|
59
|
+
/** 最后执行的步骤(做完了、下游还没接上的;都接上了就是最近做完的那步)。 */
|
|
60
|
+
last: CursorStep[];
|
|
61
|
+
/** 接下来该做的步骤(按图、判定和流水推出来的)。 */
|
|
62
|
+
next: NextStep[];
|
|
63
|
+
/** 最近几条流水。 */
|
|
64
|
+
recentLog: RunLogEntry[];
|
|
65
|
+
/** 这次改了什么(只看时没有)。 */
|
|
66
|
+
applied?: string[];
|
|
67
|
+
/** 这次才开始记状态(实例原本不记)。 */
|
|
68
|
+
created?: true;
|
|
69
|
+
}
|
|
70
|
+
/** `compile` / `resume` 回给模型的东西。 */
|
|
71
|
+
export type InstancePlan = CompileBundle & {
|
|
72
|
+
instance: string;
|
|
73
|
+
progress: Record<string, unknown>;
|
|
74
|
+
};
|
|
75
|
+
/** 会话信息:工具从执行上下文取,画布从槽位给。 */
|
|
76
|
+
export interface SessionRef {
|
|
77
|
+
id?: string;
|
|
78
|
+
cwd?: string;
|
|
79
|
+
}
|
|
80
|
+
/** `run/load` 带 `since` 且文件没变时的回答。 */
|
|
81
|
+
export interface Unchanged {
|
|
82
|
+
unchanged: true;
|
|
83
|
+
mtime: number;
|
|
84
|
+
}
|
|
85
|
+
/** 保存用户改动的结果。 */
|
|
86
|
+
export interface SaveResult {
|
|
87
|
+
/** 通知送到模型了没有;没送到时存进索引,模型下次调用工具时附上。 */
|
|
88
|
+
notified: boolean;
|
|
89
|
+
mtime: number;
|
|
90
|
+
/** 改了图时:新图的 planId。 */
|
|
91
|
+
planId?: string;
|
|
92
|
+
/** 没有通知模型:只改了不进计划的东西(挪卡片、描述),或者用户选了不通知。 */
|
|
93
|
+
quiet?: true;
|
|
94
|
+
}
|
|
95
|
+
/** 用户在实例视图里改的图:改之前那版的 planId(核对有没有被别处改过)+ 改完的整张图。 */
|
|
96
|
+
export interface GraphEdit {
|
|
97
|
+
base: string;
|
|
98
|
+
document: WorkflowDocument;
|
|
99
|
+
}
|
|
100
|
+
/** 保存时字段对不上(用户开始改之后,模型改了同一个字段)。 */
|
|
101
|
+
export interface EditConflict {
|
|
102
|
+
path: string[];
|
|
103
|
+
/** 用户以为的旧值。 */
|
|
104
|
+
from: EditValue;
|
|
105
|
+
/** 文件里现在的值。 */
|
|
106
|
+
disk: EditValue;
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* 改动按对象归成几行写给模型:整体一行、每个步骤一行。
|
|
110
|
+
* 返回的行数就是"改了几处"(用户改一个步骤的状态,连带改了轮次、时间,算一处)。
|
|
111
|
+
*/
|
|
112
|
+
export declare function describeEdits(edits: readonly StateEdit[]): string[];
|
|
113
|
+
/** 运行到哪了,写给模型的一句话(`resume` 用)。 */
|
|
114
|
+
export declare function cursorHint(cursor: RunCursor, status: RunStatus): string;
|
|
115
|
+
/**
|
|
116
|
+
* 画布上点「执行」时发进会话的那句话:短、人看得懂;完整计划由模型调 `resume` 拿
|
|
117
|
+
* (计划在工具结果里,对话里照样看得到)。
|
|
118
|
+
*/
|
|
119
|
+
export declare function startPrompt(record: InstanceRecord): string;
|
|
120
|
+
export declare class RunService {
|
|
121
|
+
readonly store: InstanceStore;
|
|
122
|
+
private readonly deps;
|
|
123
|
+
/** 每个实例的写入排队(模型的 `state`、用户的保存、插件记流水不会互相覆盖)。 */
|
|
124
|
+
private readonly queues;
|
|
125
|
+
constructor(deps: RunServiceDeps);
|
|
126
|
+
/** 同一个实例的写入一个接一个来。 */
|
|
127
|
+
private serial;
|
|
128
|
+
private problemsOf;
|
|
129
|
+
/**
|
|
130
|
+
* 编译成功之后建实例(`compile` 的 `prepareRun`):
|
|
131
|
+
* 本会话当前实例是同一张图、同一个 `planId`、而且还没开始过时直接复用(模型重复编译不会留下一堆空实例)。
|
|
132
|
+
*
|
|
133
|
+
* 快照里的产出根目录定死:没配就是默认的 `.workflow-lite/runs/<实例 id>/out`,`{instance}` 换成实例 id。
|
|
134
|
+
* 实例的 `planId` 按快照算(`resume` 从快照重编,两边对得上)。
|
|
135
|
+
*/
|
|
136
|
+
prepare(input: {
|
|
137
|
+
workflow: string;
|
|
138
|
+
document: WorkflowDocument;
|
|
139
|
+
session: SessionRef;
|
|
140
|
+
goal?: string;
|
|
141
|
+
/** 用户对输入节点的回答(已核对、补上默认值);没有输入节点就是空的。 */
|
|
142
|
+
answers?: Readonly<Record<string, InputAnswer>>;
|
|
143
|
+
/** 建状态文件(缺省按图的「记录运行状态」开关)。 */
|
|
144
|
+
track?: boolean;
|
|
145
|
+
/** 复用本会话还没开始过的同一份实例(缺省复用;画布上点「执行」每次都是新的一次)。 */
|
|
146
|
+
reuse?: boolean;
|
|
147
|
+
}): Promise<Outcome<InstanceRecord>>;
|
|
148
|
+
/** 实例建立时用户给的回答(没有输入节点、或文件不在时是空的)。 */
|
|
149
|
+
private answersOf;
|
|
150
|
+
/** 按实例的快照出计划,把任务描述写进实例目录。 */
|
|
151
|
+
private planOf;
|
|
152
|
+
/**
|
|
153
|
+
* 工具的 `compile`:图编译得出计划就建一个实例(开了「记录运行状态」才有状态;本会话还没开始过的
|
|
154
|
+
* 同一份会复用),回给模型的和 `resume` 一样。编译级问题照常回 `problems`、不建实例。
|
|
155
|
+
*/
|
|
156
|
+
compile(input: {
|
|
157
|
+
workflow: string;
|
|
158
|
+
document: WorkflowDocument;
|
|
159
|
+
problems: readonly ValidationProblem[];
|
|
160
|
+
session: SessionRef;
|
|
161
|
+
goal?: string;
|
|
162
|
+
/** 用户对输入节点的回答(输入 id → 回答);没回答的用默认值。 */
|
|
163
|
+
answers?: unknown;
|
|
164
|
+
}): Promise<Outcome<InstancePlan | CompileBundle>>;
|
|
165
|
+
/**
|
|
166
|
+
* 画布上的「执行」:用模板现在的样子建一个新实例(图的快照 + 归属 `session`,开了「记录运行状态」
|
|
167
|
+
* 再建状态文件),设成这个会话的当前实例,回一句发进会话的话——模型据此用 `resume` 拿计划。
|
|
168
|
+
* 图有编译级问题时不建(计划都出不来)。
|
|
169
|
+
*/
|
|
170
|
+
start(input: {
|
|
171
|
+
workflow: string;
|
|
172
|
+
document: WorkflowDocument;
|
|
173
|
+
problems: readonly ValidationProblem[];
|
|
174
|
+
session: SessionRef & {
|
|
175
|
+
id: string;
|
|
176
|
+
};
|
|
177
|
+
/** 用户在「执行」前填的回答(输入 id → 回答)。 */
|
|
178
|
+
answers?: unknown;
|
|
179
|
+
}): Promise<Outcome<{
|
|
180
|
+
instance: InstanceSummary;
|
|
181
|
+
prompt: string;
|
|
182
|
+
}>>;
|
|
183
|
+
private snapshot;
|
|
184
|
+
/** 读并校验状态文件。`document` 给了就对照快照。 */
|
|
185
|
+
private readState;
|
|
186
|
+
private summarize;
|
|
187
|
+
/** 列实例:`all` 为假时只列 `session` 的。新的在前。 */
|
|
188
|
+
list(session: string | undefined, all: boolean): Promise<InstanceSummary[]>;
|
|
189
|
+
/** 会话的当前实例 id(没有就 `undefined`)。 */
|
|
190
|
+
currentOf(session: string): Promise<string | undefined>;
|
|
191
|
+
/** 读一个实例给画布。`since` 等于文件当前的修改时间时只回"没变"。 */
|
|
192
|
+
view(id: string, session: string | undefined, since?: number): Promise<Outcome<InstanceView | Unchanged>>;
|
|
193
|
+
/** 看实例里的一份产出文件(文件面板与查看框)。 */
|
|
194
|
+
file(id: string, target: RunFileTarget): Promise<Outcome<RunFileResponse>>;
|
|
195
|
+
/**
|
|
196
|
+
* 设 `session` 的当前实例。实例原本属于别的会话时把它**转过来**(一个实例只属于一个会话):
|
|
197
|
+
* 原会话的当前实例若是它就清掉,状态文件的 `log` 记一条 `transfer`。
|
|
198
|
+
*/
|
|
199
|
+
bind(id: string, session: string): Promise<Outcome<{
|
|
200
|
+
transferred: boolean;
|
|
201
|
+
}>>;
|
|
202
|
+
/** 删实例记录与快照;`withState` 为真时连工作区里的状态文件一起删。 */
|
|
203
|
+
remove(id: string, withState: boolean): Promise<Outcome<{
|
|
204
|
+
removed: true;
|
|
205
|
+
}>>;
|
|
206
|
+
/**
|
|
207
|
+
* 接着跑一个实例:从快照重建计划(任务描述不在就重新写),带上运行状态段,
|
|
208
|
+
* 再给一份摘要。实例属于别的会话时先转过来。
|
|
209
|
+
*/
|
|
210
|
+
resume(id: string | undefined, session: SessionRef): Promise<Outcome<InstancePlan>>;
|
|
211
|
+
/**
|
|
212
|
+
* 工具的 `state`:看或改一个实例的运行状态。
|
|
213
|
+
*
|
|
214
|
+
* - 不带改动 = 只看;
|
|
215
|
+
* - 改步骤状态时插件补上轮次、开始 / 结束时间({@link statusFields}),每处状态变化记一条流水,更新 `updatedAt`;
|
|
216
|
+
* - 改完整份校验,不合法就整次拒绝、回问题清单(文件不动);
|
|
217
|
+
* - 实例原本不记状态(或状态文件不见了)时,按初始状态新建再改。
|
|
218
|
+
*/
|
|
219
|
+
state(id: string | undefined, session: SessionRef, patch: StatePatch): Promise<Outcome<StateReport>>;
|
|
220
|
+
/** 把一次改动落到状态对象上(就地改),回给模型看的改动清单。 */
|
|
221
|
+
private applyPatch;
|
|
222
|
+
/**
|
|
223
|
+
* 保存用户在画布上攒的改动:逐条核对"改前"还是文件里的值(对不上整次拒绝、回冲突清单),
|
|
224
|
+
* 只改这几处、追加一条 `edit` 流水、更新 `updatedAt`,校验通过才原子写;然后通知模型
|
|
225
|
+
* (`notify: false` 时不通知、也不暂存通知:模型下次读状态文件或 `resume` 时自己看到)。
|
|
226
|
+
*/
|
|
227
|
+
save(id: string, session: string | undefined, edits: readonly StateEdit[], note: string | undefined, graph?: GraphEdit, options?: {
|
|
228
|
+
notify?: boolean;
|
|
229
|
+
}): Promise<Outcome<SaveResult>>;
|
|
230
|
+
private saveNow;
|
|
231
|
+
/** 逐条核对"改前"还是文件里的值,都对上才把改动落到 YAML 上(就地改)。 */
|
|
232
|
+
private applyUserEdits;
|
|
233
|
+
/**
|
|
234
|
+
* 用户的改动记进流水:图改了记一条(不挂步骤),每个改过的步骤一条,整体的排在后面,指定下一步单记一条 `next`
|
|
235
|
+
* 排在最后;用户的说明跟在最后一条上。
|
|
236
|
+
*/
|
|
237
|
+
private appendUserLog;
|
|
238
|
+
/**
|
|
239
|
+
* 保存用户在实例视图里改的图(连同状态的改动):图快照换成新的,状态跟着对齐(新步骤补上、删掉的去掉、
|
|
240
|
+
* 身份字段 plan 换新,见 `shared/runSync.ts`),任务描述重写,再通知模型去 `resume` 拿新计划。
|
|
241
|
+
*
|
|
242
|
+
* - 图在用户开始改之后被别处改过(`base` 不是现在的 planId)→ `conflict`;
|
|
243
|
+
* - 新图有保存级 / 编译级问题、删了执行过的步骤、改完的状态不合法 → 整次拒绝,什么都不写;
|
|
244
|
+
* - 工作流设置与视口不在实例里改:沿用原快照的;
|
|
245
|
+
* - 只挪了卡片、改了描述这类不进计划的东西:照样保存,不打扰模型。
|
|
246
|
+
*/
|
|
247
|
+
private saveGraph;
|
|
248
|
+
/**
|
|
249
|
+
* 把用户的改动告诉模型:会话在跑就排进下一步、空闲就开一轮;送不到(会话的 agent 不在)就暂存进索引,
|
|
250
|
+
* 模型下次调用工具时附上。送到了回 `true`。
|
|
251
|
+
*/
|
|
252
|
+
private tell;
|
|
253
|
+
/** 取走这个会话名下所有没送到的通知(模型调用工具时附在返回值里)。 */
|
|
254
|
+
takeNotices(session: string | undefined): Promise<string[]>;
|
|
255
|
+
/** 插件替用户 / 自己往状态文件追加一条流水(转移、恢复)。文件不合法就不动它。 */
|
|
256
|
+
private appendLog;
|
|
257
|
+
private appendLogNow;
|
|
258
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 按需 skill `workflow-run-state`:运行状态的字段、`state` 动作的用法与维护规矩。
|
|
3
|
+
*
|
|
4
|
+
* 计划末尾的「运行状态」段只放执行时离不开的几条;字段全表、例子、恢复步骤、常见错误都在这里,
|
|
5
|
+
* 模型拿不准时才读(目录里只常驻一句摘要)。状态由插件写——模型经 `workflow_lite` 的 `state`
|
|
6
|
+
* 动作改,插件补时间、轮次、流水并当场校验,所以这里不教怎么手写 YAML。
|
|
7
|
+
*
|
|
8
|
+
* @module @xiaoso/dsh-workflow-lite/host/runs/skill
|
|
9
|
+
*/
|
|
10
|
+
import type { Context } from '@deepseek-ai/cordis';
|
|
11
|
+
export declare const RUN_STATE_SKILL = "workflow-run-state";
|
|
12
|
+
/**
|
|
13
|
+
* 注册 skill;`skills` 服务不在时什么也不做(计划里的「运行状态」段照写)。
|
|
14
|
+
* @returns 注销器。
|
|
15
|
+
*/
|
|
16
|
+
export declare function registerRunStateSkill(ctx: Context): () => void;
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 「工作流中心 · 存储」:数据目录的统计与清理。
|
|
3
|
+
*
|
|
4
|
+
* 统计数据目录里的几样东西:工作流、我的步骤、实例记录(`runs/` 下的图快照与回答)、
|
|
5
|
+
* 旧版本遗留的任务描述(`.dispatch/`:早先编译时写在这里,现在任务描述放在各实例目录的 `tasks/` 里,
|
|
6
|
+
* 不再有人写它、也不再有人读它)。
|
|
7
|
+
*
|
|
8
|
+
* 两样能清的东西:旧版遗留文件(随时可删)、已结束的实例记录(完成 / 已取消;只删索引条目与快照,
|
|
9
|
+
* 工作区里的状态文件不动)。
|
|
10
|
+
*
|
|
11
|
+
* @module @xiaoso/dsh-workflow-lite/host/runs/storage
|
|
12
|
+
*/
|
|
13
|
+
import type { StorageStats } from '../../shared/wire.ts';
|
|
14
|
+
import type { RunService } from './service.ts';
|
|
15
|
+
export type StorageAction = 'stats' | 'clearDispatch' | 'clearFinished';
|
|
16
|
+
export declare function storageAction(runs: RunService, dataDir: string, action: StorageAction): Promise<StorageStats>;
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 工作流实例:落盘位置与实例索引。
|
|
3
|
+
*
|
|
4
|
+
* 落盘位置:
|
|
5
|
+
* - `<dataDir>/instances.json`:实例索引,全局一份,**只有插件写**(进程内写锁 + 原子写);
|
|
6
|
+
* - `<dataDir>/runs/<实例 id>/graph.json`:建实例那一刻的图快照,建立后只读;
|
|
7
|
+
* - **实例目录** `<工作区>/.workflow-lite/runs/<实例 id>/`(拿不到工作区时退到 `<dataDir>/runs/<实例 id>/`):
|
|
8
|
+
* `state.yaml` 状态(插件写:模型经 `state` 动作、用户经画布)、`tasks/` 各步骤的任务描述、
|
|
9
|
+
* `out/` 默认的产出根目录。早先的实例状态文件在 `runs/<实例 id>.yaml`,索引里记着绝对路径,照旧能读。
|
|
10
|
+
*
|
|
11
|
+
* 状态不进索引:进度的事实源只有状态文件,索引只记"在哪、属于谁"。
|
|
12
|
+
*
|
|
13
|
+
* @module @xiaoso/dsh-workflow-lite/host/runs/store
|
|
14
|
+
*/
|
|
15
|
+
import type { InstanceRecord } from '../../shared/runState.ts';
|
|
16
|
+
export declare const INSTANCES_FILE = "instances.json";
|
|
17
|
+
export declare const RUNS_DIR = "runs";
|
|
18
|
+
/** 工作区里放实例目录的地方(隐藏目录,里面放一个忽略一切的 `.gitignore`)。 */
|
|
19
|
+
export declare const WORKSPACE_RUNS_DIR: string;
|
|
20
|
+
/** 实例目录里放任务描述的子目录。 */
|
|
21
|
+
export declare const TASKS_DIR = "tasks";
|
|
22
|
+
/** 工作区里 `.workflow-lite/` 放一个忽略一切的 `.gitignore`(状态、任务描述、默认产出都不进版本库)。 */
|
|
23
|
+
export declare function ensureWorkspaceIgnore(cwd: string): Promise<void>;
|
|
24
|
+
export declare function instancesFile(dataDir: string): string;
|
|
25
|
+
export declare function runDir(dataDir: string, id: string): string;
|
|
26
|
+
export declare function snapshotFile(dataDir: string, id: string): string;
|
|
27
|
+
/** 用户执行前对输入节点的回答(输入 id → 回答),和图快照放在一起。 */
|
|
28
|
+
export declare function answersFile(dataDir: string, id: string): string;
|
|
29
|
+
/** 实例目录:有工作区就放工作区(沙箱 `workspace-write` 档能写,执行者也找得到),否则退回数据目录。 */
|
|
30
|
+
export declare function instanceDir(dataDir: string, id: string, cwd: string | undefined): string;
|
|
31
|
+
/** 状态文件:实例目录里的 `state.yaml`。 */
|
|
32
|
+
export declare function statePathFor(dataDir: string, id: string, cwd: string | undefined): string;
|
|
33
|
+
/** 实例 id:`<YYYYMMDD>-<HHmmss>-<4 位十六进制>`,按时间天然有序、能当文件名。 */
|
|
34
|
+
export declare function newInstanceId(date?: Date): string;
|
|
35
|
+
/** 实例 id 的形状(RPC / 工具入参先过这一道,再拿去拼路径)。 */
|
|
36
|
+
export declare function isInstanceId(value: unknown): value is string;
|
|
37
|
+
export interface InstanceIndex {
|
|
38
|
+
version: 1;
|
|
39
|
+
instances: InstanceRecord[];
|
|
40
|
+
/** 会话 id → 它的当前实例 id。 */
|
|
41
|
+
current: Record<string, string>;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* 实例索引的读写。写一律走 {@link update}:进程内串行(读 → 改 → 原子写),
|
|
45
|
+
* 不会有两次修改互相覆盖。
|
|
46
|
+
*/
|
|
47
|
+
export declare class InstanceStore {
|
|
48
|
+
private chain;
|
|
49
|
+
private readonly dataDir;
|
|
50
|
+
constructor(dataDir: () => string);
|
|
51
|
+
get file(): string;
|
|
52
|
+
/** 读索引。文件不在 = 空;解析不了就把它挪到一边(`instances.json.broken-<时间>`)再当空的。 */
|
|
53
|
+
read(): Promise<InstanceIndex>;
|
|
54
|
+
/** 在写锁里读 → 改 → 写回。`change` 返回 `false` 表示没改,不写盘。 */
|
|
55
|
+
update<T>(change: (index: InstanceIndex) => T | Promise<T>): Promise<T>;
|
|
56
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 以会话里那个 agent 的眼光看 skill。
|
|
3
|
+
*
|
|
4
|
+
* web 版 DSH 把本地 skill 的发现(项目的 `.dsh/skills` `.agents/skills`、`~/.dsh/skills`、
|
|
5
|
+
* `~/.agents/skills`)挂在 **agent 预设**底下:每个预设自己的 `skill-filesystem` 注册进它那一层。
|
|
6
|
+
* 不带作用域读 `ctx.skills` 只剩全局那一层(内置的、插件注册的)——只看得到两三个。
|
|
7
|
+
*
|
|
8
|
+
* 和 DSH 自己的 skill 目录(`/` 命令的那份清单)同一套取法:
|
|
9
|
+
* - 会话的 agent 正在跑:用它预设里的 skill 服务,以它为作用域;
|
|
10
|
+
* - 没在跑(或没给会话):借默认预设的作用域读一次,读完还回去。
|
|
11
|
+
*
|
|
12
|
+
* `agentPresets` 不在本项目的依赖里,按形状收窄,不对就退回全局那一层。
|
|
13
|
+
*
|
|
14
|
+
* @module @xiaoso/dsh-workflow-lite/host/skillView
|
|
15
|
+
*/
|
|
16
|
+
import type { Context } from '@deepseek-ai/cordis';
|
|
17
|
+
import type { SkillLister, SkillViewer } from './hostFs.ts';
|
|
18
|
+
/**
|
|
19
|
+
* @param ctx - 插件的上下文(找 `agents`、`agentPresets`)。
|
|
20
|
+
* @param global - 全局的 `ctx.skills`;skill 服务不在时为 `undefined`。
|
|
21
|
+
*/
|
|
22
|
+
export declare function createSkillViewer(ctx: Context, global: () => SkillLister | undefined): SkillViewer;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 单文件原子写与文本读入;存储层唯一的写入原语。
|
|
3
|
+
*
|
|
4
|
+
* 协议(单文件原子写):同目录临时文件 `open(..., 'wx')` → 写入 → `fsync` →
|
|
5
|
+
* `rename` 覆盖目标 → `fsync` 父目录。失败一律**清掉临时文件**再抛。
|
|
6
|
+
* 单文件写入天然原子:读者看到的要么是旧全文、要么是新全文,没有中间态。
|
|
7
|
+
*
|
|
8
|
+
* `writeFileAtomic` **抛错**而不是返回错误码——把 errno 翻译成 `invalid_args` / `io_error`
|
|
9
|
+
* 是仓储层的事(见 `repository.ts` 的 `mapWriteFailure`)。
|
|
10
|
+
* @module @xiaoso/dsh-workflow-lite/host/store/atomic
|
|
11
|
+
*/
|
|
12
|
+
/**
|
|
13
|
+
* 原子写:临时文件 → fsync → rename 覆盖 → fsync 父目录。
|
|
14
|
+
* 目标父目录**必须已存在**(由仓储的 `ensureLayout` 负责)。
|
|
15
|
+
*/
|
|
16
|
+
export declare function writeFileAtomic(target: string, content: string): Promise<void>;
|
|
17
|
+
/**
|
|
18
|
+
* 读文本。**不存在 → `null`**(`ENOENT` / 中间路径是文件的 `ENOTDIR` / 目标是目录的 `EISDIR`)。
|
|
19
|
+
* 其余失败照抛——那是真 IO 故障,不该被伪装成"文件不存在"。
|
|
20
|
+
*/
|
|
21
|
+
export declare function readFileText(target: string): Promise<string | null>;
|
|
22
|
+
/** 写前冲突比对用的整图哈希(sha-256,十六进制)。同一份文本 ⇒ 同一个值。 */
|
|
23
|
+
export declare function hashOf(text: string): Promise<string>;
|
|
24
|
+
/** 删一个文件;**不存在 = 成功**(幂等)。 */
|
|
25
|
+
export declare function unlinkFile(target: string): Promise<void>;
|
|
26
|
+
/** 递归删一棵树;**不存在 = 成功**。用于 `.dispatch/<图名>` 的连带清理。 */
|
|
27
|
+
export declare function removeTree(target: string): Promise<void>;
|
|
28
|
+
/** 确保一个目录存在(递归)。父路径被文件占位时抛 `ENOTDIR` / `ENOENT`,交给上层翻译。 */
|
|
29
|
+
export declare function ensureDir(target: string): Promise<boolean>;
|
|
30
|
+
/**
|
|
31
|
+
* 同卷 `rename`,失败时清场。
|
|
32
|
+
* 单独列出来是为了让"只改大小写"的两步改名(Windows)与普通改名共用同一套错误翻译。
|
|
33
|
+
*/
|
|
34
|
+
export declare function renamePath(from: string, to: string): Promise<void>;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 编译时把任务描述写进实例目录(`tasks/` 的规矩)。
|
|
3
|
+
*
|
|
4
|
+
* 路径 = `<实例目录>/tasks/<步骤 id>.md`。三条硬规矩:
|
|
5
|
+
* 1. **一次成功编译先清空 `tasks/`、再写**——不做增量、不做局部改写;
|
|
6
|
+
* 2. 写出的文件与 `data.prompt` **字节相同**:不补尾换行、不改 EOL、无 BOM;
|
|
7
|
+
* 3. 失败(不可写 / 磁盘满)**抛错**,由上层转成 `io_error`——**绝不返回一份路径不存在的计划**。
|
|
8
|
+
*
|
|
9
|
+
* 实例的快照建立后不变,所以同一个实例反复 `resume` 写出的内容也不变。
|
|
10
|
+
* @module @xiaoso/dsh-workflow-lite/host/store/materialize
|
|
11
|
+
*/
|
|
12
|
+
/**
|
|
13
|
+
* 把每个步骤的 `data.prompt` 原样写进 `dir`。
|
|
14
|
+
*
|
|
15
|
+
* @param dir 目标目录(会先整个清空)。
|
|
16
|
+
* @param payloads 步骤 id → 正文。**没有条目的步骤不落盘**(上层已按编译级规则拦过)。
|
|
17
|
+
* @throws 任何 IO 失败、非法步骤 id——上层统一翻成 `io_error`。
|
|
18
|
+
*/
|
|
19
|
+
export declare function materialize(dir: string, payloads: ReadonlyMap<string, string>): Promise<void>;
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 字段级合并(文件级冲突,字段级合并)。
|
|
3
|
+
*
|
|
4
|
+
* 合并单位 = **`node.id` 与 `edge.id`**(大小写不敏感,与图内身份一致)。只有两种情况算冲突:
|
|
5
|
+
* 1. **同一个 node 的 `data` 双方都改过**(各改成不一样的);
|
|
6
|
+
* 2. **同一个 `id` 一方删、一方改**。
|
|
7
|
+
*
|
|
8
|
+
* 两边改的是不同节点 / 边 ⇒ **自动合并、不报冲突**——"改 A 节点不会因为 B 节点被改而冲突"。
|
|
9
|
+
* `viewport` 与 `position` 是纯视图态,**本地优先、永不冲突**(坐标与 viewport 都存盘,
|
|
10
|
+
* 但它们不承载语义,没道理为"谁最后拖的"打断作者)。
|
|
11
|
+
*
|
|
12
|
+
* 冲突时输出文档以**本地为准**("保留我的");调用方若要"用磁盘的",直接重新加载就是了。
|
|
13
|
+
* 纯函数:不碰磁盘、不改入参、不 import DSH 包。
|
|
14
|
+
* @module @xiaoso/dsh-workflow-lite/host/store/merge
|
|
15
|
+
*/
|
|
16
|
+
import type { WorkflowDocument } from '../../shared/types.ts';
|
|
17
|
+
export interface MergeResult {
|
|
18
|
+
document: WorkflowDocument;
|
|
19
|
+
/** 冲突的 `node.id` / `edge.id`(按出现顺序,已去重)。 */
|
|
20
|
+
conflictIds: string[];
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* 把「本地要写回的 `mine`」与「此刻磁盘上的 `theirs`」按 `base`(加载时的基线)合并。
|
|
24
|
+
*/
|
|
25
|
+
export declare function mergeDocuments(base: WorkflowDocument, mine: WorkflowDocument, theirs: WorkflowDocument): MergeResult;
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* dsh-workflow-lite — 数据目录的路径构造与「什么算一个图文件」的扫描判据。
|
|
3
|
+
*
|
|
4
|
+
* 目录与布局,三件要紧的事:
|
|
5
|
+
* - **同名目录也算被占用**(`create` / `save_as_template` 加序号、`rename_workflow` 拒绝);
|
|
6
|
+
* - `.dispatch/` 以 `.` 开头 ⇒ 一切扫描**天然忽略**,它也**不参与任何读入**;
|
|
7
|
+
* - 扫描只认「普通文件 + 非隐藏 + 以 `.json` 结尾(不区分大小写)」,其余条目
|
|
8
|
+
* (非 `.json`、隐藏文件、`.tmp-*`、子目录、符号链接、编辑器残渣)一律忽略,
|
|
9
|
+
* 由调用方逐条报提示。
|
|
10
|
+
*
|
|
11
|
+
* 本模块只做**只读**文件系统访问(`stat` / `readdir`)与路径拼接;一切写入在 `atomic.ts`。
|
|
12
|
+
* 依赖方向严格单向:`atomic.ts` → 本模块 → `shared/*`,不成环。
|
|
13
|
+
* @module @xiaoso/dsh-workflow-lite/host/store/paths
|
|
14
|
+
*/
|
|
15
|
+
import type { PlanId } from '../../shared/types.ts';
|
|
16
|
+
/** 图文件 / 模板文件的后缀。判据不区分大小写。 */
|
|
17
|
+
export declare const JSON_SUFFIX = ".json";
|
|
18
|
+
/** 一个路径当前的占用形态。 */
|
|
19
|
+
export type PathKind = 'file' | 'dir' | 'missing';
|
|
20
|
+
/** 一个图名在 `workflows/` 下被谁占了位。`both` = 同名 `.json` 与同名目录同时存在(保存级)。 */
|
|
21
|
+
export type NameOccupant = 'file' | 'dir' | 'both' | null;
|
|
22
|
+
/** `errno` 码;拿不到就 `null`(异常形态不可控,一律当成"未知 IO 失败")。 */
|
|
23
|
+
export declare function errnoCode(error: unknown): string | null;
|
|
24
|
+
/** 「不存在」的三种 errno:`ENOENT`、路径中间是文件的 `ENOTDIR`、目标是目录的 `EISDIR`。 */
|
|
25
|
+
export declare function isAbsentError(error: unknown): boolean;
|
|
26
|
+
/** 读路径上的失败是否应当当成「不存在」(目录缺失、目标是个目录)。 */
|
|
27
|
+
export declare function isMissingOrUnreadableAsFile(error: unknown): boolean;
|
|
28
|
+
/** `<dataDir>/workflows/`。 */
|
|
29
|
+
export declare function workflowsDir(dataDir: string): string;
|
|
30
|
+
/** `<dataDir>/templates/nodes/`:节点模板(画布步骤库的「我的步骤」)。 */
|
|
31
|
+
export declare function templatesDir(dataDir: string): string;
|
|
32
|
+
/** `<dataDir>/workflows/<名>.json`。 */
|
|
33
|
+
export declare function workflowFile(dataDir: string, name: string): string;
|
|
34
|
+
/** `<dataDir>/templates/nodes/<名>.json`。 */
|
|
35
|
+
export declare function templateFile(dataDir: string, name: string): string;
|
|
36
|
+
/** `<dataDir>/versions/<图名>/`:这个工作流存下的版本(`<序号>.json`)。 */
|
|
37
|
+
export declare function versionsDir(dataDir: string, name: string): string;
|
|
38
|
+
/** `<dataDir>/versions/<图名>/<序号>.json`。 */
|
|
39
|
+
export declare function versionFile(dataDir: string, name: string, n: number): string;
|
|
40
|
+
/** `<dataDir>/.dispatch/` —— 派生根,**启动时不创建**,编译时才建。 */
|
|
41
|
+
export declare function dispatchRoot(dataDir: string): string;
|
|
42
|
+
/** `<dataDir>/.dispatch/<图名>`。 */
|
|
43
|
+
export declare function dispatchDir(dataDir: string, workflow: string): string;
|
|
44
|
+
/** `<dataDir>/.dispatch/<图名>/<planId>`。 */
|
|
45
|
+
export declare function payloadDir(dataDir: string, workflow: string, planId: PlanId): string;
|
|
46
|
+
/** `<dataDir>/.dispatch/<图名>/<planId>/<节点 id>.md`。 */
|
|
47
|
+
export declare function payloadFile(dataDir: string, workflow: string, planId: PlanId, nodeId: string): string;
|
|
48
|
+
/** 首次启动按需创建的那两个目录(**不含** `.dispatch/`)。 */
|
|
49
|
+
export declare function layoutDirs(dataDir: string): string[];
|
|
50
|
+
/**
|
|
51
|
+
* 同目录临时文件名:`.tmp-<随机>`。
|
|
52
|
+
* 以 `.` 开头 ⇒ 一切扫描天然忽略;与目标同目录 ⇒ `rename` 同卷、原子。
|
|
53
|
+
*/
|
|
54
|
+
export declare function tempName(target: string): string;
|
|
55
|
+
export interface DirScan {
|
|
56
|
+
/** 可用的条目名(**已去掉 `.json` 后缀**,保持磁盘上的原样大小写)。 */
|
|
57
|
+
names: string[];
|
|
58
|
+
/** 被忽略的条目名:非 `.json`、隐藏、`.tmp-*`、符号链接…… */
|
|
59
|
+
ignored: string[];
|
|
60
|
+
/** 被忽略的子目录名(图目录 = 旧结构信号,见 {@link legacyStructureDetected})。 */
|
|
61
|
+
directories: string[];
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* 扫一个「一文件一 JSON」的目录。**目录不存在 = 空**(首次启动的常态),不抛错。
|
|
65
|
+
* 判据:普通文件 · 非隐藏(文件名以 `.` 开头即视为隐藏)· 以 `.json` 结尾(不区分大小写)。
|
|
66
|
+
*/
|
|
67
|
+
export declare function scanJsonDir(dir: string): Promise<DirScan>;
|
|
68
|
+
/** `workflows/` 下的图名(只认图文件;其余条目进 `ignored` / `directories`)。 */
|
|
69
|
+
export declare function scanWorkflowDir(dataDir: string): Promise<DirScan>;
|
|
70
|
+
/** `workflows/` 下的图名——`list` / `read` 的入口。 */
|
|
71
|
+
export declare function workflowNamesOnDisk(dataDir: string): Promise<string[]>;
|
|
72
|
+
/** `templates/nodes/` 下的节点模板名。 */
|
|
73
|
+
export declare function scanTemplateDir(dataDir: string): Promise<DirScan>;
|
|
74
|
+
/** 一个路径是文件、目录,还是不存在。 */
|
|
75
|
+
export declare function pathKind(target: string): Promise<PathKind>;
|
|
76
|
+
/** 一个图名在 `workflows/` 下的占位情况——**同名目录也算被占用**。 */
|
|
77
|
+
export declare function workflowOccupant(dataDir: string, name: string): Promise<NameOccupant>;
|
|
78
|
+
/** 一个节点模板名在 `templates/nodes/` 下的占位情况——同样把同名目录算进来。 */
|
|
79
|
+
export declare function templateOccupant(dataDir: string, name: string): Promise<NameOccupant>;
|
|
80
|
+
/**
|
|
81
|
+
* 旧结构(md 版)是否在场:`workflows/` 下有**目录**,或 `dataDir` 顶层有 `nodes/`。
|
|
82
|
+
* 只在启动 / `list` 呈现,报一条专用提示,**不进图列表**。
|
|
83
|
+
*/
|
|
84
|
+
export declare function legacyStructureDetected(dataDir: string): Promise<boolean>;
|
|
85
|
+
/** 占位者的人话描述,用于警告文案。 */
|
|
86
|
+
export declare function describeOccupant(occupant: NameOccupant): string;
|