Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

shescape

Package Overview
Dependencies
Maintainers
1
Versions
51
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

shescape - npm Package Compare versions

Comparing version 1.2.1 to 1.3.0

6

CHANGELOG.md

@@ -12,2 +12,8 @@ # Changelog

## [1.3.0] - 2021-12-05
- Add support to configure the shell to escape for.
- Fix escaping backticks for PowerShell.
- Fix escaping `$` for PowerShell.
## [1.2.1] - 2021-04-24

@@ -14,0 +20,0 @@

30

index.js

@@ -11,3 +11,3 @@ /**

* @module shescape
* @version 1.2.1
* @version 1.3.0
* @license MPL-2.0

@@ -27,2 +27,4 @@ * @author Eric Cornelissen <ericornelissen@gmail.com>

* @param {string} arg The argument to escape.
* @param {Object} [options] The escape options.
* @param {string} [options.shell] The shell to escape the argument for.
* @returns {string} The escaped argument.

@@ -32,5 +34,6 @@ * @throws {TypeError} The argument is not stringable.

*/
export function escape(arg) {
export function escape(arg, options = {}) {
const shell = options.shell;
const platform = os.platform();
return main.escapeShellArgByPlatform(arg, platform);
return main.escapeShellArgByPlatform(arg, platform, shell);
}

@@ -46,2 +49,4 @@

* @param {string[]} args The arguments to escape.
* @param {Object} [options] The escape options.
* @param {string} [options.shell] The shell to escape the arguments for.
* @returns {string[]} The escaped arguments.

@@ -51,9 +56,10 @@ * @throws {TypeError} One of the arguments is not stringable.

*/
export function escapeAll(args) {
export function escapeAll(args, options = {}) {
if (!Array.isArray(args)) args = [args];
const shell = options.shell;
const platform = os.platform();
const result = [];
for (const arg of args) {
const safeArg = main.escapeShellArgByPlatform(arg, platform);
const safeArg = main.escapeShellArgByPlatform(arg, platform, shell);
result.push(safeArg);

@@ -72,2 +78,4 @@ }

* @param {string} arg The argument to quote and escape.
* @param {Object} [options] The escape and quote options.
* @param {string} [options.shell] The shell to escape the argument for.
* @returns {string} The quoted and escaped argument.

@@ -77,5 +85,6 @@ * @throws {TypeError} The argument is not stringable.

*/
export function quote(arg) {
export function quote(arg, options = {}) {
const shell = options.shell;
const platform = os.platform();
return main.quoteShellArgByPlatform(arg, platform);
return main.quoteShellArgByPlatform(arg, platform, shell);
}

@@ -91,2 +100,4 @@

* @param {string[]} args The arguments to quote and escape.
* @param {Object} [options] The escape and quote options.
* @param {string} [options.shell] The shell to escape the arguments for.
* @returns {string[]} The quoted and escaped arguments.

@@ -96,9 +107,10 @@ * @throws {TypeError} One of the arguments is not stringable.

*/
export function quoteAll(args) {
export function quoteAll(args, options = {}) {
if (!Array.isArray(args)) args = [args];
const shell = options.shell;
const platform = os.platform();
const result = [];
for (const arg of args) {
const safeArg = main.quoteShellArgByPlatform(arg, platform);
const safeArg = main.quoteShellArgByPlatform(arg, platform, shell);
result.push(safeArg);

@@ -105,0 +117,0 @@ }

{
"name": "shescape",
"version": "1.2.1",
"version": "1.3.0",
"description": "simple shell escape library",

@@ -15,14 +15,17 @@ "homepage": "https://ericcornelissen.github.io/shescape/",

"scripts": {
"clean": "rm -rf .corpus/ .nyc_output/ .stryker-tmp/ reports/ crash-* index.cjs",
"format": "prettier --write ./**/*.{cjs,js,md,yml}",
"prefuzz": "npm run transpile",
"clean": "node script/clean.js",
"coverage": "c8 --reports-dir=reports/coverage --reporter=lcov --reporter=text npm test",
"format": "prettier --write ./**/*.{cjs,js,md,yml} --ignore-path .gitignore",
"prefuzz": "npm run transpile && node script/prefuzz.js",
"fuzz": "jsfuzz ./test/index.fuzz.cjs ./.corpus",
"lint": "prettier --check ./**/*.{js,md,yml}",
"_postinstall": "is-ci || husky install",
"lint": "prettier --check ./**/*.{cjs,js,md,yml} --ignore-path .gitignore",
"_postinstall": "is-ci || husky install script/hooks",
"prepublishOnly": "pinst --disable && npm run transpile",
"postpublish": "pinst --enable",
"test": "mocha test/**/*.test.js",
"test:coverage": "c8 --reports-dir=reports/coverage --reporter=lcov --reporter=text npm run test",
"test:mutation": "stryker run",
"transpile": "ncc build index.js && mv dist/index.js index.cjs && rm -rf dist"
"test": "npm run test:unit",
"test:mutation": "stryker run stryker.config.json",
"test:property": "mocha test/**/*.prop.js --timeout 15000",
"test:transpiled": "mocha test/**/*.test.cjs",
"test:unit": "mocha test/**/*.test.js",
"transpile": "rollup -c"
},

@@ -47,12 +50,14 @@ "repository": {

"devDependencies": {
"@stryker-mutator/core": "^4.6.0",
"@vercel/ncc": "^0.28.3",
"@stryker-mutator/core": "^5.0.0",
"c8": "^7.7.1",
"husky": "^6.0.0",
"dotenv": "^10.0.0",
"fast-check": "^2.17.0",
"husky": "^7.0.0",
"is-ci": "^3.0.0",
"jsfuzz": "^1.0.14",
"mocha": "^8.2.0",
"mocha": "^9.0.1",
"pinst": "^2.1.1",
"prettier": "^2.1.2",
"sinon": "^10.0.0"
"rollup": "^2.55.1",
"sinon": "^12.0.0"
},

@@ -59,0 +64,0 @@ "engines": {

@@ -16,17 +16,19 @@ # Shescape

Below is a basic example of how to use _Shescape_. In this example `spawn` is
used to invoke a shell command and `shescape.escapeAll` is used to escape any
_dangerous_ character in any of the arguments specified by the array
`userInput`.
Below is a basic example of how to use _Shescape_. In this example `execSync` is
used to invoke a shell command and `shescape.quote` is used to quote and escape
any _dangerous_ character in the user input used as command input.
```js
import cp from "child_process";
import { execSync } from "child_process";
import * as shescape from "shescape";
cp.spawn("command", shescape.escapeAll(userInput), options);
const userInput = "&& ls";
const stdout = execSync(`echo Hello ${shescape.quote(userInput)}`);
console.log(stdout.toString());
// Output: "Hello && ls"
```
[shell injection]: https://portswigger.net/web-security/os-command-injection
[ci-url]: https://github.com/ericcornelissen/shescape/actions?query=workflow%3A%22Test+and+Lint%22+branch%3Amain
[ci-image]: https://img.shields.io/github/workflow/status/ericcornelissen/shescape/Test%20and%20Lint/main?logo=github
[ci-url]: https://github.com/ericcornelissen/shescape/actions/workflows/push-checks.yml
[ci-image]: https://img.shields.io/github/workflow/status/ericcornelissen/shescape/Push%20checks/main?logo=github
[coverage-url]: https://codecov.io/gh/ericcornelissen/shescape

@@ -33,0 +35,0 @@ [coverage-image]: https://codecov.io/gh/ericcornelissen/shescape/branch/main/graph/badge.svg

@@ -8,2 +8,9 @@ /**

/**
* @constant {string} regexpPowerShell A {@link RegExp} to detect if the shell
* to escape an argument for is "PowerShell".
* @example regexpPowerShell.test("cmd.exe"); // -> false
*/
export const regexpPowerShell = /powershell.exe$/;
/**
* @constant {string} typeError The error message for incorrect parameter types.

@@ -10,0 +17,0 @@ */

@@ -33,6 +33,7 @@ /**

* @param {string} platform The platform to escape the argument for.
* @param {string} [shell] The shell to escape the argument for.
* @returns {string} The escaped argument.
* @throws {TypeError} The argument is not stringable.
*/
export function escapeShellArgByPlatform(arg, platform) {
export function escapeShellArgByPlatform(arg, platform, shell) {
if (!isStringable(arg)) {

@@ -45,3 +46,3 @@ throw new TypeError(typeError);

case win32:
return win.escapeShellArg(argAsString);
return win.escapeShellArg(argAsString, shell);
default:

@@ -60,7 +61,8 @@ return unix.escapeShellArg(argAsString);

* @param {string} platform The platform to escape and quote the argument for.
* @param {string} [shell] The shell to escape and quote the argument for.
* @returns {string} The escaped argument.
* @throws {TypeError} The argument is not stringable.
*/
export function quoteShellArgByPlatform(arg, platform) {
const safeArg = escapeShellArgByPlatform(arg, platform);
export function quoteShellArgByPlatform(arg, platform, shell) {
const safeArg = escapeShellArgByPlatform(arg, platform, shell);
switch (platform) {

@@ -67,0 +69,0 @@ case win32:

@@ -7,4 +7,6 @@ /**

import { regexpPowerShell } from "./constants.js";
/**
* Escape a shell argument.
* Escape a shell argument for use in CMD.
*

@@ -14,4 +16,33 @@ * @param {string} arg The argument to escape.

*/
export function escapeShellArg(arg) {
function escapeShellArgsForCmd(arg) {
return arg.replace(/\u{0}/gu, "").replace(/"/g, `""`);
}
/**
* Escape a shell argument for use in PowerShell.
*
* @param {string} arg The argument to escape.
* @returns {string} The escaped argument.
*/
function escapeShellArgsForPowerShell(arg) {
return arg
.replace(/\u{0}/gu, "")
.replace(/"/g, `""`)
.replace(/`/g, "``")
.replace(/\$/g, "`$");
}
/**
* Escape a shell argument.
*
* @param {string} arg The argument to escape.
* @param {string} [shell] The shell to escape the argument for.
* @returns {string} The escaped argument.
*/
export function escapeShellArg(arg, shell) {
if (regexpPowerShell.test(shell)) {
return escapeShellArgsForPowerShell(arg);
} else {
return escapeShellArgsForCmd(arg);
}
}

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc