@aiwg/cli 2026.8.0 → 2026.8.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/README.md +33 -0
- package/agentic/code/providers/capability-matrix.yaml +511 -0
- package/agentic/code/providers/model-capabilities.v1.json +120 -0
- package/agentic/code/providers/model-catalog.v1.json +96 -0
- package/agentic/code/providers/model-policy-evaluations.v1.json +50 -0
- package/agentic/code/providers/premium-model-allowlist.v1.json +36 -0
- package/bin/aiwg.mjs +14 -10
- package/dist/src/api/index.d.ts +1 -0
- package/dist/src/api/index.js +1 -0
- package/dist/src/artifacts/cli.js +2 -0
- package/dist/src/artifacts/types.js +4 -0
- package/dist/src/auth/client.js +209 -0
- package/dist/src/auth/config.js +38 -0
- package/dist/src/auth/credential-store.js +141 -0
- package/dist/src/auth/resource-credentials.js +25 -0
- package/dist/src/auth/types.js +2 -0
- package/dist/src/channel/manager.mjs +5 -5
- package/dist/src/cli/handlers/auth.js +125 -0
- package/dist/src/cli/handlers/help.js +1 -0
- package/dist/src/cli/handlers/index.js +3 -1
- package/dist/src/cli/handlers/resource-versions.js +2 -0
- package/dist/src/cli/handlers/sessions.js +23 -5
- package/dist/src/cli/handlers/subcommands.js +10 -1
- package/dist/src/cli/handlers/use.js +342 -43
- package/dist/src/config/gitignore.js +1 -0
- package/dist/src/extensions/commands/definitions.js +19 -0
- package/dist/src/memory/canonical-context.js +342 -0
- package/dist/src/memory/context-pack.js +282 -0
- package/dist/src/memory/index.js +4 -0
- package/dist/src/memory/intake.js +118 -0
- package/dist/src/resources/resolver.js +1 -0
- package/dist/src/resources/web-release.d.ts +3 -1
- package/dist/src/resources/web-release.js +14 -6
- package/dist/src/serve/agentic-sandbox-fleet-client.js +213 -0
- package/dist/src/serve/fleet-mission-conductor.js +293 -0
- package/dist/src/sessions/index.js +1 -0
- package/dist/src/sessions/output-registration.js +338 -0
- package/dist/src/sessions/promotion.js +73 -2
- package/dist/src/sessions/repository.js +2 -1
- package/dist/src/update/notifier.mjs +13 -2
- package/package.json +8 -1
- package/tools/_resolve-impl.mjs +74 -0
- package/tools/agents/deploy-agents.mjs +962 -0
- package/tools/agents/providers/base.mjs +2954 -0
- package/tools/agents/providers/claude.mjs +711 -0
- package/tools/agents/providers/codex.mjs +699 -0
- package/tools/agents/providers/copilot.mjs +659 -0
- package/tools/agents/providers/cursor.mjs +714 -0
- package/tools/agents/providers/factory.mjs +1130 -0
- package/tools/agents/providers/hermes.mjs +663 -0
- package/tools/agents/providers/hook-capabilities.mjs +85 -0
- package/tools/agents/providers/model-role.mjs +56 -0
- package/tools/agents/providers/openclaw-translator.mjs +348 -0
- package/tools/agents/providers/openclaw.mjs +680 -0
- package/tools/agents/providers/opencode.mjs +675 -0
- package/tools/agents/providers/openhuman.mjs +292 -0
- package/tools/agents/providers/warp.mjs +413 -0
- package/tools/agents/providers/windsurf.mjs +748 -0
- package/tools/commands/deploy-prompts-codex.mjs +336 -0
- package/tools/plugin/package-plugins.mjs +1013 -0
- package/tools/skills/deploy-skills-codex.mjs +571 -0
|
@@ -12,7 +12,7 @@ export class MemoryPromotionGateway {
|
|
|
12
12
|
throw new SessionContractError('MALFORMED_SOURCE', 'candidate version does not exist');
|
|
13
13
|
}
|
|
14
14
|
const existing = this.store.getPromotionReceipt(input.candidateId, input.version, input.destination.consumer);
|
|
15
|
-
if (candidate.reviewState !== 'accepted' &&
|
|
15
|
+
if (candidate.reviewState !== 'accepted' && candidate.reviewState !== 'promoted') {
|
|
16
16
|
throw new SessionContractError('OPERATION_NOT_AUTHORIZED', 'promotion requires an accepted exact candidate version');
|
|
17
17
|
}
|
|
18
18
|
const security = candidateSecurity(candidate);
|
|
@@ -165,7 +165,7 @@ export class FilesystemPromotionDispositionCoordinator {
|
|
|
165
165
|
if (!decision) {
|
|
166
166
|
throw new SessionContractError('OPERATION_NOT_AUTHORIZED', 'every promoted artifact requires an explicit disposition');
|
|
167
167
|
}
|
|
168
|
-
this.
|
|
168
|
+
this.authorizedDispositionRef(dependent.destinationRef);
|
|
169
169
|
return {
|
|
170
170
|
dependentId: dependent.dependentId,
|
|
171
171
|
destinationRef: dependent.destinationRef,
|
|
@@ -194,6 +194,12 @@ export class FilesystemPromotionDispositionCoordinator {
|
|
|
194
194
|
for (const effect of journal.effects) {
|
|
195
195
|
if (effect.outcome !== 'pending')
|
|
196
196
|
continue;
|
|
197
|
+
const lineMemory = this.lineMemoryRef(effect.destinationRef);
|
|
198
|
+
if (lineMemory) {
|
|
199
|
+
effect.outcome = this.applyLineMemoryDisposition(lineMemory.metadataPath, lineMemory.handle, purge.operationId, effect);
|
|
200
|
+
this.writeJournal(journalPath, journal);
|
|
201
|
+
continue;
|
|
202
|
+
}
|
|
197
203
|
const target = this.authorizedPath(effect.destinationRef);
|
|
198
204
|
const marker = dispositionMarker(purge.operationId, effect);
|
|
199
205
|
if (effect.action === 'delete') {
|
|
@@ -252,6 +258,65 @@ export class FilesystemPromotionDispositionCoordinator {
|
|
|
252
258
|
}
|
|
253
259
|
return target;
|
|
254
260
|
}
|
|
261
|
+
authorizedDispositionRef(destinationRef) {
|
|
262
|
+
if (this.lineMemoryRef(destinationRef))
|
|
263
|
+
return;
|
|
264
|
+
this.authorizedPath(destinationRef);
|
|
265
|
+
}
|
|
266
|
+
lineMemoryRef(destinationRef) {
|
|
267
|
+
const separator = destinationRef.lastIndexOf('#');
|
|
268
|
+
if (separator < 1)
|
|
269
|
+
return null;
|
|
270
|
+
const metadataRef = destinationRef.slice(0, separator);
|
|
271
|
+
const handle = destinationRef.slice(separator + 1);
|
|
272
|
+
if (!/^lm_[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i.test(handle)) {
|
|
273
|
+
return null;
|
|
274
|
+
}
|
|
275
|
+
return { metadataPath: this.authorizedPath(metadataRef), handle };
|
|
276
|
+
}
|
|
277
|
+
applyLineMemoryDisposition(metadataPath, handle, operationId, effect) {
|
|
278
|
+
if (!existsSync(metadataPath))
|
|
279
|
+
return 'already-applied';
|
|
280
|
+
const metadata = JSON.parse(readFileSync(metadataPath, 'utf8'));
|
|
281
|
+
if (metadata.schemaVersion !== 'aiwg.line-memory.v1' || !metadata.entries) {
|
|
282
|
+
throw new SessionContractError('IMPORT_CONFLICT', 'line-memory metadata schema is invalid');
|
|
283
|
+
}
|
|
284
|
+
const entry = metadata.entries[handle];
|
|
285
|
+
if (!entry)
|
|
286
|
+
return 'already-applied';
|
|
287
|
+
const priorOperation = entry.disposition?.operationId;
|
|
288
|
+
if (priorOperation === operationId)
|
|
289
|
+
return 'already-applied';
|
|
290
|
+
const memoryRef = metadata.store?.memoryPath ?? '.aiwg/memory/line-memory.txt';
|
|
291
|
+
const memoryPath = this.authorizedPath(memoryRef);
|
|
292
|
+
const lines = existsSync(memoryPath)
|
|
293
|
+
? readFileSync(memoryPath, 'utf8').split(/\r?\n/).filter(Boolean)
|
|
294
|
+
: [];
|
|
295
|
+
const removesActiveFact = ['delete', 'revoke', 'supersede'].includes(effect.action);
|
|
296
|
+
const nextLines = removesActiveFact
|
|
297
|
+
? removeFirstExact(lines, entry.value)
|
|
298
|
+
: lines;
|
|
299
|
+
if (effect.action === 'delete')
|
|
300
|
+
delete metadata.entries[handle];
|
|
301
|
+
else {
|
|
302
|
+
entry.status = effect.action === 'revoke' ? 'revoked'
|
|
303
|
+
: effect.action === 'supersede' ? 'superseded'
|
|
304
|
+
: effect.action === 'origin_unavailable' ? 'origin-unavailable'
|
|
305
|
+
: 'active';
|
|
306
|
+
entry.updatedAt = new Date().toISOString();
|
|
307
|
+
entry.disposition = {
|
|
308
|
+
operationId,
|
|
309
|
+
action: effect.action,
|
|
310
|
+
effect: effect.effect,
|
|
311
|
+
originAvailable: effect.action !== 'origin_unavailable',
|
|
312
|
+
};
|
|
313
|
+
}
|
|
314
|
+
if (removesActiveFact) {
|
|
315
|
+
this.atomicWrite(memoryPath, nextLines.length ? `${nextLines.join('\n')}\n` : '');
|
|
316
|
+
}
|
|
317
|
+
this.atomicWrite(metadataPath, `${JSON.stringify(metadata, null, 2)}\n`);
|
|
318
|
+
return 'applied';
|
|
319
|
+
}
|
|
255
320
|
journalPath(operationId) {
|
|
256
321
|
return resolve(this.journalRoot, `${operationId.replace(':', '-')}.json`);
|
|
257
322
|
}
|
|
@@ -290,6 +355,12 @@ function requireJournalFiles(root) {
|
|
|
290
355
|
.sort()
|
|
291
356
|
.map((name) => resolve(root, name));
|
|
292
357
|
}
|
|
358
|
+
function removeFirstExact(lines, value) {
|
|
359
|
+
const index = lines.indexOf(value);
|
|
360
|
+
return index < 0
|
|
361
|
+
? [...lines]
|
|
362
|
+
: lines.filter((_, candidate) => candidate !== index);
|
|
363
|
+
}
|
|
293
364
|
export function resolveMemoryConsumerManifest(projectRoot, consumer) {
|
|
294
365
|
const safeConsumer = assertConsumerId(consumer);
|
|
295
366
|
const candidates = [
|
|
@@ -1219,7 +1219,8 @@ export class SessionRepository {
|
|
|
1219
1219
|
if (existing)
|
|
1220
1220
|
return { ...existing, duplicate: true };
|
|
1221
1221
|
const candidate = this.getCandidate(receipt.candidateId, receipt.candidateVersion);
|
|
1222
|
-
if (!candidate
|
|
1222
|
+
if (!candidate
|
|
1223
|
+
|| (candidate.reviewState !== 'accepted' && candidate.reviewState !== 'promoted')) {
|
|
1223
1224
|
throw new SessionContractError('OPERATION_NOT_AUTHORIZED', 'promotion requires an accepted exact candidate version');
|
|
1224
1225
|
}
|
|
1225
1226
|
const evidenceIds = [...new Set(candidate.evidence.map((item) => item.eventId))].sort();
|
|
@@ -157,6 +157,16 @@ function readCurrentVersion(packageRoot) {
|
|
|
157
157
|
}
|
|
158
158
|
}
|
|
159
159
|
|
|
160
|
+
/**
|
|
161
|
+
* Return true when a cached check belongs to the package currently handling
|
|
162
|
+
* the command. A global launcher can dispatch into a newer development
|
|
163
|
+
* checkout, so cache age alone is not sufficient.
|
|
164
|
+
*/
|
|
165
|
+
export function cacheMatchesPackage(cache, packageRoot) {
|
|
166
|
+
const currentVersion = readCurrentVersion(packageRoot);
|
|
167
|
+
return !!(currentVersion && cache?.current === currentVersion);
|
|
168
|
+
}
|
|
169
|
+
|
|
160
170
|
/**
|
|
161
171
|
* Run the actual update check and write the cache file. Invoked by the
|
|
162
172
|
* spawned background child via `node src/update/notifier.mjs --check`.
|
|
@@ -183,7 +193,7 @@ export function scheduleBackgroundCheck(packageRoot) {
|
|
|
183
193
|
if (isDisabled()) return;
|
|
184
194
|
|
|
185
195
|
const cache = readCache();
|
|
186
|
-
if (cache?.lastCheckAt) {
|
|
196
|
+
if (cacheMatchesPackage(cache, packageRoot) && cache?.lastCheckAt) {
|
|
187
197
|
const age = Date.now() - new Date(cache.lastCheckAt).getTime();
|
|
188
198
|
if (age < CHECK_INTERVAL_MS) return; // recent enough — skip
|
|
189
199
|
}
|
|
@@ -213,9 +223,10 @@ export function scheduleBackgroundCheck(packageRoot) {
|
|
|
213
223
|
* is interactive, print a single-line notice to stderr. Never prompts.
|
|
214
224
|
* Safe to call unconditionally from `bin/aiwg.mjs` — gated by isDisabled().
|
|
215
225
|
*/
|
|
216
|
-
export function maybePrintNotice() {
|
|
226
|
+
export function maybePrintNotice(packageRoot) {
|
|
217
227
|
if (isDisabled()) return;
|
|
218
228
|
const cache = readCache();
|
|
229
|
+
if (!cacheMatchesPackage(cache, packageRoot)) return;
|
|
219
230
|
if (!cache?.hasUpdate || !cache.current || !cache.latest) return;
|
|
220
231
|
// One-line, non-intrusive. Users who want to update run `aiwg update`.
|
|
221
232
|
const msg = `aiwg: update available ${cache.current} → ${cache.latest} (run: aiwg update)`;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@aiwg/cli",
|
|
3
|
-
"version": "2026.8.
|
|
3
|
+
"version": "2026.8.1",
|
|
4
4
|
"description": "Lightweight AIWG CLI for signed, versioned web-backed resources.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -25,12 +25,19 @@
|
|
|
25
25
|
"files": [
|
|
26
26
|
"LICENSE",
|
|
27
27
|
"bin/",
|
|
28
|
+
"agentic/code/providers/",
|
|
28
29
|
"dist/src/",
|
|
29
30
|
"!dist/**/*.d.ts",
|
|
30
31
|
"!dist/**/*.map",
|
|
31
32
|
"dist/src/api/index.d.ts",
|
|
32
33
|
"dist/src/resources/index.d.ts",
|
|
33
34
|
"dist/src/resources/web-release.d.ts",
|
|
35
|
+
"tools/_resolve-impl.mjs",
|
|
36
|
+
"tools/agents/deploy-agents.mjs",
|
|
37
|
+
"tools/agents/providers/",
|
|
38
|
+
"tools/commands/deploy-prompts-codex.mjs",
|
|
39
|
+
"tools/plugin/package-plugins.mjs",
|
|
40
|
+
"tools/skills/deploy-skills-codex.mjs",
|
|
34
41
|
"README.md"
|
|
35
42
|
],
|
|
36
43
|
"repository": {
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { existsSync, readFileSync } from 'node:fs';
|
|
2
|
+
import { dirname, extname, join, resolve } from 'node:path';
|
|
3
|
+
import { fileURLToPath, pathToFileURL } from 'node:url';
|
|
4
|
+
|
|
5
|
+
function findPackageRoot(callerUrl) {
|
|
6
|
+
let dir = dirname(fileURLToPath(callerUrl));
|
|
7
|
+
for (let i = 0; i < 12; i += 1) {
|
|
8
|
+
const pkgPath = join(dir, 'package.json');
|
|
9
|
+
if (existsSync(pkgPath)) {
|
|
10
|
+
try {
|
|
11
|
+
const pkg = JSON.parse(readFileSync(pkgPath, 'utf8'));
|
|
12
|
+
if (pkg.name === 'aiwg' || pkg.name === '@aiwg/cli') return dir;
|
|
13
|
+
} catch {
|
|
14
|
+
// Keep walking.
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
const parent = dirname(dir);
|
|
19
|
+
if (parent === dir) break;
|
|
20
|
+
dir = parent;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
throw new Error(`Could not locate AIWG package root from ${callerUrl}`);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
function candidatesFor(root, relativeFromSrc, base) {
|
|
27
|
+
const primary = resolve(root, base, relativeFromSrc);
|
|
28
|
+
const candidates = [primary];
|
|
29
|
+
|
|
30
|
+
if (base === 'src' && extname(primary) === '.js') {
|
|
31
|
+
candidates.push(primary.slice(0, -3) + '.ts');
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
return candidates;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
function resolveCandidate(root, relativeFromSrc, base) {
|
|
38
|
+
for (const candidate of candidatesFor(root, relativeFromSrc, base)) {
|
|
39
|
+
if (existsSync(candidate)) return candidate;
|
|
40
|
+
}
|
|
41
|
+
return null;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
/**
|
|
45
|
+
* Resolve a module that may live under compiled dist/src/ or source src/.
|
|
46
|
+
*
|
|
47
|
+
* Prefers dist/src/ when present. Set AIWG_RESOLVE_IMPL_FROM=dist or src to
|
|
48
|
+
* force a side during CI/package-layout checks.
|
|
49
|
+
*/
|
|
50
|
+
export function resolveImpl(callerUrl, relativeFromSrc) {
|
|
51
|
+
const root = findPackageRoot(callerUrl);
|
|
52
|
+
const forced = process.env.AIWG_RESOLVE_IMPL_FROM;
|
|
53
|
+
|
|
54
|
+
const order = forced === 'src'
|
|
55
|
+
? ['src']
|
|
56
|
+
: forced === 'dist'
|
|
57
|
+
? ['dist/src']
|
|
58
|
+
: ['dist/src', 'src'];
|
|
59
|
+
|
|
60
|
+
for (const base of order) {
|
|
61
|
+
const candidate = resolveCandidate(root, relativeFromSrc, base);
|
|
62
|
+
if (candidate) return candidate;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
const attempted = order
|
|
66
|
+
.flatMap((base) => candidatesFor(root, relativeFromSrc, base))
|
|
67
|
+
.join(', ');
|
|
68
|
+
throw new Error(`Could not resolve ${relativeFromSrc}; attempted: ${attempted}`);
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
export async function importImpl(callerUrl, relativeFromSrc) {
|
|
72
|
+
const modulePath = resolveImpl(callerUrl, relativeFromSrc);
|
|
73
|
+
return import(pathToFileURL(modulePath).href);
|
|
74
|
+
}
|