create-agentic-workspace 0.4.0 → 0.4.1
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/bin/create-agentic-workspace.mjs +3 -2
- package/package.json +2 -2
- package/permission-floor.json +1 -1
- package/src/preview.mjs +14 -3
- package/src/run.mjs +20 -2
|
@@ -20,7 +20,9 @@ if (rawArgv.length > 0 && !rawArgv[0].startsWith('--')) {
|
|
|
20
20
|
argv = ['--dir', rawArgv[0], ...rawArgv.slice(1)];
|
|
21
21
|
}
|
|
22
22
|
|
|
23
|
-
|
|
23
|
+
// runCli streams every line to `output` as it is produced (ER #95), so the returned string is a
|
|
24
|
+
// transcript for callers, not something to print again here.
|
|
25
|
+
const { exitCode } = await runCli(argv, {
|
|
24
26
|
cwd: process.cwd(),
|
|
25
27
|
isTTY: Boolean(process.stdin.isTTY),
|
|
26
28
|
input: process.stdin,
|
|
@@ -29,5 +31,4 @@ const { exitCode, output } = await runCli(argv, {
|
|
|
29
31
|
pkgDir,
|
|
30
32
|
});
|
|
31
33
|
|
|
32
|
-
process.stdout.write(`${output}\n`);
|
|
33
34
|
process.exitCode = exitCode;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "create-agentic-workspace",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.1",
|
|
4
4
|
"description": "The pre-session bootstrap wizard for an Agentic Foundry workspace: declares (never grants) the permission floor, absorbs foundry-bootstrap.sh's out-of-session identity wiring, and scaffolds a seven-file schema-valid workspace. Zero dependencies, no lifecycle scripts, no telemetry.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
@@ -34,7 +34,7 @@
|
|
|
34
34
|
"marketplace_name": "agentic-foundry",
|
|
35
35
|
"marketplace_repo": "lukasrepublic/agentic-foundry",
|
|
36
36
|
"plugin_name": "foundry",
|
|
37
|
-
"plugin_version": "1.4.
|
|
37
|
+
"plugin_version": "1.4.1",
|
|
38
38
|
"pins_researched": "2026-08-02"
|
|
39
39
|
}
|
|
40
40
|
}
|
package/permission-floor.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"schema_version": 1,
|
|
3
3
|
"plugin_root_glob": "~/.claude/plugins/cache/*/foundry/*",
|
|
4
|
-
"generated_for_plugin_version": "1.4.
|
|
4
|
+
"generated_for_plugin_version": "1.4.1",
|
|
5
5
|
"entries": [
|
|
6
6
|
{
|
|
7
7
|
"rule": "Bash(~/.claude/plugins/cache/*/foundry/*/scripts/foundry-acceptance-contract-validate.py:*)",
|
package/src/preview.mjs
CHANGED
|
@@ -35,10 +35,21 @@ export function renderPreview({ plan, machineScopeWrites, map }) {
|
|
|
35
35
|
// previewed and nothing else; `git init` would be an un-previewed side effect, and the choice of
|
|
36
36
|
// remote is genuinely the reader's. `create-vite` prints its next steps the same way, for the same
|
|
37
37
|
// reason. Telling keeps the promise; doing would quietly break it.
|
|
38
|
-
|
|
39
|
-
|
|
38
|
+
// `reconciledExisting` is true when --reconcile-floor actually WROTE rules into a workspace that
|
|
39
|
+
// already existed. That case inverts the sentence below, and the inversion was observed live: an
|
|
40
|
+
// operator reconciled an already-trusted workspace, restarted the session, and 42 wildcarded allow
|
|
41
|
+
// rules took effect with NO trust dialog at all. The dialog is the consent ceremony for a workspace
|
|
42
|
+
// the platform has not yet trusted; for one it already trusts, THIS CLI'S OWN preview-and-confirm is
|
|
43
|
+
// the only consent moment there will be. Saying otherwise points the operator at a review that will
|
|
44
|
+
// not happen — the one claim this tool cannot afford to get wrong, since "declares, never grants" is
|
|
45
|
+
// its whole posture. (bootstrap-cli R8, answered 2026-08-12.)
|
|
46
|
+
export const TRUST_HANDOFF_TEXT = (dir, { isGitRepo = true, reconciledExisting = false } = {}) => `
|
|
47
|
+
${reconciledExisting ? `The workspace has been written, and the permission-floor rules above were added to a workspace
|
|
48
|
+
that is ALREADY TRUSTED. On that path there is no second consent ceremony: the preview and the
|
|
49
|
+
confirmation you just gave were it, and the added \`allow\` rules are in effect from the next
|
|
50
|
+
session onward with no dialog. Re-read the list above if you have not.` : `The workspace has been written. The permission floor above is a declaration, not a grant: the
|
|
40
51
|
platform's trust dialog is the consent ceremony, and the \`allow\` rules take effect only after
|
|
41
|
-
you accept it — the dialog lists them
|
|
52
|
+
you accept it — the dialog lists them.`}
|
|
42
53
|
|
|
43
54
|
cd ${dir}${isGitRepo ? '' : `
|
|
44
55
|
git init && git add -A && git commit -m 'workspace seed'
|
package/src/run.mjs
CHANGED
|
@@ -93,7 +93,20 @@ function expandPluginRootGlob(glob, homeDir) {
|
|
|
93
93
|
* caught and turned into a refusal-shaped exit 1 (or, for a bug, exit 1 with the error message). */
|
|
94
94
|
export async function runCli(argv, { cwd, isTTY, input, output, homeDir, pkgDir }) {
|
|
95
95
|
const lines = [];
|
|
96
|
-
|
|
96
|
+
// ER #95 — STREAM, don't accumulate. This used to only push into `lines`, which bin printed
|
|
97
|
+
// after runCli returned, so every prompt fired against a blank screen: "Write the workspace as
|
|
98
|
+
// previewed above? [y/N]" was asked with nothing above it, and the preview — the file plan, the
|
|
99
|
+
// machine-scope writes OUTSIDE the target root, and the 62 permission rules — scrolled past
|
|
100
|
+
// afterwards. A confirmation whose subject is not yet on screen cannot be informed consent, and
|
|
101
|
+
// its mere presence claims a review that did not happen.
|
|
102
|
+
//
|
|
103
|
+
// It became load-bearing with --reconcile-floor. R8 was answered live: reconciling an
|
|
104
|
+
// already-trusted workspace fires NO trust dialog, so this prompt is the ONLY consent moment
|
|
105
|
+
// there is. `lines` is still accumulated because runCli's return contract exposes it.
|
|
106
|
+
const print = (s) => {
|
|
107
|
+
lines.push(s);
|
|
108
|
+
output.write(`${s}\n`);
|
|
109
|
+
};
|
|
97
110
|
|
|
98
111
|
try {
|
|
99
112
|
let parsed;
|
|
@@ -254,7 +267,12 @@ export async function runCli(argv, { cwd, isTTY, input, output, homeDir, pkgDir
|
|
|
254
267
|
// on the path is the check that covers both — a directory-only test would tell a worktree user
|
|
255
268
|
// to re-init a repository they already have.
|
|
256
269
|
const isGitRepo = fs.existsSync(path.join(targetRoot, '.git'));
|
|
257
|
-
print(TRUST_HANDOFF_TEXT(targetRoot, {
|
|
270
|
+
print(TRUST_HANDOFF_TEXT(targetRoot, {
|
|
271
|
+
isGitRepo,
|
|
272
|
+
// only when a reconcile actually wrote — a dry run, a no-op second run, or a plain scaffold
|
|
273
|
+
// all keep the standard hand-off
|
|
274
|
+
reconciledExisting: Boolean(floorPlan && floorPlan.total > 0),
|
|
275
|
+
}));
|
|
258
276
|
|
|
259
277
|
return { exitCode: exitCodeForPlan(plan), output: lines.join('\n') };
|
|
260
278
|
} catch (e) {
|