@codyswann/lisa 2.230.0 → 2.231.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/dist/cli/ui-cmd.d.ts.map +1 -1
- package/dist/cli/ui-cmd.js +8 -2
- package/dist/cli/ui-cmd.js.map +1 -1
- package/dist/cli/ui-config-write.d.ts +13 -0
- package/dist/cli/ui-config-write.d.ts.map +1 -0
- package/dist/cli/ui-config-write.js +283 -0
- package/dist/cli/ui-config-write.js.map +1 -0
- package/package.json +1 -1
- package/plugins/lisa/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-agy/plugin.json +1 -1
- package/plugins/lisa-cdk/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-cdk/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-cdk-agy/plugin.json +1 -1
- package/plugins/lisa-cdk-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-cdk-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-expo/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-expo/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-expo-agy/plugin.json +1 -1
- package/plugins/lisa-expo-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-expo-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-harper-fabric/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-harper-fabric/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-harper-fabric-agy/plugin.json +1 -1
- package/plugins/lisa-harper-fabric-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-harper-fabric-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-nestjs/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-nestjs/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-nestjs-agy/plugin.json +1 -1
- package/plugins/lisa-nestjs-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-nestjs-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-openclaw/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-openclaw/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-openclaw-agy/plugin.json +1 -1
- package/plugins/lisa-openclaw-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-openclaw-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-phaser/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-phaser/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-phaser-agy/plugin.json +1 -1
- package/plugins/lisa-phaser-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-phaser-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-rails/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-rails/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-rails-agy/plugin.json +1 -1
- package/plugins/lisa-rails-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-rails-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-typescript/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-typescript/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-typescript-agy/plugin.json +1 -1
- package/plugins/lisa-typescript-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-typescript-cursor/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-wiki/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-wiki/.codex-plugin/plugin.json +1 -1
- package/plugins/lisa-wiki-agy/plugin.json +1 -1
- package/plugins/lisa-wiki-copilot/.claude-plugin/plugin.json +1 -1
- package/plugins/lisa-wiki-cursor/.claude-plugin/plugin.json +1 -1
- package/ui/index.html +71 -25
package/dist/cli/ui-cmd.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ui-cmd.d.ts","sourceRoot":"","sources":["../../src/cli/ui-cmd.ts"],"names":[],"mappings":"AAWA,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AAIlC,OAAO,EAAgB,KAAK,UAAU,EAAE,MAAM,sBAAsB,CAAC;AAGrE,OAAO,EAEL,KAAK,uBAAuB,EAC7B,MAAM,yBAAyB,CAAC;AACjC,OAAO,EAKL,KAAK,WAAW,EACjB,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"ui-cmd.d.ts","sourceRoot":"","sources":["../../src/cli/ui-cmd.ts"],"names":[],"mappings":"AAWA,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AAIlC,OAAO,EAAgB,KAAK,UAAU,EAAE,MAAM,sBAAsB,CAAC;AAGrE,OAAO,EAEL,KAAK,uBAAuB,EAC7B,MAAM,yBAAyB,CAAC;AACjC,OAAO,EAKL,KAAK,WAAW,EACjB,MAAM,gBAAgB,CAAC;AAExB,OAAO,EACL,qBAAqB,EACrB,QAAQ,EACR,KAAK,eAAe,EACpB,KAAK,eAAe,EACpB,KAAK,WAAW,EAChB,KAAK,WAAW,GACjB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,wBAAwB,EAAE,MAAM,yBAAyB,CAAC;AAEnE,6CAA6C;AAC7C,eAAO,MAAM,eAAe,OAAO,CAAC;AAKpC,iCAAiC;AACjC,MAAM,WAAW,YAAY;IAC3B,4EAA4E;IAC5E,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IACvB,mEAAmE;IACnE,QAAQ,CAAC,IAAI,CAAC,EAAE,OAAO,CAAC;CACzB;AAED,sDAAsD;AACtD,MAAM,WAAW,qBAAqB;IACpC,gDAAgD;IAChD,QAAQ,CAAC,MAAM,CAAC,EAAE,SAAS,WAAW,EAAE,CAAC;CAC1C;AAYD;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAUnD;AAmBD;;;;;;;GAOG;AACH,wBAAgB,gBAAgB,CAC9B,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,UAAU,EAClB,iBAAiB,GAAE,uBAIlB,GACA,MAAM,CAQR;AAgKD;;;;;;GAMG;AACH,wBAAsB,KAAK,CACzB,UAAU,EAAE,MAAM,GAAG,SAAS,EAC9B,OAAO,GAAE,YAAiB,EAC1B,YAAY,GAAE,qBAA0B,GACvC,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC,CAkCtB"}
|
package/dist/cli/ui-cmd.js
CHANGED
|
@@ -18,6 +18,7 @@ import { deepMerge, readJsonOrNull } from "../utils/index.js";
|
|
|
18
18
|
import { printSyncReport } from "./sync-cmd.js";
|
|
19
19
|
import { inspectRemoteEnvironment, } from "./remote-environment.js";
|
|
20
20
|
import { createGithubAuthProbe, readStatusSnapshot, validateStatusProbes, } from "./ui-status.js";
|
|
21
|
+
import { serveConfigWrite } from "./ui-config-write.js";
|
|
21
22
|
export { createGithubAuthProbe, runProbe, } from "./ui-status.js";
|
|
22
23
|
export { inspectRemoteEnvironment } from "./remote-environment.js";
|
|
23
24
|
/** Default port for the settings console. */
|
|
@@ -185,9 +186,10 @@ function isLoopbackHost(host) {
|
|
|
185
186
|
* Build the request handler after validating the complete probe registry.
|
|
186
187
|
* @param page - Hydrated settings console HTML
|
|
187
188
|
* @param probes - Live-status probes registered for this server
|
|
189
|
+
* @param destDir - Project root served by this UI process
|
|
188
190
|
* @returns Loopback HTTP request handler
|
|
189
191
|
*/
|
|
190
|
-
function createUiRequestHandler(page, probes) {
|
|
192
|
+
function createUiRequestHandler(page, probes, destDir) {
|
|
191
193
|
const readSnapshot = createStatusSnapshotReader(probes);
|
|
192
194
|
validateStatusProbes(probes);
|
|
193
195
|
return (request, response) => {
|
|
@@ -206,6 +208,10 @@ function createUiRequestHandler(page, probes) {
|
|
|
206
208
|
serveStatus(request, response, readSnapshot);
|
|
207
209
|
return;
|
|
208
210
|
}
|
|
211
|
+
if (pathname === "/api/config") {
|
|
212
|
+
serveConfigWrite(request, response, destDir);
|
|
213
|
+
return;
|
|
214
|
+
}
|
|
209
215
|
if (pathname === "/" || pathname === "/index.html") {
|
|
210
216
|
response.writeHead(200, { "content-type": "text/html; charset=utf-8" });
|
|
211
217
|
response.end(page);
|
|
@@ -239,7 +245,7 @@ export async function runUi(targetPath, options = {}, dependencies = {}) {
|
|
|
239
245
|
const remoteEnvironment = await inspectRemoteEnvironment(destDir, config, getProcessEnvironment());
|
|
240
246
|
const page = injectLiveConfig(html, config, remoteEnvironment);
|
|
241
247
|
const probes = dependencies.probes ?? [createGithubAuthProbe(destDir)];
|
|
242
|
-
const server = http.createServer(createUiRequestHandler(page, probes));
|
|
248
|
+
const server = http.createServer(createUiRequestHandler(page, probes, destDir));
|
|
243
249
|
await new Promise(resolve => {
|
|
244
250
|
server.listen(port, "127.0.0.1", resolve);
|
|
245
251
|
});
|
package/dist/cli/ui-cmd.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ui-cmd.js","sourceRoot":"","sources":["../../src/cli/ui-cmd.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"ui-cmd.js","sourceRoot":"","sources":["../../src/cli/ui-cmd.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Same-origin config write endpoint for `lisa ui`.
|
|
3
|
+
* @module cli/ui-config-write
|
|
4
|
+
*/
|
|
5
|
+
import * as http from "node:http";
|
|
6
|
+
/**
|
|
7
|
+
* Serve the same-origin committed-config write endpoint.
|
|
8
|
+
* @param request - Incoming loopback request
|
|
9
|
+
* @param response - Response associated with the request
|
|
10
|
+
* @param destDir - Project root whose committed config is written
|
|
11
|
+
*/
|
|
12
|
+
export declare function serveConfigWrite(request: http.IncomingMessage, response: http.ServerResponse, destDir: string): void;
|
|
13
|
+
//# sourceMappingURL=ui-config-write.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ui-config-write.d.ts","sourceRoot":"","sources":["../../src/cli/ui-config-write.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AA0QlC;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAC9B,OAAO,EAAE,IAAI,CAAC,eAAe,EAC7B,QAAQ,EAAE,IAAI,CAAC,cAAc,EAC7B,OAAO,EAAE,MAAM,GACd,IAAI,CAsDN"}
|
|
@@ -0,0 +1,283 @@
|
|
|
1
|
+
import * as path from "node:path";
|
|
2
|
+
import { readFile } from "node:fs/promises";
|
|
3
|
+
import { isJsonObject, setAtPath, } from "../sync/json-path.js";
|
|
4
|
+
import { writeJson } from "../utils/index.js";
|
|
5
|
+
const CONFIG_FILE = ".lisa.config.json";
|
|
6
|
+
const JSON_CONTENT_TYPE = "application/json; charset=utf-8";
|
|
7
|
+
const MAX_CONFIG_WRITE_BYTES = 128 * 1024;
|
|
8
|
+
const NO_STORE = "no-store";
|
|
9
|
+
const TEXT_CONTENT_TYPE = "text/plain; charset=utf-8";
|
|
10
|
+
const configWriteQueues = new Map();
|
|
11
|
+
/** Error raised for malformed request bodies that should return 400. */
|
|
12
|
+
class RequestBodyError extends Error {
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Read the project's committed config file.
|
|
16
|
+
* @param destDir - Project root
|
|
17
|
+
* @returns Committed config object, or an empty config if absent/malformed
|
|
18
|
+
*/
|
|
19
|
+
async function readCommittedConfig(destDir) {
|
|
20
|
+
const configPath = path.join(destDir, CONFIG_FILE);
|
|
21
|
+
try {
|
|
22
|
+
const committed = JSON.parse(await readFile(configPath, "utf8"));
|
|
23
|
+
if (!isJsonObject(committed)) {
|
|
24
|
+
throw new Error(`${CONFIG_FILE} must contain a JSON object`);
|
|
25
|
+
}
|
|
26
|
+
return committed;
|
|
27
|
+
}
|
|
28
|
+
catch (error) {
|
|
29
|
+
if (typeof error === "object" &&
|
|
30
|
+
error !== null &&
|
|
31
|
+
"code" in error &&
|
|
32
|
+
error.code === "ENOENT") {
|
|
33
|
+
return {};
|
|
34
|
+
}
|
|
35
|
+
throw error;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Restrict loopback origins to the authority advertised by `lisa ui`.
|
|
40
|
+
* @param host - Origin URL host
|
|
41
|
+
* @returns Whether the authority is 127.0.0.1 with an optional valid port
|
|
42
|
+
*/
|
|
43
|
+
function isLoopbackHost(host) {
|
|
44
|
+
if (host === "127.0.0.1") {
|
|
45
|
+
return true;
|
|
46
|
+
}
|
|
47
|
+
const prefix = "127.0.0.1:";
|
|
48
|
+
if (!host.startsWith(prefix)) {
|
|
49
|
+
return false;
|
|
50
|
+
}
|
|
51
|
+
const portText = host.slice(prefix.length);
|
|
52
|
+
const digitsOnly = Array.from(portText).every(character => character >= "0" && character <= "9");
|
|
53
|
+
const port = Number(portText);
|
|
54
|
+
return (portText.length > 0 &&
|
|
55
|
+
portText.length <= 5 &&
|
|
56
|
+
digitsOnly &&
|
|
57
|
+
port > 0 &&
|
|
58
|
+
port <= 65_535);
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Reject request origins that are not the advertised loopback listener.
|
|
62
|
+
* @param origin - Incoming Origin header
|
|
63
|
+
* @param host - Incoming Host header
|
|
64
|
+
* @returns Whether the origin is the exact http://127.0.0.1 listener authority
|
|
65
|
+
*/
|
|
66
|
+
function isExpectedLoopbackOrigin(origin, host) {
|
|
67
|
+
if (origin === undefined || host === undefined) {
|
|
68
|
+
return false;
|
|
69
|
+
}
|
|
70
|
+
try {
|
|
71
|
+
const parsed = new URL(origin);
|
|
72
|
+
return (origin === parsed.origin &&
|
|
73
|
+
parsed.protocol === "http:" &&
|
|
74
|
+
parsed.host === host &&
|
|
75
|
+
isLoopbackHost(parsed.host));
|
|
76
|
+
}
|
|
77
|
+
catch {
|
|
78
|
+
return false;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Check whether an unknown value can be serialized as JSON without dropping
|
|
83
|
+
* fields.
|
|
84
|
+
* @param value - Candidate payload value
|
|
85
|
+
* @returns Whether the value is JSON-compatible
|
|
86
|
+
*/
|
|
87
|
+
function isJsonValue(value) {
|
|
88
|
+
if (value === null ||
|
|
89
|
+
typeof value === "string" ||
|
|
90
|
+
typeof value === "number" ||
|
|
91
|
+
typeof value === "boolean") {
|
|
92
|
+
return Number.isFinite(value) || typeof value !== "number";
|
|
93
|
+
}
|
|
94
|
+
if (Array.isArray(value)) {
|
|
95
|
+
return value.every(isJsonValue);
|
|
96
|
+
}
|
|
97
|
+
if (isJsonObject(value)) {
|
|
98
|
+
return Object.values(value).every(isJsonValue);
|
|
99
|
+
}
|
|
100
|
+
return false;
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Validate a dot-path config key before it can be written to disk.
|
|
104
|
+
* @param key - Candidate config key
|
|
105
|
+
* @returns Specific validation error, or undefined when valid
|
|
106
|
+
*/
|
|
107
|
+
function validateConfigKey(key) {
|
|
108
|
+
if (key.trim() !== key || key.length === 0) {
|
|
109
|
+
return "Config change keys must be non-empty dot paths";
|
|
110
|
+
}
|
|
111
|
+
const segments = key.split(".");
|
|
112
|
+
if (segments.some(segment => segment.length === 0)) {
|
|
113
|
+
return `Config change key "${key}" contains an empty path segment`;
|
|
114
|
+
}
|
|
115
|
+
const unsafe = new Set(["__proto__", "constructor", "prototype"]);
|
|
116
|
+
if (segments.some(segment => unsafe.has(segment))) {
|
|
117
|
+
return `Config change key "${key}" is not writable`;
|
|
118
|
+
}
|
|
119
|
+
return undefined;
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* Validate one sparse config-write entry.
|
|
123
|
+
* @param key - Dot-path config key
|
|
124
|
+
* @param change - Candidate JSON value
|
|
125
|
+
* @returns Specific validation error, or undefined when valid
|
|
126
|
+
*/
|
|
127
|
+
function validateChangeEntry(key, change) {
|
|
128
|
+
const keyError = validateConfigKey(key);
|
|
129
|
+
if (keyError !== undefined) {
|
|
130
|
+
return keyError;
|
|
131
|
+
}
|
|
132
|
+
if (!isJsonValue(change)) {
|
|
133
|
+
return `Config change "${key}" must be JSON-compatible`;
|
|
134
|
+
}
|
|
135
|
+
return undefined;
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* Parse and validate the sparse config-write payload.
|
|
139
|
+
* @param value - Parsed JSON request body
|
|
140
|
+
* @returns Dot-path changes, or a specific validation error
|
|
141
|
+
*/
|
|
142
|
+
function parseConfigWritePayload(value) {
|
|
143
|
+
if (!isJsonObject(value)) {
|
|
144
|
+
return { error: "Payload must be a JSON object" };
|
|
145
|
+
}
|
|
146
|
+
const changes = value.changes;
|
|
147
|
+
if (!isJsonObject(changes)) {
|
|
148
|
+
return { error: "Payload must include a changes object" };
|
|
149
|
+
}
|
|
150
|
+
const entries = Object.entries(changes);
|
|
151
|
+
if (entries.length === 0) {
|
|
152
|
+
return { error: "Payload changes must include at least one config key" };
|
|
153
|
+
}
|
|
154
|
+
const error = entries
|
|
155
|
+
.map(([key, change]) => validateChangeEntry(key, change))
|
|
156
|
+
.find(Boolean);
|
|
157
|
+
if (error !== undefined) {
|
|
158
|
+
return { error };
|
|
159
|
+
}
|
|
160
|
+
return { changes: Object.fromEntries(entries) };
|
|
161
|
+
}
|
|
162
|
+
/**
|
|
163
|
+
* Read a bounded JSON body from an incoming request.
|
|
164
|
+
* @param request - Incoming HTTP request
|
|
165
|
+
* @returns Parsed JSON body
|
|
166
|
+
*/
|
|
167
|
+
async function readJsonBody(request) {
|
|
168
|
+
// eslint-disable-next-line functional/no-let -- bounded stream aggregation
|
|
169
|
+
let received = 0;
|
|
170
|
+
// eslint-disable-next-line functional/no-let -- bounded stream aggregation
|
|
171
|
+
let chunks = [];
|
|
172
|
+
for await (const chunk of request) {
|
|
173
|
+
const buffer = Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk);
|
|
174
|
+
received += buffer.byteLength;
|
|
175
|
+
if (received > MAX_CONFIG_WRITE_BYTES) {
|
|
176
|
+
throw new RequestBodyError("Payload exceeds 128 KiB limit");
|
|
177
|
+
}
|
|
178
|
+
chunks = [...chunks, buffer];
|
|
179
|
+
}
|
|
180
|
+
if (chunks.length === 0) {
|
|
181
|
+
throw new RequestBodyError("Payload body is required");
|
|
182
|
+
}
|
|
183
|
+
try {
|
|
184
|
+
return JSON.parse(Buffer.concat(chunks).toString("utf8"));
|
|
185
|
+
}
|
|
186
|
+
catch {
|
|
187
|
+
throw new RequestBodyError("Payload body must be valid JSON");
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
/**
|
|
191
|
+
* Serialize committed-config writes per project root.
|
|
192
|
+
* @param destDir - Project root whose committed config is being written
|
|
193
|
+
* @param operation - Read-modify-write operation to run after prior writes
|
|
194
|
+
* @returns Result of the queued operation
|
|
195
|
+
*/
|
|
196
|
+
async function withConfigWriteLock(destDir, operation) {
|
|
197
|
+
const previous = configWriteQueues.get(destDir) ?? Promise.resolve();
|
|
198
|
+
const running = previous.catch(() => undefined).then(operation);
|
|
199
|
+
const marker = running.then(() => undefined, () => undefined);
|
|
200
|
+
// eslint-disable-next-line functional/immutable-data -- per-project async write queue
|
|
201
|
+
configWriteQueues.set(destDir, marker);
|
|
202
|
+
try {
|
|
203
|
+
return await running;
|
|
204
|
+
}
|
|
205
|
+
finally {
|
|
206
|
+
if (configWriteQueues.get(destDir) === marker) {
|
|
207
|
+
// eslint-disable-next-line functional/immutable-data -- queue entry is complete
|
|
208
|
+
configWriteQueues.delete(destDir);
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
/**
|
|
213
|
+
* Write a sparse config payload after all validation has completed.
|
|
214
|
+
* @param destDir - Project root whose committed config is written
|
|
215
|
+
* @param changes - Validated dot-path changes
|
|
216
|
+
* @returns The updated committed config
|
|
217
|
+
*/
|
|
218
|
+
async function writeConfigChanges(destDir, changes) {
|
|
219
|
+
return await withConfigWriteLock(destDir, async () => {
|
|
220
|
+
const original = await readCommittedConfig(destDir);
|
|
221
|
+
const next = Object.entries(changes).reduce((state, [key, value]) => setAtPath(state, key, value), original);
|
|
222
|
+
await writeJson(path.join(destDir, CONFIG_FILE), next);
|
|
223
|
+
return next;
|
|
224
|
+
});
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* Serve the same-origin committed-config write endpoint.
|
|
228
|
+
* @param request - Incoming loopback request
|
|
229
|
+
* @param response - Response associated with the request
|
|
230
|
+
* @param destDir - Project root whose committed config is written
|
|
231
|
+
*/
|
|
232
|
+
export function serveConfigWrite(request, response, destDir) {
|
|
233
|
+
if (request.method !== "POST") {
|
|
234
|
+
response.writeHead(405, {
|
|
235
|
+
allow: "POST",
|
|
236
|
+
"cache-control": NO_STORE,
|
|
237
|
+
"content-type": TEXT_CONTENT_TYPE,
|
|
238
|
+
});
|
|
239
|
+
response.end("Method not allowed");
|
|
240
|
+
return;
|
|
241
|
+
}
|
|
242
|
+
if (!isExpectedLoopbackOrigin(request.headers.origin, request.headers.host)) {
|
|
243
|
+
response.writeHead(403, {
|
|
244
|
+
"cache-control": NO_STORE,
|
|
245
|
+
"content-type": JSON_CONTENT_TYPE,
|
|
246
|
+
});
|
|
247
|
+
response.end(JSON.stringify({
|
|
248
|
+
error: "Write requests must come from http://127.0.0.1",
|
|
249
|
+
}));
|
|
250
|
+
return;
|
|
251
|
+
}
|
|
252
|
+
void readJsonBody(request)
|
|
253
|
+
.then(parseConfigWritePayload)
|
|
254
|
+
.then(async (parsed) => {
|
|
255
|
+
if ("error" in parsed) {
|
|
256
|
+
response.writeHead(400, {
|
|
257
|
+
"cache-control": NO_STORE,
|
|
258
|
+
"content-type": JSON_CONTENT_TYPE,
|
|
259
|
+
});
|
|
260
|
+
response.end(JSON.stringify({ error: parsed.error }));
|
|
261
|
+
return;
|
|
262
|
+
}
|
|
263
|
+
const committed = await writeConfigChanges(destDir, parsed.changes);
|
|
264
|
+
response.writeHead(200, {
|
|
265
|
+
"cache-control": NO_STORE,
|
|
266
|
+
"content-type": JSON_CONTENT_TYPE,
|
|
267
|
+
});
|
|
268
|
+
response.end(JSON.stringify({ ok: true, config: committed }));
|
|
269
|
+
})
|
|
270
|
+
.catch(error => {
|
|
271
|
+
const isRequestBodyError = error instanceof RequestBodyError;
|
|
272
|
+
response.writeHead(isRequestBodyError ? 400 : 500, {
|
|
273
|
+
"cache-control": NO_STORE,
|
|
274
|
+
"content-type": JSON_CONTENT_TYPE,
|
|
275
|
+
});
|
|
276
|
+
response.end(JSON.stringify({
|
|
277
|
+
error: isRequestBodyError
|
|
278
|
+
? error.message
|
|
279
|
+
: "Unable to write Lisa config",
|
|
280
|
+
}));
|
|
281
|
+
});
|
|
282
|
+
}
|
|
283
|
+
//# sourceMappingURL=ui-config-write.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ui-config-write.js","sourceRoot":"","sources":["../../src/cli/ui-config-write.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -102,7 +102,7 @@
|
|
|
102
102
|
"form-data": ">=4.0.6"
|
|
103
103
|
},
|
|
104
104
|
"name": "@codyswann/lisa",
|
|
105
|
-
"version": "2.
|
|
105
|
+
"version": "2.231.0",
|
|
106
106
|
"description": "Claude Code governance framework that applies guardrails, guidance, and automated enforcement to projects",
|
|
107
107
|
"main": "dist/index.js",
|
|
108
108
|
"exports": {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "lisa-openclaw",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.231.0",
|
|
4
4
|
"description": "Connect staff roles to Telegram or Slack via OpenClaw — facilitator/specialist hub-and-spoke routing and repo-coding topics, for Claude Code and Codex",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "Cody Swann"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "lisa-openclaw",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.231.0",
|
|
4
4
|
"description": "Connect staff roles to Telegram or Slack via OpenClaw — facilitator/specialist hub-and-spoke routing and repo-coding topics, across Claude and Codex.",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "Cody Swann"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "lisa-openclaw",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.231.0",
|
|
4
4
|
"description": "Connect staff roles to Telegram or Slack via OpenClaw — facilitator/specialist hub-and-spoke routing and repo-coding topics, for Claude Code and Codex",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "Cody Swann"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "lisa-openclaw",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.231.0",
|
|
4
4
|
"description": "Connect staff roles to Telegram or Slack via OpenClaw — facilitator/specialist hub-and-spoke routing and repo-coding topics, for Claude Code and Codex",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "Cody Swann"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "lisa-openclaw",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.231.0",
|
|
4
4
|
"description": "Connect staff roles to Telegram or Slack via OpenClaw — facilitator/specialist hub-and-spoke routing and repo-coding topics, for Claude Code and Codex",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "Cody Swann"
|
package/ui/index.html
CHANGED
|
@@ -366,6 +366,13 @@
|
|
|
366
366
|
border-color: var(--good);
|
|
367
367
|
color: #fff;
|
|
368
368
|
}
|
|
369
|
+
.ck:disabled {
|
|
370
|
+
cursor: not-allowed;
|
|
371
|
+
opacity: 0.65;
|
|
372
|
+
}
|
|
373
|
+
.ck:disabled:hover {
|
|
374
|
+
border-color: var(--line-strong);
|
|
375
|
+
}
|
|
369
376
|
.check-content {
|
|
370
377
|
flex: 1;
|
|
371
378
|
min-width: 0;
|
|
@@ -732,6 +739,17 @@
|
|
|
732
739
|
.action-btn:hover {
|
|
733
740
|
background: var(--accent-soft);
|
|
734
741
|
}
|
|
742
|
+
.action-btn:disabled {
|
|
743
|
+
border-color: var(--line-strong);
|
|
744
|
+
color: var(--muted);
|
|
745
|
+
background: var(--surface2);
|
|
746
|
+
cursor: not-allowed;
|
|
747
|
+
}
|
|
748
|
+
.readonly-reason {
|
|
749
|
+
display: block;
|
|
750
|
+
margin-top: 6px;
|
|
751
|
+
max-width: 28ch;
|
|
752
|
+
}
|
|
735
753
|
|
|
736
754
|
.envmap {
|
|
737
755
|
display: grid;
|
|
@@ -1078,6 +1096,11 @@
|
|
|
1078
1096
|
background: var(--accent);
|
|
1079
1097
|
color: var(--accent-ink);
|
|
1080
1098
|
}
|
|
1099
|
+
.savebar .save:disabled {
|
|
1100
|
+
background: var(--surface2);
|
|
1101
|
+
color: var(--muted);
|
|
1102
|
+
cursor: not-allowed;
|
|
1103
|
+
}
|
|
1081
1104
|
|
|
1082
1105
|
.toast {
|
|
1083
1106
|
position: fixed;
|
|
@@ -1265,11 +1288,21 @@
|
|
|
1265
1288
|
></span
|
|
1266
1289
|
>
|
|
1267
1290
|
<button class="discard" id="discardBtn" type="button">Discard</button>
|
|
1268
|
-
<button
|
|
1269
|
-
|
|
1270
|
-
|
|
1271
|
-
|
|
1291
|
+
<button
|
|
1292
|
+
class="save"
|
|
1293
|
+
id="saveBtn"
|
|
1294
|
+
type="button"
|
|
1295
|
+
disabled
|
|
1296
|
+
title="read-only: the write-path has not shipped yet"
|
|
1297
|
+
aria-describedby="saveReadonlyReason"
|
|
1298
|
+
>
|
|
1299
|
+
Save changes
|
|
1300
|
+
</button>
|
|
1301
|
+
<span class="status-why readonly-reason" id="saveReadonlyReason">
|
|
1302
|
+
read-only: the write-path has not shipped yet
|
|
1303
|
+
</span>
|
|
1272
1304
|
</div>
|
|
1305
|
+
<div class="toast" id="toast"></div>
|
|
1273
1306
|
<script>
|
|
1274
1307
|
"use strict";
|
|
1275
1308
|
document.title = "Lisa Console — Project Settings";
|
|
@@ -1807,8 +1840,8 @@
|
|
|
1807
1840
|
control: {
|
|
1808
1841
|
type: "button",
|
|
1809
1842
|
label: "Run health check",
|
|
1810
|
-
|
|
1811
|
-
|
|
1843
|
+
disabled: true,
|
|
1844
|
+
reason: "read-only: the health engine has not shipped yet",
|
|
1812
1845
|
},
|
|
1813
1846
|
},
|
|
1814
1847
|
{
|
|
@@ -2280,7 +2313,8 @@
|
|
|
2280
2313
|
control: {
|
|
2281
2314
|
type: "button",
|
|
2282
2315
|
label: "Sync now",
|
|
2283
|
-
|
|
2316
|
+
disabled: true,
|
|
2317
|
+
reason: "read-only: starter sync has not shipped yet",
|
|
2284
2318
|
},
|
|
2285
2319
|
},
|
|
2286
2320
|
],
|
|
@@ -5399,10 +5433,27 @@
|
|
|
5399
5433
|
} else if (control.type === "button") {
|
|
5400
5434
|
const b = el("button", "action-btn", esc(control.label));
|
|
5401
5435
|
b.type = "button";
|
|
5402
|
-
|
|
5403
|
-
|
|
5404
|
-
|
|
5436
|
+
if (control.disabled) {
|
|
5437
|
+
b.disabled = true;
|
|
5438
|
+
if (control.reason) {
|
|
5439
|
+
b.title = control.reason;
|
|
5440
|
+
b.setAttribute("aria-describedby", id + "-reason");
|
|
5441
|
+
}
|
|
5442
|
+
} else {
|
|
5443
|
+
b.addEventListener("click", () =>
|
|
5444
|
+
showToast(control.toast || "Prototype action")
|
|
5445
|
+
);
|
|
5446
|
+
}
|
|
5405
5447
|
wrap.appendChild(b);
|
|
5448
|
+
if (control.disabled && control.reason) {
|
|
5449
|
+
const reason = el(
|
|
5450
|
+
"span",
|
|
5451
|
+
"status-why readonly-reason",
|
|
5452
|
+
esc(control.reason)
|
|
5453
|
+
);
|
|
5454
|
+
reason.id = id + "-reason";
|
|
5455
|
+
wrap.appendChild(reason);
|
|
5456
|
+
}
|
|
5406
5457
|
} else if (control.type === "static") {
|
|
5407
5458
|
wrap.appendChild(
|
|
5408
5459
|
el("span", control.cls === "mono" ? "mono" : "", esc(control.value))
|
|
@@ -5704,17 +5755,19 @@
|
|
|
5704
5755
|
if (!isDone && item.why) {
|
|
5705
5756
|
right.appendChild(el("span", "status-why", esc(item.why)));
|
|
5706
5757
|
}
|
|
5758
|
+
right.appendChild(
|
|
5759
|
+
el(
|
|
5760
|
+
"span",
|
|
5761
|
+
"status-why",
|
|
5762
|
+
"read-only: setup checklist state has not shipped yet"
|
|
5763
|
+
)
|
|
5764
|
+
);
|
|
5707
5765
|
};
|
|
5708
5766
|
const ck = el("button", "ck");
|
|
5709
5767
|
ck.type = "button";
|
|
5710
|
-
ck.
|
|
5711
|
-
ck.
|
|
5712
|
-
ck.
|
|
5713
|
-
row.classList.toggle("done");
|
|
5714
|
-
refreshRight();
|
|
5715
|
-
refreshNote();
|
|
5716
|
-
markDirty("setup·" + item.label, null);
|
|
5717
|
-
});
|
|
5768
|
+
ck.disabled = true;
|
|
5769
|
+
ck.title = "read-only: setup checklist state has not shipped yet";
|
|
5770
|
+
ck.setAttribute("aria-label", item.label + " checklist status");
|
|
5718
5771
|
row.appendChild(ck);
|
|
5719
5772
|
const content = el("div", "check-content");
|
|
5720
5773
|
const lab = el("div", "check-label", esc(item.label));
|
|
@@ -6078,13 +6131,6 @@
|
|
|
6078
6131
|
}
|
|
6079
6132
|
});
|
|
6080
6133
|
|
|
6081
|
-
document.getElementById("saveBtn").addEventListener("click", () => {
|
|
6082
|
-
clearDirty();
|
|
6083
|
-
document
|
|
6084
|
-
.querySelectorAll(".row.modified")
|
|
6085
|
-
.forEach(r => r.classList.remove("modified"));
|
|
6086
|
-
showToast("Saved — prototype only, nothing was written");
|
|
6087
|
-
});
|
|
6088
6134
|
document.getElementById("discardBtn").addEventListener("click", () => {
|
|
6089
6135
|
clearDirty();
|
|
6090
6136
|
renderAll();
|