@vercel/build-utils
Advanced tools
+15
-0
| # @vercel/build-utils | ||
| ## 13.4.0 | ||
| ### Minor Changes | ||
| - [services] synchronize dependencies in dev mode for JS/TS and Python services ([#14987](https://github.com/vercel/vercel/pull/14987)) | ||
| - [services] inject service URLs into web services as local paths ([#15024](https://github.com/vercel/vercel/pull/15024)) | ||
| ### Patch Changes | ||
| - Add new expirementalTrigger format for queues v2beta ([#14970](https://github.com/vercel/vercel/pull/14970)) | ||
| - Updated dependencies [[`a960cf23a42ff1a570c808ee9567670c24422f98`](https://github.com/vercel/vercel/commit/a960cf23a42ff1a570c808ee9567670c24422f98)]: | ||
| - @vercel/python-analysis@0.4.1 | ||
| ## 13.3.5 | ||
@@ -4,0 +19,0 @@ |
| /// <reference types="node" /> | ||
| /// <reference types="node" /> | ||
| import { SpawnOptions } from 'child_process'; | ||
@@ -76,3 +77,23 @@ import { Meta, PackageJson, NodeVersion, Config, BunVersion } from '../types'; | ||
| ignoreNon0Exit?: boolean; | ||
| /** | ||
| * Writable stream to pipe stdout to (e.g., for prefixing output in multi-service mode). | ||
| * When provided, stdio is automatically set to 'pipe'. | ||
| */ | ||
| outputStream?: NodeJS.WritableStream; | ||
| /** | ||
| * Writable stream to pipe stderr to (e.g., for prefixing output in multi-service mode). | ||
| * When provided, stdio is automatically set to 'pipe'. | ||
| */ | ||
| errorStream?: NodeJS.WritableStream; | ||
| } | ||
| export interface NpmInstallOutput { | ||
| /** | ||
| * Writable stream for stdout (e.g., for prefixing output in multi-service mode) | ||
| */ | ||
| stdout?: NodeJS.WritableStream; | ||
| /** | ||
| * Writable stream for stderr (e.g., for prefixing output in multi-service mode) | ||
| */ | ||
| stderr?: NodeJS.WritableStream; | ||
| } | ||
| export declare function spawnAsync(command: string, args: string[], opts?: SpawnOptionsExtended): Promise<void>; | ||
@@ -115,3 +136,3 @@ export declare function spawnCommand(command: string, options?: SpawnOptions): import("child_process").ChildProcess; | ||
| export declare function resetCustomInstallCommandSet(): void; | ||
| export declare function runNpmInstall(destPath: string, args?: string[], spawnOpts?: SpawnOptions, meta?: Meta, projectCreatedAt?: number): Promise<boolean>; | ||
| export declare function runNpmInstall(destPath: string, args?: string[], spawnOpts?: SpawnOptions, meta?: Meta, projectCreatedAt?: number, output?: NpmInstallOutput): Promise<boolean>; | ||
| /** | ||
@@ -118,0 +139,0 @@ * Prepares the input environment based on the used package manager and lockfile |
@@ -82,5 +82,17 @@ "use strict"; | ||
| const stderrLogs = []; | ||
| opts = { stdio: "inherit", ...opts }; | ||
| const hasCustomStreams = opts.outputStream || opts.errorStream; | ||
| if (hasCustomStreams) { | ||
| opts = { ...opts, stdio: ["inherit", "pipe", "pipe"] }; | ||
| } else { | ||
| opts = { stdio: "inherit", ...opts }; | ||
| } | ||
| const child = (0, import_cross_spawn.default)(command, args, opts); | ||
| if (opts.stdio === "pipe" && child.stderr) { | ||
| if (hasCustomStreams) { | ||
| if (child.stdout && opts.outputStream) { | ||
| child.stdout.pipe(opts.outputStream); | ||
| } | ||
| if (child.stderr && opts.errorStream) { | ||
| child.stderr.pipe(opts.errorStream); | ||
| } | ||
| } else if (opts.stdio === "pipe" && child.stderr) { | ||
| child.stderr.on("data", (data) => stderrLogs.push(data)); | ||
@@ -97,3 +109,3 @@ } | ||
| code: `BUILD_UTILS_SPAWN_${code || signal}`, | ||
| message: opts.stdio === "inherit" ? `${cmd} exited with ${code || signal}` : stderrLogs.map((line) => line.toString()).join("") | ||
| message: opts.stdio === "inherit" || hasCustomStreams ? `${cmd} exited with ${code || signal}` : stderrLogs.map((line) => line.toString()).join("") | ||
| }) | ||
@@ -523,3 +535,4 @@ ); | ||
| args, | ||
| opts | ||
| opts, | ||
| output | ||
| }) { | ||
@@ -531,2 +544,4 @@ const { commandArguments, prettyCommand } = getInstallCommandForPackageManager(packageManager, args); | ||
| } | ||
| opts.outputStream = output?.stdout; | ||
| opts.errorStream = output?.stderr; | ||
| await spawnAsync(packageManager, commandArguments, opts); | ||
@@ -551,3 +566,3 @@ } | ||
| } | ||
| async function runNpmInstall(destPath, args = [], spawnOpts, meta, projectCreatedAt) { | ||
| async function runNpmInstall(destPath, args = [], spawnOpts, meta, projectCreatedAt, output) { | ||
| if (meta?.isDev) { | ||
@@ -604,3 +619,7 @@ (0, import_debug.default)("Skipping dependency installation because dev mode is enabled"); | ||
| const installTime = Date.now(); | ||
| console.log("Installing dependencies..."); | ||
| if (output?.stdout) { | ||
| output.stdout.write("Installing dependencies...\n"); | ||
| } else { | ||
| console.log("Installing dependencies..."); | ||
| } | ||
| (0, import_debug.default)(`Installing to ${destPath}`); | ||
@@ -628,3 +647,4 @@ const opts = { cwd: destPath, ...spawnOpts }; | ||
| args, | ||
| opts | ||
| opts, | ||
| output | ||
| }); | ||
@@ -631,0 +651,0 @@ (0, import_debug.default)(`Install complete [${Date.now() - installTime}ms]`); |
@@ -14,2 +14,3 @@ import type { Service } from './types'; | ||
| deploymentUrl?: string; | ||
| origin?: string; | ||
| } | ||
@@ -16,0 +17,0 @@ /** |
@@ -27,8 +27,11 @@ "use strict"; | ||
| } | ||
| function computeServiceUrl(deploymentUrl, routePrefix) { | ||
| function computeServiceUrl(baseUrl, routePrefix, isOrigin) { | ||
| if (!isOrigin) { | ||
| baseUrl = `https://${baseUrl}`; | ||
| } | ||
| if (routePrefix === "/") { | ||
| return `https://${deploymentUrl}`; | ||
| return baseUrl; | ||
| } | ||
| const normalizedPrefix = routePrefix.startsWith("/") ? routePrefix.slice(1) : routePrefix; | ||
| return `https://${deploymentUrl}/${normalizedPrefix}`; | ||
| return `${baseUrl}/${normalizedPrefix}`; | ||
| } | ||
@@ -44,4 +47,11 @@ function getFrameworkEnvPrefix(frameworkSlug, frameworkList) { | ||
| function getServiceUrlEnvVars(options) { | ||
| const { services, frameworkList, currentEnv = {}, deploymentUrl } = options; | ||
| if (!deploymentUrl || !services || services.length === 0) { | ||
| const { | ||
| services, | ||
| frameworkList, | ||
| currentEnv = {}, | ||
| deploymentUrl, | ||
| origin | ||
| } = options; | ||
| const baseUrl = origin || deploymentUrl; | ||
| if (!baseUrl || !services || services.length === 0) { | ||
| return {}; | ||
@@ -62,3 +72,7 @@ } | ||
| const baseEnvVarName = serviceNameToEnvVar(service.name); | ||
| const absoluteUrl = computeServiceUrl(deploymentUrl, service.routePrefix); | ||
| const absoluteUrl = computeServiceUrl( | ||
| baseUrl, | ||
| service.routePrefix, | ||
| !!origin | ||
| ); | ||
| if (!(baseEnvVarName in currentEnv)) { | ||
@@ -65,0 +79,0 @@ envVars[baseEnvVarName] = absoluteUrl; |
+3
-3
| import FileBlob from './file-blob'; | ||
| import FileFsRef from './file-fs-ref'; | ||
| import FileRef from './file-ref'; | ||
| import { Lambda, createLambda, getLambdaOptionsFromFunction } from './lambda'; | ||
| import { Lambda, createLambda, getLambdaOptionsFromFunction, sanitizeConsumerName } from './lambda'; | ||
| import { NodejsLambda } from './nodejs-lambda'; | ||
@@ -11,3 +11,3 @@ import { Prerender } from './prerender'; | ||
| import rename from './fs/rename'; | ||
| import { spawnAsync, execCommand, spawnCommand, walkParentDirs, getScriptName, installDependencies, runPackageJsonScript, runNpmInstall, runBundleInstall, runPipInstall, runShellScript, runCustomInstallCommand, resetCustomInstallCommandSet, getEnvForPackageManager, getNodeVersion, getPathForPackageManager, detectPackageManager, getSpawnOptions, getNodeBinPath, getNodeBinPaths, scanParentDirs, findPackageJson, traverseUpDirectories, PipInstallResult } from './fs/run-user-scripts'; | ||
| import { spawnAsync, execCommand, spawnCommand, walkParentDirs, getScriptName, installDependencies, runPackageJsonScript, runNpmInstall, runBundleInstall, runPipInstall, runShellScript, runCustomInstallCommand, resetCustomInstallCommandSet, getEnvForPackageManager, getNodeVersion, getPathForPackageManager, detectPackageManager, getSpawnOptions, getNodeBinPath, getNodeBinPaths, scanParentDirs, findPackageJson, traverseUpDirectories, PipInstallResult, NpmInstallOutput } from './fs/run-user-scripts'; | ||
| import { getLatestNodeVersion, getDiscontinuedNodeVersions, getSupportedNodeVersion, isBunVersion, getSupportedBunVersion } from './fs/node-version'; | ||
@@ -23,3 +23,3 @@ import streamToBuffer, { streamToBufferChunks } from './fs/stream-to-buffer'; | ||
| import { validateNpmrc } from './validate-npmrc'; | ||
| export { FileBlob, FileFsRef, FileRef, Lambda, NodejsLambda, createLambda, Prerender, download, downloadFile, DownloadedFiles, getWriteableDirectory, glob, GlobOptions, rename, spawnAsync, getScriptName, installDependencies, runPackageJsonScript, execCommand, spawnCommand, walkParentDirs, getNodeBinPath, getNodeBinPaths, getSupportedNodeVersion, isBunVersion, getSupportedBunVersion, detectPackageManager, runNpmInstall, runBundleInstall, runPipInstall, PipInstallResult, runShellScript, runCustomInstallCommand, resetCustomInstallCommandSet, getEnvForPackageManager, getNodeVersion, getPathForPackageManager, getLatestNodeVersion, getDiscontinuedNodeVersions, getSpawnOptions, getPlatformEnv, getPrefixedEnvVars, getServiceUrlEnvVars, streamToBuffer, streamToBufferChunks, debug, isSymbolicLink, isDirectory, getLambdaOptionsFromFunction, scanParentDirs, findPackageJson, getIgnoreFilter, cloneEnv, hardLinkDir, traverseUpDirectories, validateNpmrc, }; | ||
| export { FileBlob, FileFsRef, FileRef, Lambda, NodejsLambda, createLambda, Prerender, download, downloadFile, DownloadedFiles, getWriteableDirectory, glob, GlobOptions, rename, spawnAsync, getScriptName, installDependencies, runPackageJsonScript, execCommand, spawnCommand, walkParentDirs, getNodeBinPath, getNodeBinPaths, getSupportedNodeVersion, isBunVersion, getSupportedBunVersion, detectPackageManager, runNpmInstall, NpmInstallOutput, runBundleInstall, runPipInstall, PipInstallResult, runShellScript, runCustomInstallCommand, resetCustomInstallCommandSet, getEnvForPackageManager, getNodeVersion, getPathForPackageManager, getLatestNodeVersion, getDiscontinuedNodeVersions, getSpawnOptions, getPlatformEnv, getPrefixedEnvVars, getServiceUrlEnvVars, streamToBuffer, streamToBufferChunks, debug, isSymbolicLink, isDirectory, getLambdaOptionsFromFunction, sanitizeConsumerName, scanParentDirs, findPackageJson, getIgnoreFilter, cloneEnv, hardLinkDir, traverseUpDirectories, validateNpmrc, }; | ||
| export { EdgeFunction } from './edge-function'; | ||
@@ -26,0 +26,0 @@ export { readConfigFile, getPackageJson } from './fs/read-config-file'; |
+19
-2
| /// <reference types="node" /> | ||
| import type { Config, Env, Files, FunctionFramework, TriggerEvent } from './types'; | ||
| export type { TriggerEvent }; | ||
| import type { Config, Env, Files, FunctionFramework, TriggerEvent, TriggerEventInput } from './types'; | ||
| export type { TriggerEvent, TriggerEventInput }; | ||
| /** | ||
| * Encodes a function path into a valid consumer name using mnemonic escapes. | ||
| * For queue/v2beta triggers, the consumer name is derived from the function path. | ||
| * This encoding is collision-free (bijective/reversible). | ||
| * | ||
| * Encoding scheme: | ||
| * - `_` → `__` (escape character itself) | ||
| * - `/` → `_S` (slash) | ||
| * - `.` → `_D` (dot) | ||
| * - Other invalid chars → `_XX` (hex code) | ||
| * | ||
| * @example | ||
| * sanitizeConsumerName('api/test.js') // => 'api_Stest_Djs' | ||
| * sanitizeConsumerName('api/users/handler.ts') // => 'api_Susers_Shandler_Dts' | ||
| * sanitizeConsumerName('my_func.ts') // => 'my__func_Dts' | ||
| */ | ||
| export declare function sanitizeConsumerName(functionPath: string): string; | ||
| export type LambdaOptions = LambdaOptionsWithFiles | LambdaOptionsWithZipBuffer; | ||
@@ -5,0 +22,0 @@ export type LambdaExecutableRuntimeLanguages = 'rust' | 'go'; |
+41
-5
@@ -34,3 +34,4 @@ "use strict"; | ||
| createZip: () => createZip, | ||
| getLambdaOptionsFromFunction: () => getLambdaOptionsFromFunction | ||
| getLambdaOptionsFromFunction: () => getLambdaOptionsFromFunction, | ||
| sanitizeConsumerName: () => sanitizeConsumerName | ||
| }); | ||
@@ -45,2 +46,19 @@ module.exports = __toCommonJS(lambda_exports); | ||
| var import_stream_to_buffer = __toESM(require("./fs/stream-to-buffer")); | ||
| function sanitizeConsumerName(functionPath) { | ||
| let result = ""; | ||
| for (const char of functionPath) { | ||
| if (char === "_") { | ||
| result += "__"; | ||
| } else if (char === "/") { | ||
| result += "_S"; | ||
| } else if (char === ".") { | ||
| result += "_D"; | ||
| } else if (/[A-Za-z0-9-]/.test(char)) { | ||
| result += char; | ||
| } else { | ||
| result += "_" + char.charCodeAt(0).toString(16).toUpperCase().padStart(2, "0"); | ||
| } | ||
| } | ||
| return result; | ||
| } | ||
| function getDefaultLambdaArchitecture(architecture) { | ||
@@ -167,4 +185,4 @@ if (architecture) { | ||
| (0, import_assert.default)( | ||
| trigger.type === "queue/v1beta", | ||
| `${prefix}.type must be "queue/v1beta"` | ||
| trigger.type === "queue/v1beta" || trigger.type === "queue/v2beta", | ||
| `${prefix}.type must be "queue/v1beta" or "queue/v2beta"` | ||
| ); | ||
@@ -184,2 +202,8 @@ (0, import_assert.default)( | ||
| ); | ||
| if (trigger.type === "queue/v2beta") { | ||
| (0, import_assert.default)( | ||
| experimentalTriggers.length === 1, | ||
| '"experimentalTriggers" can only have one item for queue/v2beta' | ||
| ); | ||
| } | ||
| if (trigger.maxDeliveries !== void 0) { | ||
@@ -325,2 +349,13 @@ (0, import_assert.default)( | ||
| if (sourceFile === pattern || (0, import_minimatch.default)(sourceFile, pattern)) { | ||
| const experimentalTriggers = fn.experimentalTriggers?.map( | ||
| (trigger) => { | ||
| if (trigger.type === "queue/v2beta") { | ||
| return { | ||
| ...trigger, | ||
| consumer: sanitizeConsumerName(pattern) | ||
| }; | ||
| } | ||
| return trigger; | ||
| } | ||
| ); | ||
| return { | ||
@@ -331,3 +366,3 @@ architecture: fn.architecture, | ||
| regions: fn.regions, | ||
| experimentalTriggers: fn.experimentalTriggers, | ||
| experimentalTriggers, | ||
| supportsCancellation: fn.supportsCancellation | ||
@@ -345,3 +380,4 @@ }; | ||
| createZip, | ||
| getLambdaOptionsFromFunction | ||
| getLambdaOptionsFromFunction, | ||
| sanitizeConsumerName | ||
| }); |
+30
-32
@@ -45,35 +45,33 @@ export declare const functionsSchema: { | ||
| items: { | ||
| type: string; | ||
| properties: { | ||
| type: { | ||
| type: string; | ||
| const: string; | ||
| oneOf: { | ||
| type: string; | ||
| properties: { | ||
| type: { | ||
| type: string; | ||
| const: string; | ||
| }; | ||
| topic: { | ||
| type: string; | ||
| minLength: number; | ||
| }; | ||
| maxDeliveries: { | ||
| type: string; | ||
| minimum: number; | ||
| }; | ||
| retryAfterSeconds: { | ||
| type: string; | ||
| exclusiveMinimum: number; | ||
| }; | ||
| initialDelaySeconds: { | ||
| type: string; | ||
| minimum: number; | ||
| }; | ||
| maxConcurrency: { | ||
| type: string; | ||
| minimum: number; | ||
| }; | ||
| }; | ||
| topic: { | ||
| type: string; | ||
| minLength: number; | ||
| }; | ||
| consumer: { | ||
| type: string; | ||
| minLength: number; | ||
| }; | ||
| maxDeliveries: { | ||
| type: string; | ||
| minimum: number; | ||
| }; | ||
| retryAfterSeconds: { | ||
| type: string; | ||
| exclusiveMinimum: number; | ||
| }; | ||
| initialDelaySeconds: { | ||
| type: string; | ||
| minimum: number; | ||
| }; | ||
| maxConcurrency: { | ||
| type: string; | ||
| minimum: number; | ||
| }; | ||
| }; | ||
| required: string[]; | ||
| additionalProperties: boolean; | ||
| required: string[]; | ||
| additionalProperties: boolean; | ||
| }[]; | ||
| }; | ||
@@ -80,0 +78,0 @@ }; |
+35
-1
@@ -25,3 +25,3 @@ "use strict"; | ||
| module.exports = __toCommonJS(schemas_exports); | ||
| const triggerEventSchema = { | ||
| const triggerEventSchemaV1 = { | ||
| type: "object", | ||
@@ -61,2 +61,36 @@ properties: { | ||
| }; | ||
| const triggerEventSchemaV2 = { | ||
| type: "object", | ||
| properties: { | ||
| type: { | ||
| type: "string", | ||
| const: "queue/v2beta" | ||
| }, | ||
| topic: { | ||
| type: "string", | ||
| minLength: 1 | ||
| }, | ||
| maxDeliveries: { | ||
| type: "number", | ||
| minimum: 1 | ||
| }, | ||
| retryAfterSeconds: { | ||
| type: "number", | ||
| exclusiveMinimum: 0 | ||
| }, | ||
| initialDelaySeconds: { | ||
| type: "number", | ||
| minimum: 0 | ||
| }, | ||
| maxConcurrency: { | ||
| type: "number", | ||
| minimum: 1 | ||
| } | ||
| }, | ||
| required: ["type", "topic"], | ||
| additionalProperties: false | ||
| }; | ||
| const triggerEventSchema = { | ||
| oneOf: [triggerEventSchemaV1, triggerEventSchemaV2] | ||
| }; | ||
| const functionsSchema = { | ||
@@ -63,0 +97,0 @@ type: "object", |
+36
-10
@@ -361,3 +361,3 @@ /// <reference types="node" /> | ||
| excludeFiles?: string; | ||
| experimentalTriggers?: TriggerEvent[]; | ||
| experimentalTriggers?: TriggerEventInput[]; | ||
| supportsCancellation?: boolean; | ||
@@ -563,13 +563,5 @@ }; | ||
| } | ||
| /** | ||
| * Queue trigger event for Vercel's queue system. | ||
| * Handles "queue/v1beta" events with queue-specific configuration. | ||
| */ | ||
| export interface TriggerEvent { | ||
| /** Event type - must be "queue/v1beta" (REQUIRED) */ | ||
| type: 'queue/v1beta'; | ||
| interface TriggerEventBase { | ||
| /** Name of the queue topic to consume from (REQUIRED) */ | ||
| topic: string; | ||
| /** Name of the consumer group for this trigger (REQUIRED) */ | ||
| consumer: string; | ||
| /** | ||
@@ -600,2 +592,36 @@ * Maximum number of delivery attempts for message processing (OPTIONAL) | ||
| } | ||
| /** | ||
| * Queue trigger input event for v1beta (from vercel.json config). | ||
| * Requires explicit consumer name. | ||
| */ | ||
| export interface TriggerEventInputV1 extends TriggerEventBase { | ||
| /** Event type - must be "queue/v1beta" (REQUIRED) */ | ||
| type: 'queue/v1beta'; | ||
| /** Name of the consumer group for this trigger (REQUIRED) */ | ||
| consumer: string; | ||
| } | ||
| /** | ||
| * Queue trigger input event for v2beta (from vercel.json config). | ||
| * Consumer name is implicitly derived from the function path. | ||
| * Only one trigger per function is allowed. | ||
| */ | ||
| export interface TriggerEventInputV2 extends TriggerEventBase { | ||
| /** Event type - must be "queue/v2beta" (REQUIRED) */ | ||
| type: 'queue/v2beta'; | ||
| } | ||
| /** | ||
| * Queue trigger input event from vercel.json config. | ||
| * v1beta requires explicit consumer, v2beta derives consumer from function path. | ||
| */ | ||
| export type TriggerEventInput = TriggerEventInputV1 | TriggerEventInputV2; | ||
| /** | ||
| * Processed queue trigger event for Lambda. | ||
| * Consumer is always present (explicitly provided for v1beta, derived for v2beta). | ||
| */ | ||
| export interface TriggerEvent extends TriggerEventBase { | ||
| /** Event type */ | ||
| type: 'queue/v1beta' | 'queue/v2beta'; | ||
| /** Name of the consumer group for this trigger (always present in processed output) */ | ||
| consumer: string; | ||
| } | ||
| export type ServiceRuntime = 'node' | 'python' | 'go' | 'rust' | 'ruby'; | ||
@@ -602,0 +628,0 @@ export type ServiceType = 'web' | 'cron' | 'worker'; |
+4
-4
| { | ||
| "name": "@vercel/build-utils", | ||
| "version": "13.4.0-canary.20260211174907.cdd2da6", | ||
| "version": "13.4.0", | ||
| "license": "Apache-2.0", | ||
@@ -14,3 +14,3 @@ "main": "./dist/index.js", | ||
| "dependencies": { | ||
| "@vercel/python-analysis": "0.5.0-canary.20260211174907.cdd2da6" | ||
| "@vercel/python-analysis": "0.4.1" | ||
| }, | ||
@@ -54,4 +54,4 @@ "devDependencies": { | ||
| "json5": "2.2.3", | ||
| "@vercel/error-utils": "2.1.0-canary.20260211174907.cdd2da6", | ||
| "@vercel/routing-utils": "5.4.0-canary.20260211174907.cdd2da6" | ||
| "@vercel/routing-utils": "5.3.2", | ||
| "@vercel/error-utils": "2.0.3" | ||
| }, | ||
@@ -58,0 +58,0 @@ "scripts": { |
Sorry, the diff of this file is too big to display
Network access
Supply chain riskThis module accesses the network.
Found 1 instance in 1 package
Shell access
Supply chain riskThis module accesses the system shell. Accessing the system shell increases the risk of executing arbitrary code.
Found 1 instance in 1 package
Dynamic require
Supply chain riskDynamic require can indicate the package is performing dangerous or unsafe dynamic code execution.
Found 1 instance in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 11 instances in 1 package
Filesystem access
Supply chain riskAccesses the file system, and could potentially read sensitive data.
Found 3 instances in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
URL strings
Supply chain riskPackage contains fragments of external URLs or IP addresses, which the package may be accessing at runtime.
Found 1 instance in 1 package
Network access
Supply chain riskThis module accesses the network.
Found 1 instance in 1 package
Shell access
Supply chain riskThis module accesses the system shell. Accessing the system shell increases the risk of executing arbitrary code.
Found 1 instance in 1 package
Dynamic require
Supply chain riskDynamic require can indicate the package is performing dangerous or unsafe dynamic code execution.
Found 1 instance in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 11 instances in 1 package
Filesystem access
Supply chain riskAccesses the file system, and could potentially read sensitive data.
Found 3 instances in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
URL strings
Supply chain riskPackage contains fragments of external URLs or IP addresses, which the package may be accessing at runtime.
Found 1 instance in 1 package
1404701
0.58%32202
0.85%0
-100%+ Added
- Removed