@widnyana/design-thinking 0.0.5 → 0.0.6
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 +1 -0
- package/extensions/design-thinking.ts +43 -28
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -61,6 +61,7 @@ pi -e ./pi-packages/design-thinking
|
|
|
61
61
|
|---|---|
|
|
62
62
|
| `/dt` | Toggle Design Thinking mode. While on, plans and reviews render as Design Graphs. Persists across restarts. |
|
|
63
63
|
| `/dt on\|off\|status` | Set or query the mode explicitly. |
|
|
64
|
+
| `/dt approve\|deny` | Arm/revoke file edits for the next agent run — run `approve` after a presented graph to let the implementation run edit, `deny` to re-lock. |
|
|
64
65
|
| `/dt <prompt>` | Turn the mode **on** (never off), then run `<prompt>` under it — graph and clarifying questions first, implementation after your go-ahead. |
|
|
65
66
|
| `/cg <module \| task>` | Generate a call graph: extract the graph existing code implements, or sketch one for a task. |
|
|
66
67
|
| `/cg-plan <task>` | Design before code — full Design Graph, then implement to match it. |
|
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
* /dt toggle Design Thinking mode
|
|
16
16
|
* /dt on|off set explicitly
|
|
17
17
|
* /dt status show current state
|
|
18
|
+
* /dt approve|deny arm/revoke file edits for the next agent run
|
|
18
19
|
* /dt <prompt> turn mode ON (never off), then run <prompt> as a user
|
|
19
20
|
* message — graph + clarifying questions before implementation
|
|
20
21
|
*
|
|
@@ -42,7 +43,7 @@ const REF_DIR = path.resolve(
|
|
|
42
43
|
"references",
|
|
43
44
|
);
|
|
44
45
|
|
|
45
|
-
/** Compact distilled prompt block injected while active
|
|
46
|
+
/** Compact distilled prompt block injected while active. */
|
|
46
47
|
const DISTILLED = `
|
|
47
48
|
DESIGN THINKING MODE — active.
|
|
48
49
|
Read the problem. Draw the data flow as a call graph. Write code that IS the graph.
|
|
@@ -65,7 +66,9 @@ Rules:
|
|
|
65
66
|
refactor — the model does NOT get to reclassify the request): render the
|
|
66
67
|
Design Graph in Graph Protocol form and any clarifying questions FIRST;
|
|
67
68
|
ZERO file edits until the user approves the design. Reading/exploring code
|
|
68
|
-
first is fine; the FIRST edit is not allowed before the graph.
|
|
69
|
+
first is fine; the FIRST edit is not allowed before the graph. Once the
|
|
70
|
+
user runs /dt approve, edits are armed for the NEXT run: implement the
|
|
71
|
+
approved design without re-presenting the graph.
|
|
69
72
|
- Design, plan, and review answers must render a Design Graph — fixed
|
|
70
73
|
sections: PROBLEM, SHAPES, GRAPH, CARDINALITY, BOUNDARIES, BEHAVIOR, SCOPE,
|
|
71
74
|
TEST LAYERS, VERDICT.
|
|
@@ -82,16 +85,18 @@ Skills load BY NAME into the agent (/skill:<name>); the files above are named
|
|
|
82
85
|
by stem, NOT by skill name. Exact mapping:
|
|
83
86
|
/skill:graph-protocol → protocol.md /skill:design-method → method.md
|
|
84
87
|
/skill:design-graph → design-graph.md
|
|
85
|
-
|
|
86
|
-
|
|
88
|
+
The extension blocks write/edit tools mechanically until the user runs
|
|
89
|
+
/dt approve — it arms the NEXT run, cleared when that run ends. Re-approve
|
|
90
|
+
per implementation round. Present the graph first.
|
|
87
91
|
NEVER read references/<skill-name>.md — no such files exist.
|
|
88
92
|
`.trim();
|
|
89
93
|
|
|
94
|
+
// pi's file-edit tools — the mechanical gate's scope ("file edits"). Bash
|
|
95
|
+
// stays open for read-only exploration. apply_patch/multiedit are Claude Code
|
|
96
|
+
// tool names that never fire in pi; keep this list to real pi mutators.
|
|
90
97
|
const MUTATING_TOOLS: Record<string, true> = {
|
|
91
98
|
write: true,
|
|
92
99
|
edit: true,
|
|
93
|
-
apply_patch: true,
|
|
94
|
-
multiedit: true,
|
|
95
100
|
};
|
|
96
101
|
|
|
97
102
|
interface DtState {
|
|
@@ -99,12 +104,13 @@ interface DtState {
|
|
|
99
104
|
}
|
|
100
105
|
|
|
101
106
|
const GATE_REASON =
|
|
102
|
-
"Design Thinking mode is ON: present the Design Graph (Graph Protocol) and wait for user approval before file edits. The user
|
|
107
|
+
"Design Thinking mode is ON: present the Design Graph (Graph Protocol) and wait for user approval before file edits. The user arms the NEXT run with /dt approve; the approval clears when that run ends.";
|
|
103
108
|
|
|
104
109
|
export default function designThinkingExtension(pi: ExtensionAPI) {
|
|
105
110
|
let enabled = false;
|
|
106
|
-
//
|
|
107
|
-
|
|
111
|
+
// Armed by /dt approve for the NEXT agent run. Cleared when that run ends
|
|
112
|
+
// (agent_end), by /dt deny, or when the mode turns off. Not persisted.
|
|
113
|
+
let editsApproved = false;
|
|
108
114
|
|
|
109
115
|
function applyStatus(ctx: ExtensionContext) {
|
|
110
116
|
ctx.ui.setStatus(
|
|
@@ -143,28 +149,34 @@ export default function designThinkingExtension(pi: ExtensionAPI) {
|
|
|
143
149
|
ctx.ui.setStatus("design-thinking", undefined);
|
|
144
150
|
});
|
|
145
151
|
|
|
146
|
-
// /dt — the Design Thinking tool. Toggles mode
|
|
152
|
+
// /dt — the Design Thinking tool. Toggles mode; on|off|status set/query;
|
|
153
|
+
// approve|deny arm/revoke file edits; anything else runs as a prompt with mode on.
|
|
147
154
|
pi.registerCommand("dt", {
|
|
148
|
-
description: "Design Thinking mode: /dt toggles, on|off|status set/query, approve
|
|
155
|
+
description: "Design Thinking mode: /dt toggles, on|off|status set/query, approve arms the next run for file edits, deny revokes; anything else runs as a prompt with mode on",
|
|
149
156
|
handler: async (args, ctx) => {
|
|
150
157
|
const arg = (args ?? "").trim();
|
|
151
158
|
const lower = arg.toLowerCase();
|
|
152
159
|
|
|
153
160
|
if (lower === "status") {
|
|
154
|
-
ctx.ui.notify(`Design Thinking mode: ${enabled ? "on" : "off"}${
|
|
161
|
+
ctx.ui.notify(`Design Thinking mode: ${enabled ? "on" : "off"}${editsApproved ? " (file edits armed for the next run)" : ""}`, "info");
|
|
155
162
|
return;
|
|
156
163
|
}
|
|
157
164
|
|
|
158
|
-
// /dt approve|deny — explicit user unlock/lock for the CURRENT turn.
|
|
159
165
|
if (lower === "approve") {
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
166
|
+
if (!enabled) {
|
|
167
|
+
ctx.ui.notify("Design Thinking is OFF — nothing to approve. Run /dt on first.", "info");
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
170
|
+
editsApproved = true;
|
|
171
|
+
ctx.ui.notify("Design Thinking: file edits armed (current or next run) — it may implement the approved design without re-presenting the graph", "info");
|
|
172
|
+
return;
|
|
165
173
|
}
|
|
166
174
|
if (lower === "deny") {
|
|
167
|
-
|
|
175
|
+
if (!editsApproved) {
|
|
176
|
+
ctx.ui.notify("Design Thinking: no approval in effect — file edits are already blocked", "info");
|
|
177
|
+
return;
|
|
178
|
+
}
|
|
179
|
+
editsApproved = false;
|
|
168
180
|
ctx.ui.notify("Design Thinking: file edits blocked again", "info");
|
|
169
181
|
return;
|
|
170
182
|
}
|
|
@@ -173,7 +185,7 @@ export default function designThinkingExtension(pi: ExtensionAPI) {
|
|
|
173
185
|
// mode and always turns the mode ON (never toggles it off); bare /dt toggles.
|
|
174
186
|
const prompt = /^(on|off|status)$/.test(lower) ? "" : arg;
|
|
175
187
|
enabled = lower === "on" || prompt ? true : lower === "off" ? false : !enabled;
|
|
176
|
-
if (!enabled)
|
|
188
|
+
if (!enabled) editsApproved = false;
|
|
177
189
|
persist();
|
|
178
190
|
applyStatus(ctx);
|
|
179
191
|
ctx.ui.notify(
|
|
@@ -193,22 +205,25 @@ export default function designThinkingExtension(pi: ExtensionAPI) {
|
|
|
193
205
|
},
|
|
194
206
|
});
|
|
195
207
|
|
|
196
|
-
// While active, append the distilled block to the system prompt every
|
|
208
|
+
// While active, append the distilled block to the system prompt every run.
|
|
197
209
|
pi.on("before_agent_start", async (event) => {
|
|
198
|
-
// A new user turn starts a fresh agent run: the approval from the
|
|
199
|
-
// previous turn does not carry over.
|
|
200
|
-
approvedForTurn = false;
|
|
201
210
|
if (!enabled) return undefined;
|
|
202
211
|
return {
|
|
203
212
|
systemPrompt: event.systemPrompt + "\n\n" + DISTILLED + "\n",
|
|
204
213
|
};
|
|
205
214
|
});
|
|
206
215
|
|
|
207
|
-
//
|
|
208
|
-
//
|
|
209
|
-
|
|
216
|
+
// An approved run consumes the approval: clear it when the run ends so
|
|
217
|
+
// later runs are gated again until the user re-approves with /dt approve.
|
|
218
|
+
pi.on("agent_end", async () => {
|
|
219
|
+
editsApproved = false;
|
|
220
|
+
});
|
|
221
|
+
|
|
222
|
+
// Hard gate: while enabled, file-edit tools are blocked until the user
|
|
223
|
+
// arms the next run with /dt approve. Prompt-level rules alone proved
|
|
224
|
+
// insufficient — this is the mechanical backstop.
|
|
210
225
|
pi.on("tool_call", async (event) => {
|
|
211
|
-
if (!enabled ||
|
|
226
|
+
if (!enabled || editsApproved) return undefined;
|
|
212
227
|
if (!MUTATING_TOOLS[event.toolName]) return undefined;
|
|
213
228
|
return { block: true, reason: GATE_REASON };
|
|
214
229
|
});
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@widnyana/design-thinking",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.6",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Design Thinking · Design Graph · Graph Protocol — a stack-agnostic design methodology for pi. Turns every plan, review, and refactor into an annotated call graph. Method originally by r17x; generalized to a pi package by widnyana.",
|
|
6
6
|
"author": {
|