@pieai/pro-gov 0.3.6 → 0.3.7
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.
|
@@ -129,6 +129,12 @@ The plan file is the safety gate. Review it before applying. It creates managed
|
|
|
129
129
|
symlinks and `.pro-gov/assets.lock.json`; it should not overwrite unmanaged
|
|
130
130
|
project files.
|
|
131
131
|
|
|
132
|
+
Managed symlinks are relative by default. A target project's normal
|
|
133
|
+
`assets check` validates the local lock and linked content without requiring the
|
|
134
|
+
public package to know a maintainer's private registry. Maintainers can add
|
|
135
|
+
`--strict-registry`, or run `pro-gov portfolio assets-check --config
|
|
136
|
+
/path/to/portfolio.json`, when they need central private-registry validation.
|
|
137
|
+
|
|
132
138
|
When a maintainer promotes a private asset into `public-agent-assets/`, the
|
|
133
139
|
public registry must record the private-source hash and the public-copy hash.
|
|
134
140
|
Run this in the upstream checkout before publishing:
|
package/dist/cli.js
CHANGED
|
@@ -422,6 +422,7 @@ function listFiles3(absolutePath) {
|
|
|
422
422
|
if (stats.isFile()) return [absolutePath];
|
|
423
423
|
const files = [];
|
|
424
424
|
for (const entry of readdirSync4(absolutePath, { withFileTypes: true })) {
|
|
425
|
+
if (shouldIgnoreAssetHashEntry(entry.name)) continue;
|
|
425
426
|
const entryPath = join5(absolutePath, entry.name);
|
|
426
427
|
if (entry.isDirectory()) {
|
|
427
428
|
files.push(...listFiles3(entryPath));
|
|
@@ -431,6 +432,9 @@ function listFiles3(absolutePath) {
|
|
|
431
432
|
}
|
|
432
433
|
return files.sort();
|
|
433
434
|
}
|
|
435
|
+
function shouldIgnoreAssetHashEntry(name) {
|
|
436
|
+
return name === "__pycache__" || name === ".DS_Store" || name === "Thumbs.db" || name === "node_modules" || name.endsWith(".pyc") || name.endsWith(".pyo");
|
|
437
|
+
}
|
|
434
438
|
function toUnixPath3(path) {
|
|
435
439
|
return path.replaceAll("\\", "/");
|
|
436
440
|
}
|
|
@@ -532,8 +536,8 @@ function resolveSafePath(root, sourcePath) {
|
|
|
532
536
|
}
|
|
533
537
|
|
|
534
538
|
// src/asset-targets/apply.ts
|
|
535
|
-
import { existsSync as existsSync7, lstatSync as lstatSync2, mkdirSync as mkdirSync2, symlinkSync, unlinkSync, writeFileSync } from "node:fs";
|
|
536
|
-
import { dirname as dirname3, join as join7, resolve } from "node:path";
|
|
539
|
+
import { existsSync as existsSync7, lstatSync as lstatSync2, mkdirSync as mkdirSync2, realpathSync, symlinkSync, unlinkSync, writeFileSync } from "node:fs";
|
|
540
|
+
import { dirname as dirname3, join as join7, relative as relative4, resolve } from "node:path";
|
|
537
541
|
function applyAssetInstallPlan(plan) {
|
|
538
542
|
const appliedActions = [];
|
|
539
543
|
for (const action of plan.actions) {
|
|
@@ -555,15 +559,16 @@ function applyAction(targetDir, action) {
|
|
|
555
559
|
}
|
|
556
560
|
mkdirSync2(dirname3(targetAbsolutePath), { recursive: true });
|
|
557
561
|
const sourceAbsolutePath = resolve(action.sourcePath);
|
|
562
|
+
const symlinkTarget = relative4(realpathSync(dirname3(targetAbsolutePath)), realpathSync(sourceAbsolutePath)) || ".";
|
|
558
563
|
if (action.type === "symlink") {
|
|
559
564
|
if (pathExistsEvenIfDanglingSymlink2(targetAbsolutePath)) {
|
|
560
565
|
throw new Error(`Refusing to overwrite unmanaged target: ${action.targetPath}`);
|
|
561
566
|
}
|
|
562
|
-
symlinkSync(
|
|
567
|
+
symlinkSync(symlinkTarget, targetAbsolutePath);
|
|
563
568
|
return;
|
|
564
569
|
}
|
|
565
570
|
if (!pathExistsEvenIfDanglingSymlink2(targetAbsolutePath)) {
|
|
566
|
-
symlinkSync(
|
|
571
|
+
symlinkSync(symlinkTarget, targetAbsolutePath);
|
|
567
572
|
return;
|
|
568
573
|
}
|
|
569
574
|
const stats = lstatSync2(targetAbsolutePath);
|
|
@@ -571,7 +576,7 @@ function applyAction(targetDir, action) {
|
|
|
571
576
|
throw new Error(`Refusing to overwrite unmanaged target: ${action.targetPath}`);
|
|
572
577
|
}
|
|
573
578
|
unlinkSync(targetAbsolutePath);
|
|
574
|
-
symlinkSync(
|
|
579
|
+
symlinkSync(symlinkTarget, targetAbsolutePath);
|
|
575
580
|
}
|
|
576
581
|
function pathExistsEvenIfDanglingSymlink2(path) {
|
|
577
582
|
try {
|
|
@@ -601,20 +606,19 @@ function checkInstalledAssets(options) {
|
|
|
601
606
|
const registryById = new Map(options.registry.assets.map((asset) => [asset.id, asset]));
|
|
602
607
|
const lockfile = JSON.parse(readFileSync4(lockfilePath, "utf8"));
|
|
603
608
|
const issues = [];
|
|
609
|
+
const strictRegistry = options.strictRegistry ?? false;
|
|
604
610
|
for (const entry of lockfile.assets ?? []) {
|
|
605
611
|
const asset = registryById.get(entry.id);
|
|
606
612
|
const targetAbsolutePath = join8(options.targetDir, entry.targetPath);
|
|
607
|
-
|
|
608
|
-
if (!asset) {
|
|
613
|
+
if (!asset && strictRegistry) {
|
|
609
614
|
issues.push({
|
|
610
615
|
type: "unknown-asset",
|
|
611
616
|
id: entry.id,
|
|
612
617
|
targetPath: entry.targetPath,
|
|
613
618
|
message: `Lockfile references unknown asset: ${entry.id}`
|
|
614
619
|
});
|
|
615
|
-
continue;
|
|
616
620
|
}
|
|
617
|
-
if (asset
|
|
621
|
+
if (asset?.kind === "skill" && asset.defaultScope === "user") {
|
|
618
622
|
issues.push({
|
|
619
623
|
type: "user-scoped-asset-in-project-lock",
|
|
620
624
|
id: entry.id,
|
|
@@ -622,13 +626,15 @@ function checkInstalledAssets(options) {
|
|
|
622
626
|
message: `User-scoped skill is still locked into this project; move it to the user skill roots: ${entry.id}`
|
|
623
627
|
});
|
|
624
628
|
}
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
629
|
+
if (asset) {
|
|
630
|
+
const hostFolderIssue = checkHostFolder(lockfile.host, asset.kind, entry.targetPath, entry.id);
|
|
631
|
+
if (hostFolderIssue) {
|
|
632
|
+
issues.push(hostFolderIssue);
|
|
633
|
+
}
|
|
634
|
+
const placementDriftIssue = checkRegistryPlacement(lockfile, asset, entry.targetPath);
|
|
635
|
+
if (placementDriftIssue) {
|
|
636
|
+
issues.push(placementDriftIssue);
|
|
637
|
+
}
|
|
632
638
|
}
|
|
633
639
|
if (!pathExistsEvenIfDanglingSymlink3(targetAbsolutePath)) {
|
|
634
640
|
issues.push({
|
|
@@ -658,6 +664,18 @@ function checkInstalledAssets(options) {
|
|
|
658
664
|
});
|
|
659
665
|
continue;
|
|
660
666
|
}
|
|
667
|
+
const currentTargetHash = hashAssetPathContent(targetAbsolutePath);
|
|
668
|
+
const targetHashMatchesLock = currentTargetHash === entry.contentHash;
|
|
669
|
+
if (!targetHashMatchesLock) {
|
|
670
|
+
issues.push({
|
|
671
|
+
type: "hash-drift",
|
|
672
|
+
id: entry.id,
|
|
673
|
+
targetPath: entry.targetPath,
|
|
674
|
+
message: `Managed asset hash drifted: ${entry.id}`
|
|
675
|
+
});
|
|
676
|
+
}
|
|
677
|
+
if (!asset || !strictRegistry) continue;
|
|
678
|
+
const sourceAbsolutePath = join8(options.agentAssetsDir, asset.sourcePath);
|
|
661
679
|
if (!existsSync8(sourceAbsolutePath)) {
|
|
662
680
|
issues.push({
|
|
663
681
|
type: "missing-source",
|
|
@@ -667,8 +685,8 @@ function checkInstalledAssets(options) {
|
|
|
667
685
|
});
|
|
668
686
|
continue;
|
|
669
687
|
}
|
|
670
|
-
const
|
|
671
|
-
if (
|
|
688
|
+
const currentSourceHash = hashAgentAssetContent(asset, options.agentAssetsDir);
|
|
689
|
+
if (targetHashMatchesLock && currentSourceHash !== entry.contentHash) {
|
|
672
690
|
issues.push({
|
|
673
691
|
type: "hash-drift",
|
|
674
692
|
id: entry.id,
|
|
@@ -1145,7 +1163,8 @@ function runAssetsCheck(args) {
|
|
|
1145
1163
|
const result = checkInstalledAssets({
|
|
1146
1164
|
targetDir: options.value.targetDir,
|
|
1147
1165
|
agentAssetsDir: loaded.agentAssetsDir,
|
|
1148
|
-
registry: loaded.registry
|
|
1166
|
+
registry: loaded.registry,
|
|
1167
|
+
strictRegistry: options.value.strictRegistry
|
|
1149
1168
|
});
|
|
1150
1169
|
if (options.value.json) {
|
|
1151
1170
|
console.log(JSON.stringify(result, null, 2));
|
|
@@ -1300,6 +1319,8 @@ function parseTargetJsonOptions(args) {
|
|
|
1300
1319
|
if (!targetDir) return { ok: false, error: "Expected --target <path>" };
|
|
1301
1320
|
options.targetDir = targetDir;
|
|
1302
1321
|
index += 1;
|
|
1322
|
+
} else if (arg === "--strict-registry") {
|
|
1323
|
+
options.strictRegistry = true;
|
|
1303
1324
|
} else if (arg === "--json") {
|
|
1304
1325
|
options.json = true;
|
|
1305
1326
|
} else {
|
|
@@ -1717,7 +1738,7 @@ function bulletList(values) {
|
|
|
1717
1738
|
// src/lens/scan.ts
|
|
1718
1739
|
import { spawnSync as spawnSync3 } from "node:child_process";
|
|
1719
1740
|
import { existsSync as existsSync13, readdirSync as readdirSync6, readFileSync as readFileSync8, statSync as statSync3 } from "node:fs";
|
|
1720
|
-
import { join as join13, relative as
|
|
1741
|
+
import { join as join13, relative as relative5 } from "node:path";
|
|
1721
1742
|
var ignoredDirectories = /* @__PURE__ */ new Set([
|
|
1722
1743
|
".git",
|
|
1723
1744
|
".next",
|
|
@@ -1792,7 +1813,7 @@ function collectFiles2(rootDir, currentDir, files) {
|
|
|
1792
1813
|
if (ignoredDirectories.has(entry.name)) continue;
|
|
1793
1814
|
collectFiles2(rootDir, join13(currentDir, entry.name), files);
|
|
1794
1815
|
} else if (entry.isFile()) {
|
|
1795
|
-
files.push(toUnixPath4(
|
|
1816
|
+
files.push(toUnixPath4(relative5(rootDir, join13(currentDir, entry.name))));
|
|
1796
1817
|
}
|
|
1797
1818
|
}
|
|
1798
1819
|
}
|
|
@@ -1886,6 +1907,10 @@ function printUsage2() {
|
|
|
1886
1907
|
console.error("Usage: pro-gov lens report --target <path> --out <path>");
|
|
1887
1908
|
}
|
|
1888
1909
|
|
|
1910
|
+
// src/commands/portfolio.ts
|
|
1911
|
+
import { existsSync as existsSync15 } from "node:fs";
|
|
1912
|
+
import { join as join14 } from "node:path";
|
|
1913
|
+
|
|
1889
1914
|
// src/portfolio/manifest.ts
|
|
1890
1915
|
import { existsSync as existsSync14, readFileSync as readFileSync9 } from "node:fs";
|
|
1891
1916
|
function loadPortfolioManifest(configPath) {
|
|
@@ -1935,6 +1960,7 @@ function validatePortfolioManifest(value) {
|
|
|
1935
1960
|
message: "Portfolio manifest portfolioId must be a non-empty string."
|
|
1936
1961
|
});
|
|
1937
1962
|
}
|
|
1963
|
+
validateAllowedFields(value, "root", ["schemaVersion", "portfolioId", "controlPlane", "executionEngine", "targets"], issues);
|
|
1938
1964
|
validateEndpoint(value.controlPlane, "controlPlane", issues);
|
|
1939
1965
|
validateEndpoint(value.executionEngine, "executionEngine", issues);
|
|
1940
1966
|
if (!Array.isArray(value.targets)) {
|
|
@@ -1956,6 +1982,7 @@ function validatePortfolioManifest(value) {
|
|
|
1956
1982
|
continue;
|
|
1957
1983
|
}
|
|
1958
1984
|
validateEndpoint(target, "targets", issues);
|
|
1985
|
+
validateAllowedFields(target, "target", ["id", "path", "profile", "assetBundles"], issues);
|
|
1959
1986
|
if (typeof target.id === "string") {
|
|
1960
1987
|
if (seenTargetIds.has(target.id)) {
|
|
1961
1988
|
issues.push({
|
|
@@ -1966,14 +1993,41 @@ function validatePortfolioManifest(value) {
|
|
|
1966
1993
|
}
|
|
1967
1994
|
seenTargetIds.add(target.id);
|
|
1968
1995
|
}
|
|
1996
|
+
if (target.profile !== void 0 && (typeof target.profile !== "string" || !isValidProfile(target.profile))) {
|
|
1997
|
+
issues.push({
|
|
1998
|
+
type: "invalid-field",
|
|
1999
|
+
id: typeof target.id === "string" ? target.id : void 0,
|
|
2000
|
+
field: "profile",
|
|
2001
|
+
message: "Portfolio target profile must be engineering-runtime or doc-only."
|
|
2002
|
+
});
|
|
2003
|
+
}
|
|
1969
2004
|
validateOptionalStringArray(target.assetBundles, target.id, "assetBundles", issues);
|
|
1970
|
-
|
|
2005
|
+
if ("sharedRules" in target) {
|
|
2006
|
+
issues.push({
|
|
2007
|
+
type: "invalid-field",
|
|
2008
|
+
id: typeof target.id === "string" ? target.id : void 0,
|
|
2009
|
+
field: "sharedRules",
|
|
2010
|
+
message: "Portfolio target sharedRules is not managed yet; remove it until plan/check supports it."
|
|
2011
|
+
});
|
|
2012
|
+
}
|
|
1971
2013
|
}
|
|
1972
2014
|
return issues;
|
|
1973
2015
|
}
|
|
1974
2016
|
function getDefaultPortfolioTargets(manifest) {
|
|
1975
2017
|
return manifest?.targets ?? [];
|
|
1976
2018
|
}
|
|
2019
|
+
function validateAllowedFields(value, location, allowedFields, issues) {
|
|
2020
|
+
const allowed = new Set(allowedFields);
|
|
2021
|
+
for (const field of Object.keys(value)) {
|
|
2022
|
+
if (allowed.has(field)) continue;
|
|
2023
|
+
issues.push({
|
|
2024
|
+
type: "invalid-field",
|
|
2025
|
+
id: typeof value.id === "string" ? value.id : void 0,
|
|
2026
|
+
field,
|
|
2027
|
+
message: `Unknown portfolio ${location} field: ${field}`
|
|
2028
|
+
});
|
|
2029
|
+
}
|
|
2030
|
+
}
|
|
1977
2031
|
function validateEndpoint(value, field, issues) {
|
|
1978
2032
|
if (value === void 0) return;
|
|
1979
2033
|
if (!isRecord(value)) {
|
|
@@ -2029,6 +2083,7 @@ function runPortfolio(args) {
|
|
|
2029
2083
|
const [subcommand2, ...rest] = args;
|
|
2030
2084
|
if (subcommand2 === "check") return runPortfolioCheck(rest);
|
|
2031
2085
|
if (subcommand2 === "plan") return runPortfolioPlan(rest);
|
|
2086
|
+
if (subcommand2 === "assets-check") return runPortfolioAssetsCheck(rest);
|
|
2032
2087
|
printUsage3();
|
|
2033
2088
|
return 1;
|
|
2034
2089
|
}
|
|
@@ -2085,7 +2140,9 @@ function runPortfolioPlan(args) {
|
|
|
2085
2140
|
console.error(`Unknown portfolio target: ${options.value.targetId}`);
|
|
2086
2141
|
return 1;
|
|
2087
2142
|
}
|
|
2088
|
-
const loadedAssets = loadAgentAssetRegistry(
|
|
2143
|
+
const loadedAssets = loadAgentAssetRegistry({
|
|
2144
|
+
agentAssetsDir: findPortfolioAgentAssetsDir(loaded.manifest)
|
|
2145
|
+
});
|
|
2089
2146
|
if (loadedAssets.issues.length > 0) {
|
|
2090
2147
|
for (const issue of loadedAssets.issues) {
|
|
2091
2148
|
console.error(`${issue.type}: ${issue.message}`);
|
|
@@ -2136,6 +2193,106 @@ function runPortfolioPlan(args) {
|
|
|
2136
2193
|
return 1;
|
|
2137
2194
|
}
|
|
2138
2195
|
}
|
|
2196
|
+
function runPortfolioAssetsCheck(args) {
|
|
2197
|
+
const options = parsePortfolioOptions(args);
|
|
2198
|
+
if (!options.ok) {
|
|
2199
|
+
console.error(options.error);
|
|
2200
|
+
printUsage3();
|
|
2201
|
+
return 1;
|
|
2202
|
+
}
|
|
2203
|
+
const loaded = loadPortfolioManifest(options.value.configPath);
|
|
2204
|
+
if (loaded.issues.length > 0 || !loaded.manifest) {
|
|
2205
|
+
if (options.value.json) {
|
|
2206
|
+
console.log(
|
|
2207
|
+
JSON.stringify(
|
|
2208
|
+
{
|
|
2209
|
+
ok: false,
|
|
2210
|
+
configPath: loaded.configPath,
|
|
2211
|
+
issues: loaded.issues,
|
|
2212
|
+
targets: []
|
|
2213
|
+
},
|
|
2214
|
+
null,
|
|
2215
|
+
2
|
|
2216
|
+
)
|
|
2217
|
+
);
|
|
2218
|
+
} else {
|
|
2219
|
+
for (const issue of loaded.issues) {
|
|
2220
|
+
console.error(`${issue.type}: ${issue.message}`);
|
|
2221
|
+
}
|
|
2222
|
+
}
|
|
2223
|
+
return 1;
|
|
2224
|
+
}
|
|
2225
|
+
const targets = getDefaultPortfolioTargets(loaded.manifest).filter(
|
|
2226
|
+
(target) => !options.value.targetId || options.value.targetId === "all" || target.id === options.value.targetId
|
|
2227
|
+
);
|
|
2228
|
+
if (targets.length === 0) {
|
|
2229
|
+
console.error(`Unknown portfolio target: ${options.value.targetId}`);
|
|
2230
|
+
return 1;
|
|
2231
|
+
}
|
|
2232
|
+
const loadedAssets = loadAgentAssetRegistry({
|
|
2233
|
+
agentAssetsDir: findPortfolioAgentAssetsDir(loaded.manifest)
|
|
2234
|
+
});
|
|
2235
|
+
if (loadedAssets.issues.length > 0) {
|
|
2236
|
+
if (options.value.json) {
|
|
2237
|
+
console.log(
|
|
2238
|
+
JSON.stringify(
|
|
2239
|
+
{
|
|
2240
|
+
ok: false,
|
|
2241
|
+
configPath: loaded.configPath,
|
|
2242
|
+
portfolioId: loaded.manifest.portfolioId,
|
|
2243
|
+
registryIssues: loadedAssets.issues,
|
|
2244
|
+
targets: []
|
|
2245
|
+
},
|
|
2246
|
+
null,
|
|
2247
|
+
2
|
|
2248
|
+
)
|
|
2249
|
+
);
|
|
2250
|
+
} else {
|
|
2251
|
+
for (const issue of loadedAssets.issues) {
|
|
2252
|
+
console.error(`${issue.type}: ${issue.message}`);
|
|
2253
|
+
}
|
|
2254
|
+
}
|
|
2255
|
+
return 1;
|
|
2256
|
+
}
|
|
2257
|
+
const targetResults = targets.map((target) => {
|
|
2258
|
+
const result = checkInstalledAssets({
|
|
2259
|
+
targetDir: target.path,
|
|
2260
|
+
agentAssetsDir: loadedAssets.agentAssetsDir,
|
|
2261
|
+
registry: loadedAssets.registry,
|
|
2262
|
+
strictRegistry: true
|
|
2263
|
+
});
|
|
2264
|
+
return {
|
|
2265
|
+
id: target.id,
|
|
2266
|
+
path: target.path,
|
|
2267
|
+
issues: result.issues
|
|
2268
|
+
};
|
|
2269
|
+
});
|
|
2270
|
+
const ok = targetResults.every((target) => target.issues.length === 0);
|
|
2271
|
+
if (options.value.json) {
|
|
2272
|
+
console.log(
|
|
2273
|
+
JSON.stringify(
|
|
2274
|
+
{
|
|
2275
|
+
ok,
|
|
2276
|
+
configPath: loaded.configPath,
|
|
2277
|
+
portfolioId: loaded.manifest.portfolioId,
|
|
2278
|
+
agentAssetsDir: loadedAssets.agentAssetsDir,
|
|
2279
|
+
targets: targetResults
|
|
2280
|
+
},
|
|
2281
|
+
null,
|
|
2282
|
+
2
|
|
2283
|
+
)
|
|
2284
|
+
);
|
|
2285
|
+
} else if (ok) {
|
|
2286
|
+
console.log(`portfolio assets check passed (${targetResults.length} targets)`);
|
|
2287
|
+
} else {
|
|
2288
|
+
for (const target of targetResults) {
|
|
2289
|
+
for (const issue of target.issues) {
|
|
2290
|
+
console.log(`${target.id} ${issue.type}: ${issue.message}`);
|
|
2291
|
+
}
|
|
2292
|
+
}
|
|
2293
|
+
}
|
|
2294
|
+
return ok ? 0 : 1;
|
|
2295
|
+
}
|
|
2139
2296
|
function parsePortfolioOptions(args) {
|
|
2140
2297
|
const options = {
|
|
2141
2298
|
configPath: "",
|
|
@@ -2171,15 +2328,20 @@ function parsePortfolioOptions(args) {
|
|
|
2171
2328
|
function isHost2(value) {
|
|
2172
2329
|
return value === "codex" || value === "claude-code" || value === "gemini-cli" || value === "antigravity";
|
|
2173
2330
|
}
|
|
2331
|
+
function findPortfolioAgentAssetsDir(manifest) {
|
|
2332
|
+
const agentAssetsDir = manifest?.executionEngine?.path ? join14(manifest.executionEngine.path, "agent-assets") : void 0;
|
|
2333
|
+
return agentAssetsDir && existsSync15(join14(agentAssetsDir, "registry.json")) ? agentAssetsDir : void 0;
|
|
2334
|
+
}
|
|
2174
2335
|
function printUsage3() {
|
|
2175
2336
|
console.error("Usage:");
|
|
2176
2337
|
console.error(" pro-gov portfolio check --config <path> [--json]");
|
|
2177
2338
|
console.error(" pro-gov portfolio plan --config <path> [--target <id|all>] [--host codex|claude-code|gemini-cli|antigravity] [--json]");
|
|
2339
|
+
console.error(" pro-gov portfolio assets-check --config <path> [--target <id|all>] [--json]");
|
|
2178
2340
|
}
|
|
2179
2341
|
|
|
2180
2342
|
// src/commands/sync.ts
|
|
2181
|
-
import { existsSync as
|
|
2182
|
-
import { join as
|
|
2343
|
+
import { existsSync as existsSync16, readFileSync as readFileSync10 } from "node:fs";
|
|
2344
|
+
import { join as join15 } from "node:path";
|
|
2183
2345
|
function runSync(args) {
|
|
2184
2346
|
if (!args.includes("--check")) {
|
|
2185
2347
|
console.error("pro-gov sync requires --check in this first read-only release.");
|
|
@@ -2188,8 +2350,8 @@ function runSync(args) {
|
|
|
2188
2350
|
let differences = 0;
|
|
2189
2351
|
console.log("pro-gov sync check");
|
|
2190
2352
|
for (const file of planStarterFiles()) {
|
|
2191
|
-
const targetPath =
|
|
2192
|
-
if (!
|
|
2353
|
+
const targetPath = join15(process.cwd(), file.targetPath);
|
|
2354
|
+
if (!existsSync16(targetPath)) {
|
|
2193
2355
|
console.log(`missing: ${file.targetPath}`);
|
|
2194
2356
|
differences += 1;
|
|
2195
2357
|
continue;
|
|
@@ -2216,11 +2378,12 @@ var COMMANDS = [
|
|
|
2216
2378
|
"assets recommend [--target <path>] [--json]",
|
|
2217
2379
|
"assets plan --bundle <bundle-id> [--target <path>] [--json]",
|
|
2218
2380
|
"assets apply --plan <path>",
|
|
2219
|
-
"assets check [--target <path>] [--json]",
|
|
2381
|
+
"assets check [--target <path>] [--strict-registry] [--json]",
|
|
2220
2382
|
"assets public-check [--public-root <path>] [--private-root <path>] [--json]",
|
|
2221
2383
|
"assets npx add|update ... --plan",
|
|
2222
2384
|
"portfolio check --config <path> [--json]",
|
|
2223
2385
|
"portfolio plan --config <path> [--target <id|all>] [--json]",
|
|
2386
|
+
"portfolio assets-check --config <path> [--target <id|all>] [--json]",
|
|
2224
2387
|
"lens scan [--target <path>] [--json]",
|
|
2225
2388
|
"lens inspect [--target <path>] [--format text|json]",
|
|
2226
2389
|
"lens report --target <path> --out <path>",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@pieai/pro-gov",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.7",
|
|
4
4
|
"description": "Project-level distribution kit for Project Governance System.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"ai-agents",
|
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
"access": "public"
|
|
36
36
|
},
|
|
37
37
|
"dependencies": {
|
|
38
|
-
"@pieai/doc-gov": "^0.3.
|
|
38
|
+
"@pieai/doc-gov": "^0.3.7"
|
|
39
39
|
},
|
|
40
40
|
"devDependencies": {
|
|
41
41
|
"@types/node": "24.13.2",
|