pi-fabric 0.22.2 → 0.22.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/README.md +15 -13
- package/dist/audit/details.d.ts +6 -0
- package/dist/audit/details.d.ts.map +1 -1
- package/dist/audit/details.js +16 -0
- package/dist/audit/details.js.map +1 -1
- package/dist/audit/projection.d.ts.map +1 -1
- package/dist/audit/projection.js +6 -0
- package/dist/audit/projection.js.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +38 -12
- package/dist/index.js.map +1 -1
- package/dist/ui/fabric-render.d.ts.map +1 -1
- package/dist/ui/fabric-render.js +58 -8
- package/dist/ui/fabric-render.js.map +1 -1
- package/dist/ui/structured.d.ts +1 -0
- package/dist/ui/structured.d.ts.map +1 -1
- package/dist/ui/structured.js +8 -2
- package/dist/ui/structured.js.map +1 -1
- package/dist/util.d.ts +1 -0
- package/dist/util.d.ts.map +1 -1
- package/dist/util.js +8 -0
- package/dist/util.js.map +1 -1
- package/docs/agents.md +291 -0
- package/docs/architecture.md +73 -0
- package/docs/audit-trace.md +112 -0
- package/docs/certification.md +134 -0
- package/docs/compaction.md +177 -0
- package/docs/configuration.md +245 -0
- package/docs/interface.md +87 -0
- package/docs/memory-recall.md +347 -0
- package/docs/programmatic-compaction.md +208 -0
- package/docs/providers.md +50 -0
- package/docs/schema-enforcement.md +165 -0
- package/docs/skills.md +45 -0
- package/docs/state-layer.md +197 -0
- package/package.json +2 -1
- package/skills/fabric-advisor/SKILL.md +6 -2
- package/skills/fabric-ambient/SKILL.md +8 -4
- package/skills/fabric-ambient/references/setup.md +37 -18
- package/skills/fabric-council/SKILL.md +79 -13
- package/skills/fabric-exec/SKILL.md +2 -2
- package/skills/fabric-exec/references/agents.md +1 -1
- package/skills/fabric-fusion/SKILL.md +130 -62
- package/skills/fabric-guide/SKILL.md +27 -0
- package/skills/fabric-rlm/SKILL.md +243 -24
- package/skills/fabric-schema/SKILL.md +33 -6
- package/skills/fabric-supervisor/SKILL.md +6 -2
- package/skills/fabric-workflow/SKILL.md +92 -21
|
@@ -1,28 +1,94 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: fabric-council
|
|
3
|
-
description: Runs a bounded multi-perspective Pi Fabric council with independent reviewers and
|
|
3
|
+
description: Runs a bounded multi-perspective Pi Fabric council with independent reviewers and best-effort synthesis. Use for architecture choices, plans, reviews, and adversarial cross-checking.
|
|
4
4
|
disable-model-invocation: true
|
|
5
5
|
---
|
|
6
6
|
|
|
7
7
|
# Fabric Council
|
|
8
8
|
|
|
9
|
-
Use one `fabric_exec` call
|
|
9
|
+
Use one `fabric_exec` call with bounded role fan-out. Choose three to five roles that disagree usefully rather than duplicating one another, such as correctness, security, operability, maintainability, and requirements skepticism.
|
|
10
10
|
|
|
11
11
|
```ts
|
|
12
|
-
|
|
12
|
+
type CouncilOutcome =
|
|
13
|
+
| { role: string; status: "completed"; report: string }
|
|
14
|
+
| { role: string; status: "failed"; error: string };
|
|
15
|
+
|
|
16
|
+
const roles = [...new Set(
|
|
17
|
+
(JSON.parse(π.roles) as string[]).map((role) => role.trim()).filter(Boolean),
|
|
18
|
+
)];
|
|
19
|
+
if (roles.length < 3 || roles.length > 5) {
|
|
20
|
+
throw new Error("Council requires 3–5 distinct non-empty roles.");
|
|
21
|
+
}
|
|
13
22
|
await workflow.configure({
|
|
14
23
|
name: "Council review",
|
|
15
|
-
description: `${roles.length} independent perspectives with synthesis`,
|
|
16
|
-
});
|
|
17
|
-
await phase("Deliberate", { total: roles.length });
|
|
18
|
-
return council.run({
|
|
19
|
-
task: π.task,
|
|
20
|
-
roles,
|
|
21
|
-
tools: ["read", "grep", "find", "ls"],
|
|
22
|
-
synthesize: true,
|
|
24
|
+
description: `${roles.length} independent perspectives with best-effort synthesis`,
|
|
23
25
|
});
|
|
26
|
+
await phase("Deliberate", { total: roles.length + 1 });
|
|
27
|
+
const outcomes = await parallel(
|
|
28
|
+
roles.map((role) => async (): Promise<CouncilOutcome> => {
|
|
29
|
+
try {
|
|
30
|
+
const report = await agent(
|
|
31
|
+
`Act as the ${role} council member. Independently analyze this task:\n\n${π.task}`,
|
|
32
|
+
{ label: role, tools: ["read", "grep", "find", "ls"] },
|
|
33
|
+
);
|
|
34
|
+
return { role, status: "completed", report };
|
|
35
|
+
} catch (error) {
|
|
36
|
+
return {
|
|
37
|
+
role,
|
|
38
|
+
status: "failed",
|
|
39
|
+
error: error instanceof Error ? error.message : String(error),
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
}),
|
|
43
|
+
{ concurrency: roles.length },
|
|
44
|
+
);
|
|
45
|
+
const completed = outcomes.filter(
|
|
46
|
+
(outcome): outcome is Extract<CouncilOutcome, { status: "completed" }> =>
|
|
47
|
+
outcome.status === "completed",
|
|
48
|
+
);
|
|
49
|
+
const failures = outcomes.filter(
|
|
50
|
+
(outcome): outcome is Extract<CouncilOutcome, { status: "failed" }> =>
|
|
51
|
+
outcome.status === "failed",
|
|
52
|
+
);
|
|
53
|
+
const coverage = { requested: roles.length, completed: completed.length };
|
|
54
|
+
if (completed.length === 0) {
|
|
55
|
+
return { status: "failed", coverage, failures, result: null };
|
|
56
|
+
}
|
|
57
|
+
if (completed.length === 1) {
|
|
58
|
+
return {
|
|
59
|
+
status: "partial",
|
|
60
|
+
coverage,
|
|
61
|
+
failures,
|
|
62
|
+
result: completed[0].report,
|
|
63
|
+
synthesisSkipped: "Only one role completed; another agent would add no diversity.",
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
try {
|
|
68
|
+
const result = await agent(
|
|
69
|
+
`Synthesize these completed reports into one decision. Reject unsupported claims, preserve material disagreements, attribute each concern to its role. Do not infer the views of failed roles.\n\nTask:\n${π.task}\n\nReports:\n${JSON.stringify(completed)}`,
|
|
70
|
+
{ label: "council synthesis", tools: ["read", "grep", "find", "ls"] },
|
|
71
|
+
);
|
|
72
|
+
return {
|
|
73
|
+
status: failures.length === 0 ? "success" : "partial",
|
|
74
|
+
coverage,
|
|
75
|
+
failures,
|
|
76
|
+
result,
|
|
77
|
+
};
|
|
78
|
+
} catch (error) {
|
|
79
|
+
return {
|
|
80
|
+
status: "partial",
|
|
81
|
+
coverage,
|
|
82
|
+
failures,
|
|
83
|
+
result: null,
|
|
84
|
+
synthesisError: error instanceof Error ? error.message : String(error),
|
|
85
|
+
fallback: completed,
|
|
86
|
+
};
|
|
87
|
+
}
|
|
24
88
|
```
|
|
25
89
|
|
|
26
|
-
Pass the task as `strings.task` and the JSON role array as `strings.roles`.
|
|
90
|
+
Pass the task as `strings.task` and the JSON role array as `strings.roles`. Successful synthesis returns only the compact decision, coverage, and failures. Raw completed reports return only when synthesis fails; one surviving role returns directly without spending another agent call.
|
|
91
|
+
|
|
92
|
+
Concurrent calls can overshoot an observational `tokenBudget` because usage settles afterward. Reserve at least `roles.length + 1` top-level agent calls when synthesis may run, and use a finite role set rather than relying on token accounting as a hard concurrent ceiling.
|
|
27
93
|
|
|
28
|
-
|
|
94
|
+
Status is `success`, `partial`, or `failed`. A partial result is usable evidence with named gaps and must not trigger an automatic whole-council rerun. If a missing perspective matters, retry that role with one plain agent using the original task and role; do not invoke a new council or rerun successful roles. Do not use a council for a lookup or a decision with no meaningful competing considerations.
|
|
@@ -60,7 +60,7 @@ All calls return promises. Fields ending in `?` are optional; `unknown` marks pr
|
|
|
60
60
|
|
|
61
61
|
### Dynamic provider return shapes
|
|
62
62
|
|
|
63
|
-
- `mcp.<sanitized_server>.<sanitized_tool>(args)` resolves to the server-defined result, commonly `{text:string,content:unknown[],structuredContent:unknown}`; for example `mcp.fal_ai.get_model_schema({ endpoint_id: "openai/gpt-image-2" })`.
|
|
63
|
+
- `mcp.<sanitized_server>.<sanitized_tool>(args)` resolves to the server-defined result, commonly `{text:string,content:unknown[],structuredContent:unknown}`; for example `mcp.fal_ai.get_model_schema({ endpoint_id: "openai/gpt-image-2" })`. `references/mcp.md` is a branch pointer for MCP naming and management only when the task needs MCP.
|
|
64
64
|
- `extensions.<tool>(args)` in full code mode resolves to `{content:Array<{type,text?,...}>,text:string,details?,isError:boolean,terminate?,source:{path,source,scope,origin,baseDir?}}`.
|
|
65
65
|
|
|
66
66
|
The guest TypeScript declarations contain the complete argument and return contracts. For a discovered or dynamic action, use `tools.describe({ref})`; inspect `outputSchema` when supplied, otherwise treat the result as `unknown`.
|
|
@@ -72,7 +72,7 @@ Refs are namespaced (`pi.grep`, `extensions.<tool>`, `mcp.<server>.<tool>`, `sch
|
|
|
72
72
|
Read the line-numbered error → `await tools.describe({ref})` for the schema → match `inputSchema`, rerun (don't guess). Common mistakes: bare ref (`grep`→`pi.grep`); 2 positional args on `read`/`bash`/`ls` (use an options object — positional is supported only for `grep`/`find`/`write`/`edit`).
|
|
73
73
|
|
|
74
74
|
## Orchestration surfaces (opt-in)
|
|
75
|
-
|
|
75
|
+
Advanced workflow skills are user-invoked; never load them autonomously. When the user has explicitly invoked an agent or mesh workflow, `references/agents.md` and `references/mesh.md` are branch pointers for low-level API detail.
|
|
76
76
|
|
|
77
77
|
`agents.main()` returns the dashboard-owning root Pi session; `agents.peers()` lists other live root sessions in the shared project mesh as `Peer <session-prefix>` targets. Peers support `agents.steer()` and `agents.followUp()` by exact id.
|
|
78
78
|
|
|
@@ -118,4 +118,4 @@ Mailbox:
|
|
|
118
118
|
return rlm.query({ task: "Decompose this repository and produce a compact architecture map.", transport: "process" });
|
|
119
119
|
```
|
|
120
120
|
|
|
121
|
-
`council.run({ task, roles, synthesize?, ...agentOptions })` runs several `agents.run` calls concurrently under the subagent semaphore and optionally synthesizes them; load `/skill:fabric-council`
|
|
121
|
+
`council.run({ task, roles, synthesize?, ...agentOptions })` runs several `agents.run` calls concurrently under the subagent semaphore and optionally synthesizes them. The full council pattern is user-invoked; never load `/skill:fabric-council` autonomously.
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: fabric-fusion
|
|
3
|
-
description: Multi-model deliberation.
|
|
3
|
+
description: Multi-model deliberation. Two to 8 distinct models answer in parallel with web-capable tools, then a judge compares consensus, contradictions, coverage gaps, unique insights, and blind spots. Use when the cost of being wrong justifies multiple completions.
|
|
4
4
|
disable-model-invocation: true
|
|
5
5
|
---
|
|
6
6
|
|
|
7
7
|
# Fabric Fusion
|
|
8
8
|
|
|
9
|
-
Use one `fabric_exec` call for a
|
|
9
|
+
Use one `fabric_exec` call for a 2–8 model panel and a judge when at least two responses complete. The judge compares rather than merges responses; return a compact status/coverage/analysis envelope so the caller writes the final answer. Use fusion for model-diverse research or critique, not tactical work or a lookup.
|
|
10
10
|
|
|
11
11
|
Pass every key: `strings.task`; JSON `strings.panel` as `Array<{ model, label? }>`; and optional `strings.judge`, `strings.tools`, and `strings.thinking` as empty strings when unset. Labels are attribution only. Tools default to `read`, `grep`, `find`, `ls`, and `bash`; thinking defaults to configured subagent thinking.
|
|
12
12
|
|
|
@@ -21,8 +21,8 @@ type FusionAnalysis = {
|
|
|
21
21
|
|
|
22
22
|
const task = π.task;
|
|
23
23
|
const panel = JSON.parse(π.panel) as Array<{ model: string; label?: string }>;
|
|
24
|
-
if (panel.length <
|
|
25
|
-
throw new Error("Fusion panel (analysis_models) must have
|
|
24
|
+
if (panel.length < 2 || panel.length > 8) {
|
|
25
|
+
throw new Error("Fusion panel (analysis_models) must have 2–8 members.");
|
|
26
26
|
}
|
|
27
27
|
const toolset = π.tools ? (JSON.parse(π.tools) as string[]) : ["read", "grep", "find", "ls", "bash"];
|
|
28
28
|
const thinking = π.thinking ? (π.thinking as FabricThinking) : undefined;
|
|
@@ -53,83 +53,151 @@ try {
|
|
|
53
53
|
}
|
|
54
54
|
const resolve = (needle: string): RunnerModel => {
|
|
55
55
|
const n = needle.toLowerCase();
|
|
56
|
-
const
|
|
56
|
+
const exact = models.filter((entry) => entry.key.toLowerCase() === n);
|
|
57
|
+
if (exact.length === 1) return exact[0];
|
|
58
|
+
const fuzzy = models.filter(
|
|
57
59
|
(entry) =>
|
|
58
|
-
entry.
|
|
59
|
-
entry.id.toLowerCase().includes(n) ||
|
|
60
|
-
entry.name.toLowerCase().includes(n),
|
|
60
|
+
entry.id.toLowerCase().includes(n) || entry.name.toLowerCase().includes(n),
|
|
61
61
|
);
|
|
62
|
-
if (
|
|
62
|
+
if (fuzzy.length !== 1) {
|
|
63
63
|
throw new Error(
|
|
64
|
-
|
|
64
|
+
fuzzy.length === 0
|
|
65
|
+
? `Fusion: model "${needle}" not found. Available: ${models.map((entry) => entry.key).join(", ")}`
|
|
66
|
+
: `Fusion: model "${needle}" is ambiguous. Matches: ${fuzzy.map((entry) => entry.key).join(", ")}`,
|
|
65
67
|
);
|
|
66
68
|
}
|
|
67
|
-
return
|
|
69
|
+
return fuzzy[0];
|
|
68
70
|
};
|
|
69
71
|
const members = panel.map((member) => ({
|
|
70
72
|
...resolve(member.model),
|
|
71
|
-
label: member.label || member.model,
|
|
73
|
+
label: (member.label || member.model).trim(),
|
|
72
74
|
}));
|
|
73
|
-
const
|
|
75
|
+
const modelIdentities = members.map((member) =>
|
|
76
|
+
`${member.runner}:${member.provider}:${member.resolvedModel ?? member.id}`
|
|
77
|
+
);
|
|
78
|
+
if (new Set(modelIdentities).size !== members.length) {
|
|
79
|
+
throw new Error("Fusion requires distinct resolved models, not aliases of the same model.");
|
|
80
|
+
}
|
|
81
|
+
if (members.some((member) => !member.label) ||
|
|
82
|
+
new Set(members.map((member) => member.label)).size !== members.length) {
|
|
83
|
+
throw new Error("Fusion requires distinct non-empty labels.");
|
|
84
|
+
}
|
|
85
|
+
const explicitJudge = π.judge ? resolve(π.judge) : undefined;
|
|
74
86
|
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
87
|
+
type PanelOutcome =
|
|
88
|
+
| { label: string; model: string; runner: FabricAgentRunner; status: "completed"; response: string }
|
|
89
|
+
| { label: string; model: string; runner: FabricAgentRunner; status: "failed"; error: string };
|
|
90
|
+
|
|
91
|
+
// Plain, non-recursive members preserve one level of deliberation.
|
|
79
92
|
await phase("Panel", { total: members.length });
|
|
80
|
-
const
|
|
81
|
-
members.map((
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
+
const outcomes = await parallel(
|
|
94
|
+
members.map((member) => async (): Promise<PanelOutcome> => {
|
|
95
|
+
try {
|
|
96
|
+
const response = await agent<string>(
|
|
97
|
+
`Independently answer this task. Use web search (run gsearch or curl via bash) when fresh sources help, and cite them inline.\n\nTask:\n${task}`,
|
|
98
|
+
{
|
|
99
|
+
label: `panel · ${member.label}`.slice(0, 50),
|
|
100
|
+
runner: member.runner,
|
|
101
|
+
model: member.key,
|
|
102
|
+
tools: toolset,
|
|
103
|
+
...(thinking ? { thinking } : {}),
|
|
104
|
+
},
|
|
105
|
+
);
|
|
106
|
+
return {
|
|
107
|
+
label: member.label, model: member.key, runner: member.runner,
|
|
108
|
+
status: "completed", response,
|
|
109
|
+
};
|
|
110
|
+
} catch (error) {
|
|
111
|
+
return {
|
|
112
|
+
label: member.label, model: member.key, runner: member.runner,
|
|
113
|
+
status: "failed",
|
|
114
|
+
error: error instanceof Error ? error.message : String(error),
|
|
115
|
+
};
|
|
116
|
+
}
|
|
117
|
+
}),
|
|
93
118
|
{ concurrency: members.length },
|
|
94
119
|
);
|
|
120
|
+
const completed = outcomes.filter(
|
|
121
|
+
(outcome): outcome is Extract<PanelOutcome, { status: "completed" }> =>
|
|
122
|
+
outcome.status === "completed",
|
|
123
|
+
);
|
|
124
|
+
const failures = outcomes.filter(
|
|
125
|
+
(outcome): outcome is Extract<PanelOutcome, { status: "failed" }> =>
|
|
126
|
+
outcome.status === "failed",
|
|
127
|
+
);
|
|
128
|
+
const coverage = { requested: members.length, completed: completed.length };
|
|
129
|
+
if (completed.length === 0) {
|
|
130
|
+
return { status: "failed", coverage, failures, analysis: null };
|
|
131
|
+
}
|
|
132
|
+
if (completed.length === 1) {
|
|
133
|
+
return {
|
|
134
|
+
status: "partial",
|
|
135
|
+
coverage,
|
|
136
|
+
failures,
|
|
137
|
+
analysis: null,
|
|
138
|
+
judgeSkipped: "At least two model responses are required for comparison.",
|
|
139
|
+
fallback: completed,
|
|
140
|
+
};
|
|
141
|
+
}
|
|
95
142
|
|
|
96
|
-
|
|
97
|
-
|
|
143
|
+
const judgeModel = explicitJudge ?? {
|
|
144
|
+
key: completed[0].model,
|
|
145
|
+
runner: completed[0].runner,
|
|
146
|
+
};
|
|
98
147
|
await phase("Judge", { total: 1 });
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
`
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
148
|
+
try {
|
|
149
|
+
const analysis = await agent<FusionAnalysis>(
|
|
150
|
+
`You are the fusion judge. Compare these ${completed.length} completed panel responses — do NOT merge them into one answer or infer claims from failed models.\n` +
|
|
151
|
+
`Return structured analysis: consensus (points all or most agree on, higher-confidence), ` +
|
|
152
|
+
`contradictions (where they disagreed), partial_coverage (what only some covered), ` +
|
|
153
|
+
`unique_insights (insights from individual models), blind_spots (gaps none addressed). ` +
|
|
154
|
+
`You may search the web to verify claims.\n\nTask:\n${task}\n\nPanel responses:\n` +
|
|
155
|
+
JSON.stringify(completed),
|
|
156
|
+
{
|
|
157
|
+
label: "fusion judge",
|
|
158
|
+
runner: judgeModel.runner,
|
|
159
|
+
model: judgeModel.key,
|
|
160
|
+
tools: toolset,
|
|
161
|
+
...(thinking ? { thinking } : {}),
|
|
162
|
+
schema: {
|
|
163
|
+
type: "object",
|
|
164
|
+
properties: {
|
|
165
|
+
consensus: { type: "array", items: { type: "string" } },
|
|
166
|
+
contradictions: { type: "array", items: { type: "string" } },
|
|
167
|
+
partial_coverage: { type: "array", items: { type: "string" } },
|
|
168
|
+
unique_insights: { type: "array", items: { type: "string" } },
|
|
169
|
+
blind_spots: { type: "array", items: { type: "string" } },
|
|
170
|
+
},
|
|
171
|
+
required: ["consensus", "contradictions", "partial_coverage", "unique_insights", "blind_spots"],
|
|
172
|
+
additionalProperties: false,
|
|
120
173
|
},
|
|
121
|
-
required: ["consensus", "contradictions", "partial_coverage", "unique_insights", "blind_spots"],
|
|
122
|
-
additionalProperties: false,
|
|
123
174
|
},
|
|
124
|
-
|
|
125
|
-
);
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
175
|
+
);
|
|
176
|
+
await workflow.event({ message: `Fusion complete · ${completed.length}/${members.length} models judged`, level: "success" });
|
|
177
|
+
return {
|
|
178
|
+
status: failures.length === 0 ? "success" : "partial",
|
|
179
|
+
coverage,
|
|
180
|
+
failures,
|
|
181
|
+
analysis,
|
|
182
|
+
};
|
|
183
|
+
} catch (error) {
|
|
184
|
+
return {
|
|
185
|
+
status: "partial",
|
|
186
|
+
coverage,
|
|
187
|
+
failures,
|
|
188
|
+
analysis: null,
|
|
189
|
+
judgeError: error instanceof Error ? error.message : String(error),
|
|
190
|
+
fallback: completed,
|
|
191
|
+
};
|
|
192
|
+
}
|
|
129
193
|
```
|
|
130
194
|
|
|
131
|
-
Choose distinct models by intent: strongest available, budget-balanced with a frontier judge, or similar-latency models for faster fan-out. The default panel size is three. Cost is N panel calls plus
|
|
195
|
+
Choose distinct models by intent: strongest available, budget-balanced with a frontier judge, or similar-latency models for faster fan-out. The default panel size is three. Cost is N panel calls plus a judge when comparison is possible. Reserve `panel.length + 1` top-level agent calls. Concurrent calls can overshoot observational token/USD checks because usage settles afterward; those settings are not hard concurrent reservations.
|
|
132
196
|
|
|
133
197
|
Panel members and the judge are plain, non-recursive agents, so deliberation is one level. `bash` enables web access through local search/fetch commands and requires execute approval. Concurrency is capped by `subagents.maxConcurrent`; inner calls otherwise inherit provider limits and use `thinking` for reasoning effort.
|
|
134
198
|
|
|
135
|
-
|
|
199
|
+
For same-model role diversity, recommend `/skill:fabric-council` for the user to invoke; do not invoke another user-only skill yourself. Use a plain agent when competing model perspectives do not justify the cost.
|
|
200
|
+
|
|
201
|
+
## Completion criterion
|
|
202
|
+
|
|
203
|
+
Return `success`, `partial`, or `failed` with explicit panel coverage. Successful judging returns only the structured comparison; raw responses return only when judging fails or fewer than two models complete. A partial result is usable and must not trigger an automatic full-panel rerun. Failures retain label, canonical model key, and runner; retry only failed models or the judge when that missing coverage matters.
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: fabric-guide
|
|
3
|
+
description: Recommends the right user-invoked Pi Fabric workflow without running it. Use when you want help choosing among workflow, council, fusion, RLM, Schema, ambient actors, or swarm.
|
|
4
|
+
disable-model-invocation: true
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Fabric Guide
|
|
8
|
+
|
|
9
|
+
Recommend the smallest sufficient path; do not invoke it. Core coding needs no advanced skill: answer `No advanced skill — use the core fabric_exec path.`
|
|
10
|
+
|
|
11
|
+
| Need | Recommend |
|
|
12
|
+
|---|---|
|
|
13
|
+
| Finite discover → fan-out → verify work | `/skill:fabric-workflow` |
|
|
14
|
+
| Same-model independent roles and synthesis | `/skill:fabric-council` |
|
|
15
|
+
| Different models compared by a judge | `/skill:fabric-fusion` |
|
|
16
|
+
| Work too large for one context window | `/skill:fabric-rlm` |
|
|
17
|
+
| Evidence-gated or transactional local-file mutation | `/skill:fabric-schema` |
|
|
18
|
+
| Persistent material peer advice | `/skill:fabric-advisor` |
|
|
19
|
+
| Persistent progress toward one measurable goal | `/skill:fabric-supervisor` |
|
|
20
|
+
| One command that infers advisor versus supervisor | `/skill:fabric-ambient` |
|
|
21
|
+
| Durable actor team with mailboxes and CAS tasks | `/skill:fabric-swarm` |
|
|
22
|
+
|
|
23
|
+
Prefer the smallest sufficient mechanism. Distinguish workflow/council/fusion by execution shape, RLM by context size, ambient roles by persistence, and swarm by durable multi-actor coordination.
|
|
24
|
+
|
|
25
|
+
## Completion criterion
|
|
26
|
+
|
|
27
|
+
Complete with one of three outputs: (1) `No advanced skill` plus one-sentence reasoning for core work; (2) one advanced recommendation, one-sentence reasoning, and an exact `/skill:...` command that preserves the user’s task as arguments; or (3) one discriminating question when two choices are genuinely tied. Never load or execute a recommended skill yourself.
|