cognium-dev 4.9.24 → 4.9.25
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/dist/cli.js +85 -23
- package/package.json +3 -5
package/dist/cli.js
CHANGED
|
@@ -50156,19 +50156,30 @@ var YELLOW = "\x1B[93m";
|
|
|
50156
50156
|
var BLUE = "\x1B[94m";
|
|
50157
50157
|
var CYAN = "\x1B[96m";
|
|
50158
50158
|
var MAGENTA = "\x1B[95m";
|
|
50159
|
+
function colorEnabled() {
|
|
50160
|
+
const noColor = process.env.NO_COLOR;
|
|
50161
|
+
if (noColor !== undefined && noColor !== "")
|
|
50162
|
+
return false;
|
|
50163
|
+
if (process.env.TERM === "dumb")
|
|
50164
|
+
return false;
|
|
50165
|
+
return true;
|
|
50166
|
+
}
|
|
50167
|
+
function paint(code, text) {
|
|
50168
|
+
return colorEnabled() ? `${code}${text}${RESET}` : text;
|
|
50169
|
+
}
|
|
50159
50170
|
var colors = {
|
|
50160
|
-
red: (text) =>
|
|
50161
|
-
green: (text) =>
|
|
50162
|
-
yellow: (text) =>
|
|
50163
|
-
blue: (text) =>
|
|
50164
|
-
cyan: (text) =>
|
|
50165
|
-
magenta: (text) =>
|
|
50166
|
-
bold: (text) =>
|
|
50171
|
+
red: (text) => paint(RED, text),
|
|
50172
|
+
green: (text) => paint(GREEN, text),
|
|
50173
|
+
yellow: (text) => paint(YELLOW, text),
|
|
50174
|
+
blue: (text) => paint(BLUE, text),
|
|
50175
|
+
cyan: (text) => paint(CYAN, text),
|
|
50176
|
+
magenta: (text) => paint(MAGENTA, text),
|
|
50177
|
+
bold: (text) => paint(BOLD, text),
|
|
50167
50178
|
dim: (text) => text
|
|
50168
50179
|
};
|
|
50169
50180
|
|
|
50170
50181
|
// src/version.ts
|
|
50171
|
-
var version = "4.9.
|
|
50182
|
+
var version = "4.9.25";
|
|
50172
50183
|
|
|
50173
50184
|
// src/formatters.ts
|
|
50174
50185
|
var LIBRARY_API_SURFACE_TAG2 = "library-api-surface:caller-responsibility";
|
|
@@ -50713,8 +50724,8 @@ function generateSarifResults(results, crossFileData) {
|
|
|
50713
50724
|
|
|
50714
50725
|
// src/build-info.ts
|
|
50715
50726
|
var buildInfo = {
|
|
50716
|
-
gitSha: "
|
|
50717
|
-
builtAt: "2026-09-
|
|
50727
|
+
gitSha: "2467260",
|
|
50728
|
+
builtAt: "2026-09-24T06:46:18.058Z"
|
|
50718
50729
|
};
|
|
50719
50730
|
|
|
50720
50731
|
// src/utils/args.ts
|
|
@@ -50773,7 +50784,7 @@ COMMANDS:
|
|
|
50773
50784
|
version Display version information
|
|
50774
50785
|
|
|
50775
50786
|
SCAN OPTIONS:
|
|
50776
|
-
-l, --language <lang> Scan only files for language (bash|go|html|java|javascript|typescript|python|rust)
|
|
50787
|
+
-l, --language <lang> Scan only files for language (bash|csharp|go|html|java|javascript|typescript|python|rust)
|
|
50777
50788
|
-f, --format <format> Output format (text|json|sarif) [default: text]
|
|
50778
50789
|
--threads <n> Parallel analysis threads [default: 4]
|
|
50779
50790
|
--severity <level> Filter by severity:
|
|
@@ -50806,7 +50817,7 @@ SCAN OPTIONS:
|
|
|
50806
50817
|
surfaced in output (text warning / JSON / SARIF field).
|
|
50807
50818
|
|
|
50808
50819
|
METRICS OPTIONS:
|
|
50809
|
-
-l, --language <lang> Analyze only files for language (bash|go|html|java|javascript|typescript|python|rust)
|
|
50820
|
+
-l, --language <lang> Analyze only files for language (bash|csharp|go|html|java|javascript|typescript|python|rust)
|
|
50810
50821
|
-f, --format <format> Output format (text|json) [default: text]
|
|
50811
50822
|
--category <cats> Filter by metric category (comma-separated):
|
|
50812
50823
|
- Valid categories: complexity, size, coupling,
|
|
@@ -50915,19 +50926,19 @@ class Spinner {
|
|
|
50915
50926
|
succeed(text) {
|
|
50916
50927
|
this.stop();
|
|
50917
50928
|
const message = text || this._text;
|
|
50918
|
-
console.error(
|
|
50929
|
+
console.error(`${colors.green(CHECKMARK)} ${message}`);
|
|
50919
50930
|
return this;
|
|
50920
50931
|
}
|
|
50921
50932
|
fail(text) {
|
|
50922
50933
|
this.stop();
|
|
50923
50934
|
const message = text || this._text;
|
|
50924
|
-
console.error(
|
|
50935
|
+
console.error(`${colors.red(CROSS)} ${message}`);
|
|
50925
50936
|
return this;
|
|
50926
50937
|
}
|
|
50927
50938
|
warn(text) {
|
|
50928
50939
|
this.stop();
|
|
50929
50940
|
const message = text || this._text;
|
|
50930
|
-
console.error(
|
|
50941
|
+
console.error(`${colors.yellow(WARNING)} ${message}`);
|
|
50931
50942
|
return this;
|
|
50932
50943
|
}
|
|
50933
50944
|
set text(value) {
|
|
@@ -50954,8 +50965,7 @@ function loadConfig(profilePath) {
|
|
|
50954
50965
|
const content = readFileSync(configPath, "utf-8");
|
|
50955
50966
|
return JSON.parse(content);
|
|
50956
50967
|
} catch (err2) {
|
|
50957
|
-
|
|
50958
|
-
return null;
|
|
50968
|
+
throw new Error(`Failed to parse ${configPath}: ${err2 instanceof Error ? err2.message : String(err2)}. ` + "Fix the JSON or remove the file.");
|
|
50959
50969
|
}
|
|
50960
50970
|
}
|
|
50961
50971
|
function convertConfigToPassOptions(config) {
|
|
@@ -51021,6 +51031,27 @@ function applySuppressionsToResults(results, suppressions, basePath) {
|
|
|
51021
51031
|
return { ...result, vulnerabilities: filteredVulns };
|
|
51022
51032
|
});
|
|
51023
51033
|
}
|
|
51034
|
+
function applySuppressionsToTaintPaths(paths, suppressions, basePath) {
|
|
51035
|
+
if (suppressions.length === 0)
|
|
51036
|
+
return paths;
|
|
51037
|
+
return paths.filter((path) => {
|
|
51038
|
+
for (const supp of suppressions) {
|
|
51039
|
+
const sinkType = path.sink.type;
|
|
51040
|
+
if (supp.pass !== sinkType && supp.pass !== `cross-file-${sinkType}`)
|
|
51041
|
+
continue;
|
|
51042
|
+
if (supp.file) {
|
|
51043
|
+
const suppFile = supp.file.replace(/^\.\//, "");
|
|
51044
|
+
const relativeFile = relative4(basePath, path.sink.file) || path.sink.file;
|
|
51045
|
+
if (suppFile !== relativeFile && suppFile !== path.sink.file)
|
|
51046
|
+
continue;
|
|
51047
|
+
}
|
|
51048
|
+
if (supp.line !== undefined && supp.line !== path.sink.line)
|
|
51049
|
+
continue;
|
|
51050
|
+
return false;
|
|
51051
|
+
}
|
|
51052
|
+
return true;
|
|
51053
|
+
});
|
|
51054
|
+
}
|
|
51024
51055
|
var TEST_PATTERNS = [
|
|
51025
51056
|
/[\/\\]test[\/\\]/i,
|
|
51026
51057
|
/[\/\\]tests[\/\\]/i,
|
|
@@ -51078,9 +51109,30 @@ function detectLanguage7(filePath) {
|
|
|
51078
51109
|
const ext = extname(filePath).toLowerCase();
|
|
51079
51110
|
return LANG_MAP[ext] || null;
|
|
51080
51111
|
}
|
|
51112
|
+
var SUPPORTED_SCAN_LANGUAGES = [
|
|
51113
|
+
...new Set(Object.values(LANG_MAP))
|
|
51114
|
+
].sort();
|
|
51081
51115
|
function normalizeLanguage(language) {
|
|
51082
51116
|
return language.trim().toLowerCase();
|
|
51083
51117
|
}
|
|
51118
|
+
function resolveScanLanguage(raw) {
|
|
51119
|
+
if (raw === undefined || raw === "")
|
|
51120
|
+
return;
|
|
51121
|
+
const normalized = normalizeLanguage(String(raw));
|
|
51122
|
+
if (!SUPPORTED_SCAN_LANGUAGES.includes(normalized)) {
|
|
51123
|
+
throw new Error(`Invalid language: ${normalized}
|
|
51124
|
+
Valid options: ${SUPPORTED_SCAN_LANGUAGES.join(", ")}`);
|
|
51125
|
+
}
|
|
51126
|
+
return normalized;
|
|
51127
|
+
}
|
|
51128
|
+
function languageFromCliOptions(options) {
|
|
51129
|
+
try {
|
|
51130
|
+
return resolveScanLanguage(options.language || options.l);
|
|
51131
|
+
} catch (err2) {
|
|
51132
|
+
console.error(colors.red(`Error: ${err2.message}`));
|
|
51133
|
+
process.exit(1);
|
|
51134
|
+
}
|
|
51135
|
+
}
|
|
51084
51136
|
function fileMatchesLanguage(filePath, language) {
|
|
51085
51137
|
const detected = detectLanguage7(filePath);
|
|
51086
51138
|
if (!detected)
|
|
@@ -51091,9 +51143,13 @@ function fileMatchesLanguage(filePath, language) {
|
|
|
51091
51143
|
}
|
|
51092
51144
|
function matchesGlob(filePath, pattern) {
|
|
51093
51145
|
const normalizedPath = filePath.replace(/\\/g, "/");
|
|
51094
|
-
|
|
51146
|
+
let normalizedPattern = pattern.replace(/\\/g, "/");
|
|
51147
|
+
normalizedPattern = normalizedPattern.replace(/\*{3,}/g, "**").replace(/(?:\*\*\/)+/g, "**/").replace(/(?:\/\*\*)+/g, "/**");
|
|
51148
|
+
const globstarCount = (normalizedPattern.match(/\*\*/g) ?? []).length;
|
|
51149
|
+
if (globstarCount > 4)
|
|
51150
|
+
return false;
|
|
51095
51151
|
let regex = normalizedPattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*\*/g, "{{GLOBSTAR}}").replace(/\*/g, "[^/]*").replace(/\?/g, ".");
|
|
51096
|
-
regex = regex.replace(/\{\{GLOBSTAR\}\}\//g, "(
|
|
51152
|
+
regex = regex.replace(/\{\{GLOBSTAR\}\}\//g, "(?:[^/]+/)*").replace(/\/\{\{GLOBSTAR\}\}/g, "(?:/[^/]+)*").replace(/\{\{GLOBSTAR\}\}/g, "[^]*");
|
|
51097
51153
|
return new RegExp("^" + regex + "$").test(normalizedPath);
|
|
51098
51154
|
}
|
|
51099
51155
|
function matchesAnyPattern(filePath, patterns) {
|
|
@@ -51484,9 +51540,12 @@ async function runScan(targetPath, options) {
|
|
|
51484
51540
|
if (spin)
|
|
51485
51541
|
spin.succeed(`Scanned ${files.length} file(s)`);
|
|
51486
51542
|
if (suppressions.length > 0) {
|
|
51487
|
-
const beforeCount = results.reduce((sum, r) => sum + r.vulnerabilities.length, 0);
|
|
51543
|
+
const beforeCount = results.reduce((sum, r) => sum + r.vulnerabilities.length, 0) + (crossFileData?.taintPaths.length ?? 0);
|
|
51488
51544
|
results = applySuppressionsToResults(results, suppressions, process.cwd());
|
|
51489
|
-
|
|
51545
|
+
if (crossFileData) {
|
|
51546
|
+
crossFileData.taintPaths = applySuppressionsToTaintPaths(crossFileData.taintPaths, suppressions, process.cwd());
|
|
51547
|
+
}
|
|
51548
|
+
const afterCount = results.reduce((sum, r) => sum + r.vulnerabilities.length, 0) + (crossFileData?.taintPaths.length ?? 0);
|
|
51490
51549
|
if (!options.quiet && beforeCount !== afterCount) {
|
|
51491
51550
|
console.error(colors.dim(`Suppressed ${beforeCount - afterCount} finding(s) via config`));
|
|
51492
51551
|
}
|
|
@@ -52035,7 +52094,7 @@ Usage: cognium-dev metrics <path> [options]`);
|
|
|
52035
52094
|
category: options.category,
|
|
52036
52095
|
output: options.output || options.o,
|
|
52037
52096
|
quiet: options.quiet === true || options.q === true,
|
|
52038
|
-
language:
|
|
52097
|
+
language: languageFromCliOptions(options),
|
|
52039
52098
|
excludeTests: options["exclude-tests"] === true,
|
|
52040
52099
|
profile: options.profile || options.p
|
|
52041
52100
|
};
|
|
@@ -52073,7 +52132,7 @@ Usage: cognium-dev scan <path> [options]`);
|
|
|
52073
52132
|
}
|
|
52074
52133
|
const targetPath = args2[0];
|
|
52075
52134
|
const scanOptions = {
|
|
52076
|
-
language:
|
|
52135
|
+
language: languageFromCliOptions(options),
|
|
52077
52136
|
format: options.format || options.f || "text",
|
|
52078
52137
|
threads: parseInt(options.threads || "4", 10),
|
|
52079
52138
|
severity: options.severity,
|
|
@@ -52107,12 +52166,15 @@ main().catch((error) => {
|
|
|
52107
52166
|
process.exit(2);
|
|
52108
52167
|
});
|
|
52109
52168
|
export {
|
|
52169
|
+
resolveScanLanguage,
|
|
52110
52170
|
matchesGlob,
|
|
52111
52171
|
loadConfig,
|
|
52112
52172
|
isTestFile2 as isTestFile,
|
|
52113
52173
|
detectLanguage7 as detectLanguage,
|
|
52114
52174
|
dedupeVulnerabilities,
|
|
52115
52175
|
convertConfigToPassOptions,
|
|
52176
|
+
applySuppressionsToTaintPaths,
|
|
52116
52177
|
applySuppressionsToResults,
|
|
52178
|
+
SUPPORTED_SCAN_LANGUAGES,
|
|
52117
52179
|
PASS_REGISTRY
|
|
52118
52180
|
};
|
package/package.json
CHANGED
|
@@ -1,9 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "cognium-dev",
|
|
3
|
-
"version": "4.9.
|
|
3
|
+
"version": "4.9.25",
|
|
4
4
|
"description": "Static Application Security Testing CLI for detecting security vulnerabilities via taint tracking",
|
|
5
|
-
"main": "dist/index.js",
|
|
6
|
-
"types": "dist/index.d.ts",
|
|
7
5
|
"bin": {
|
|
8
6
|
"cognium-dev": "dist/cli.js"
|
|
9
7
|
},
|
|
@@ -14,7 +12,7 @@
|
|
|
14
12
|
"test": "bun test",
|
|
15
13
|
"clean": "rm -rf dist cognium-dev cognium-dev-* *.bun-build wasm",
|
|
16
14
|
"typecheck": "tsc --noEmit",
|
|
17
|
-
"version": "node -e \"const v = require('./package.json').version; require('fs').writeFileSync('src/version.ts', '/**\\n * Version information\\n *\\n * Kept in sync with package.json via the \\`version\\` npm lifecycle script.\\n * Do not edit manually
|
|
15
|
+
"version": "node -e \"const v = require('./package.json').version; require('fs').writeFileSync('src/version.ts', '/**\\n * Version information\\n *\\n * Kept in sync with package.json via the \\`version\\` npm lifecycle script.\\n * Do not edit manually \u2014 use \\`npm version patch|minor|major\\` instead.\\n */\\nexport const version = \\x27' + v + '\\x27;\\n')\" && git add src/version.ts",
|
|
18
16
|
"dogfood": "bun run src/cli.ts scan src/ -q",
|
|
19
17
|
"prepublishOnly": "bun run build",
|
|
20
18
|
"test:coverage": "bun test --coverage"
|
|
@@ -67,7 +65,7 @@
|
|
|
67
65
|
},
|
|
68
66
|
"dependencies": {
|
|
69
67
|
"@cognium/project-profile-detect": "1.1.1",
|
|
70
|
-
"circle-ir": "4.9.
|
|
68
|
+
"circle-ir": "4.9.25"
|
|
71
69
|
},
|
|
72
70
|
"devDependencies": {
|
|
73
71
|
"@types/node": "^26.6.1",
|