AI Security Review
scanned 2h ago · by lpm-firewall-aiNpm preinstall automatically executes the package in the consuming project's working directory. It maps the directory, gathers host/user metadata, and exfiltrates up to 500 files to Discord.
Static reason
High-risk behavior combination matched malicious policy.
Trigger
`npm install` / dependency installation invokes the `preinstall` script.
Impact
Unauthorized disclosure of source files and local project/environment metadata.
Mechanism
install-time recursive file harvesting and Discord webhook exfiltration
Attack narrative
During npm preinstall, `index.js` immediately runs. It enumerates the installation working directory, sends a directory tree plus hostname, root path, username, and platform to one Discord webhook, then reads and uploads up to 500 non-excluded files up to 8 MiB each to another webhook.
Rationale
Direct source inspection confirms automatic install-time execution and broad local-file exfiltration to attacker-controlled Discord webhooks. This is concrete malicious behavior, not merely a risky primitive.
Evidence
package.jsonindex.js<process.cwd()>/**/*
Network endpoints2
discord.com/api/webhooks/1525551922281578586/NyRpxBSpZEAI2TYjchHrRlqsXpwH5qk70TBeQrQZTH2j0vGOwm_1wIaqPs3DOpIwgoC-discord.com/api/webhooks/1525552129572343958/ylicnDNawLzhBNSDeFu2jXQ0t3FtMNc7fQQtmzJ4pbTMOL6LhsbSOO-1gfhoAyUtaix6
Decision evidence
public snapshotAI called this Malicious at 99.0% confidence as Malware with low false-positive risk.
Evidence for block
- `package.json` runs `node index.js` in `preinstall`.
- `index.js` executes `main()` on load.
- `index.js` recursively enumerates up to 500 cwd files.
- `index.js` reads selected files and uploads contents.
- `index.js` posts host, path, and user metadata.
- Two hard-coded Discord webhook endpoints receive data.
Evidence against
- No child-process, eval, persistence, or destructive writes found.
- Collection excludes some binaries, archives, and manifest files, but remains broad.
Behavioral surface
EnvironmentVarsFilesystemNetwork
HighEntropyStringsUrlStrings
Source & flagged code
3 flagged · loading sourcepackage.jsonView file
•scripts.preinstall = node index.js
High
Install Time Lifecycle Scripts
Package defines install-time lifecycle scripts.
package.jsonView on unpkgindex.jsView file
2const path = require('path');
L3: const https = require('https');
L4: const os = require('os');
...
L30: const SKIP_FILENAMES = new Set([
L31: 'package.json',
L32: 'package-lock.json',
...
L124: req.on('error', reject);
L125: req.write(data);
L126: req.end();
...
L142:
L143: const payloadBuffer = Buffer.from(payload, 'utf8');
L144: const footerBuffer = Buffer.from(`\r\n--${boundary}--\r\n`);
Critical
Credential Exfiltration
Source appears to send environment or credential material to an external endpoint.
index.jsView on unpkg · L22Trigger-reachable chain: scripts.preinstall -> index.js
L2: const path = require('path');
L3: const https = require('https');
L4: const os = require('os');
...
L30: const SKIP_FILENAMES = new Set([
L31: 'package.json',
L32: 'package-lock.json',
...
L124: req.on('error', reject);
L125: req.write(data);
L126: req.end();
...
L142:
L143: const payloadBuffer = Buffer.from(payload, 'utf8');
L144: const footerBuffer = Buffer.from(`\r\n--${boundary}--\r\n`);
Critical
Trigger Reachable Dangerous Capability
A package entrypoint or install-time lifecycle script reaches a source file with blocking dangerous behavior.
index.jsView on unpkg · L2Findings
2 Critical1 High3 Medium4 Low
CriticalCredential Exfiltrationindex.js
CriticalTrigger Reachable Dangerous Capabilityindex.js
HighInstall Time Lifecycle Scriptspackage.json
MediumNetwork
MediumEnvironment Vars
MediumStructural Risk Force Deep Review
LowScripts Present
LowFilesystem
LowHigh Entropy Strings
LowUrl Strings