aislop 0.4.0 → 0.5.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 +74 -54
- package/dist/cli.js +3755 -1768
- package/dist/{expo-doctor-Cm5892Y8.js → expo-doctor-Bz0LZhQ6.js} +13 -76
- package/dist/generic-BrcWMW7E.js +109 -0
- package/dist/index.d.ts +72 -16
- package/dist/index.js +4549 -2839
- package/dist/{json-L5x3hQdy.js → json-B51etWTw.js} +2 -0
- package/dist/{json-CdzBXUbz.js → json-D_i2_5_-.js} +3 -1
- package/dist/rolldown-runtime-Cbj13DAv.js +20 -0
- package/dist/subprocess-CQUJDGgn.js +59 -0
- package/dist/{engine-info-s7Gy2StX.js → version-CIlgPf8Q.js} +11 -11
- package/package.json +4 -3
|
@@ -1,81 +1,9 @@
|
|
|
1
|
+
import { t as __exportAll } from "./rolldown-runtime-Cbj13DAv.js";
|
|
2
|
+
import { n as runSubprocess } from "./subprocess-CQUJDGgn.js";
|
|
1
3
|
import { createRequire } from "node:module";
|
|
2
4
|
import fs from "node:fs";
|
|
3
5
|
import path from "node:path";
|
|
4
|
-
import { spawn } from "node:child_process";
|
|
5
6
|
|
|
6
|
-
//#region \0rolldown/runtime.js
|
|
7
|
-
var __defProp = Object.defineProperty;
|
|
8
|
-
var __exportAll = (all, no_symbols) => {
|
|
9
|
-
let target = {};
|
|
10
|
-
for (var name in all) {
|
|
11
|
-
__defProp(target, name, {
|
|
12
|
-
get: all[name],
|
|
13
|
-
enumerable: true
|
|
14
|
-
});
|
|
15
|
-
}
|
|
16
|
-
if (!no_symbols) {
|
|
17
|
-
__defProp(target, Symbol.toStringTag, { value: "Module" });
|
|
18
|
-
}
|
|
19
|
-
return target;
|
|
20
|
-
};
|
|
21
|
-
|
|
22
|
-
//#endregion
|
|
23
|
-
//#region src/utils/subprocess.ts
|
|
24
|
-
const runSubprocess = (command, args, options = {}) => {
|
|
25
|
-
return new Promise((resolve, reject) => {
|
|
26
|
-
const child = spawn(command, args, {
|
|
27
|
-
cwd: options.cwd,
|
|
28
|
-
env: {
|
|
29
|
-
...process.env,
|
|
30
|
-
...options.env
|
|
31
|
-
},
|
|
32
|
-
stdio: [
|
|
33
|
-
"ignore",
|
|
34
|
-
"pipe",
|
|
35
|
-
"pipe"
|
|
36
|
-
],
|
|
37
|
-
windowsHide: true
|
|
38
|
-
});
|
|
39
|
-
const stdoutBuffers = [];
|
|
40
|
-
const stderrBuffers = [];
|
|
41
|
-
child.stdout?.on("data", (buffer) => stdoutBuffers.push(buffer));
|
|
42
|
-
child.stderr?.on("data", (buffer) => stderrBuffers.push(buffer));
|
|
43
|
-
let settled = false;
|
|
44
|
-
let timer;
|
|
45
|
-
const finalize = (callback) => {
|
|
46
|
-
if (settled) return;
|
|
47
|
-
settled = true;
|
|
48
|
-
if (timer) clearTimeout(timer);
|
|
49
|
-
callback();
|
|
50
|
-
};
|
|
51
|
-
if (options.timeout && options.timeout > 0) {
|
|
52
|
-
timer = setTimeout(() => {
|
|
53
|
-
child.kill("SIGTERM");
|
|
54
|
-
setTimeout(() => child.kill("SIGKILL"), 1e3).unref();
|
|
55
|
-
finalize(() => reject(/* @__PURE__ */ new Error(`Command timed out after ${options.timeout}ms: ${command}`)));
|
|
56
|
-
}, options.timeout);
|
|
57
|
-
timer.unref();
|
|
58
|
-
}
|
|
59
|
-
child.once("error", (error) => finalize(() => reject(/* @__PURE__ */ new Error(`Failed to run ${command}: ${error.message}`))));
|
|
60
|
-
child.once("close", (code) => {
|
|
61
|
-
finalize(() => resolve({
|
|
62
|
-
stdout: Buffer.concat(stdoutBuffers).toString("utf-8").trim(),
|
|
63
|
-
stderr: Buffer.concat(stderrBuffers).toString("utf-8").trim(),
|
|
64
|
-
exitCode: code
|
|
65
|
-
}));
|
|
66
|
-
});
|
|
67
|
-
});
|
|
68
|
-
};
|
|
69
|
-
const isToolInstalled = async (tool) => {
|
|
70
|
-
try {
|
|
71
|
-
const result = await runSubprocess("which", [tool]);
|
|
72
|
-
return result.exitCode === 0 && result.stdout.length > 0;
|
|
73
|
-
} catch {
|
|
74
|
-
return false;
|
|
75
|
-
}
|
|
76
|
-
};
|
|
77
|
-
|
|
78
|
-
//#endregion
|
|
79
7
|
//#region src/engines/lint/expo-doctor.ts
|
|
80
8
|
var expo_doctor_exports = /* @__PURE__ */ __exportAll({ runExpoDoctor: () => runExpoDoctor });
|
|
81
9
|
const esmRequire = createRequire(import.meta.url);
|
|
@@ -146,7 +74,16 @@ const toDiagnostics = (issues) => issues.map((issue) => {
|
|
|
146
74
|
fixable: false
|
|
147
75
|
};
|
|
148
76
|
});
|
|
77
|
+
const hasExpoInstalled = (rootDirectory) => {
|
|
78
|
+
try {
|
|
79
|
+
createRequire(path.join(rootDirectory, "package.json")).resolve("expo/package.json");
|
|
80
|
+
return true;
|
|
81
|
+
} catch {
|
|
82
|
+
return false;
|
|
83
|
+
}
|
|
84
|
+
};
|
|
149
85
|
const runExpoDoctor = async (context) => {
|
|
86
|
+
if (!hasExpoInstalled(context.rootDirectory)) return [];
|
|
150
87
|
const scriptPath = resolveExpoDoctorScript();
|
|
151
88
|
let stdout = "";
|
|
152
89
|
let stderr = "";
|
|
@@ -187,7 +124,7 @@ const runExpoDoctor = async (context) => {
|
|
|
187
124
|
rule: "expo-doctor/config-error",
|
|
188
125
|
severity: "warning",
|
|
189
126
|
message: configError,
|
|
190
|
-
help: "Install project dependencies, then re-run `aislop scan`.",
|
|
127
|
+
help: "Install project dependencies, then re-run `npx aislop scan`.",
|
|
191
128
|
line: 0,
|
|
192
129
|
column: 0,
|
|
193
130
|
category: "Expo",
|
|
@@ -197,4 +134,4 @@ const runExpoDoctor = async (context) => {
|
|
|
197
134
|
};
|
|
198
135
|
|
|
199
136
|
//#endregion
|
|
200
|
-
export {
|
|
137
|
+
export { runExpoDoctor as n, expo_doctor_exports as t };
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
import { t as __exportAll } from "./rolldown-runtime-Cbj13DAv.js";
|
|
2
|
+
import { n as runSubprocess } from "./subprocess-CQUJDGgn.js";
|
|
3
|
+
|
|
4
|
+
//#region src/engines/lint/generic.ts
|
|
5
|
+
var generic_exports = /* @__PURE__ */ __exportAll({
|
|
6
|
+
fixRubyLint: () => fixRubyLint,
|
|
7
|
+
runGenericLinter: () => runGenericLinter
|
|
8
|
+
});
|
|
9
|
+
const runGenericLinter = async (context, language) => {
|
|
10
|
+
switch (language) {
|
|
11
|
+
case "rust": return runClippy(context);
|
|
12
|
+
case "ruby": return runRubocop(context);
|
|
13
|
+
default: return [];
|
|
14
|
+
}
|
|
15
|
+
};
|
|
16
|
+
const fixRubyLint = async (rootDirectory) => {
|
|
17
|
+
const result = await runSubprocess("rubocop", [
|
|
18
|
+
"-a",
|
|
19
|
+
"--except",
|
|
20
|
+
"Layout"
|
|
21
|
+
], {
|
|
22
|
+
cwd: rootDirectory,
|
|
23
|
+
timeout: 6e4
|
|
24
|
+
});
|
|
25
|
+
if (result.exitCode !== null && result.exitCode > 1) throw new Error(result.stderr || result.stdout || `rubocop exited with code ${result.exitCode}`);
|
|
26
|
+
};
|
|
27
|
+
const runClippy = async (context) => {
|
|
28
|
+
try {
|
|
29
|
+
return parseClippyDiagnostics((await runSubprocess("cargo", [
|
|
30
|
+
"clippy",
|
|
31
|
+
"--message-format=json",
|
|
32
|
+
"--quiet"
|
|
33
|
+
], {
|
|
34
|
+
cwd: context.rootDirectory,
|
|
35
|
+
timeout: 12e4
|
|
36
|
+
})).stdout);
|
|
37
|
+
} catch {
|
|
38
|
+
return [];
|
|
39
|
+
}
|
|
40
|
+
};
|
|
41
|
+
const parseClippyEntry = (line) => {
|
|
42
|
+
if (!line.startsWith("{")) return null;
|
|
43
|
+
try {
|
|
44
|
+
return JSON.parse(line);
|
|
45
|
+
} catch {
|
|
46
|
+
return null;
|
|
47
|
+
}
|
|
48
|
+
};
|
|
49
|
+
const toClippyDiagnostic = (entry) => {
|
|
50
|
+
if (entry.reason !== "compiler-message" || !entry.message) return null;
|
|
51
|
+
const message = entry.message;
|
|
52
|
+
const span = message.spans?.[0];
|
|
53
|
+
return {
|
|
54
|
+
filePath: span?.file_name ?? "",
|
|
55
|
+
engine: "lint",
|
|
56
|
+
rule: `clippy/${message.code?.code ?? "unknown"}`,
|
|
57
|
+
severity: message.level === "error" ? "error" : "warning",
|
|
58
|
+
message: message.message ?? "",
|
|
59
|
+
help: message.children?.[0]?.message ?? "",
|
|
60
|
+
line: span?.line_start ?? 0,
|
|
61
|
+
column: span?.column_start ?? 0,
|
|
62
|
+
category: "Rust Lint",
|
|
63
|
+
fixable: false
|
|
64
|
+
};
|
|
65
|
+
};
|
|
66
|
+
const parseClippyDiagnostics = (output) => {
|
|
67
|
+
const diagnostics = [];
|
|
68
|
+
for (const line of output.split("\n")) {
|
|
69
|
+
const entry = parseClippyEntry(line);
|
|
70
|
+
if (!entry) continue;
|
|
71
|
+
const diagnostic = toClippyDiagnostic(entry);
|
|
72
|
+
if (diagnostic) diagnostics.push(diagnostic);
|
|
73
|
+
}
|
|
74
|
+
return diagnostics;
|
|
75
|
+
};
|
|
76
|
+
const runRubocop = async (context) => {
|
|
77
|
+
try {
|
|
78
|
+
const output = (await runSubprocess("rubocop", [
|
|
79
|
+
"--format",
|
|
80
|
+
"json",
|
|
81
|
+
"--except",
|
|
82
|
+
"Layout"
|
|
83
|
+
], {
|
|
84
|
+
cwd: context.rootDirectory,
|
|
85
|
+
timeout: 6e4
|
|
86
|
+
})).stdout;
|
|
87
|
+
if (!output) return [];
|
|
88
|
+
const parsed = JSON.parse(output);
|
|
89
|
+
const diagnostics = [];
|
|
90
|
+
for (const file of parsed.files ?? []) for (const offense of file.offenses ?? []) diagnostics.push({
|
|
91
|
+
filePath: file.path,
|
|
92
|
+
engine: "lint",
|
|
93
|
+
rule: `rubocop/${offense.cop_name}`,
|
|
94
|
+
severity: offense.severity === "error" || offense.severity === "fatal" ? "error" : "warning",
|
|
95
|
+
message: offense.message,
|
|
96
|
+
help: "",
|
|
97
|
+
line: offense.location?.start_line ?? 0,
|
|
98
|
+
column: offense.location?.start_column ?? 0,
|
|
99
|
+
category: "Ruby Lint",
|
|
100
|
+
fixable: offense.correctable ?? false
|
|
101
|
+
});
|
|
102
|
+
return diagnostics;
|
|
103
|
+
} catch {
|
|
104
|
+
return [];
|
|
105
|
+
}
|
|
106
|
+
};
|
|
107
|
+
|
|
108
|
+
//#endregion
|
|
109
|
+
export { generic_exports as n, runGenericLinter as r, fixRubyLint as t };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,25 @@
|
|
|
1
1
|
import { z } from "zod/v4";
|
|
2
2
|
|
|
3
3
|
//#region src/commands/doctor.d.ts
|
|
4
|
-
|
|
4
|
+
interface DoctorEngineRow {
|
|
5
|
+
engine: string;
|
|
6
|
+
tool: string;
|
|
7
|
+
status: "ok" | "missing" | "skipped";
|
|
8
|
+
remediation?: string;
|
|
9
|
+
skipReason?: string;
|
|
10
|
+
}
|
|
11
|
+
interface BuildDoctorRenderInput {
|
|
12
|
+
projectName: string;
|
|
13
|
+
languageLabel: string;
|
|
14
|
+
rows: DoctorEngineRow[];
|
|
15
|
+
invocation: string;
|
|
16
|
+
printBrand?: boolean;
|
|
17
|
+
}
|
|
18
|
+
declare const buildDoctorRender: (input: BuildDoctorRenderInput) => string;
|
|
19
|
+
interface DoctorOptions {
|
|
20
|
+
printBrand?: boolean;
|
|
21
|
+
}
|
|
22
|
+
declare const doctorCommand: (directory: string, options?: DoctorOptions) => Promise<void>;
|
|
5
23
|
//#endregion
|
|
6
24
|
//#region src/config/schema.d.ts
|
|
7
25
|
declare const AislopConfigSchema: z.ZodObject<{
|
|
@@ -47,6 +65,14 @@ type AislopConfig = z.infer<typeof AislopConfigSchema>;
|
|
|
47
65
|
//#region src/config/index.d.ts
|
|
48
66
|
declare const loadConfig: (directory: string) => AislopConfig;
|
|
49
67
|
//#endregion
|
|
68
|
+
//#region src/ui/rail.d.ts
|
|
69
|
+
type RailStepStatus = "active" | "done" | "warn" | "failed" | "skipped";
|
|
70
|
+
interface RailStep {
|
|
71
|
+
status: RailStepStatus;
|
|
72
|
+
label: string;
|
|
73
|
+
notes?: string[];
|
|
74
|
+
}
|
|
75
|
+
//#endregion
|
|
50
76
|
//#region src/commands/fix.d.ts
|
|
51
77
|
interface FixOptions {
|
|
52
78
|
verbose: boolean;
|
|
@@ -56,29 +82,44 @@ interface FixOptions {
|
|
|
56
82
|
/** Print the prompt to stdout instead of launching an agent */
|
|
57
83
|
prompt?: boolean;
|
|
58
84
|
showHeader?: boolean;
|
|
85
|
+
printBrand?: boolean;
|
|
59
86
|
}
|
|
60
87
|
declare const fixCommand: (directory: string, config: AislopConfig, options?: FixOptions) => Promise<void>;
|
|
61
88
|
//#endregion
|
|
62
89
|
//#region src/commands/init.d.ts
|
|
63
|
-
|
|
90
|
+
interface BuildInitRenderInput {
|
|
91
|
+
steps: RailStep[];
|
|
92
|
+
nextCommand: string;
|
|
93
|
+
includeHeader?: boolean;
|
|
94
|
+
printBrand?: boolean;
|
|
95
|
+
}
|
|
96
|
+
declare const buildInitSuccessRender: (input: BuildInitRenderInput) => string;
|
|
97
|
+
interface InitOptions {
|
|
98
|
+
printBrand?: boolean;
|
|
99
|
+
}
|
|
100
|
+
declare const initCommand: (directory: string, options?: InitOptions) => Promise<void>;
|
|
64
101
|
//#endregion
|
|
65
|
-
//#region src/commands/
|
|
66
|
-
interface
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
showHeader?: boolean;
|
|
72
|
-
/** Used for telemetry to distinguish scan vs ci invocation */
|
|
73
|
-
command?: "scan" | "ci";
|
|
102
|
+
//#region src/commands/rules.d.ts
|
|
103
|
+
interface RuleEntry {
|
|
104
|
+
id: string;
|
|
105
|
+
engine: string;
|
|
106
|
+
severity: "error" | "warning" | "info";
|
|
107
|
+
fixable: boolean;
|
|
74
108
|
}
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
109
|
+
interface BuildRulesRenderInput {
|
|
110
|
+
rules: RuleEntry[];
|
|
111
|
+
invocation?: string;
|
|
112
|
+
printBrand?: boolean;
|
|
113
|
+
}
|
|
114
|
+
declare const buildRulesRender: (input: BuildRulesRenderInput) => string;
|
|
115
|
+
interface RulesOptions {
|
|
116
|
+
printBrand?: boolean;
|
|
117
|
+
}
|
|
118
|
+
declare const rulesCommand: (directory: string, options?: RulesOptions) => Promise<void>;
|
|
78
119
|
//#endregion
|
|
79
120
|
//#region src/utils/discover.d.ts
|
|
80
121
|
type Language = "typescript" | "javascript" | "python" | "go" | "rust" | "java" | "ruby" | "php";
|
|
81
|
-
type Framework = "nextjs" | "react" | "vite" | "remix" | "expo" | "django" | "flask" | "fastapi" | "none";
|
|
122
|
+
type Framework = "nextjs" | "react" | "vite" | "remix" | "expo" | "astro" | "django" | "flask" | "fastapi" | "none";
|
|
82
123
|
interface ProjectInfo {
|
|
83
124
|
rootDirectory: string;
|
|
84
125
|
projectName: string;
|
|
@@ -112,6 +153,21 @@ interface EngineResult {
|
|
|
112
153
|
skipReason?: string;
|
|
113
154
|
}
|
|
114
155
|
//#endregion
|
|
156
|
+
//#region src/commands/scan.d.ts
|
|
157
|
+
interface ScanOptions {
|
|
158
|
+
changes: boolean;
|
|
159
|
+
staged: boolean;
|
|
160
|
+
verbose: boolean;
|
|
161
|
+
json: boolean;
|
|
162
|
+
showHeader?: boolean;
|
|
163
|
+
printBrand?: boolean;
|
|
164
|
+
/** Used for telemetry to distinguish scan vs ci invocation */
|
|
165
|
+
command?: "scan" | "ci";
|
|
166
|
+
}
|
|
167
|
+
declare const scanCommand: (directory: string, config: AislopConfig, options: ScanOptions) => Promise<{
|
|
168
|
+
exitCode: number;
|
|
169
|
+
}>;
|
|
170
|
+
//#endregion
|
|
115
171
|
//#region src/scoring/index.d.ts
|
|
116
172
|
interface ScoreResult {
|
|
117
173
|
score: number;
|
|
@@ -122,4 +178,4 @@ declare const calculateScore: (diagnostics: Diagnostic[], weights: Record<string
|
|
|
122
178
|
ok: number;
|
|
123
179
|
}, sourceFileCount?: number, smoothing?: number) => ScoreResult;
|
|
124
180
|
//#endregion
|
|
125
|
-
export { type AislopConfig, type Diagnostic, type EngineName, type EngineResult, type Framework, type Language, type ProjectInfo, type ScoreResult, type Severity, calculateScore, discoverProject, doctorCommand, fixCommand, initCommand, loadConfig, scanCommand };
|
|
181
|
+
export { type AislopConfig, type Diagnostic, type EngineName, type EngineResult, type Framework, type Language, type ProjectInfo, type ScoreResult, type Severity, buildDoctorRender, buildInitSuccessRender, buildRulesRender, calculateScore, discoverProject, doctorCommand, fixCommand, initCommand, loadConfig, rulesCommand, scanCommand };
|