@aionlabsai/aion 0.2.15 → 0.2.17

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.
@@ -0,0 +1,209 @@
1
+ import { spawnSync } from 'child_process';
2
+ import { existsSync, readFileSync } from 'fs';
3
+ import { join } from 'path';
4
+ // ── Provider detection ────────────────────────────────────────────────────────
5
+ export function detectProviders() {
6
+ const detected = [];
7
+ if (process.env['AWS_ACCESS_KEY_ID'] || process.env['AWS_PROFILE'])
8
+ detected.push('aws');
9
+ if (process.env['AZURE_SUBSCRIPTION_ID'] || process.env['AZURE_TENANT_ID'])
10
+ detected.push('azure');
11
+ if (process.env['GOOGLE_APPLICATION_CREDENTIALS'] || process.env['GOOGLE_CLOUD_PROJECT'])
12
+ detected.push('gcp');
13
+ return detected;
14
+ }
15
+ function cli(cmd, args, timeout = 15000) {
16
+ const r = spawnSync(cmd, args, { encoding: 'utf8', timeout });
17
+ return { ok: r.status === 0, stdout: r.stdout ?? '' };
18
+ }
19
+ // ── AWS (read-only) ───────────────────────────────────────────────────────────
20
+ function readAws() {
21
+ const check = cli('aws', ['sts', 'get-caller-identity', '--output', 'json']);
22
+ if (!check.ok)
23
+ return { ok: false, resources: [] };
24
+ const resources = [];
25
+ // EC2 instances
26
+ const ec2 = cli('aws', ['ec2', 'describe-instances', '--query',
27
+ 'Reservations[].Instances[].[InstanceId,State.Name,InstanceType]', '--output', 'json']);
28
+ if (ec2.ok) {
29
+ try {
30
+ const items = JSON.parse(ec2.stdout);
31
+ items.forEach(([id, state, type]) => resources.push({ type: 'EC2', name: `${id} (${type})`, status: state }));
32
+ }
33
+ catch { /* skip */ }
34
+ }
35
+ // RDS
36
+ const rds = cli('aws', ['rds', 'describe-db-instances', '--query',
37
+ 'DBInstances[].[DBInstanceIdentifier,DBInstanceStatus,Engine]', '--output', 'json']);
38
+ if (rds.ok) {
39
+ try {
40
+ const items = JSON.parse(rds.stdout);
41
+ items.forEach(([id, status, engine]) => resources.push({ type: 'RDS', name: `${id} (${engine})`, status }));
42
+ }
43
+ catch { /* skip */ }
44
+ }
45
+ // S3 buckets
46
+ const s3 = cli('aws', ['s3api', 'list-buckets', '--query', 'Buckets[].Name', '--output', 'json']);
47
+ if (s3.ok) {
48
+ try {
49
+ const names = JSON.parse(s3.stdout);
50
+ names.forEach((n) => resources.push({ type: 'S3', name: n }));
51
+ }
52
+ catch { /* skip */ }
53
+ }
54
+ // Lambda
55
+ const lambda = cli('aws', ['lambda', 'list-functions', '--query',
56
+ 'Functions[].[FunctionName,Runtime,State]', '--output', 'json']);
57
+ if (lambda.ok) {
58
+ try {
59
+ const items = JSON.parse(lambda.stdout);
60
+ items.forEach(([name, runtime, state]) => resources.push({ type: 'Lambda', name: `${name} (${runtime})`, status: state }));
61
+ }
62
+ catch { /* skip */ }
63
+ }
64
+ return { ok: true, resources };
65
+ }
66
+ // ── Azure (read-only) ─────────────────────────────────────────────────────────
67
+ function readAzure() {
68
+ const check = cli('az', ['account', 'show', '--output', 'json']);
69
+ if (!check.ok)
70
+ return { ok: false, resources: [] };
71
+ const resources = [];
72
+ // VMs
73
+ const vms = cli('az', ['vm', 'list', '--output', 'json', '--query', '[].{name:name,status:provisioningState,location:location}']);
74
+ if (vms.ok) {
75
+ try {
76
+ const items = JSON.parse(vms.stdout);
77
+ items.forEach((vm) => resources.push({ type: 'VM', name: vm.name, region: vm.location, status: vm.status }));
78
+ }
79
+ catch { /* skip */ }
80
+ }
81
+ // AKS
82
+ const aks = cli('az', ['aks', 'list', '--output', 'json', '--query', '[].{name:name,location:location}']);
83
+ if (aks.ok) {
84
+ try {
85
+ const items = JSON.parse(aks.stdout);
86
+ items.forEach((c) => resources.push({ type: 'AKS', name: c.name, region: c.location }));
87
+ }
88
+ catch { /* skip */ }
89
+ }
90
+ // Databases
91
+ const sql = cli('az', ['sql', 'server', 'list', '--output', 'json', '--query', '[].{name:name,location:location}']);
92
+ if (sql.ok) {
93
+ try {
94
+ const items = JSON.parse(sql.stdout);
95
+ items.forEach((s) => resources.push({ type: 'SQL', name: s.name, region: s.location }));
96
+ }
97
+ catch { /* skip */ }
98
+ }
99
+ return { ok: true, resources };
100
+ }
101
+ // ── GCP (read-only) ───────────────────────────────────────────────────────────
102
+ function readGcp() {
103
+ const check = cli('gcloud', ['auth', 'print-access-token'], 5000);
104
+ if (!check.ok)
105
+ return { ok: false, resources: [] };
106
+ const resources = [];
107
+ const project = process.env['GOOGLE_CLOUD_PROJECT'] ?? '';
108
+ // Compute instances
109
+ const gce = cli('gcloud', ['compute', 'instances', 'list', '--format=json', ...(project ? ['--project', project] : [])]);
110
+ if (gce.ok) {
111
+ try {
112
+ const items = JSON.parse(gce.stdout);
113
+ items.forEach((i) => resources.push({ type: 'GCE', name: i.name, region: i.zone, status: i.status }));
114
+ }
115
+ catch { /* skip */ }
116
+ }
117
+ // Cloud SQL
118
+ const sql = cli('gcloud', ['sql', 'instances', 'list', '--format=json', ...(project ? ['--project', project] : [])]);
119
+ if (sql.ok) {
120
+ try {
121
+ const items = JSON.parse(sql.stdout);
122
+ items.forEach((i) => resources.push({ type: 'CloudSQL', name: i.name, region: i.region, status: i.state }));
123
+ }
124
+ catch { /* skip */ }
125
+ }
126
+ return { ok: true, resources };
127
+ }
128
+ // ── Gap detection ─────────────────────────────────────────────────────────────
129
+ function detectGaps(cwd, resources) {
130
+ const gaps = [];
131
+ const resourceTypes = new Set(resources.map((r) => r.type.toLowerCase()));
132
+ // Read project signals
133
+ let envContent = '';
134
+ for (const f of ['.env.example', '.env.sample', '.env']) {
135
+ try {
136
+ envContent += readFileSync(join(cwd, f), 'utf8');
137
+ }
138
+ catch { /* ok */ }
139
+ }
140
+ // Check sbom for common services
141
+ const sbomPath = join(cwd, '.ai-runtime', 'sbom.json');
142
+ let deps = [];
143
+ if (existsSync(sbomPath)) {
144
+ try {
145
+ deps = Object.keys(JSON.parse(readFileSync(sbomPath, 'utf8')).packages ?? {});
146
+ }
147
+ catch { /* ok */ }
148
+ }
149
+ // Check IaC files
150
+ const hasIac = ['terraform', 'serverless.yml', 'docker-compose.yml', 'k8s', 'helm'].some((f) => existsSync(join(cwd, f)));
151
+ if (!hasIac) {
152
+ gaps.push({ severity: 'medium', category: 'missing-service', description: 'No IaC files detected', detail: 'No terraform/, serverless.yml, docker-compose.yml, or k8s/ found — infrastructure is not version-controlled' });
153
+ }
154
+ // DB dependency but no DB resource in cloud
155
+ const hasDbDep = deps.some((d) => /pg|mysql|mongo|redis|sqlite|prisma|sequelize|typeorm/i.test(d)) ||
156
+ /DATABASE_URL|REDIS_URL|MONGO_URI|DB_HOST/i.test(envContent);
157
+ const hasDbResource = resourceTypes.has('rds') || resourceTypes.has('sql') || resourceTypes.has('cloudsql') || resourceTypes.has('cosmos');
158
+ if (hasDbDep && !hasDbResource) {
159
+ gaps.push({ severity: 'high', category: 'missing-service', description: 'Database dependency with no managed DB resource', detail: 'Project uses a database client but no managed database found in cloud account' });
160
+ }
161
+ // S3/storage usage but no bucket
162
+ const hasStorageDep = deps.some((d) => /aws-sdk|@aws-sdk\/client-s3|googleapis|azure-storage/i.test(d)) ||
163
+ /S3_BUCKET|STORAGE_BUCKET|BLOB_CONTAINER/i.test(envContent);
164
+ const hasStorage = resourceTypes.has('s3') || resourceTypes.has('blob') || resourceTypes.has('gcs');
165
+ if (hasStorageDep && !hasStorage) {
166
+ gaps.push({ severity: 'high', category: 'missing-service', description: 'Storage SDK used but no bucket/container found', detail: 'Project imports cloud storage SDK but no bucket or container visible in cloud account' });
167
+ }
168
+ // No compute at all
169
+ const hasCompute = resourceTypes.has('ec2') || resourceTypes.has('vm') || resourceTypes.has('gce') ||
170
+ resourceTypes.has('lambda') || resourceTypes.has('aks') || resourceTypes.has('gke');
171
+ if (resources.length > 0 && !hasCompute) {
172
+ gaps.push({ severity: 'medium', category: 'missing-service', description: 'No compute resources visible', detail: 'Cloud account has resources but no compute instances, containers, or functions found' });
173
+ }
174
+ // Secrets in env but not likely in secrets manager
175
+ const secretVars = (envContent.match(/^[A-Z_]+_(?:KEY|SECRET|TOKEN|PASSWORD|CREDENTIAL)=.+/gm) ?? []);
176
+ if (secretVars.length > 3) {
177
+ gaps.push({ severity: 'medium', category: 'config-mismatch', description: `${secretVars.length} secret-like env vars in .env.example`, detail: 'Consider moving secrets to AWS Secrets Manager / Azure Key Vault / GCP Secret Manager' });
178
+ }
179
+ return gaps;
180
+ }
181
+ // ── Main ──────────────────────────────────────────────────────────────────────
182
+ export function analyzeCloud(cwd, provider) {
183
+ let result;
184
+ if (provider === 'aws')
185
+ result = readAws();
186
+ else if (provider === 'azure')
187
+ result = readAzure();
188
+ else
189
+ result = readGcp();
190
+ if (!result.ok) {
191
+ return {
192
+ provider,
193
+ authenticated: false,
194
+ resources: [],
195
+ gaps: [],
196
+ summary: `Not authenticated — configure credentials for ${provider.toUpperCase()} CLI`,
197
+ };
198
+ }
199
+ const gaps = detectGaps(cwd, result.resources);
200
+ const highCount = gaps.filter((g) => g.severity === 'high').length;
201
+ return {
202
+ provider,
203
+ authenticated: true,
204
+ resources: result.resources,
205
+ gaps,
206
+ summary: `${result.resources.length} resources found, ${gaps.length} gaps${highCount > 0 ? ` (${highCount} critical)` : ''}`,
207
+ };
208
+ }
209
+ //# sourceMappingURL=cloud-analyzer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cloud-analyzer.js","sourceRoot":"","sources":["../../src/infra/cloud-analyzer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,24 @@
1
+ import type { DepGraph } from './dep-graph.js';
2
+ interface StoredGraph {
3
+ nodes: Array<{
4
+ file: string;
5
+ loc: number;
6
+ exports: string[];
7
+ }>;
8
+ edges: Array<[string, string]>;
9
+ builtAt: number;
10
+ }
11
+ export declare function saveDepGraph(cwd: string, graph: DepGraph): void;
12
+ export declare function loadDepGraph(cwd: string): StoredGraph | null;
13
+ export declare function isDepGraphCached(cwd: string): boolean;
14
+ export interface ImpactResult {
15
+ changedFile: string;
16
+ directImporters: string[];
17
+ transitiveFiles: string[];
18
+ totalImpact: number;
19
+ hotspotOverlap: string[];
20
+ }
21
+ export declare function computeImpact(graph: StoredGraph, changedFile: string, hotspotFiles?: string[]): ImpactResult;
22
+ export declare function formatImpactReport(result: ImpactResult): string;
23
+ export {};
24
+ //# sourceMappingURL=dep-graph-db.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dep-graph-db.d.ts","sourceRoot":"","sources":["../../src/infra/dep-graph-db.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAM/C,UAAU,WAAW;IACnB,KAAK,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,EAAE,CAAA;KAAE,CAAC,CAAC;IAC/D,KAAK,EAAE,KAAK,CAAC,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAC/B,OAAO,EAAE,MAAM,CAAC;CACjB;AAQD,wBAAgB,YAAY,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,QAAQ,GAAG,IAAI,CAW/D;AAED,wBAAgB,YAAY,CAAC,GAAG,EAAE,MAAM,GAAG,WAAW,GAAG,IAAI,CAM5D;AAED,wBAAgB,gBAAgB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAErD;AAID,MAAM,WAAW,YAAY;IAC3B,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,MAAM,EAAE,CAAC;IAC1B,eAAe,EAAE,MAAM,EAAE,CAAC;IAC1B,WAAW,EAAE,MAAM,CAAC;IACpB,cAAc,EAAE,MAAM,EAAE,CAAC;CAC1B;AAED,wBAAgB,aAAa,CAAC,KAAK,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,EAAE,YAAY,GAAE,MAAM,EAAO,GAAG,YAAY,CAkChH;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,YAAY,GAAG,MAAM,CA2B/D"}
@@ -0,0 +1,94 @@
1
+ import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'fs';
2
+ import { join } from 'path';
3
+ const CACHE_TTL_MS = 60 * 60 * 1000; // 1 hour
4
+ function storedPath(cwd) {
5
+ return join(cwd, '.ai-runtime', 'dep-graph.json');
6
+ }
7
+ export function saveDepGraph(cwd, graph) {
8
+ const nodes = [...graph.nodes.values()].map((n) => ({
9
+ file: n.file, loc: n.loc, exports: n.exports,
10
+ }));
11
+ const edges = [];
12
+ for (const node of graph.nodes.values()) {
13
+ for (const imp of node.imports)
14
+ edges.push([node.file, imp]);
15
+ }
16
+ const stored = { nodes, edges, builtAt: Date.now() };
17
+ mkdirSync(join(cwd, '.ai-runtime'), { recursive: true });
18
+ writeFileSync(storedPath(cwd), JSON.stringify(stored), 'utf8');
19
+ }
20
+ export function loadDepGraph(cwd) {
21
+ try {
22
+ const raw = JSON.parse(readFileSync(storedPath(cwd), 'utf8'));
23
+ if (Date.now() - raw.builtAt > CACHE_TTL_MS)
24
+ return null; // stale
25
+ return raw;
26
+ }
27
+ catch {
28
+ return null;
29
+ }
30
+ }
31
+ export function isDepGraphCached(cwd) {
32
+ return existsSync(storedPath(cwd));
33
+ }
34
+ export function computeImpact(graph, changedFile, hotspotFiles = []) {
35
+ // Build reverse adjacency: file → files that import it
36
+ const reverseEdges = new Map();
37
+ for (const [from, to] of graph.edges) {
38
+ const list = reverseEdges.get(to) ?? [];
39
+ list.push(from);
40
+ reverseEdges.set(to, list);
41
+ }
42
+ const directImporters = reverseEdges.get(changedFile) ?? [];
43
+ // BFS for transitive impact
44
+ const visited = new Set();
45
+ const queue = [...directImporters];
46
+ while (queue.length) {
47
+ const cur = queue.shift();
48
+ if (visited.has(cur))
49
+ continue;
50
+ visited.add(cur);
51
+ for (const importer of reverseEdges.get(cur) ?? []) {
52
+ if (!visited.has(importer))
53
+ queue.push(importer);
54
+ }
55
+ }
56
+ const transitiveFiles = [...visited].filter((f) => !directImporters.includes(f)).sort();
57
+ const hotspotSet = new Set(hotspotFiles);
58
+ const hotspotOverlap = [...visited].filter((f) => hotspotSet.has(f)).sort();
59
+ return {
60
+ changedFile,
61
+ directImporters: directImporters.sort(),
62
+ transitiveFiles,
63
+ totalImpact: visited.size,
64
+ hotspotOverlap,
65
+ };
66
+ }
67
+ export function formatImpactReport(result) {
68
+ const lines = [];
69
+ lines.push(`Impact analysis: ${result.changedFile}`);
70
+ lines.push(`Total affected: ${result.totalImpact} file(s)\n`);
71
+ if (result.directImporters.length === 0) {
72
+ lines.push('No files import this module directly.');
73
+ return lines.join('\n');
74
+ }
75
+ lines.push(`Direct importers (${result.directImporters.length}):`);
76
+ for (const f of result.directImporters)
77
+ lines.push(` → ${f}`);
78
+ if (result.transitiveFiles.length > 0) {
79
+ lines.push(`\nTransitive impact (${result.transitiveFiles.length} more):`);
80
+ for (const f of result.transitiveFiles.slice(0, 20))
81
+ lines.push(` ↪ ${f}`);
82
+ if (result.transitiveFiles.length > 20)
83
+ lines.push(` ... and ${result.transitiveFiles.length - 20} more`);
84
+ }
85
+ if (result.hotspotOverlap.length > 0) {
86
+ lines.push(`\nHotspot overlap (${result.hotspotOverlap.length} high-risk files also affected):`);
87
+ for (const f of result.hotspotOverlap)
88
+ lines.push(` ⚠ ${f}`);
89
+ }
90
+ const risk = result.totalImpact > 20 ? 'HIGH' : result.totalImpact > 5 ? 'MEDIUM' : 'LOW';
91
+ lines.push(`\nRisk: ${risk}`);
92
+ return lines.join('\n');
93
+ }
94
+ //# sourceMappingURL=dep-graph-db.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dep-graph-db.js","sourceRoot":"","sources":["../../src/infra/dep-graph-db.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,15 @@
1
+ export interface DocGap {
2
+ type: 'missing-file' | 'missing-section' | 'undocumented-export' | 'missing-docstring';
3
+ severity: 'high' | 'medium' | 'low';
4
+ file?: string;
5
+ description: string;
6
+ suggestion: string;
7
+ }
8
+ export interface DocsReport {
9
+ gaps: DocGap[];
10
+ score: number;
11
+ existingDocs: string[];
12
+ summary: string;
13
+ }
14
+ export declare function analyzeProjectDocs(cwd: string): DocsReport;
15
+ //# sourceMappingURL=docs-analyzer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"docs-analyzer.d.ts","sourceRoot":"","sources":["../../src/infra/docs-analyzer.ts"],"names":[],"mappings":"AAIA,MAAM,WAAW,MAAM;IACrB,IAAI,EAAE,cAAc,GAAG,iBAAiB,GAAG,qBAAqB,GAAG,mBAAmB,CAAC;IACvF,QAAQ,EAAE,MAAM,GAAG,QAAQ,GAAG,KAAK,CAAC;IACpC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;IACd,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,OAAO,EAAE,MAAM,CAAC;CACjB;AAqFD,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,MAAM,GAAG,UAAU,CA+C1D"}
@@ -0,0 +1,136 @@
1
+ import { existsSync, readFileSync, readdirSync, statSync } from 'fs';
2
+ import { join, relative, extname } from 'path';
3
+ import { IGNORE_DIRS, SOURCE_EXTS } from '../cli/cli-utils.js';
4
+ // ── Required files ────────────────────────────────────────────────────────────
5
+ const REQUIRED_FILES = [
6
+ { file: 'README.md', severity: 'high', suggestion: 'Create README.md with install, usage, and configuration sections' },
7
+ { file: 'CHANGELOG.md', severity: 'low', suggestion: 'Create CHANGELOG.md to track version history' },
8
+ { file: 'CONTRIBUTING.md', severity: 'low', suggestion: 'Create CONTRIBUTING.md with development setup and PR guidelines' },
9
+ { file: '.env.example', severity: 'medium', suggestion: 'Create .env.example listing all required environment variables' },
10
+ ];
11
+ const README_SECTIONS = [
12
+ { pattern: /#+\s*(install|installation|getting.?started)/i, label: 'Installation', severity: 'high' },
13
+ { pattern: /#+\s*(usage|quick.?start|example)/i, label: 'Usage', severity: 'high' },
14
+ { pattern: /#+\s*(config|configuration|environment|env)/i, label: 'Configuration', severity: 'medium' },
15
+ { pattern: /#+\s*(api|endpoints|routes)/i, label: 'API reference', severity: 'low' },
16
+ { pattern: /#+\s*(contribut|development|dev.?setup)/i, label: 'Contributing', severity: 'low' },
17
+ ];
18
+ // ── JSDoc / docstring detection ───────────────────────────────────────────────
19
+ function hasDocstring(content, exportLine, lines) {
20
+ // Check the line above for JSDoc /** or Python docstring """
21
+ const above = lines[exportLine - 2] ?? '';
22
+ const twoAbove = lines[exportLine - 3] ?? '';
23
+ return above.trim().startsWith('*') ||
24
+ above.trim().startsWith('*/') ||
25
+ twoAbove.trim().startsWith('/**') ||
26
+ above.trim().startsWith('"""') ||
27
+ above.trim().startsWith("'''");
28
+ }
29
+ const EXPORT_RE = /^export\s+(function|class|const|interface|type|enum|async function)\s+([A-Za-z_]\w*)/;
30
+ const PY_DEF_RE = /^(?:def|class|async def)\s+([A-Za-z_]\w*)/;
31
+ function findUndocumentedExports(cwd, file) {
32
+ const gaps = [];
33
+ let content;
34
+ try {
35
+ content = readFileSync(join(cwd, file), 'utf8');
36
+ }
37
+ catch {
38
+ return [];
39
+ }
40
+ const lines = content.split('\n');
41
+ const ext = extname(file);
42
+ const isPy = ext === '.py';
43
+ lines.forEach((line, i) => {
44
+ const m = isPy ? PY_DEF_RE.exec(line.trim()) : EXPORT_RE.exec(line);
45
+ if (!m)
46
+ return;
47
+ const name = isPy ? m[1] : m[2];
48
+ if (!name || name.startsWith('_'))
49
+ return; // skip private
50
+ if (!hasDocstring(content, i, lines)) {
51
+ gaps.push({
52
+ type: 'missing-docstring',
53
+ severity: 'low',
54
+ file,
55
+ description: `${isPy ? 'def' : 'export'} \`${name}\` has no docstring`,
56
+ suggestion: `Add JSDoc/docstring above \`${name}\` in ${file}`,
57
+ });
58
+ }
59
+ });
60
+ return gaps.slice(0, 5); // max 5 per file to avoid noise
61
+ }
62
+ // ── Walker ────────────────────────────────────────────────────────────────────
63
+ function walkSrc(cwd) {
64
+ const files = [];
65
+ const walk = (dir) => {
66
+ let entries;
67
+ try {
68
+ entries = readdirSync(dir);
69
+ }
70
+ catch {
71
+ return;
72
+ }
73
+ for (const entry of entries) {
74
+ if (IGNORE_DIRS.has(entry) || entry.startsWith('.'))
75
+ continue;
76
+ const full = join(dir, entry);
77
+ try {
78
+ if (statSync(full).isDirectory()) {
79
+ walk(full);
80
+ continue;
81
+ }
82
+ if (SOURCE_EXTS.includes(extname(entry)))
83
+ files.push(relative(cwd, full));
84
+ }
85
+ catch { /* skip */ }
86
+ }
87
+ };
88
+ walk(cwd);
89
+ return files;
90
+ }
91
+ // ── Main ──────────────────────────────────────────────────────────────────────
92
+ export function analyzeProjectDocs(cwd) {
93
+ const gaps = [];
94
+ const existingDocs = [];
95
+ // 1. Required files
96
+ for (const { file, severity, suggestion } of REQUIRED_FILES) {
97
+ if (existsSync(join(cwd, file))) {
98
+ existingDocs.push(file);
99
+ }
100
+ else {
101
+ gaps.push({ type: 'missing-file', severity, description: `Missing ${file}`, suggestion, file });
102
+ }
103
+ }
104
+ // 2. README sections
105
+ const readmePath = join(cwd, 'README.md');
106
+ if (existsSync(readmePath)) {
107
+ const readme = readFileSync(readmePath, 'utf8');
108
+ for (const { pattern, label, severity } of README_SECTIONS) {
109
+ if (!pattern.test(readme)) {
110
+ gaps.push({
111
+ type: 'missing-section',
112
+ severity,
113
+ file: 'README.md',
114
+ description: `README.md missing "${label}" section`,
115
+ suggestion: `Add a ## ${label} section to README.md`,
116
+ });
117
+ }
118
+ }
119
+ }
120
+ // 3. Undocumented exports (sample: top 20 files by path depth)
121
+ const srcFiles = walkSrc(cwd).slice(0, 20);
122
+ for (const file of srcFiles) {
123
+ if (/\.(test|spec)\./.test(file))
124
+ continue;
125
+ gaps.push(...findUndocumentedExports(cwd, file));
126
+ }
127
+ // Score: start at 100, deduct per gap
128
+ const deductions = { high: 20, medium: 10, low: 3 };
129
+ const score = Math.max(0, 100 - gaps.reduce((s, g) => s + deductions[g.severity], 0));
130
+ const highCount = gaps.filter((g) => g.severity === 'high').length;
131
+ const summary = highCount > 0
132
+ ? `${gaps.length} documentation gaps found (${highCount} critical)`
133
+ : `${gaps.length} documentation gaps found`;
134
+ return { gaps, score, existingDocs, summary };
135
+ }
136
+ //# sourceMappingURL=docs-analyzer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"docs-analyzer.js","sourceRoot":"","sources":["../../src/infra/docs-analyzer.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aionlabsai/aion",
3
- "version": "0.2.15",
3
+ "version": "0.2.17",
4
4
  "description": "Multi-agent AI engineering runtime — audit, fix, graph, analyze",
5
5
  "type": "module",
6
6
  "bin": {