nanos-lint 3.0.1 → 3.1.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/README.md +52 -14
- package/action.yml +47 -2
- package/dist/{cli-B9EpAClV.js → cli-Cb3wLBCr.js} +480 -30
- package/dist/cli-Cb3wLBCr.js.map +1 -0
- package/dist/cli-dxsaVVVq.d.ts.map +1 -1
- package/dist/cli.js +1 -1
- package/dist/index.d.ts +65 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -2
- package/package.json +1 -1
- package/dist/cli-B9EpAClV.js.map +0 -1
|
@@ -1186,10 +1186,12 @@ function mergeConfigs(base, override = {}, definitionsPath = getDefaultAnnotatio
|
|
|
1186
1186
|
const normalizedDefPath = resolvedPath.split(path.sep).join("/");
|
|
1187
1187
|
const baseLibraries = base.workspace?.library ?? [];
|
|
1188
1188
|
const overrideLibraries = override.workspace?.library ?? [];
|
|
1189
|
+
const depLibraries = (options?.dependencyLibraries ?? []).map((p) => p.replace(/\\/g, "/"));
|
|
1189
1190
|
const librarySet = /* @__PURE__ */ new Set([
|
|
1190
1191
|
normalizedDefPath,
|
|
1191
1192
|
...baseLibraries,
|
|
1192
|
-
...overrideLibraries
|
|
1193
|
+
...overrideLibraries,
|
|
1194
|
+
...depLibraries
|
|
1193
1195
|
]);
|
|
1194
1196
|
const baseGlobals = base.diagnostics?.globals ?? [];
|
|
1195
1197
|
const overrideGlobals = override.diagnostics?.globals ?? [];
|
|
@@ -1328,7 +1330,10 @@ function buildWorkspaceConfig(workspacePath, customConfigPath, options) {
|
|
|
1328
1330
|
}
|
|
1329
1331
|
cliIgnore = expanded;
|
|
1330
1332
|
}
|
|
1331
|
-
const merged = mergeConfigs(defaultTemplate, userConfig, activeAnnotationsPath, {
|
|
1333
|
+
const merged = mergeConfigs(defaultTemplate, userConfig, activeAnnotationsPath, {
|
|
1334
|
+
cliIgnore,
|
|
1335
|
+
dependencyLibraries: options?.dependencyLibraries
|
|
1336
|
+
});
|
|
1332
1337
|
if (!hasCliIgnore) {
|
|
1333
1338
|
const resolvedTarget = path.resolve(workspacePath);
|
|
1334
1339
|
if (fs.existsSync(path.join(resolvedTarget, "main.lua")) && (fs.existsSync(path.join(resolvedTarget, "bin", "lua-language-server.exe")) || fs.existsSync(path.join(resolvedTarget, "bin", "lua-language-server")))) {
|
|
@@ -1343,6 +1348,11 @@ function buildWorkspaceConfig(workspacePath, customConfigPath, options) {
|
|
|
1343
1348
|
])];
|
|
1344
1349
|
}
|
|
1345
1350
|
}
|
|
1351
|
+
if (options?.unrequestedExclusions && options.unrequestedExclusions.length > 0) {
|
|
1352
|
+
merged.files = merged.files ?? {};
|
|
1353
|
+
const existingExclude = merged.files.exclude ?? [];
|
|
1354
|
+
merged.files.exclude = [.../* @__PURE__ */ new Set([...existingExclude, ...options.unrequestedExclusions])];
|
|
1355
|
+
}
|
|
1346
1356
|
return merged;
|
|
1347
1357
|
}
|
|
1348
1358
|
/**
|
|
@@ -6340,6 +6350,236 @@ async function downloadAndPromoteLuaLS(resolvedVersion, info, destDir, binaryPat
|
|
|
6340
6350
|
}
|
|
6341
6351
|
}
|
|
6342
6352
|
//#endregion
|
|
6353
|
+
//#region src/target-resolver.ts
|
|
6354
|
+
/** Resolves the canonical filesystem path, falling back to original path on failure. */
|
|
6355
|
+
function getCanonicalPath(p) {
|
|
6356
|
+
try {
|
|
6357
|
+
return fs.realpathSync.native ? fs.realpathSync.native(p) : fs.realpathSync(p);
|
|
6358
|
+
} catch {
|
|
6359
|
+
return p;
|
|
6360
|
+
}
|
|
6361
|
+
}
|
|
6362
|
+
/** Determines whether a path points to the root of a filesystem volume. */
|
|
6363
|
+
function isFilesystemRoot(dir) {
|
|
6364
|
+
const stripped = dir.trim();
|
|
6365
|
+
if (stripped === "/" || stripped === "\\" || stripped === "") return true;
|
|
6366
|
+
if (/^[a-zA-Z]:[\\/]?$/.test(stripped)) return true;
|
|
6367
|
+
const norm = path.resolve(stripped);
|
|
6368
|
+
if (norm === "/" || norm === "\\") return true;
|
|
6369
|
+
return /^[a-zA-Z]:[\\/]?$/.test(norm);
|
|
6370
|
+
}
|
|
6371
|
+
/**
|
|
6372
|
+
* Computes the lowest common ancestor directory for a set of paths.
|
|
6373
|
+
* All paths must reside on the same filesystem root or volume.
|
|
6374
|
+
*/
|
|
6375
|
+
function findCommonAncestorDirectory(paths) {
|
|
6376
|
+
if (paths.length === 0) return path.resolve(".");
|
|
6377
|
+
const resolved = paths.map((p) => {
|
|
6378
|
+
const abs = path.resolve(p);
|
|
6379
|
+
try {
|
|
6380
|
+
if (fs.existsSync(abs)) return fs.statSync(abs).isDirectory() ? abs : path.dirname(abs);
|
|
6381
|
+
} catch (err) {}
|
|
6382
|
+
return path.dirname(abs);
|
|
6383
|
+
});
|
|
6384
|
+
if (resolved.length === 1 && resolved[0]) return resolved[0];
|
|
6385
|
+
const isWin = process.platform === "win32";
|
|
6386
|
+
const splitPaths = resolved.map((p) => path.resolve(p).split(path.sep));
|
|
6387
|
+
const first = splitPaths[0];
|
|
6388
|
+
if (!first || first.length === 0) return path.resolve(".");
|
|
6389
|
+
const firstRoot = first[0];
|
|
6390
|
+
if (!splitPaths.every((p) => {
|
|
6391
|
+
const rootSeg = p[0];
|
|
6392
|
+
if (rootSeg === void 0) return false;
|
|
6393
|
+
return isWin ? rootSeg.toLowerCase() === firstRoot?.toLowerCase() : rootSeg === firstRoot;
|
|
6394
|
+
}) || firstRoot === void 0) throw new ConfigError(`Cannot check paths across different root drives or volumes: ${paths.join(", ")}`, "ERR_MULTIPLE_ROOTS", "Ensure all checked paths are within the same workspace or project root.");
|
|
6395
|
+
const minLen = Math.min(...splitPaths.map((p) => p.length));
|
|
6396
|
+
let commonLen = 0;
|
|
6397
|
+
for (let i = 0; i < minLen; i++) {
|
|
6398
|
+
const segment = first[i];
|
|
6399
|
+
if (segment === void 0) break;
|
|
6400
|
+
if (!splitPaths.every((p) => {
|
|
6401
|
+
const seg = p[i];
|
|
6402
|
+
if (seg === void 0) return false;
|
|
6403
|
+
return isWin ? seg.toLowerCase() === segment.toLowerCase() : seg === segment;
|
|
6404
|
+
})) break;
|
|
6405
|
+
commonLen++;
|
|
6406
|
+
}
|
|
6407
|
+
if (commonLen === 0) throw new ConfigError(`Cannot check paths across different root drives or volumes: ${paths.join(", ")}`, "ERR_MULTIPLE_ROOTS", "Ensure all checked paths are within the same workspace or project root.");
|
|
6408
|
+
let commonPath = first.slice(0, commonLen).join(path.sep);
|
|
6409
|
+
if (!commonPath) commonPath = path.sep;
|
|
6410
|
+
if (isWin && /^[a-zA-Z]:$/.test(commonPath)) commonPath = `${commonPath}\\`;
|
|
6411
|
+
return path.resolve(commonPath);
|
|
6412
|
+
}
|
|
6413
|
+
/**
|
|
6414
|
+
* Searches upward from a starting directory to locate an enclosing project root
|
|
6415
|
+
* containing `.luarc.json`. Returns the start directory if not found.
|
|
6416
|
+
*/
|
|
6417
|
+
function findProjectRoot(startDir) {
|
|
6418
|
+
let curr = path.resolve(startDir);
|
|
6419
|
+
while (true) {
|
|
6420
|
+
if (fs.existsSync(path.join(curr, ".luarc.json"))) return curr;
|
|
6421
|
+
if (fs.existsSync(path.join(curr, ".git"))) break;
|
|
6422
|
+
const parent = path.dirname(curr);
|
|
6423
|
+
if (parent === curr) break;
|
|
6424
|
+
curr = parent;
|
|
6425
|
+
}
|
|
6426
|
+
return startDir;
|
|
6427
|
+
}
|
|
6428
|
+
/**
|
|
6429
|
+
* Characters the LuaLS glob matcher treats as syntax.
|
|
6430
|
+
*
|
|
6431
|
+
* LuaLS compiles `files.exclude` with `glob.gitignore` (see its
|
|
6432
|
+
* `script/glob/glob.lua`), whose grammar only understands backslash escapes:
|
|
6433
|
+
* bracket expressions such as `[[]` are parsed as character ranges and match
|
|
6434
|
+
* nothing useful. Escaping is therefore done with `\`.
|
|
6435
|
+
*/
|
|
6436
|
+
const GLOB_METACHARACTERS = /* @__PURE__ */ new Set([
|
|
6437
|
+
"*",
|
|
6438
|
+
"?",
|
|
6439
|
+
"[",
|
|
6440
|
+
"]",
|
|
6441
|
+
"{",
|
|
6442
|
+
"}",
|
|
6443
|
+
",",
|
|
6444
|
+
"\\"
|
|
6445
|
+
]);
|
|
6446
|
+
/**
|
|
6447
|
+
* Escapes the glob metacharacters of a single path segment so it matches literally.
|
|
6448
|
+
*
|
|
6449
|
+
* Note: `normalizePattern()` in `src/luals/files.ts` rewrites backslashes to path
|
|
6450
|
+
* separators when counting checked files, so these escapes only reach LuaLS. That is
|
|
6451
|
+
* harmless: the counted file set is filtered by the requested target paths anyway.
|
|
6452
|
+
*/
|
|
6453
|
+
function escapeGlobSegment(segment) {
|
|
6454
|
+
let escaped = "";
|
|
6455
|
+
for (const char of segment) escaped += GLOB_METACHARACTERS.has(char) ? `\\${char}` : char;
|
|
6456
|
+
return escaped;
|
|
6457
|
+
}
|
|
6458
|
+
/** Escapes glob metacharacters in every segment of a slash-separated relative path. */
|
|
6459
|
+
function escapeGlobPath(relativePath) {
|
|
6460
|
+
return relativePath.split("/").map(escapeGlobSegment).join("/");
|
|
6461
|
+
}
|
|
6462
|
+
/**
|
|
6463
|
+
* Computes glob exclusion patterns for directories and files under workspace root
|
|
6464
|
+
* that are completely outside the requested target paths.
|
|
6465
|
+
*/
|
|
6466
|
+
function computeUnrequestedExclusions(root, targetPaths) {
|
|
6467
|
+
const resolvedRoot = path.resolve(root);
|
|
6468
|
+
if (targetPaths.length === 0 || targetPaths.some((t) => t === "." || t === "" || path.resolve(resolvedRoot, t) === resolvedRoot)) return [];
|
|
6469
|
+
const isWin = process.platform === "win32";
|
|
6470
|
+
const canonicalRoot = getCanonicalPath(resolvedRoot);
|
|
6471
|
+
const relTargets = targetPaths.map((t) => {
|
|
6472
|
+
const canonical = getCanonicalPath(path.isAbsolute(t) ? t : path.resolve(canonicalRoot, t));
|
|
6473
|
+
const rel = path.relative(canonicalRoot, canonical).replace(/\\/g, "/");
|
|
6474
|
+
return isWin ? rel.toLowerCase() : rel;
|
|
6475
|
+
}).filter((rel) => !rel.startsWith("../") && rel !== "..");
|
|
6476
|
+
if (relTargets.length === 0 || relTargets.includes("") || relTargets.includes(".")) return [];
|
|
6477
|
+
const exclusions = [];
|
|
6478
|
+
/** Recursively scans directory entries to identify unrequested paths. */
|
|
6479
|
+
function scanDir(dir, relPrefix) {
|
|
6480
|
+
let entries;
|
|
6481
|
+
try {
|
|
6482
|
+
entries = fs.readdirSync(dir, { withFileTypes: true });
|
|
6483
|
+
} catch {
|
|
6484
|
+
return;
|
|
6485
|
+
}
|
|
6486
|
+
for (const entry of entries) {
|
|
6487
|
+
const entryRel = relPrefix ? `${relPrefix}/${entry.name}` : entry.name;
|
|
6488
|
+
const normEntry = isWin ? entryRel.toLowerCase() : entryRel;
|
|
6489
|
+
let isExactTarget = false;
|
|
6490
|
+
let isAncestorOfTarget = false;
|
|
6491
|
+
let isDescendantOfTarget = false;
|
|
6492
|
+
for (const target of relTargets) {
|
|
6493
|
+
if (normEntry === target) {
|
|
6494
|
+
isExactTarget = true;
|
|
6495
|
+
break;
|
|
6496
|
+
}
|
|
6497
|
+
if (target.startsWith(`${normEntry}/`)) {
|
|
6498
|
+
isAncestorOfTarget = true;
|
|
6499
|
+
break;
|
|
6500
|
+
}
|
|
6501
|
+
if (normEntry.startsWith(`${target}/`)) {
|
|
6502
|
+
isDescendantOfTarget = true;
|
|
6503
|
+
break;
|
|
6504
|
+
}
|
|
6505
|
+
}
|
|
6506
|
+
if (isExactTarget || isDescendantOfTarget) continue;
|
|
6507
|
+
if (isAncestorOfTarget) {
|
|
6508
|
+
if (entry.isDirectory()) scanDir(path.join(dir, entry.name), entryRel);
|
|
6509
|
+
continue;
|
|
6510
|
+
}
|
|
6511
|
+
if (entry.isDirectory()) exclusions.push(`${escapeGlobPath(entryRel)}/**`);
|
|
6512
|
+
else if (entry.isFile() && entry.name.toLowerCase().endsWith(".lua")) exclusions.push(escapeGlobPath(entryRel));
|
|
6513
|
+
}
|
|
6514
|
+
}
|
|
6515
|
+
scanDir(canonicalRoot, "");
|
|
6516
|
+
return exclusions;
|
|
6517
|
+
}
|
|
6518
|
+
/** Determines whether a workspace-relative file path matches any of the target paths. */
|
|
6519
|
+
function matchesTargetPaths(relativePath, root, targetPaths) {
|
|
6520
|
+
if (targetPaths.length === 0 || targetPaths.length === 1 && (targetPaths[0] === "." || targetPaths[0] === "")) return true;
|
|
6521
|
+
const isWin = process.platform === "win32";
|
|
6522
|
+
const canonicalRoot = getCanonicalPath(root);
|
|
6523
|
+
const normRel = isWin ? relativePath.replace(/\\/g, "/").toLowerCase() : relativePath.replace(/\\/g, "/");
|
|
6524
|
+
for (const rawTarget of targetPaths) {
|
|
6525
|
+
const fromCwd = path.resolve(rawTarget);
|
|
6526
|
+
const canonicalTarget = getCanonicalPath(fs.existsSync(fromCwd) ? fromCwd : path.isAbsolute(rawTarget) ? rawTarget : path.resolve(canonicalRoot, rawTarget));
|
|
6527
|
+
let relTarget = path.relative(canonicalRoot, canonicalTarget).replace(/\\/g, "/");
|
|
6528
|
+
relTarget = stripTrailingSlashes(relTarget).replace(/^\.\//, "");
|
|
6529
|
+
const normTarget = isWin ? relTarget.toLowerCase() : relTarget;
|
|
6530
|
+
if (normTarget === "" || normTarget === ".") return true;
|
|
6531
|
+
if (normRel === normTarget || normRel.startsWith(`${normTarget}/`)) return true;
|
|
6532
|
+
}
|
|
6533
|
+
return false;
|
|
6534
|
+
}
|
|
6535
|
+
/** Keeps only diagnostics for files that match the requested target paths. */
|
|
6536
|
+
function filterReportByTargetPaths(report, root, targetPaths) {
|
|
6537
|
+
if (targetPaths.length === 0 || targetPaths.length === 1 && (targetPaths[0] === "." || targetPaths[0] === "")) return report;
|
|
6538
|
+
const filtered = {};
|
|
6539
|
+
const canonicalRoot = getCanonicalPath(root);
|
|
6540
|
+
for (const [uri, diags] of Object.entries(report)) {
|
|
6541
|
+
const filePath = fileUriToPath(uri);
|
|
6542
|
+
const canonicalFile = getCanonicalPath(path.resolve(filePath));
|
|
6543
|
+
if (matchesTargetPaths(path.relative(canonicalRoot, canonicalFile).replace(/\\/g, "/"), canonicalRoot, targetPaths)) filtered[uri] = diags;
|
|
6544
|
+
}
|
|
6545
|
+
return filtered;
|
|
6546
|
+
}
|
|
6547
|
+
/** Validates and resolves CLI target paths into a common root directory and target list. */
|
|
6548
|
+
function resolveCheckTargets(rawPaths) {
|
|
6549
|
+
const paths = rawPaths && rawPaths.length > 0 ? rawPaths : ["."];
|
|
6550
|
+
const canonicalTargets = paths.map((targetPath) => {
|
|
6551
|
+
const resolved = path.resolve(targetPath);
|
|
6552
|
+
if (!fs.existsSync(resolved)) throw new LuaLSError(`Target path does not exist: ${targetPath}`, "ERR_TARGET_NOT_FOUND", "Verify that the target path exists and is accessible.");
|
|
6553
|
+
return getCanonicalPath(resolved);
|
|
6554
|
+
});
|
|
6555
|
+
const first = paths[0];
|
|
6556
|
+
if (paths.length === 1 && first) {
|
|
6557
|
+
const canonicalFirst = canonicalTargets[0];
|
|
6558
|
+
const startDir = fs.statSync(canonicalFirst).isFile() ? path.dirname(canonicalFirst) : canonicalFirst;
|
|
6559
|
+
const projRoot = findProjectRoot(startDir);
|
|
6560
|
+
if (projRoot !== startDir) {
|
|
6561
|
+
if (isFilesystemRoot(projRoot)) throw new ConfigError(`Cannot check targets across the root filesystem (${projRoot}): checked paths must share a common project directory.`, "ERR_ROOT_ANCESTOR", "Ensure all checked paths reside within a common project directory.");
|
|
6562
|
+
logger.debug(`[targets] Using discovered project root "${projRoot}" for "${first}".`);
|
|
6563
|
+
return {
|
|
6564
|
+
rootPath: projRoot,
|
|
6565
|
+
targetPaths: canonicalTargets
|
|
6566
|
+
};
|
|
6567
|
+
}
|
|
6568
|
+
return {
|
|
6569
|
+
rootPath: first,
|
|
6570
|
+
targetPaths: canonicalTargets
|
|
6571
|
+
};
|
|
6572
|
+
}
|
|
6573
|
+
const ancestor = findCommonAncestorDirectory(canonicalTargets);
|
|
6574
|
+
if (isFilesystemRoot(ancestor)) throw new ConfigError(`Cannot check targets across the root filesystem (${ancestor}): checked paths must share a common project directory.`, "ERR_ROOT_ANCESTOR", "Ensure all checked paths reside within a common project directory.");
|
|
6575
|
+
const rootPath = findProjectRoot(ancestor);
|
|
6576
|
+
if (rootPath !== ancestor) logger.debug(`[targets] Using discovered project root "${rootPath}" for "${ancestor}".`);
|
|
6577
|
+
return {
|
|
6578
|
+
rootPath,
|
|
6579
|
+
targetPaths: canonicalTargets
|
|
6580
|
+
};
|
|
6581
|
+
}
|
|
6582
|
+
//#endregion
|
|
6343
6583
|
//#region src/luals/files.ts
|
|
6344
6584
|
/** Directories skipped unless the workspace config overrides `workspace.ignoreDir`. */
|
|
6345
6585
|
const DEFAULT_IGNORE_DIRS = [
|
|
@@ -6463,7 +6703,7 @@ function resolveTargetPath(targetPath) {
|
|
|
6463
6703
|
* honoring `workspace.ignoreDir` and `files.exclude` (#27). Absolute paths are returned
|
|
6464
6704
|
* for single-file targets, and an empty list is returned when the walk fails.
|
|
6465
6705
|
*/
|
|
6466
|
-
function listCheckedFiles(targetPath, configPath) {
|
|
6706
|
+
function listCheckedFiles(targetPath, configPath, targetPaths) {
|
|
6467
6707
|
const absPath = resolveTargetPath(targetPath);
|
|
6468
6708
|
if (!absPath) return [];
|
|
6469
6709
|
if (fs.statSync(absPath).isFile()) return absPath.toLowerCase().endsWith(".lua") ? [absPath] : [];
|
|
@@ -6478,7 +6718,7 @@ function listCheckedFiles(targetPath, configPath) {
|
|
|
6478
6718
|
}
|
|
6479
6719
|
const ignore = [...toIgnorePatterns(ignoreDirs), ...toIgnorePatterns(excludePatterns)];
|
|
6480
6720
|
try {
|
|
6481
|
-
|
|
6721
|
+
const files = ts(LUA_FILE_PATTERN, {
|
|
6482
6722
|
cwd: absPath,
|
|
6483
6723
|
ignore,
|
|
6484
6724
|
dot: true,
|
|
@@ -6486,14 +6726,16 @@ function listCheckedFiles(targetPath, configPath) {
|
|
|
6486
6726
|
follow: false,
|
|
6487
6727
|
withFileTypes: true
|
|
6488
6728
|
}).filter((entry) => entry.isFile()).map((entry) => entry.relativePosix());
|
|
6729
|
+
if (targetPaths && targetPaths.length > 0) return files.filter((f) => matchesTargetPaths(f, absPath, targetPaths));
|
|
6730
|
+
return files;
|
|
6489
6731
|
} catch (err) {
|
|
6490
6732
|
logger.warn(`[luals] Failed to walk ${absPath} while listing checked files: ${err instanceof Error ? err.message : String(err)}`);
|
|
6491
6733
|
return [];
|
|
6492
6734
|
}
|
|
6493
6735
|
}
|
|
6494
6736
|
/** Counts candidate Lua files within targetPath, taking workspace ignoreDir and files.exclude into account (#27). */
|
|
6495
|
-
function countCheckedFiles(targetPath, configPath) {
|
|
6496
|
-
return listCheckedFiles(targetPath, configPath).length;
|
|
6737
|
+
function countCheckedFiles(targetPath, configPath, targetPaths) {
|
|
6738
|
+
return listCheckedFiles(targetPath, configPath, targetPaths).length;
|
|
6497
6739
|
}
|
|
6498
6740
|
//#endregion
|
|
6499
6741
|
//#region src/luals/runner.ts
|
|
@@ -6705,7 +6947,7 @@ async function runLuaLSCheck(targetPath, configPath, options) {
|
|
|
6705
6947
|
const normTarget = normalizeComparable(targetFileOnly);
|
|
6706
6948
|
for (const [rawUri, diags] of Object.entries(diagnostics)) if (normalizeComparable(fileUriToPath(rawUri)) === normTarget) filtered[rawUri] = diags;
|
|
6707
6949
|
diagnostics = filtered;
|
|
6708
|
-
}
|
|
6950
|
+
} else if (options.paths && options.paths.length > 0) diagnostics = filterReportByTargetPaths(diagnostics, checkDir, options.paths);
|
|
6709
6951
|
let totalProblems = 0;
|
|
6710
6952
|
let totalErrors = 0;
|
|
6711
6953
|
let totalWarnings = 0;
|
|
@@ -6717,7 +6959,7 @@ async function runLuaLSCheck(targetPath, configPath, options) {
|
|
|
6717
6959
|
else if (d.severity === 2) totalWarnings += 1;
|
|
6718
6960
|
}
|
|
6719
6961
|
const passed = totalProblems === 0;
|
|
6720
|
-
const filesChecked = countCheckedFiles(targetPath, configPath);
|
|
6962
|
+
const filesChecked = countCheckedFiles(targetPath, configPath, options.paths);
|
|
6721
6963
|
return {
|
|
6722
6964
|
passed,
|
|
6723
6965
|
totalProblems,
|
|
@@ -6729,6 +6971,179 @@ async function runLuaLSCheck(targetPath, configPath, options) {
|
|
|
6729
6971
|
};
|
|
6730
6972
|
}
|
|
6731
6973
|
//#endregion
|
|
6974
|
+
//#region src/deps.ts
|
|
6975
|
+
/** Accumulates repeatable --dep arguments. */
|
|
6976
|
+
function collectDeps(val, prev) {
|
|
6977
|
+
const trimmed = val.trim();
|
|
6978
|
+
if (!trimmed) return prev ?? [];
|
|
6979
|
+
return (prev ?? []).concat(trimmed);
|
|
6980
|
+
}
|
|
6981
|
+
/** Normalizes a filesystem path to forward slashes for LuaLS compatibility. */
|
|
6982
|
+
function normalizeSlash(p) {
|
|
6983
|
+
return p.replace(/\\/g, "/");
|
|
6984
|
+
}
|
|
6985
|
+
/**
|
|
6986
|
+
* Resolves package dependencies declared in .luarc.json (nanos.deps) or via CLI (--dep),
|
|
6987
|
+
* resolving transitive dependencies with cycle detection and partitioning them by realm.
|
|
6988
|
+
*/
|
|
6989
|
+
function resolvePackageDependencies(root, userConfig, cliDeps) {
|
|
6990
|
+
const visited = /* @__PURE__ */ new Set();
|
|
6991
|
+
const queue = [];
|
|
6992
|
+
if (cliDeps && cliDeps.length > 0) {
|
|
6993
|
+
for (const dep of cliDeps) if (typeof dep === "string" && dep.trim()) queue.push({
|
|
6994
|
+
rawPath: dep.trim(),
|
|
6995
|
+
fromDir: process.cwd()
|
|
6996
|
+
});
|
|
6997
|
+
}
|
|
6998
|
+
const rawConfigDeps = userConfig.nanos?.deps;
|
|
6999
|
+
if (rawConfigDeps !== void 0) {
|
|
7000
|
+
if (Array.isArray(rawConfigDeps)) for (const dep of rawConfigDeps) if (typeof dep === "string" && dep.trim()) queue.push({
|
|
7001
|
+
rawPath: dep.trim(),
|
|
7002
|
+
fromDir: root
|
|
7003
|
+
});
|
|
7004
|
+
else logger.warn(`[deps] Skipping invalid nanos.deps entry: expected a string path.`);
|
|
7005
|
+
else logger.warn(`[deps] Ignoring nanos.deps: expected an array of path strings.`);
|
|
7006
|
+
}
|
|
7007
|
+
const resolvedFiles = [];
|
|
7008
|
+
const resolvedDirs = [];
|
|
7009
|
+
const depConfigMap = /* @__PURE__ */ new Map();
|
|
7010
|
+
const isWin = process.platform === "win32";
|
|
7011
|
+
while (queue.length > 0) {
|
|
7012
|
+
const item = queue.shift();
|
|
7013
|
+
if (!item) continue;
|
|
7014
|
+
const { rawPath, fromDir } = item;
|
|
7015
|
+
const absPath = path.resolve(fromDir, rawPath);
|
|
7016
|
+
if (!fs.existsSync(absPath)) {
|
|
7017
|
+
logger.warn(`[deps] Dependency path not found: "${rawPath}" (skipping).`);
|
|
7018
|
+
continue;
|
|
7019
|
+
}
|
|
7020
|
+
let canonical;
|
|
7021
|
+
try {
|
|
7022
|
+
canonical = fs.realpathSync.native(absPath);
|
|
7023
|
+
} catch (err) {
|
|
7024
|
+
try {
|
|
7025
|
+
canonical = fs.realpathSync(absPath);
|
|
7026
|
+
} catch (innerErr) {
|
|
7027
|
+
canonical = absPath;
|
|
7028
|
+
}
|
|
7029
|
+
}
|
|
7030
|
+
const cycleKey = isWin ? canonical.toLowerCase() : canonical;
|
|
7031
|
+
if (visited.has(cycleKey)) continue;
|
|
7032
|
+
visited.add(cycleKey);
|
|
7033
|
+
let stat;
|
|
7034
|
+
try {
|
|
7035
|
+
stat = fs.statSync(canonical);
|
|
7036
|
+
} catch (err) {
|
|
7037
|
+
continue;
|
|
7038
|
+
}
|
|
7039
|
+
if (stat.isFile()) {
|
|
7040
|
+
if (canonical.toLowerCase().endsWith(".lua")) resolvedFiles.push(normalizeSlash(canonical));
|
|
7041
|
+
else logger.warn(`[deps] Skipping non-Lua dependency file: "${rawPath}".`);
|
|
7042
|
+
continue;
|
|
7043
|
+
}
|
|
7044
|
+
if (stat.isDirectory()) {
|
|
7045
|
+
resolvedDirs.push(canonical);
|
|
7046
|
+
const candidateLuarc = path.join(canonical, ".luarc.json");
|
|
7047
|
+
if (fs.existsSync(candidateLuarc)) try {
|
|
7048
|
+
const depConfig = loadUserConfig(canonical);
|
|
7049
|
+
depConfigMap.set(canonical, depConfig);
|
|
7050
|
+
const transDeps = depConfig.nanos?.deps;
|
|
7051
|
+
if (transDeps !== void 0) {
|
|
7052
|
+
if (Array.isArray(transDeps)) for (const trans of transDeps) if (typeof trans === "string" && trans.trim()) queue.push({
|
|
7053
|
+
rawPath: trans.trim(),
|
|
7054
|
+
fromDir: canonical
|
|
7055
|
+
});
|
|
7056
|
+
else logger.warn(`[deps] Skipping invalid nanos.deps entry in "${canonical}": expected a string path.`);
|
|
7057
|
+
else logger.warn(`[deps] Ignoring nanos.deps in "${canonical}": expected an array of path strings.`);
|
|
7058
|
+
}
|
|
7059
|
+
} catch (err) {
|
|
7060
|
+
logger.warn(`[deps] Failed to parse transitive dependency configuration at "${candidateLuarc}": ${err instanceof Error ? err.message : String(err)}`);
|
|
7061
|
+
}
|
|
7062
|
+
}
|
|
7063
|
+
}
|
|
7064
|
+
const serverSet = /* @__PURE__ */ new Set();
|
|
7065
|
+
const clientSet = /* @__PURE__ */ new Set();
|
|
7066
|
+
const sharedSet = /* @__PURE__ */ new Set();
|
|
7067
|
+
const allSet = /* @__PURE__ */ new Set();
|
|
7068
|
+
for (const file of resolvedFiles) {
|
|
7069
|
+
serverSet.add(file);
|
|
7070
|
+
clientSet.add(file);
|
|
7071
|
+
sharedSet.add(file);
|
|
7072
|
+
allSet.add(file);
|
|
7073
|
+
}
|
|
7074
|
+
for (const depDir of resolvedDirs) {
|
|
7075
|
+
const normDepDir = normalizeSlash(depDir);
|
|
7076
|
+
allSet.add(normDepDir);
|
|
7077
|
+
let depConfig = depConfigMap.get(depDir);
|
|
7078
|
+
if (!depConfig) try {
|
|
7079
|
+
depConfig = loadUserConfig(depDir);
|
|
7080
|
+
} catch (err) {
|
|
7081
|
+
depConfig = {};
|
|
7082
|
+
}
|
|
7083
|
+
const { enabled, mappings } = resolveRealmMappings(depConfig);
|
|
7084
|
+
if (!enabled) {
|
|
7085
|
+
serverSet.add(normDepDir);
|
|
7086
|
+
clientSet.add(normDepDir);
|
|
7087
|
+
sharedSet.add(normDepDir);
|
|
7088
|
+
continue;
|
|
7089
|
+
}
|
|
7090
|
+
const serverFolder = path.join(depDir, "Server");
|
|
7091
|
+
const clientFolder = path.join(depDir, "Client");
|
|
7092
|
+
const sharedFolder = path.join(depDir, "Shared");
|
|
7093
|
+
const hasServer = fs.existsSync(serverFolder);
|
|
7094
|
+
const hasClient = fs.existsSync(clientFolder);
|
|
7095
|
+
const hasShared = fs.existsSync(sharedFolder);
|
|
7096
|
+
if (hasServer || hasClient || hasShared) {
|
|
7097
|
+
if (hasServer) serverSet.add(normalizeSlash(serverFolder));
|
|
7098
|
+
if (hasClient) clientSet.add(normalizeSlash(clientFolder));
|
|
7099
|
+
if (hasShared) {
|
|
7100
|
+
const normShared = normalizeSlash(sharedFolder);
|
|
7101
|
+
serverSet.add(normShared);
|
|
7102
|
+
clientSet.add(normShared);
|
|
7103
|
+
sharedSet.add(normShared);
|
|
7104
|
+
}
|
|
7105
|
+
try {
|
|
7106
|
+
const entries = fs.readdirSync(depDir, { withFileTypes: true });
|
|
7107
|
+
for (const entry of entries) if (entry.isFile() && entry.name.toLowerCase().endsWith(".lua")) {
|
|
7108
|
+
const rootFile = normalizeSlash(path.join(depDir, entry.name));
|
|
7109
|
+
serverSet.add(rootFile);
|
|
7110
|
+
clientSet.add(rootFile);
|
|
7111
|
+
sharedSet.add(rootFile);
|
|
7112
|
+
}
|
|
7113
|
+
} catch (err) {}
|
|
7114
|
+
continue;
|
|
7115
|
+
}
|
|
7116
|
+
if (depConfig.nanos?.realms) {
|
|
7117
|
+
let matchedAnyCustom = false;
|
|
7118
|
+
for (const { pattern, realm } of mappings) {
|
|
7119
|
+
const baseFolder = pattern.replace(/\/\*\*.*$/, "").replace(/\/\*.*$/, "");
|
|
7120
|
+
const targetPath = path.join(depDir, baseFolder);
|
|
7121
|
+
if (fs.existsSync(targetPath)) {
|
|
7122
|
+
matchedAnyCustom = true;
|
|
7123
|
+
const norm = normalizeSlash(targetPath);
|
|
7124
|
+
if (realm === "server") serverSet.add(norm);
|
|
7125
|
+
else if (realm === "client") clientSet.add(norm);
|
|
7126
|
+
else {
|
|
7127
|
+
serverSet.add(norm);
|
|
7128
|
+
clientSet.add(norm);
|
|
7129
|
+
sharedSet.add(norm);
|
|
7130
|
+
}
|
|
7131
|
+
}
|
|
7132
|
+
}
|
|
7133
|
+
if (matchedAnyCustom) continue;
|
|
7134
|
+
}
|
|
7135
|
+
serverSet.add(normDepDir);
|
|
7136
|
+
clientSet.add(normDepDir);
|
|
7137
|
+
sharedSet.add(normDepDir);
|
|
7138
|
+
}
|
|
7139
|
+
return {
|
|
7140
|
+
server: Array.from(serverSet),
|
|
7141
|
+
client: Array.from(clientSet),
|
|
7142
|
+
shared: Array.from(sharedSet),
|
|
7143
|
+
all: Array.from(allSet)
|
|
7144
|
+
};
|
|
7145
|
+
}
|
|
7146
|
+
//#endregion
|
|
6732
7147
|
//#region src/realms.ts
|
|
6733
7148
|
/** Normalizes a workspace-relative path for case-insensitive comparison on Windows. */
|
|
6734
7149
|
function normalizeRelative(candidate) {
|
|
@@ -6786,13 +7201,17 @@ function selectedRealms(selection) {
|
|
|
6786
7201
|
return ["shared", selection];
|
|
6787
7202
|
}
|
|
6788
7203
|
/** Builds a pass config from the merged base config by swapping library and exclusions. */
|
|
6789
|
-
function buildPassConfig(baseConfig, realm, annotationsPath, realmAnnotationPath, excludedPatterns) {
|
|
7204
|
+
function buildPassConfig(baseConfig, realm, annotationsPath, realmAnnotationPath, excludedPatterns, dependencyLibraries = []) {
|
|
6790
7205
|
const config = JSON.parse(JSON.stringify(baseConfig));
|
|
6791
7206
|
const normalizedFull = annotationsPath.replace(/\\/g, "/");
|
|
6792
7207
|
const libraries = (config.workspace?.library ?? []).filter((entry) => entry.replace(/\\/g, "/") !== normalizedFull);
|
|
6793
7208
|
config.workspace = {
|
|
6794
7209
|
...config.workspace ?? {},
|
|
6795
|
-
library: [
|
|
7210
|
+
library: Array.from(/* @__PURE__ */ new Set([
|
|
7211
|
+
realmAnnotationPath,
|
|
7212
|
+
...libraries,
|
|
7213
|
+
...dependencyLibraries
|
|
7214
|
+
]))
|
|
6796
7215
|
};
|
|
6797
7216
|
if (realm !== "shared" && excludedPatterns.length > 0) config.files = {
|
|
6798
7217
|
...config.files ?? {},
|
|
@@ -6814,19 +7233,25 @@ function planRealmCheck(options) {
|
|
|
6814
7233
|
logger.debug("[realms] Realm mapping disabled; running a single standard pass.");
|
|
6815
7234
|
return null;
|
|
6816
7235
|
}
|
|
7236
|
+
const unrequestedExclusions = options.targetPaths ? computeUnrequestedExclusions(resolvedTarget, options.targetPaths) : [];
|
|
6817
7237
|
const baseConfig = buildWorkspaceConfig(resolvedTarget, options.customConfigPath, {
|
|
6818
7238
|
ignore: options.ignore,
|
|
6819
|
-
annotationsPath
|
|
7239
|
+
annotationsPath,
|
|
7240
|
+
unrequestedExclusions
|
|
6820
7241
|
});
|
|
6821
7242
|
const tempConfigs = [];
|
|
6822
7243
|
const baseConfigPath = writeTempConfig(baseConfig);
|
|
6823
7244
|
tempConfigs.push(baseConfigPath);
|
|
6824
7245
|
try {
|
|
6825
7246
|
const realmFiles = collectRealmFiles(resolvedTarget, mappings, listCheckedFiles(resolvedTarget, baseConfigPath));
|
|
7247
|
+
const isTargetFile = (file) => {
|
|
7248
|
+
if (!options.targetPaths || options.targetPaths.length === 0) return true;
|
|
7249
|
+
return matchesTargetPaths(file, resolvedTarget, options.targetPaths);
|
|
7250
|
+
};
|
|
6826
7251
|
const realmReportFiles = {
|
|
6827
|
-
client: new Set(realmFiles.client.map(normalizeRelative)),
|
|
6828
|
-
server: new Set(realmFiles.server.map(normalizeRelative)),
|
|
6829
|
-
shared: new Set([...realmFiles.shared, ...realmFiles.unmatched].map(normalizeRelative))
|
|
7252
|
+
client: new Set(realmFiles.client.filter(isTargetFile).map(normalizeRelative)),
|
|
7253
|
+
server: new Set(realmFiles.server.filter(isTargetFile).map(normalizeRelative)),
|
|
7254
|
+
shared: new Set([...realmFiles.shared, ...realmFiles.unmatched].filter(isTargetFile).map(normalizeRelative))
|
|
6830
7255
|
};
|
|
6831
7256
|
const hasRealmFolders = realmFiles.client.length > 0 || realmFiles.server.length > 0 || realmFiles.shared.length > 0;
|
|
6832
7257
|
if (selection === "all" && !hasRealmFolders) {
|
|
@@ -6835,14 +7260,22 @@ function planRealmCheck(options) {
|
|
|
6835
7260
|
return null;
|
|
6836
7261
|
}
|
|
6837
7262
|
const wanted = selectedRealms(selection).filter((realm) => realmReportFiles[realm].size > 0);
|
|
7263
|
+
if (wanted.length === 0) {
|
|
7264
|
+
if (selection !== "all") logger.warn(`[realms] No target files match the requested realm "${selection}"; falling back to a standard check.`);
|
|
7265
|
+
else logger.debug("[realms] No files to report for selected realm pass; running a single standard pass.");
|
|
7266
|
+
for (const tempConfig of tempConfigs) removeTempConfig(tempConfig);
|
|
7267
|
+
return null;
|
|
7268
|
+
}
|
|
6838
7269
|
const derived = wanted.some((realm) => realm !== "shared") ? deriveRealmAnnotationFiles(annotationsPath) : {
|
|
6839
7270
|
client: annotationsPath,
|
|
6840
7271
|
server: annotationsPath
|
|
6841
7272
|
};
|
|
7273
|
+
const resolvedDeps = resolvePackageDependencies(resolvedTarget, userConfig, options.cliDeps);
|
|
6842
7274
|
const passes = [];
|
|
6843
7275
|
for (const realm of wanted) {
|
|
6844
7276
|
const excluded = mappings.filter((mapping) => mapping.realm !== realm && mapping.realm !== "shared").map((mapping) => mapping.pattern);
|
|
6845
|
-
const
|
|
7277
|
+
const depLibraries = realm === "server" ? resolvedDeps.server : realm === "client" ? resolvedDeps.client : resolvedDeps.shared;
|
|
7278
|
+
const configPath = writeTempConfig(buildPassConfig(baseConfig, realm, annotationsPath, realm === "client" ? derived.client : realm === "server" ? derived.server : annotationsPath, excluded, depLibraries));
|
|
6846
7279
|
tempConfigs.push(configPath);
|
|
6847
7280
|
passes.push({
|
|
6848
7281
|
realm,
|
|
@@ -6873,9 +7306,15 @@ function removeTempConfig(configPath) {
|
|
|
6873
7306
|
/** Keeps only the diagnostics of files owned by the pass. */
|
|
6874
7307
|
function filterReportByFiles(report, root, reportFiles) {
|
|
6875
7308
|
const filtered = {};
|
|
7309
|
+
const canonicalRoot = getCanonicalPath(root);
|
|
6876
7310
|
for (const [uri, diagnostics] of Object.entries(report)) {
|
|
6877
7311
|
const filePath = fileUriToPath(uri);
|
|
6878
|
-
const
|
|
7312
|
+
const resolvedFile = path.resolve(filePath);
|
|
7313
|
+
let relative = normalizeRelative(path.relative(root, resolvedFile));
|
|
7314
|
+
if (!reportFiles.has(relative)) {
|
|
7315
|
+
const canonicalFile = getCanonicalPath(resolvedFile);
|
|
7316
|
+
relative = normalizeRelative(path.relative(canonicalRoot, canonicalFile));
|
|
7317
|
+
}
|
|
6879
7318
|
if (reportFiles.has(relative)) filtered[uri] = diagnostics;
|
|
6880
7319
|
}
|
|
6881
7320
|
return filtered;
|
|
@@ -10451,7 +10890,7 @@ function createProgram(options) {
|
|
|
10451
10890
|
writeOut: (str) => console.log(str.trimEnd()),
|
|
10452
10891
|
writeErr: (str) => logger.error(str.trimEnd())
|
|
10453
10892
|
});
|
|
10454
|
-
program.command("check [
|
|
10893
|
+
program.command("check [paths...]", { isDefault: true }).description("Check workspace files or directories (default command)").addOption(new Option("--checklevel <level>", "Minimum diagnostic level: Error, Warning, Information, Hint").choices([
|
|
10455
10894
|
"Error",
|
|
10456
10895
|
"Warning",
|
|
10457
10896
|
"Information",
|
|
@@ -10460,7 +10899,7 @@ function createProgram(options) {
|
|
|
10460
10899
|
"pretty",
|
|
10461
10900
|
"json",
|
|
10462
10901
|
"github"
|
|
10463
|
-
])).option("-i, --ignore <pattern>", "Files or directories to ignore (supports glob patterns, repeatable)", collectIgnorePatterns).option("--luals-version <ver>", `Version of LuaLS to use (default: ${DEFAULT_LUALS_VERSION})`, DEFAULT_LUALS_VERSION).option("--no-fail", "Do not exit with code 1 if diagnostics are found").addOption(new Option("-l, --log-level <level>", "Logging level: error, warn, info, debug, silent").choices([
|
|
10902
|
+
])).option("-i, --ignore <pattern>", "Files or directories to ignore (supports glob patterns, repeatable)", collectIgnorePatterns).option("-d, --dep <path>", "Path to package dependency or Lua definition file (repeatable)", collectDeps).option("--luals-version <ver>", `Version of LuaLS to use (default: ${DEFAULT_LUALS_VERSION})`, DEFAULT_LUALS_VERSION).option("--no-fail", "Do not exit with code 1 if diagnostics are found").addOption(new Option("-l, --log-level <level>", "Logging level: error, warn, info, debug, silent").choices([
|
|
10464
10903
|
"error",
|
|
10465
10904
|
"warn",
|
|
10466
10905
|
"info",
|
|
@@ -10471,44 +10910,54 @@ function createProgram(options) {
|
|
|
10471
10910
|
"client",
|
|
10472
10911
|
"server",
|
|
10473
10912
|
"shared"
|
|
10474
|
-
]).default("all")).action(async (
|
|
10913
|
+
]).default("all")).action(async (targetPaths = ["."], opts) => {
|
|
10475
10914
|
if (opts.logLevel && isValidLogLevel(opts.logLevel)) logger.setLevel(opts.logLevel);
|
|
10915
|
+
const { rootPath, targetPaths: canonicalTargets } = resolveCheckTargets(targetPaths && targetPaths.length > 0 ? targetPaths : ["."]);
|
|
10476
10916
|
const format = opts.github ? "github" : opts.format || (process.env.GITHUB_ACTIONS ? "github" : "pretty");
|
|
10477
10917
|
const checkOptions = {
|
|
10478
|
-
path:
|
|
10918
|
+
path: rootPath,
|
|
10919
|
+
paths: canonicalTargets,
|
|
10479
10920
|
configpath: opts.config,
|
|
10480
10921
|
checklevel: opts.checklevel,
|
|
10481
10922
|
format,
|
|
10482
10923
|
lualsVersion: opts.lualsVersion,
|
|
10483
10924
|
failOnError: opts.fail !== false,
|
|
10484
|
-
ignore: opts.ignore
|
|
10925
|
+
ignore: opts.ignore,
|
|
10926
|
+
deps: opts.dep
|
|
10485
10927
|
};
|
|
10486
10928
|
if (opts.config) {
|
|
10487
10929
|
const resolvedConfig = path.resolve(opts.config);
|
|
10488
10930
|
if (!fs.existsSync(resolvedConfig)) throw new ConfigError(`Configuration file not found: ${resolvedConfig}`, "ERR_CONFIG_NOT_FOUND", "Verify the path passed to --config exists and is readable.");
|
|
10489
10931
|
}
|
|
10490
10932
|
const annotationsPath = await resolveAnnotations({ customPath: opts.annotations });
|
|
10933
|
+
const userConfig = loadUserConfig(rootPath, checkOptions.configpath);
|
|
10491
10934
|
const realmPlan = planRealmCheck({
|
|
10492
|
-
targetPath,
|
|
10493
|
-
userConfig
|
|
10935
|
+
targetPath: rootPath,
|
|
10936
|
+
userConfig,
|
|
10494
10937
|
selection: opts.realm ?? "all",
|
|
10495
10938
|
annotationsPath,
|
|
10496
10939
|
customConfigPath: checkOptions.configpath,
|
|
10497
|
-
ignore: checkOptions.ignore
|
|
10940
|
+
ignore: checkOptions.ignore,
|
|
10941
|
+
targetPaths: canonicalTargets,
|
|
10942
|
+
cliDeps: checkOptions.deps
|
|
10498
10943
|
});
|
|
10499
10944
|
let result;
|
|
10500
10945
|
if (realmPlan) try {
|
|
10501
|
-
result = await runRealmAwareCheck(realmPlan,
|
|
10946
|
+
result = await runRealmAwareCheck(realmPlan, rootPath, checkOptions);
|
|
10502
10947
|
} finally {
|
|
10503
10948
|
realmPlan.cleanup();
|
|
10504
10949
|
}
|
|
10505
10950
|
else {
|
|
10506
|
-
const
|
|
10951
|
+
const resolvedDeps = resolvePackageDependencies(rootPath, userConfig, checkOptions.deps);
|
|
10952
|
+
const unrequestedExclusions = computeUnrequestedExclusions(rootPath, canonicalTargets);
|
|
10953
|
+
const resolved = resolveWorkspaceConfig(rootPath, checkOptions.configpath, {
|
|
10507
10954
|
ignore: checkOptions.ignore,
|
|
10508
|
-
annotationsPath
|
|
10955
|
+
annotationsPath,
|
|
10956
|
+
dependencyLibraries: resolvedDeps.all,
|
|
10957
|
+
unrequestedExclusions
|
|
10509
10958
|
});
|
|
10510
10959
|
try {
|
|
10511
|
-
result = await runLuaLSCheck(
|
|
10960
|
+
result = await runLuaLSCheck(rootPath, resolved.configPath, checkOptions);
|
|
10512
10961
|
} finally {
|
|
10513
10962
|
if (resolved.isTemp && fs.existsSync(resolved.configPath)) try {
|
|
10514
10963
|
fs.unlinkSync(resolved.configPath);
|
|
@@ -10589,6 +11038,7 @@ Examples:
|
|
|
10589
11038
|
$ npx nanos-lint check . --checklevel=Error
|
|
10590
11039
|
$ npx nanos-lint check . --ignore "myfolder/hello-*.lua"
|
|
10591
11040
|
$ npx nanos-lint check . --realm server
|
|
11041
|
+
$ npx nanos-lint check Shared/ Server/ --realm server
|
|
10592
11042
|
$ npx nanos-lint init
|
|
10593
11043
|
$ npx nanos-lint clean-cache
|
|
10594
11044
|
`);
|
|
@@ -10668,6 +11118,6 @@ if (isDirectExecution()) runCLI().then((code) => {
|
|
|
10668
11118
|
process.exit(1);
|
|
10669
11119
|
});
|
|
10670
11120
|
//#endregion
|
|
10671
|
-
export {
|
|
11121
|
+
export { ALLOWED_DOWNLOAD_DOMAINS as $, stripJsonComments as $t, formatProblemSummary as A, getPlatformInfo as At, resolvePackageDependencies as B, VALID_LUALS_DIAGNOSTIC_CODES as Bt, getCachedAnnotationsFilePath as C, inspectZipMembers as Ct, updateLastCheckedDate as D, isZipArchive as Dt, readAnnotationsMetadata as E, isGzipArchive as Et, shouldEnableColor as F, resolveLuaLSVersion as Ft, computeUnrequestedExclusions as G, getPackageRoot as Gt, runLuaLSCheck as H, getDefaultAnnotationsPath as Ht, collectRealmFiles as I, sanitizeLuaLSVersion as It, findProjectRoot as J, loadUserConfig as Jt, filterReportByTargetPaths as K, initWorkspace as Kt, planRealmCheck as L, deriveRealmAnnotationFiles as Lt, formatSeverityBadge as M, FALLBACK_LUALS_VERSION as Mt, getColors as N, fetchLatestLuaLSVersionFromGitHub as Nt, formatGitHubAnnotations as O, parseTarTvSize as Ot, pluralize as P, resolveLatestLuaLSVersion as Pt, resolveCheckTargets as Q, resolveWorkspaceConfig as Qt, runRealmAwareCheck as R, splitAnnotationsByRealm as Rt, getAnnotationsMetadataFilePath as S, getTarBinary as St, isAnnotationsValid as T, isBinaryValid as Tt, countCheckedFiles as U, getDefaultTemplatePath as Ut, resolveLuaLSBinary as V, buildWorkspaceConfig as Vt, listCheckedFiles as W, getDefinitionsDir as Wt, isFilesystemRoot as X, parseJsonc as Xt, getCanonicalPath as Y, mergeConfigs as Yt, matchesTargetPaths as Z, resolveRealmMappings as Zt, MAX_ANNOTATIONS_SIZE_BYTES as _, logger as _n, MAX_ARCHIVE_MEMBER_COUNT as _t, formatCacheStatusPretty as a, LuaLSError as an, limitDownloadStream as at, MIN_ANNOTATIONS_SIZE_BYTES as b, assertValidLuaLSBinary as bt, DOCGEN_BRANCH as c, formatBytes as cn, findExistingLuaLSDir as ct, RAW_ANNOTATIONS_URL as d, fileUriToPath as dn, getIsoWeek as dt, stripTrailingSlashes as en, DOWNLOAD_TIMEOUT_MS as et, downloadAndCacheAnnotations as f, DEFAULT_LOG_LEVEL as fn, getLuaLSMetadataPath as ft, ANNOTATIONS_FILENAME as g, isValidLogLevel as gn, writeLuaLSMetadata as gt, getRawAnnotationsUrl as h, Logger as hn, readLuaLSMetadata as ht, runCLI as i, ConfigError as in, isAllowedDownloadUrl as it, formatReport as j, DEFAULT_LUALS_VERSION as jt, formatPretty as k, validateArchiveMembers as kt, DOCGEN_REPO as l, getDirectorySize as ln, getBaseLuaLSCacheDir as lt, fetchRawAnnotationsContent as m, LOG_LEVEL_PRIORITY as mn, listCachedLuaLSVersions as mt, createProgram as n, AnnotationsError as nn, computeFileSha256 as nt, getCacheStatus as o, NanosLintError as on, LUALS_METADATA_FILENAME as ot, fetchLatestCommitId as p, LOG_LEVELS as pn, listCachedLuaLSVersionDirs as pt, findCommonAncestorDirectory as q, loadConfigFile as qt, isDirectExecution as r, CacheError as rn, downloadAndExtractLuaLS as rt, resolveAnnotations as s, cleanCache as sn, cleanupOldCachedLuaLSVersions as st, collectIgnorePatterns as t, writeTempConfig as tn, MAX_ARCHIVE_SIZE_BYTES as tt, GITHUB_COMMITS_API as u, systemPaths as un, getCacheDir as ut, MAX_COMMIT_JSON_SIZE_BYTES as v, parseLogLevel as vn, MAX_DECOMPRESSED_SIZE_BYTES as vt, getTodayDateString as w, isBinaryRunnable as wt, getAnnotationsCacheDir as x, escapePowerShellSingleQuote as xt, METADATA_FILENAME as y, MIN_DOWNLOADED_BINARY_SIZE_BYTES as yt, collectDeps as z, DEFAULT_REALM_MAPPINGS as zt };
|
|
10672
11122
|
|
|
10673
|
-
//# sourceMappingURL=cli-
|
|
11123
|
+
//# sourceMappingURL=cli-Cb3wLBCr.js.map
|