diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 5a534d7..ac3400d 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -10,7 +10,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - node-version: [20.x, 22.x, latest] + node-version: [20.x, 22.x, lts/*, latest] fail-fast: false steps: - name: Checkout diff --git a/docs/modules/bcrypt.md b/docs/modules/bcrypt.md new file mode 100644 index 0000000..6419cbb --- /dev/null +++ b/docs/modules/bcrypt.md @@ -0,0 +1,37 @@ +--- +description: Modern alternatives to the bcrypt package for password hashing +--- + +# Replacements for `bcrypt` + +The `bcrypt` package can be replaced by native functionality in most runtimes, or more performant packages. + +## `bcryptjs` + +[`bcryptjs`](https://github.com/dcodeIO/bcrypt.js) is a widely used pure JavaScript implementation with a very similar API surface to `bcrypt`. + +```ts +import bcrypt from 'bcrypt' // [!code --] +import bcrypt from 'bcryptjs' // [!code ++] + +const salt = await bcrypt.genSalt(10) + +const hash = await bcrypt.hash('password', salt) +``` + +## `node:crypto` (native, Node.js built-in) + +Node provides [`node:crypto`](https://nodejs.org/api/crypto.html) for secure password hashing primitives (for example `scrypt` and `pbkdf2`). This is not a drop-in `bcrypt` API replacement, but is a good option if you can switch to a more secure cryptographic algorithm it supports. + +## Web Crypto API (native) + +The [Web Crypto API](https://developer.mozilla.org/docs/Web/API/Web_Crypto_API) provides native functionality for cryptographic operations in both web browsers and Node. + +> [!NOTE] +> A few legacy algorithms are intentionally omitted for security reasons (e.g. MD5). + +## Bun (built-in) + +Bun supports the Web Crypto API natively, and also provides support for streaming hashing via [`Bun.CryptoHasher`](https://bun.sh/docs/api/hashing). + +As with the Web Crypto API, many legacy algorithms are intentionally omitted for security reasons (e.g. MD5). diff --git a/docs/modules/wrap-ansi.md b/docs/modules/wrap-ansi.md new file mode 100644 index 0000000..3b13bad --- /dev/null +++ b/docs/modules/wrap-ansi.md @@ -0,0 +1,18 @@ +--- +description: Modern replacement for the wrap-ansi package for wrapping terminal strings (including ANSI-colored output) +--- + +# Replacements for `wrap-ansi` + +## `fast-wrap-ansi` + +[`fast-wrap-ansi`](https://github.com/43081j/fast-wrap-ansi) is a drop‑in replacement for `wrap-ansi` that’s faster and smaller. + +```ts +import wrapAnsi from 'wrap-ansi' // [!code --] +import wrapAnsi from 'fast-wrap-ansi' // [!code ++] + +const value = '\u001B[36mhello-super-long-token-without-spaces\u001B[39m' + +console.log(wrapAnsi(value, 12, { hard: true, trim: false })) +``` diff --git a/manifests/micro-utilities.json b/manifests/micro-utilities.json index d5329a5..a7fa062 100644 --- a/manifests/micro-utilities.json +++ b/manifests/micro-utilities.json @@ -96,6 +96,12 @@ "description": "Every modern runtime provides a way to get the iterator function through the `Symbol.iterator` symbol.", "example": "const iterator = obj[Symbol.iterator]?.()" }, + "snippet::has-ansi": { + "id": "snippet::has-ansi", + "type": "simple", + "description": "You can use the `includes` method on the string to check if a specific ANSI byte is present.", + "example": "string.includes(\"\u001B\") || string.includes(\"\u009B\")" + }, "snippet::has-argv": { "id": "snippet::has-argv", "type": "simple", @@ -467,6 +473,11 @@ "moduleName": "for-own", "replacements": ["snippet::for-own"] }, + "has-ansi": { + "type": "module", + "moduleName": "has-ansi", + "replacements": ["snippet::has-ansi"] + }, "has-flag": { "type": "module", "moduleName": "has-flag", diff --git a/manifests/native.json b/manifests/native.json index 565021d..8cc7e55 100644 --- a/manifests/native.json +++ b/manifests/native.json @@ -627,6 +627,18 @@ "compatKey": "javascript.builtins.Date.now" } }, + "Error": { + "id": "Error", + "type": "native", + "url": { + "type": "mdn", + "id": "Web/JavaScript/Reference/Global_Objects/Error" + }, + "webFeatureId": { + "featureId": "javascript", + "compatKey": "javascript.builtins.Error" + } + }, "Error.isError": { "id": "Error.isError", "type": "native", @@ -2037,11 +2049,26 @@ "moduleName": "es5-shim", "replacements": ["es5-shim"] }, + "es6-error": { + "type": "module", + "moduleName": "es6-error", + "replacements": ["Error"] + }, + "es6-map": { + "type": "module", + "moduleName": "es6-map", + "replacements": ["Map"] + }, "es6-promise": { "type": "module", "moduleName": "es6-promise", "replacements": ["Promise"] }, + "es6-set": { + "type": "module", + "moduleName": "es6-set", + "replacements": ["Set"] + }, "es6-shim": { "type": "module", "moduleName": "es6-shim", @@ -2217,6 +2244,11 @@ "moduleName": "indexof", "replacements": ["Array.prototype.indexOf"] }, + "is-arrayish": { + "type": "module", + "moduleName": "is-arrayish", + "replacements": ["Array.isArray"] + }, "is-buffer": { "type": "module", "moduleName": "is-buffer", diff --git a/manifests/preferred.json b/manifests/preferred.json index e275345..e2e8a9c 100644 --- a/manifests/preferred.json +++ b/manifests/preferred.json @@ -48,6 +48,12 @@ "replacements": ["fetch", "ofetch", "ky"], "url": {"type": "e18e", "id": "fetch"} }, + "bcrypt": { + "type": "module", + "moduleName": "bcrypt", + "replacements": ["bcryptjs", "node:crypto", "crypto", "Bun.CryptoHasher"], + "url": {"type": "e18e", "id": "bcrypt"} + }, "bluebird": { "type": "module", "moduleName": "bluebird", @@ -2690,6 +2696,12 @@ "replacements": ["fetch", "ofetch", "ky"], "url": {"type": "e18e", "id": "fetch"} }, + "wrap-ansi": { + "type": "module", + "moduleName": "wrap-ansi", + "replacements": ["fast-wrap-ansi"], + "url": {"type": "e18e", "id": "wrap-ansi"} + }, "xmldom": { "type": "module", "moduleName": "xmldom", @@ -2905,6 +2917,11 @@ "type": "documented", "replacementModule": "ansis" }, + "bcryptjs": { + "id": "bcryptjs", + "type": "documented", + "replacementModule": "bcryptjs" + }, "betterknown": { "id": "betterknown", "type": "documented", @@ -3027,6 +3044,11 @@ "type": "documented", "replacementModule": "fast-uri" }, + "fast-wrap-ansi": { + "id": "fast-wrap-ansi", + "type": "documented", + "replacementModule": "fast-wrap-ansi" + }, "fdir": {"id": "fdir", "type": "documented", "replacementModule": "fdir"}, "fetch": { "id": "fetch",