mirror of
https://github.com/oven-sh/bun
synced 2026-02-02 15:08:46 +00:00
Introduce Bun.stripANSI (#21801)
### What does this PR do? Introduce `Bun.stripANSI`, a SIMD-accelerated drop-in replacement for the popular `"strip-ansi"` package. `Bun.stripANSI` performs >10x faster and fixes several bugs in `strip-ansi`, like [this long-standing one](https://github.com/chalk/strip-ansi/issues/43). ### How did you verify your code works? There are tests that check the output of `strip-ansi` matches `Bun.stripANSI`. For cases where `strip-ansi`'s behavior is incorrect, the expected value is manually provided. --------- Co-authored-by: Jarred-Sumner <709451+Jarred-Sumner@users.noreply.github.com> Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com> Co-authored-by: Claude Bot <claude-bot@bun.sh> Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: taylor.fish <contact@taylor.fish>
This commit is contained in:
@@ -15,11 +15,13 @@
|
|||||||
"eventemitter3": "^5.0.0",
|
"eventemitter3": "^5.0.0",
|
||||||
"execa": "^8.0.1",
|
"execa": "^8.0.1",
|
||||||
"fast-glob": "3.3.1",
|
"fast-glob": "3.3.1",
|
||||||
|
"fastify": "^5.0.0",
|
||||||
"fdir": "^6.1.0",
|
"fdir": "^6.1.0",
|
||||||
"mitata": "^1.0.25",
|
"mitata": "^1.0.25",
|
||||||
"react": "^18.3.1",
|
"react": "^18.3.1",
|
||||||
"react-dom": "^18.3.1",
|
"react-dom": "^18.3.1",
|
||||||
"string-width": "7.1.0",
|
"string-width": "7.1.0",
|
||||||
|
"strip-ansi": "^7.1.0",
|
||||||
"tinycolor2": "^1.6.0",
|
"tinycolor2": "^1.6.0",
|
||||||
"zx": "^7.2.3",
|
"zx": "^7.2.3",
|
||||||
},
|
},
|
||||||
@@ -93,6 +95,18 @@
|
|||||||
|
|
||||||
"@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.14.54", "", { "os": "linux", "cpu": "none" }, "sha512-bZBrLAIX1kpWelV0XemxBZllyRmM6vgFQQG2GdNb+r3Fkp0FOh1NJSvekXDs7jq70k4euu1cryLMfU+mTXlEpw=="],
|
"@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.14.54", "", { "os": "linux", "cpu": "none" }, "sha512-bZBrLAIX1kpWelV0XemxBZllyRmM6vgFQQG2GdNb+r3Fkp0FOh1NJSvekXDs7jq70k4euu1cryLMfU+mTXlEpw=="],
|
||||||
|
|
||||||
|
"@fastify/ajv-compiler": ["@fastify/ajv-compiler@4.0.2", "", { "dependencies": { "ajv": "^8.12.0", "ajv-formats": "^3.0.1", "fast-uri": "^3.0.0" } }, "sha512-Rkiu/8wIjpsf46Rr+Fitd3HRP+VsxUFDDeag0hs9L0ksfnwx2g7SPQQTFL0E8Qv+rfXzQOxBJnjUB9ITUDjfWQ=="],
|
||||||
|
|
||||||
|
"@fastify/error": ["@fastify/error@4.2.0", "", {}, "sha512-RSo3sVDXfHskiBZKBPRgnQTtIqpi/7zhJOEmAxCiBcM7d0uwdGdxLlsCaLzGs8v8NnxIRlfG0N51p5yFaOentQ=="],
|
||||||
|
|
||||||
|
"@fastify/fast-json-stringify-compiler": ["@fastify/fast-json-stringify-compiler@5.0.3", "", { "dependencies": { "fast-json-stringify": "^6.0.0" } }, "sha512-uik7yYHkLr6fxd8hJSZ8c+xF4WafPK+XzneQDPU+D10r5X19GW8lJcom2YijX2+qtFF1ENJlHXKFM9ouXNJYgQ=="],
|
||||||
|
|
||||||
|
"@fastify/forwarded": ["@fastify/forwarded@3.0.0", "", {}, "sha512-kJExsp4JCms7ipzg7SJ3y8DwmePaELHxKYtg+tZow+k0znUTf3cb+npgyqm8+ATZOdmfgfydIebPDWM172wfyA=="],
|
||||||
|
|
||||||
|
"@fastify/merge-json-schemas": ["@fastify/merge-json-schemas@0.2.1", "", { "dependencies": { "dequal": "^2.0.3" } }, "sha512-OA3KGBCy6KtIvLf8DINC5880o5iBlDX4SxzLQS8HorJAbqluzLRn80UXU0bxZn7UOFhFgpRJDasfwn9nG4FG4A=="],
|
||||||
|
|
||||||
|
"@fastify/proxy-addr": ["@fastify/proxy-addr@5.0.0", "", { "dependencies": { "@fastify/forwarded": "^3.0.0", "ipaddr.js": "^2.1.0" } }, "sha512-37qVVA1qZ5sgH7KpHkkC4z9SK6StIsIcOmpjvMPXNb3vx2GQxhZocogVYbr2PbbeLCQxYIPDok307xEvRZOzGA=="],
|
||||||
|
|
||||||
"@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.1.1", "", { "dependencies": { "@jridgewell/set-array": "^1.0.0", "@jridgewell/sourcemap-codec": "^1.4.10" } }, "sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w=="],
|
"@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.1.1", "", { "dependencies": { "@jridgewell/set-array": "^1.0.0", "@jridgewell/sourcemap-codec": "^1.4.10" } }, "sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w=="],
|
||||||
|
|
||||||
"@jridgewell/resolve-uri": ["@jridgewell/resolve-uri@3.1.0", "", {}, "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w=="],
|
"@jridgewell/resolve-uri": ["@jridgewell/resolve-uri@3.1.0", "", {}, "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w=="],
|
||||||
@@ -143,10 +157,20 @@
|
|||||||
|
|
||||||
"@types/which": ["@types/which@3.0.3", "", {}, "sha512-2C1+XoY0huExTbs8MQv1DuS5FS86+SEjdM9F/+GS61gg5Hqbtj8ZiDSx8MfWcyei907fIPbfPGCOrNUTnVHY1g=="],
|
"@types/which": ["@types/which@3.0.3", "", {}, "sha512-2C1+XoY0huExTbs8MQv1DuS5FS86+SEjdM9F/+GS61gg5Hqbtj8ZiDSx8MfWcyei907fIPbfPGCOrNUTnVHY1g=="],
|
||||||
|
|
||||||
|
"abstract-logging": ["abstract-logging@2.0.1", "", {}, "sha512-2BjRTZxTPvheOvGbBslFSYOUkr+SjPtOnrLP33f+VIWLzezQpZcqVg7ja3L4dBXmzzgwT+a029jRx5PCi3JuiA=="],
|
||||||
|
|
||||||
|
"ajv": ["ajv@8.17.1", "", { "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", "json-schema-traverse": "^1.0.0", "require-from-string": "^2.0.2" } }, "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g=="],
|
||||||
|
|
||||||
|
"ajv-formats": ["ajv-formats@3.0.1", "", { "dependencies": { "ajv": "^8.0.0" } }, "sha512-8iUql50EUR+uUcdRQ3HDqa6EVyo3docL8g5WJ3FNcWmu62IbkGUue/pEyLBW8VGKKucTPgqeks4fIU1DA4yowQ=="],
|
||||||
|
|
||||||
"ansi-regex": ["ansi-regex@6.0.1", "", {}, "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA=="],
|
"ansi-regex": ["ansi-regex@6.0.1", "", {}, "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA=="],
|
||||||
|
|
||||||
"ansi-styles": ["ansi-styles@3.2.1", "", { "dependencies": { "color-convert": "^1.9.0" } }, "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA=="],
|
"ansi-styles": ["ansi-styles@3.2.1", "", { "dependencies": { "color-convert": "^1.9.0" } }, "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA=="],
|
||||||
|
|
||||||
|
"atomic-sleep": ["atomic-sleep@1.0.0", "", {}, "sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ=="],
|
||||||
|
|
||||||
|
"avvio": ["avvio@9.1.0", "", { "dependencies": { "@fastify/error": "^4.0.0", "fastq": "^1.17.1" } }, "sha512-fYASnYi600CsH/j9EQov7lECAniYiBFiiAtBNuZYLA2leLe9qOvZzqYHFjtIj6gD2VMoMLP14834LFWvr4IfDw=="],
|
||||||
|
|
||||||
"benchmark": ["benchmark@2.1.4", "", { "dependencies": { "lodash": "^4.17.4", "platform": "^1.3.3" } }, "sha512-l9MlfN4M1K/H2fbhfMy3B7vJd6AGKJVQn2h6Sg/Yx+KckoUA7ewS5Vv6TjSq18ooE1kS9hhAlQRH3AkXIh/aOQ=="],
|
"benchmark": ["benchmark@2.1.4", "", { "dependencies": { "lodash": "^4.17.4", "platform": "^1.3.3" } }, "sha512-l9MlfN4M1K/H2fbhfMy3B7vJd6AGKJVQn2h6Sg/Yx+KckoUA7ewS5Vv6TjSq18ooE1kS9hhAlQRH3AkXIh/aOQ=="],
|
||||||
|
|
||||||
"braces": ["braces@3.0.2", "", { "dependencies": { "fill-range": "^7.0.1" } }, "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A=="],
|
"braces": ["braces@3.0.2", "", { "dependencies": { "fill-range": "^7.0.1" } }, "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A=="],
|
||||||
@@ -167,12 +191,16 @@
|
|||||||
|
|
||||||
"convert-source-map": ["convert-source-map@1.9.0", "", {}, "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A=="],
|
"convert-source-map": ["convert-source-map@1.9.0", "", {}, "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A=="],
|
||||||
|
|
||||||
|
"cookie": ["cookie@1.0.2", "", {}, "sha512-9Kr/j4O16ISv8zBBhJoi4bXOYNTkFLOqSL3UDB0njXxCXNezjeyVrJyGOWtgfs/q2km1gwBcfH8q1yEGoMYunA=="],
|
||||||
|
|
||||||
"cross-spawn": ["cross-spawn@7.0.3", "", { "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", "which": "^2.0.1" } }, "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w=="],
|
"cross-spawn": ["cross-spawn@7.0.3", "", { "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", "which": "^2.0.1" } }, "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w=="],
|
||||||
|
|
||||||
"data-uri-to-buffer": ["data-uri-to-buffer@4.0.1", "", {}, "sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A=="],
|
"data-uri-to-buffer": ["data-uri-to-buffer@4.0.1", "", {}, "sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A=="],
|
||||||
|
|
||||||
"debug": ["debug@4.3.4", "", { "dependencies": { "ms": "2.1.2" } }, "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ=="],
|
"debug": ["debug@4.3.4", "", { "dependencies": { "ms": "2.1.2" } }, "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ=="],
|
||||||
|
|
||||||
|
"dequal": ["dequal@2.0.3", "", {}, "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA=="],
|
||||||
|
|
||||||
"dir-glob": ["dir-glob@3.0.1", "", { "dependencies": { "path-type": "^4.0.0" } }, "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA=="],
|
"dir-glob": ["dir-glob@3.0.1", "", { "dependencies": { "path-type": "^4.0.0" } }, "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA=="],
|
||||||
|
|
||||||
"duplexer": ["duplexer@0.1.2", "", {}, "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg=="],
|
"duplexer": ["duplexer@0.1.2", "", {}, "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg=="],
|
||||||
@@ -233,10 +261,22 @@
|
|||||||
|
|
||||||
"execa": ["execa@8.0.1", "", { "dependencies": { "cross-spawn": "^7.0.3", "get-stream": "^8.0.1", "human-signals": "^5.0.0", "is-stream": "^3.0.0", "merge-stream": "^2.0.0", "npm-run-path": "^5.1.0", "onetime": "^6.0.0", "signal-exit": "^4.1.0", "strip-final-newline": "^3.0.0" } }, "sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg=="],
|
"execa": ["execa@8.0.1", "", { "dependencies": { "cross-spawn": "^7.0.3", "get-stream": "^8.0.1", "human-signals": "^5.0.0", "is-stream": "^3.0.0", "merge-stream": "^2.0.0", "npm-run-path": "^5.1.0", "onetime": "^6.0.0", "signal-exit": "^4.1.0", "strip-final-newline": "^3.0.0" } }, "sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg=="],
|
||||||
|
|
||||||
|
"fast-decode-uri-component": ["fast-decode-uri-component@1.0.1", "", {}, "sha512-WKgKWg5eUxvRZGwW8FvfbaH7AXSh2cL+3j5fMGzUMCxWBJ3dV3a7Wz8y2f/uQ0e3B6WmodD3oS54jTQ9HVTIIg=="],
|
||||||
|
|
||||||
"fast-deep-equal": ["fast-deep-equal@3.1.3", "", {}, "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="],
|
"fast-deep-equal": ["fast-deep-equal@3.1.3", "", {}, "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="],
|
||||||
|
|
||||||
"fast-glob": ["fast-glob@3.3.1", "", { "dependencies": { "@nodelib/fs.stat": "^2.0.2", "@nodelib/fs.walk": "^1.2.3", "glob-parent": "^5.1.2", "merge2": "^1.3.0", "micromatch": "^4.0.4" } }, "sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg=="],
|
"fast-glob": ["fast-glob@3.3.1", "", { "dependencies": { "@nodelib/fs.stat": "^2.0.2", "@nodelib/fs.walk": "^1.2.3", "glob-parent": "^5.1.2", "merge2": "^1.3.0", "micromatch": "^4.0.4" } }, "sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg=="],
|
||||||
|
|
||||||
|
"fast-json-stringify": ["fast-json-stringify@6.0.1", "", { "dependencies": { "@fastify/merge-json-schemas": "^0.2.0", "ajv": "^8.12.0", "ajv-formats": "^3.0.1", "fast-uri": "^3.0.0", "json-schema-ref-resolver": "^2.0.0", "rfdc": "^1.2.0" } }, "sha512-s7SJE83QKBZwg54dIbD5rCtzOBVD43V1ReWXXYqBgwCwHLYAAT0RQc/FmrQglXqWPpz6omtryJQOau5jI4Nrvg=="],
|
||||||
|
|
||||||
|
"fast-querystring": ["fast-querystring@1.1.2", "", { "dependencies": { "fast-decode-uri-component": "^1.0.1" } }, "sha512-g6KuKWmFXc0fID8WWH0jit4g0AGBoJhCkJMb1RmbsSEUNvQ+ZC8D6CUZ+GtF8nMzSPXnhiePyyqqipzNNEnHjg=="],
|
||||||
|
|
||||||
|
"fast-redact": ["fast-redact@3.5.0", "", {}, "sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A=="],
|
||||||
|
|
||||||
|
"fast-uri": ["fast-uri@3.0.6", "", {}, "sha512-Atfo14OibSv5wAp4VWNsFYE1AchQRTv9cBGWET4pZWHzYshFSS9NQI6I57rdKn9croWVMbYFbLhJ+yJvmZIIHw=="],
|
||||||
|
|
||||||
|
"fastify": ["fastify@5.5.0", "", { "dependencies": { "@fastify/ajv-compiler": "^4.0.0", "@fastify/error": "^4.0.0", "@fastify/fast-json-stringify-compiler": "^5.0.0", "@fastify/proxy-addr": "^5.0.0", "abstract-logging": "^2.0.1", "avvio": "^9.0.0", "fast-json-stringify": "^6.0.0", "find-my-way": "^9.0.0", "light-my-request": "^6.0.0", "pino": "^9.0.0", "process-warning": "^5.0.0", "rfdc": "^1.3.1", "secure-json-parse": "^4.0.0", "semver": "^7.6.0", "toad-cache": "^3.7.0" } }, "sha512-ZWSWlzj3K/DcULCnCjEiC2zn2FBPdlZsSA/pnPa/dbUfLvxkD/Nqmb0XXMXLrWkeM4uQPUvjdJpwtXmTfriXqw=="],
|
||||||
|
|
||||||
"fastq": ["fastq@1.15.0", "", { "dependencies": { "reusify": "^1.0.4" } }, "sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw=="],
|
"fastq": ["fastq@1.15.0", "", { "dependencies": { "reusify": "^1.0.4" } }, "sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw=="],
|
||||||
|
|
||||||
"fdir": ["fdir@6.1.0", "", { "peerDependencies": { "picomatch": "2.x" } }, "sha512-274qhz5PxNnA/fybOu6apTCUnM0GnO3QazB6VH+oag/7DQskdYq8lm07ZSm90kEQuWYH5GvjAxGruuHrEr0bcg=="],
|
"fdir": ["fdir@6.1.0", "", { "peerDependencies": { "picomatch": "2.x" } }, "sha512-274qhz5PxNnA/fybOu6apTCUnM0GnO3QazB6VH+oag/7DQskdYq8lm07ZSm90kEQuWYH5GvjAxGruuHrEr0bcg=="],
|
||||||
@@ -245,6 +285,8 @@
|
|||||||
|
|
||||||
"fill-range": ["fill-range@7.0.1", "", { "dependencies": { "to-regex-range": "^5.0.1" } }, "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ=="],
|
"fill-range": ["fill-range@7.0.1", "", { "dependencies": { "to-regex-range": "^5.0.1" } }, "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ=="],
|
||||||
|
|
||||||
|
"find-my-way": ["find-my-way@9.3.0", "", { "dependencies": { "fast-deep-equal": "^3.1.3", "fast-querystring": "^1.0.0", "safe-regex2": "^5.0.0" } }, "sha512-eRoFWQw+Yv2tuYlK2pjFS2jGXSxSppAs3hSQjfxVKxM5amECzIgYYc1FEI8ZmhSh/Ig+FrKEz43NLRKJjYCZVg=="],
|
||||||
|
|
||||||
"formdata-polyfill": ["formdata-polyfill@4.0.10", "", { "dependencies": { "fetch-blob": "^3.1.2" } }, "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g=="],
|
"formdata-polyfill": ["formdata-polyfill@4.0.10", "", { "dependencies": { "fetch-blob": "^3.1.2" } }, "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g=="],
|
||||||
|
|
||||||
"from": ["from@0.1.7", "", {}, "sha512-twe20eF1OxVxp/ML/kq2p1uc6KvFK/+vs8WjEbeKmV2He22MKm7YF2ANIt+EOqhJ5L3K/SuuPhk0hWQDjOM23g=="],
|
"from": ["from@0.1.7", "", {}, "sha512-twe20eF1OxVxp/ML/kq2p1uc6KvFK/+vs8WjEbeKmV2He22MKm7YF2ANIt+EOqhJ5L3K/SuuPhk0hWQDjOM23g=="],
|
||||||
@@ -273,6 +315,8 @@
|
|||||||
|
|
||||||
"ignore": ["ignore@5.3.0", "", {}, "sha512-g7dmpshy+gD7mh88OC9NwSGTKoc3kyLAZQRU1mt53Aw/vnvfXnbC+F/7F7QoYVKbV+KNvJx8wArewKy1vXMtlg=="],
|
"ignore": ["ignore@5.3.0", "", {}, "sha512-g7dmpshy+gD7mh88OC9NwSGTKoc3kyLAZQRU1mt53Aw/vnvfXnbC+F/7F7QoYVKbV+KNvJx8wArewKy1vXMtlg=="],
|
||||||
|
|
||||||
|
"ipaddr.js": ["ipaddr.js@2.2.0", "", {}, "sha512-Ag3wB2o37wslZS19hZqorUnrnzSkpOVy+IiiDEiTqNubEYpYuHWIf6K4psgN2ZWKExS4xhVCrRVfb/wfW8fWJA=="],
|
||||||
|
|
||||||
"is-arrayish": ["is-arrayish@0.3.2", "", {}, "sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ=="],
|
"is-arrayish": ["is-arrayish@0.3.2", "", {}, "sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ=="],
|
||||||
|
|
||||||
"is-extglob": ["is-extglob@2.1.1", "", {}, "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ=="],
|
"is-extglob": ["is-extglob@2.1.1", "", {}, "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ=="],
|
||||||
@@ -289,10 +333,16 @@
|
|||||||
|
|
||||||
"jsesc": ["jsesc@2.5.2", "", { "bin": { "jsesc": "bin/jsesc" } }, "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA=="],
|
"jsesc": ["jsesc@2.5.2", "", { "bin": { "jsesc": "bin/jsesc" } }, "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA=="],
|
||||||
|
|
||||||
|
"json-schema-ref-resolver": ["json-schema-ref-resolver@2.0.1", "", { "dependencies": { "dequal": "^2.0.3" } }, "sha512-HG0SIB9X4J8bwbxCbnd5FfPEbcXAJYTi1pBJeP/QPON+w8ovSME8iRG+ElHNxZNX2Qh6eYn1GdzJFS4cDFfx0Q=="],
|
||||||
|
|
||||||
|
"json-schema-traverse": ["json-schema-traverse@1.0.0", "", {}, "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug=="],
|
||||||
|
|
||||||
"json5": ["json5@2.2.3", "", { "bin": { "json5": "lib/cli.js" } }, "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg=="],
|
"json5": ["json5@2.2.3", "", { "bin": { "json5": "lib/cli.js" } }, "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg=="],
|
||||||
|
|
||||||
"jsonfile": ["jsonfile@6.1.0", "", { "dependencies": { "universalify": "^2.0.0" }, "optionalDependencies": { "graceful-fs": "^4.1.6" } }, "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ=="],
|
"jsonfile": ["jsonfile@6.1.0", "", { "dependencies": { "universalify": "^2.0.0" }, "optionalDependencies": { "graceful-fs": "^4.1.6" } }, "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ=="],
|
||||||
|
|
||||||
|
"light-my-request": ["light-my-request@6.6.0", "", { "dependencies": { "cookie": "^1.0.1", "process-warning": "^4.0.0", "set-cookie-parser": "^2.6.0" } }, "sha512-CHYbu8RtboSIoVsHZ6Ye4cj4Aw/yg2oAFimlF7mNvfDV192LR7nDiKtSIfCuLT7KokPSTn/9kfVLm5OGN0A28A=="],
|
||||||
|
|
||||||
"lodash": ["lodash@4.17.21", "", {}, "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="],
|
"lodash": ["lodash@4.17.21", "", {}, "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="],
|
||||||
|
|
||||||
"loose-envify": ["loose-envify@1.4.0", "", { "dependencies": { "js-tokens": "^3.0.0 || ^4.0.0" }, "bin": { "loose-envify": "cli.js" } }, "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q=="],
|
"loose-envify": ["loose-envify@1.4.0", "", { "dependencies": { "js-tokens": "^3.0.0 || ^4.0.0" }, "bin": { "loose-envify": "cli.js" } }, "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q=="],
|
||||||
@@ -323,6 +373,8 @@
|
|||||||
|
|
||||||
"npm-run-path": ["npm-run-path@5.2.0", "", { "dependencies": { "path-key": "^4.0.0" } }, "sha512-W4/tgAXFqFA0iL7fk0+uQ3g7wkL8xJmx3XdK0VGb4cHW//eZTtKGvFBBoRKVTpY7n6ze4NL9ly7rgXcHufqXKg=="],
|
"npm-run-path": ["npm-run-path@5.2.0", "", { "dependencies": { "path-key": "^4.0.0" } }, "sha512-W4/tgAXFqFA0iL7fk0+uQ3g7wkL8xJmx3XdK0VGb4cHW//eZTtKGvFBBoRKVTpY7n6ze4NL9ly7rgXcHufqXKg=="],
|
||||||
|
|
||||||
|
"on-exit-leak-free": ["on-exit-leak-free@2.1.2", "", {}, "sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA=="],
|
||||||
|
|
||||||
"onetime": ["onetime@6.0.0", "", { "dependencies": { "mimic-fn": "^4.0.0" } }, "sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ=="],
|
"onetime": ["onetime@6.0.0", "", { "dependencies": { "mimic-fn": "^4.0.0" } }, "sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ=="],
|
||||||
|
|
||||||
"path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="],
|
"path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="],
|
||||||
@@ -335,24 +387,50 @@
|
|||||||
|
|
||||||
"picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="],
|
"picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="],
|
||||||
|
|
||||||
|
"pino": ["pino@9.9.0", "", { "dependencies": { "atomic-sleep": "^1.0.0", "fast-redact": "^3.1.1", "on-exit-leak-free": "^2.1.0", "pino-abstract-transport": "^2.0.0", "pino-std-serializers": "^7.0.0", "process-warning": "^5.0.0", "quick-format-unescaped": "^4.0.3", "real-require": "^0.2.0", "safe-stable-stringify": "^2.3.1", "sonic-boom": "^4.0.1", "thread-stream": "^3.0.0" }, "bin": { "pino": "bin.js" } }, "sha512-zxsRIQG9HzG+jEljmvmZupOMDUQ0Jpj0yAgE28jQvvrdYTlEaiGwelJpdndMl/MBuRr70heIj83QyqJUWaU8mQ=="],
|
||||||
|
|
||||||
|
"pino-abstract-transport": ["pino-abstract-transport@2.0.0", "", { "dependencies": { "split2": "^4.0.0" } }, "sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw=="],
|
||||||
|
|
||||||
|
"pino-std-serializers": ["pino-std-serializers@7.0.0", "", {}, "sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA=="],
|
||||||
|
|
||||||
"platform": ["platform@1.3.6", "", {}, "sha512-fnWVljUchTro6RiCFvCXBbNhJc2NijN7oIQxbwsyL0buWJPG85v81ehlHI9fXrJsMNgTofEoWIQeClKpgxFLrg=="],
|
"platform": ["platform@1.3.6", "", {}, "sha512-fnWVljUchTro6RiCFvCXBbNhJc2NijN7oIQxbwsyL0buWJPG85v81ehlHI9fXrJsMNgTofEoWIQeClKpgxFLrg=="],
|
||||||
|
|
||||||
|
"process-warning": ["process-warning@5.0.0", "", {}, "sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA=="],
|
||||||
|
|
||||||
"ps-tree": ["ps-tree@1.2.0", "", { "dependencies": { "event-stream": "=3.3.4" }, "bin": { "ps-tree": "./bin/ps-tree.js" } }, "sha512-0VnamPPYHl4uaU/nSFeZZpR21QAWRz+sRv4iW9+v/GS/J5U5iZB5BNN6J0RMoOvdx2gWM2+ZFMIm58q24e4UYA=="],
|
"ps-tree": ["ps-tree@1.2.0", "", { "dependencies": { "event-stream": "=3.3.4" }, "bin": { "ps-tree": "./bin/ps-tree.js" } }, "sha512-0VnamPPYHl4uaU/nSFeZZpR21QAWRz+sRv4iW9+v/GS/J5U5iZB5BNN6J0RMoOvdx2gWM2+ZFMIm58q24e4UYA=="],
|
||||||
|
|
||||||
"queue-microtask": ["queue-microtask@1.2.3", "", {}, "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A=="],
|
"queue-microtask": ["queue-microtask@1.2.3", "", {}, "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A=="],
|
||||||
|
|
||||||
|
"quick-format-unescaped": ["quick-format-unescaped@4.0.4", "", {}, "sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg=="],
|
||||||
|
|
||||||
"react": ["react@18.3.1", "", { "dependencies": { "loose-envify": "^1.1.0" } }, "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ=="],
|
"react": ["react@18.3.1", "", { "dependencies": { "loose-envify": "^1.1.0" } }, "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ=="],
|
||||||
|
|
||||||
"react-dom": ["react-dom@18.3.1", "", { "dependencies": { "loose-envify": "^1.1.0", "scheduler": "^0.23.2" }, "peerDependencies": { "react": "^18.3.1" } }, "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw=="],
|
"react-dom": ["react-dom@18.3.1", "", { "dependencies": { "loose-envify": "^1.1.0", "scheduler": "^0.23.2" }, "peerDependencies": { "react": "^18.3.1" } }, "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw=="],
|
||||||
|
|
||||||
|
"real-require": ["real-require@0.2.0", "", {}, "sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg=="],
|
||||||
|
|
||||||
|
"require-from-string": ["require-from-string@2.0.2", "", {}, "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw=="],
|
||||||
|
|
||||||
|
"ret": ["ret@0.5.0", "", {}, "sha512-I1XxrZSQ+oErkRR4jYbAyEEu2I0avBvvMM5JN+6EBprOGRCs63ENqZ3vjavq8fBw2+62G5LF5XelKwuJpcvcxw=="],
|
||||||
|
|
||||||
"reusify": ["reusify@1.0.4", "", {}, "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw=="],
|
"reusify": ["reusify@1.0.4", "", {}, "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw=="],
|
||||||
|
|
||||||
|
"rfdc": ["rfdc@1.4.1", "", {}, "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA=="],
|
||||||
|
|
||||||
"run-parallel": ["run-parallel@1.2.0", "", { "dependencies": { "queue-microtask": "^1.2.2" } }, "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA=="],
|
"run-parallel": ["run-parallel@1.2.0", "", { "dependencies": { "queue-microtask": "^1.2.2" } }, "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA=="],
|
||||||
|
|
||||||
|
"safe-regex2": ["safe-regex2@5.0.0", "", { "dependencies": { "ret": "~0.5.0" } }, "sha512-YwJwe5a51WlK7KbOJREPdjNrpViQBI3p4T50lfwPuDhZnE3XGVTlGvi+aolc5+RvxDD6bnUmjVsU9n1eboLUYw=="],
|
||||||
|
|
||||||
|
"safe-stable-stringify": ["safe-stable-stringify@2.5.0", "", {}, "sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA=="],
|
||||||
|
|
||||||
"scheduler": ["scheduler@0.23.2", "", { "dependencies": { "loose-envify": "^1.1.0" } }, "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ=="],
|
"scheduler": ["scheduler@0.23.2", "", { "dependencies": { "loose-envify": "^1.1.0" } }, "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ=="],
|
||||||
|
|
||||||
|
"secure-json-parse": ["secure-json-parse@4.0.0", "", {}, "sha512-dxtLJO6sc35jWidmLxo7ij+Eg48PM/kleBsxpC8QJE0qJICe+KawkDQmvCMZUr9u7WKVHgMW6vy3fQ7zMiFZMA=="],
|
||||||
|
|
||||||
"semver": ["semver@6.3.0", "", { "bin": { "semver": "./bin/semver.js" } }, "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw=="],
|
"semver": ["semver@6.3.0", "", { "bin": { "semver": "./bin/semver.js" } }, "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw=="],
|
||||||
|
|
||||||
|
"set-cookie-parser": ["set-cookie-parser@2.7.1", "", {}, "sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ=="],
|
||||||
|
|
||||||
"shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="],
|
"shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="],
|
||||||
|
|
||||||
"shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="],
|
"shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="],
|
||||||
@@ -363,8 +441,12 @@
|
|||||||
|
|
||||||
"slash": ["slash@4.0.0", "", {}, "sha512-3dOsAHXXUkQTpOYcoAxLIorMTp4gIQr5IW3iVb7A7lFIp0VHhnynm9izx6TssdrIcVIESAlVjtnO2K8bg+Coew=="],
|
"slash": ["slash@4.0.0", "", {}, "sha512-3dOsAHXXUkQTpOYcoAxLIorMTp4gIQr5IW3iVb7A7lFIp0VHhnynm9izx6TssdrIcVIESAlVjtnO2K8bg+Coew=="],
|
||||||
|
|
||||||
|
"sonic-boom": ["sonic-boom@4.2.0", "", { "dependencies": { "atomic-sleep": "^1.0.0" } }, "sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww=="],
|
||||||
|
|
||||||
"split": ["split@0.3.3", "", { "dependencies": { "through": "2" } }, "sha512-wD2AeVmxXRBoX44wAycgjVpMhvbwdI2aZjCkvfNcH1YqHQvJVa1duWc73OyVGJUc05fhFaTZeQ/PYsrmyH0JVA=="],
|
"split": ["split@0.3.3", "", { "dependencies": { "through": "2" } }, "sha512-wD2AeVmxXRBoX44wAycgjVpMhvbwdI2aZjCkvfNcH1YqHQvJVa1duWc73OyVGJUc05fhFaTZeQ/PYsrmyH0JVA=="],
|
||||||
|
|
||||||
|
"split2": ["split2@4.2.0", "", {}, "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg=="],
|
||||||
|
|
||||||
"stream-combiner": ["stream-combiner@0.0.4", "", { "dependencies": { "duplexer": "~0.1.1" } }, "sha512-rT00SPnTVyRsaSz5zgSPma/aHSOic5U1prhYdRy5HS2kTZviFpmDgzilbtsJsxiroqACmayynDN/9VzIbX5DOw=="],
|
"stream-combiner": ["stream-combiner@0.0.4", "", { "dependencies": { "duplexer": "~0.1.1" } }, "sha512-rT00SPnTVyRsaSz5zgSPma/aHSOic5U1prhYdRy5HS2kTZviFpmDgzilbtsJsxiroqACmayynDN/9VzIbX5DOw=="],
|
||||||
|
|
||||||
"string-width": ["string-width@7.1.0", "", { "dependencies": { "emoji-regex": "^10.3.0", "get-east-asian-width": "^1.0.0", "strip-ansi": "^7.1.0" } }, "sha512-SEIJCWiX7Kg4c129n48aDRwLbFb2LJmXXFrWBG4NGaRtMQ3myKPKbwrD1BKqQn74oCoNMBVrfDEr5M9YxCsrkw=="],
|
"string-width": ["string-width@7.1.0", "", { "dependencies": { "emoji-regex": "^10.3.0", "get-east-asian-width": "^1.0.0", "strip-ansi": "^7.1.0" } }, "sha512-SEIJCWiX7Kg4c129n48aDRwLbFb2LJmXXFrWBG4NGaRtMQ3myKPKbwrD1BKqQn74oCoNMBVrfDEr5M9YxCsrkw=="],
|
||||||
@@ -375,6 +457,8 @@
|
|||||||
|
|
||||||
"supports-color": ["supports-color@5.5.0", "", { "dependencies": { "has-flag": "^3.0.0" } }, "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow=="],
|
"supports-color": ["supports-color@5.5.0", "", { "dependencies": { "has-flag": "^3.0.0" } }, "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow=="],
|
||||||
|
|
||||||
|
"thread-stream": ["thread-stream@3.1.0", "", { "dependencies": { "real-require": "^0.2.0" } }, "sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A=="],
|
||||||
|
|
||||||
"through": ["through@2.3.8", "", {}, "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg=="],
|
"through": ["through@2.3.8", "", {}, "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg=="],
|
||||||
|
|
||||||
"tinycolor2": ["tinycolor2@1.6.0", "", {}, "sha512-XPaBkWQJdsf3pLKJV9p4qN/S+fm2Oj8AIPo1BTUhg5oxkvm9+SVEGFdhyOz7tTdUTfvxMiAs4sp6/eZO2Ew+pw=="],
|
"tinycolor2": ["tinycolor2@1.6.0", "", {}, "sha512-XPaBkWQJdsf3pLKJV9p4qN/S+fm2Oj8AIPo1BTUhg5oxkvm9+SVEGFdhyOz7tTdUTfvxMiAs4sp6/eZO2Ew+pw=="],
|
||||||
@@ -383,6 +467,8 @@
|
|||||||
|
|
||||||
"to-regex-range": ["to-regex-range@5.0.1", "", { "dependencies": { "is-number": "^7.0.0" } }, "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ=="],
|
"to-regex-range": ["to-regex-range@5.0.1", "", { "dependencies": { "is-number": "^7.0.0" } }, "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ=="],
|
||||||
|
|
||||||
|
"toad-cache": ["toad-cache@3.7.0", "", {}, "sha512-/m8M+2BJUpoJdgAHoG+baCwBT+tf2VraSfkBgl0Y00qIWt41DJ8R5B8nsEw0I58YwF5IZH6z24/2TobDKnqSWw=="],
|
||||||
|
|
||||||
"undici-types": ["undici-types@5.26.5", "", {}, "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA=="],
|
"undici-types": ["undici-types@5.26.5", "", {}, "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA=="],
|
||||||
|
|
||||||
"universalify": ["universalify@2.0.1", "", {}, "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw=="],
|
"universalify": ["universalify@2.0.1", "", {}, "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw=="],
|
||||||
@@ -407,8 +493,14 @@
|
|||||||
|
|
||||||
"ansi-styles/color-convert": ["color-convert@1.9.3", "", { "dependencies": { "color-name": "1.1.3" } }, "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg=="],
|
"ansi-styles/color-convert": ["color-convert@1.9.3", "", { "dependencies": { "color-name": "1.1.3" } }, "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg=="],
|
||||||
|
|
||||||
|
"avvio/fastq": ["fastq@1.19.1", "", { "dependencies": { "reusify": "^1.0.4" } }, "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ=="],
|
||||||
|
|
||||||
"cross-spawn/which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="],
|
"cross-spawn/which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="],
|
||||||
|
|
||||||
|
"fastify/semver": ["semver@7.7.2", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA=="],
|
||||||
|
|
||||||
|
"light-my-request/process-warning": ["process-warning@4.0.1", "", {}, "sha512-3c2LzQ3rY9d0hc1emcsHhfT9Jwz0cChib/QN89oME2R451w5fy3f0afAhERFZAwrbDU43wk12d0ORBpDVME50Q=="],
|
||||||
|
|
||||||
"npm-run-path/path-key": ["path-key@4.0.0", "", {}, "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ=="],
|
"npm-run-path/path-key": ["path-key@4.0.0", "", {}, "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ=="],
|
||||||
|
|
||||||
"ansi-styles/color-convert/color-name": ["color-name@1.1.3", "", {}, "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw=="],
|
"ansi-styles/color-convert/color-name": ["color-name@1.1.3", "", {}, "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw=="],
|
||||||
|
|||||||
@@ -18,6 +18,7 @@
|
|||||||
"react": "^18.3.1",
|
"react": "^18.3.1",
|
||||||
"react-dom": "^18.3.1",
|
"react-dom": "^18.3.1",
|
||||||
"string-width": "7.1.0",
|
"string-width": "7.1.0",
|
||||||
|
"strip-ansi": "^7.1.0",
|
||||||
"tinycolor2": "^1.6.0",
|
"tinycolor2": "^1.6.0",
|
||||||
"zx": "^7.2.3"
|
"zx": "^7.2.3"
|
||||||
},
|
},
|
||||||
|
|||||||
37
bench/snippets/strip-ansi.mjs
Normal file
37
bench/snippets/strip-ansi.mjs
Normal file
@@ -0,0 +1,37 @@
|
|||||||
|
import npmStripAnsi from "strip-ansi";
|
||||||
|
import { bench, run } from "../runner.mjs";
|
||||||
|
|
||||||
|
let bunStripANSI = null;
|
||||||
|
if (!process.env.FORCE_NPM) {
|
||||||
|
bunStripANSI = globalThis?.Bun?.stripANSI;
|
||||||
|
}
|
||||||
|
|
||||||
|
const stripANSI = bunStripANSI || npmStripAnsi;
|
||||||
|
const formatter = new Intl.NumberFormat();
|
||||||
|
const format = n => {
|
||||||
|
return formatter.format(n);
|
||||||
|
};
|
||||||
|
|
||||||
|
const inputs = [
|
||||||
|
["hello world", "no-ansi"],
|
||||||
|
["\x1b[31mred\x1b[39m", "ansi"],
|
||||||
|
["a".repeat(1024 * 16), "long-no-ansi"],
|
||||||
|
["\x1b[31mred\x1b[39m".repeat(1024 * 16), "long-ansi"],
|
||||||
|
];
|
||||||
|
|
||||||
|
const maxInputLength = Math.max(...inputs.map(([input]) => input.length));
|
||||||
|
|
||||||
|
for (const [input, textLabel] of inputs) {
|
||||||
|
const label = bunStripANSI ? "Bun.stripANSI" : "npm/strip-ansi";
|
||||||
|
const name = `${label} ${format(input.length).padStart(format(maxInputLength).length, " ")} chars ${textLabel}`;
|
||||||
|
|
||||||
|
bench(name, () => {
|
||||||
|
stripANSI(input);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (bunStripANSI && bunStripANSI(input) !== npmStripAnsi(input)) {
|
||||||
|
throw new Error("strip-ansi mismatch");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
await run();
|
||||||
12
bun.lock
12
bun.lock
@@ -39,8 +39,8 @@
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
"overrides": {
|
"overrides": {
|
||||||
"@types/bun": "workspace:packages/@types/bun",
|
|
||||||
"bun-types": "workspace:packages/bun-types",
|
"bun-types": "workspace:packages/bun-types",
|
||||||
|
"@types/bun": "workspace:packages/@types/bun",
|
||||||
},
|
},
|
||||||
"packages": {
|
"packages": {
|
||||||
"@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.21.5", "", { "os": "aix", "cpu": "ppc64" }, "sha512-1SDgH6ZSPTlggy1yI6+Dbkiz8xzpHJEVAlF/AM1tHPLsf5STom9rwtjE4hKAF20FfXXNTFqEYXyJNWh1GiZedQ=="],
|
"@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.21.5", "", { "os": "aix", "cpu": "ppc64" }, "sha512-1SDgH6ZSPTlggy1yI6+Dbkiz8xzpHJEVAlF/AM1tHPLsf5STom9rwtjE4hKAF20FfXXNTFqEYXyJNWh1GiZedQ=="],
|
||||||
@@ -147,7 +147,7 @@
|
|||||||
|
|
||||||
"@octokit/webhooks-types": ["@octokit/webhooks-types@7.6.1", "", {}, "sha512-S8u2cJzklBC0FgTwWVLaM8tMrDuDMVE4xiTK4EYXM9GntyvrdbSoxqDQa+Fh57CCNApyIpyeqPhhFEmHPfrXgw=="],
|
"@octokit/webhooks-types": ["@octokit/webhooks-types@7.6.1", "", {}, "sha512-S8u2cJzklBC0FgTwWVLaM8tMrDuDMVE4xiTK4EYXM9GntyvrdbSoxqDQa+Fh57CCNApyIpyeqPhhFEmHPfrXgw=="],
|
||||||
|
|
||||||
"@sentry/types": ["@sentry/types@7.120.3", "", {}, "sha512-C4z+3kGWNFJ303FC+FxAd4KkHvxpNFYAFN8iMIgBwJdpIl25KZ8Q/VdGn0MLLUEHNLvjob0+wvwlcRBBNLXOow=="],
|
"@sentry/types": ["@sentry/types@7.120.4", "", {}, "sha512-cUq2hSSe6/qrU6oZsEP4InMI5VVdD86aypE+ENrQ6eZEVLTCYm1w6XhW1NvIu3UuWh7gZec4a9J7AFpYxki88Q=="],
|
||||||
|
|
||||||
"@types/aws-lambda": ["@types/aws-lambda@8.10.152", "", {}, "sha512-soT/c2gYBnT5ygwiHPmd9a1bftj462NWVk2tKCc1PYHSIacB2UwbTS2zYG4jzag1mRDuzg/OjtxQjQ2NKRB6Rw=="],
|
"@types/aws-lambda": ["@types/aws-lambda@8.10.152", "", {}, "sha512-soT/c2gYBnT5ygwiHPmd9a1bftj462NWVk2tKCc1PYHSIacB2UwbTS2zYG4jzag1mRDuzg/OjtxQjQ2NKRB6Rw=="],
|
||||||
|
|
||||||
@@ -159,9 +159,9 @@
|
|||||||
|
|
||||||
"@types/ms": ["@types/ms@2.1.0", "", {}, "sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA=="],
|
"@types/ms": ["@types/ms@2.1.0", "", {}, "sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA=="],
|
||||||
|
|
||||||
"@types/node": ["@types/node@24.1.0", "", { "dependencies": { "undici-types": "~7.8.0" } }, "sha512-ut5FthK5moxFKH2T1CUOC6ctR67rQRvvHdFLCD2Ql6KXmMuCrjsSsRI9UsLCm9M18BMwClv4pn327UvB7eeO1w=="],
|
"@types/node": ["@types/node@24.2.1", "", { "dependencies": { "undici-types": "~7.10.0" } }, "sha512-DRh5K+ka5eJic8CjH7td8QpYEV6Zo10gfRkjHCO3weqZHWDtAaSTFtl4+VMqOJ4N5jcuhZ9/l+yy8rVgw7BQeQ=="],
|
||||||
|
|
||||||
"@types/react": ["@types/react@19.1.8", "", { "dependencies": { "csstype": "^3.0.2" } }, "sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g=="],
|
"@types/react": ["@types/react@19.1.10", "", { "dependencies": { "csstype": "^3.0.2" } }, "sha512-EhBeSYX0Y6ye8pNebpKrwFJq7BoQ8J5SO6NlvNwwHjSj6adXJViPQrKlsyPw7hLBLvckEMO1yxeGdR82YBBlDg=="],
|
||||||
|
|
||||||
"aggregate-error": ["aggregate-error@3.1.0", "", { "dependencies": { "clean-stack": "^2.0.0", "indent-string": "^4.0.0" } }, "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA=="],
|
"aggregate-error": ["aggregate-error@3.1.0", "", { "dependencies": { "clean-stack": "^2.0.0", "indent-string": "^4.0.0" } }, "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA=="],
|
||||||
|
|
||||||
@@ -311,7 +311,7 @@
|
|||||||
|
|
||||||
"uglify-js": ["uglify-js@3.19.3", "", { "bin": { "uglifyjs": "bin/uglifyjs" } }, "sha512-v3Xu+yuwBXisp6QYTcH4UbH+xYJXqnq2m/LtQVWKWzYc1iehYnLixoQDN9FH6/j9/oybfd6W9Ghwkl8+UMKTKQ=="],
|
"uglify-js": ["uglify-js@3.19.3", "", { "bin": { "uglifyjs": "bin/uglifyjs" } }, "sha512-v3Xu+yuwBXisp6QYTcH4UbH+xYJXqnq2m/LtQVWKWzYc1iehYnLixoQDN9FH6/j9/oybfd6W9Ghwkl8+UMKTKQ=="],
|
||||||
|
|
||||||
"undici-types": ["undici-types@7.8.0", "", {}, "sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw=="],
|
"undici-types": ["undici-types@7.10.0", "", {}, "sha512-t5Fy/nfn+14LuOc2KNYg75vZqClpAiqscVvMygNnlsHBFpSXdJaYtXMcdNLpl/Qvc3P2cB3s6lOV51nqsFq4ag=="],
|
||||||
|
|
||||||
"universal-github-app-jwt": ["universal-github-app-jwt@1.2.0", "", { "dependencies": { "@types/jsonwebtoken": "^9.0.0", "jsonwebtoken": "^9.0.2" } }, "sha512-dncpMpnsKBk0eetwfN8D8OUHGfiDhhJ+mtsbMl+7PfW7mYjiH8LIcqRmYMtzYLgSh47HjfdBtrBwIQ/gizKR3g=="],
|
"universal-github-app-jwt": ["universal-github-app-jwt@1.2.0", "", { "dependencies": { "@types/jsonwebtoken": "^9.0.0", "jsonwebtoken": "^9.0.2" } }, "sha512-dncpMpnsKBk0eetwfN8D8OUHGfiDhhJ+mtsbMl+7PfW7mYjiH8LIcqRmYMtzYLgSh47HjfdBtrBwIQ/gizKR3g=="],
|
||||||
|
|
||||||
@@ -333,8 +333,6 @@
|
|||||||
|
|
||||||
"@octokit/webhooks/@octokit/webhooks-methods": ["@octokit/webhooks-methods@4.1.0", "", {}, "sha512-zoQyKw8h9STNPqtm28UGOYFE7O6D4Il8VJwhAtMHFt2C4L0VQT1qGKLeefUOqHNs1mNRYSadVv7x0z8U2yyeWQ=="],
|
"@octokit/webhooks/@octokit/webhooks-methods": ["@octokit/webhooks-methods@4.1.0", "", {}, "sha512-zoQyKw8h9STNPqtm28UGOYFE7O6D4Il8VJwhAtMHFt2C4L0VQT1qGKLeefUOqHNs1mNRYSadVv7x0z8U2yyeWQ=="],
|
||||||
|
|
||||||
"bun-tracestrings/typescript": ["typescript@5.8.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ=="],
|
|
||||||
|
|
||||||
"camel-case/no-case": ["no-case@2.3.2", "", { "dependencies": { "lower-case": "^1.1.1" } }, "sha512-rmTZ9kz+f3rCvK2TD1Ue/oZlns7OGoIWP4fc3llxxRXlOkHKoWPPWJOfFYpITabSow43QJbRIoHQXtt10VldyQ=="],
|
"camel-case/no-case": ["no-case@2.3.2", "", { "dependencies": { "lower-case": "^1.1.1" } }, "sha512-rmTZ9kz+f3rCvK2TD1Ue/oZlns7OGoIWP4fc3llxxRXlOkHKoWPPWJOfFYpITabSow43QJbRIoHQXtt10VldyQ=="],
|
||||||
|
|
||||||
"change-case/camel-case": ["camel-case@4.1.2", "", { "dependencies": { "pascal-case": "^3.1.2", "tslib": "^2.0.3" } }, "sha512-gxGWBrTT1JuMx6R+o5PTXMmUnhnVzLQ9SNutD4YqKtI6ap897t3tKECYla6gCWEkplXnlNybEkZg9GEGxKFCgw=="],
|
"change-case/camel-case": ["camel-case@4.1.2", "", { "dependencies": { "pascal-case": "^3.1.2", "tslib": "^2.0.3" } }, "sha512-gxGWBrTT1JuMx6R+o5PTXMmUnhnVzLQ9SNutD4YqKtI6ap897t3tKECYla6gCWEkplXnlNybEkZg9GEGxKFCgw=="],
|
||||||
|
|||||||
@@ -192,6 +192,7 @@ src/bun.js/bindings/ServerRouteList.cpp
|
|||||||
src/bun.js/bindings/spawn.cpp
|
src/bun.js/bindings/spawn.cpp
|
||||||
src/bun.js/bindings/SQLClient.cpp
|
src/bun.js/bindings/SQLClient.cpp
|
||||||
src/bun.js/bindings/sqlite/JSSQLStatement.cpp
|
src/bun.js/bindings/sqlite/JSSQLStatement.cpp
|
||||||
|
src/bun.js/bindings/stripANSI.cpp
|
||||||
src/bun.js/bindings/Strong.cpp
|
src/bun.js/bindings/Strong.cpp
|
||||||
src/bun.js/bindings/Uint8Array.cpp
|
src/bun.js/bindings/Uint8Array.cpp
|
||||||
src/bun.js/bindings/Undici.cpp
|
src/bun.js/bindings/Undici.cpp
|
||||||
|
|||||||
17
packages/bun-types/bun.d.ts
vendored
17
packages/bun-types/bun.d.ts
vendored
@@ -596,6 +596,23 @@ declare module "bun" {
|
|||||||
options?: StringWidthOptions,
|
options?: StringWidthOptions,
|
||||||
): number;
|
): number;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove ANSI escape codes from a string.
|
||||||
|
*
|
||||||
|
* @category Utilities
|
||||||
|
*
|
||||||
|
* @param input The string to remove ANSI escape codes from.
|
||||||
|
* @returns The string with ANSI escape codes removed.
|
||||||
|
*
|
||||||
|
* @example
|
||||||
|
* ```ts
|
||||||
|
* import { stripANSI } from "bun";
|
||||||
|
*
|
||||||
|
* console.log(stripANSI("\u001b[31mhello\u001b[39m")); // "hello"
|
||||||
|
* ```
|
||||||
|
*/
|
||||||
|
function stripANSI(input: string): string;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TOML related APIs
|
* TOML related APIs
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -72,6 +72,10 @@ BUN_DECLARE_HOST_FUNCTION(Bun__fetchPreconnect);
|
|||||||
BUN_DECLARE_HOST_FUNCTION(Bun__randomUUIDv7);
|
BUN_DECLARE_HOST_FUNCTION(Bun__randomUUIDv7);
|
||||||
BUN_DECLARE_HOST_FUNCTION(Bun__randomUUIDv5);
|
BUN_DECLARE_HOST_FUNCTION(Bun__randomUUIDv5);
|
||||||
|
|
||||||
|
namespace Bun {
|
||||||
|
JSC_DECLARE_HOST_FUNCTION(jsFunctionBunStripANSI);
|
||||||
|
}
|
||||||
|
|
||||||
using namespace JSC;
|
using namespace JSC;
|
||||||
using namespace WebCore;
|
using namespace WebCore;
|
||||||
|
|
||||||
@@ -782,6 +786,7 @@ JSC_DEFINE_HOST_FUNCTION(functionFileURLToPath, (JSC::JSGlobalObject * globalObj
|
|||||||
stdin BunObject_lazyPropCb_wrap_stdin DontDelete|PropertyCallback
|
stdin BunObject_lazyPropCb_wrap_stdin DontDelete|PropertyCallback
|
||||||
stdout BunObject_lazyPropCb_wrap_stdout DontDelete|PropertyCallback
|
stdout BunObject_lazyPropCb_wrap_stdout DontDelete|PropertyCallback
|
||||||
stringWidth Generated::BunObject::jsStringWidth DontDelete|Function 2
|
stringWidth Generated::BunObject::jsStringWidth DontDelete|Function 2
|
||||||
|
stripANSI jsFunctionBunStripANSI DontDelete|Function 1
|
||||||
unsafe BunObject_lazyPropCb_wrap_unsafe DontDelete|PropertyCallback
|
unsafe BunObject_lazyPropCb_wrap_unsafe DontDelete|PropertyCallback
|
||||||
version constructBunVersion ReadOnly|DontDelete|PropertyCallback
|
version constructBunVersion ReadOnly|DontDelete|PropertyCallback
|
||||||
which BunObject_callback_which DontDelete|Function 1
|
which BunObject_callback_which DontDelete|Function 1
|
||||||
|
|||||||
265
src/bun.js/bindings/stripANSI.cpp
Normal file
265
src/bun.js/bindings/stripANSI.cpp
Normal file
@@ -0,0 +1,265 @@
|
|||||||
|
#include "root.h"
|
||||||
|
#include "stripANSI.h"
|
||||||
|
|
||||||
|
#include <wtf/text/WTFString.h>
|
||||||
|
#include <wtf/text/StringBuilder.h>
|
||||||
|
#include <wtf/SIMDHelpers.h>
|
||||||
|
|
||||||
|
namespace Bun {
|
||||||
|
using namespace WTF;
|
||||||
|
|
||||||
|
template<typename Char>
|
||||||
|
static inline bool isEscapeCharacter(const Char c)
|
||||||
|
{
|
||||||
|
switch (c) {
|
||||||
|
case 0x1b: // escape
|
||||||
|
case 0x9b: // control sequence introducer
|
||||||
|
case 0x9d: // operating system command
|
||||||
|
case 0x90: // device control string
|
||||||
|
case 0x98: // start of string
|
||||||
|
case 0x9e: // privacy message
|
||||||
|
case 0x9f: // application program command
|
||||||
|
return true;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template<typename Char>
|
||||||
|
static const Char* findEscapeCharacter(const Char* const start, const Char* const end)
|
||||||
|
{
|
||||||
|
static_assert(sizeof(Char) == 1 || sizeof(Char) == 2);
|
||||||
|
using SIMDType = std::conditional_t<sizeof(Char) == 1, uint8_t, uint16_t>;
|
||||||
|
|
||||||
|
constexpr size_t stride = SIMD::stride<SIMDType>;
|
||||||
|
// Matches 0x10-0x1f and 0x90-0x9f. These characters have a high
|
||||||
|
// probability of being escape characters.
|
||||||
|
constexpr auto escMask = SIMD::splat<SIMDType>(static_cast<SIMDType>(~0b10001111U));
|
||||||
|
constexpr auto escVector = SIMD::splat<SIMDType>(0b00010000);
|
||||||
|
|
||||||
|
auto it = start;
|
||||||
|
// Search for escape sequences using SIMD
|
||||||
|
// [Implementation note: aligning `it` did not improve performance]
|
||||||
|
for (; end - it >= stride; it += stride) {
|
||||||
|
const auto chunk = SIMD::load(reinterpret_cast<const SIMDType*>(it));
|
||||||
|
const auto chunkMasked = SIMD::bitAnd(chunk, escMask);
|
||||||
|
const auto chunkIsEsc = SIMD::equal(chunkMasked, escVector);
|
||||||
|
if (const auto index = SIMD::findFirstNonZeroIndex(chunkIsEsc)) {
|
||||||
|
return it + *index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check remaining characters
|
||||||
|
for (; it != end; ++it) {
|
||||||
|
if (isEscapeCharacter(*it)) return it;
|
||||||
|
}
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Consume an ANSI escape sequence that starts at `start`. Returns a pointer to
|
||||||
|
// the first byte immediately following the escape sequence.
|
||||||
|
//
|
||||||
|
// If the ANSI escape sequence is immediately followed by another escape
|
||||||
|
// sequence, this function will consume that one as well, and so on.
|
||||||
|
template<typename Char>
|
||||||
|
static const Char* consumeANSI(const Char* const start, const Char* const end)
|
||||||
|
{
|
||||||
|
enum class State {
|
||||||
|
start,
|
||||||
|
gotEsc,
|
||||||
|
ignoreNextChar,
|
||||||
|
inCsi,
|
||||||
|
inOsc,
|
||||||
|
inOscGotEsc,
|
||||||
|
needSt,
|
||||||
|
needStGotEsc,
|
||||||
|
};
|
||||||
|
|
||||||
|
auto state = State::start;
|
||||||
|
for (auto it = start; it != end; ++it) {
|
||||||
|
const auto c = *it;
|
||||||
|
switch (state) {
|
||||||
|
case State::start:
|
||||||
|
switch (c) {
|
||||||
|
case 0x1b:
|
||||||
|
state = State::gotEsc;
|
||||||
|
break;
|
||||||
|
case 0x9b:
|
||||||
|
state = State::inCsi;
|
||||||
|
break;
|
||||||
|
case 0x9d:
|
||||||
|
state = State::inOsc;
|
||||||
|
break;
|
||||||
|
// Other sequences terminated by ST, from ECMA-48, 5th ed.
|
||||||
|
case 0x90: // device control string
|
||||||
|
case 0x98: // start of string
|
||||||
|
case 0x9e: // privacy message
|
||||||
|
case 0x9f: // application program command
|
||||||
|
state = State::needSt;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return it;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::gotEsc:
|
||||||
|
switch (c) {
|
||||||
|
case '[':
|
||||||
|
state = State::inCsi;
|
||||||
|
break;
|
||||||
|
// Two-byte XTerm sequences
|
||||||
|
// https://invisible-island.net/xterm/ctlseqs/ctlseqs.html
|
||||||
|
case ' ':
|
||||||
|
case '#':
|
||||||
|
case '%':
|
||||||
|
case '(':
|
||||||
|
case ')':
|
||||||
|
case '*':
|
||||||
|
case '+':
|
||||||
|
case '.':
|
||||||
|
case '/':
|
||||||
|
state = State::ignoreNextChar;
|
||||||
|
break;
|
||||||
|
case ']':
|
||||||
|
state = State::inOsc;
|
||||||
|
break;
|
||||||
|
// Other sequences terminated by ST, from ECMA-48, 5th ed.
|
||||||
|
case 'P': // device control string
|
||||||
|
case 'X': // start of string
|
||||||
|
case '^': // privacy message
|
||||||
|
case '_': // application program command
|
||||||
|
state = State::needSt;
|
||||||
|
default:
|
||||||
|
// Otherwise, assume this is a one-byte sequence
|
||||||
|
state = State::start;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::ignoreNextChar:
|
||||||
|
state = State::start;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::inCsi:
|
||||||
|
// ECMA-48, 5th ed. §5.4 d)
|
||||||
|
if (c >= 0x40 && c <= 0x7e) {
|
||||||
|
state = State::start;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::inOsc:
|
||||||
|
switch (c) {
|
||||||
|
case 0x1b:
|
||||||
|
state = State::inOscGotEsc;
|
||||||
|
break;
|
||||||
|
case 0x9c: // ST
|
||||||
|
case 0x07: // XTerm can also end OSC with 0x07
|
||||||
|
state = State::start;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::inOscGotEsc:
|
||||||
|
if (c == '\\') {
|
||||||
|
state = State::start;
|
||||||
|
} else {
|
||||||
|
state = State::inOsc;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::needSt:
|
||||||
|
switch (c) {
|
||||||
|
case 0x1b:
|
||||||
|
state = State::needStGotEsc;
|
||||||
|
break;
|
||||||
|
case 0x9c:
|
||||||
|
state = State::start;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case State::needStGotEsc:
|
||||||
|
if (c == '\\') {
|
||||||
|
state = State::start;
|
||||||
|
} else {
|
||||||
|
state = State::needSt;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return end;
|
||||||
|
}
|
||||||
|
|
||||||
|
template<typename Char>
|
||||||
|
static std::optional<WTF::String> stripANSI(const std::span<const Char> input)
|
||||||
|
{
|
||||||
|
if (input.empty()) {
|
||||||
|
// Signal that the original string should be used
|
||||||
|
return std::nullopt;
|
||||||
|
}
|
||||||
|
|
||||||
|
StringBuilder result;
|
||||||
|
bool foundANSI = false;
|
||||||
|
|
||||||
|
auto start = input.data();
|
||||||
|
const auto end = start + input.size();
|
||||||
|
|
||||||
|
while (start != end) {
|
||||||
|
const auto escPos = findEscapeCharacter(start, end);
|
||||||
|
if (!escPos) {
|
||||||
|
// If no escape sequences found, return null to signal that the
|
||||||
|
// original string should be used.
|
||||||
|
if (!foundANSI) return std::nullopt;
|
||||||
|
// Append the rest of the string
|
||||||
|
result.append(std::span { start, end });
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Lazily reserve capacity on first ESC found
|
||||||
|
if (!foundANSI) {
|
||||||
|
result.reserveCapacity(input.size());
|
||||||
|
}
|
||||||
|
|
||||||
|
// Append everything before the escape sequence
|
||||||
|
result.append(std::span { start, escPos });
|
||||||
|
const auto newPos = consumeANSI(escPos, end);
|
||||||
|
ASSERT(newPos > start);
|
||||||
|
ASSERT(newPos <= end);
|
||||||
|
foundANSI = true;
|
||||||
|
start = newPos;
|
||||||
|
}
|
||||||
|
return result.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
JSC_DEFINE_HOST_FUNCTION(jsFunctionBunStripANSI, (JSC::JSGlobalObject * globalObject, JSC::CallFrame* callFrame))
|
||||||
|
{
|
||||||
|
auto& vm = globalObject->vm();
|
||||||
|
auto scope = DECLARE_THROW_SCOPE(vm);
|
||||||
|
|
||||||
|
const JSC::JSValue input = callFrame->argument(0);
|
||||||
|
|
||||||
|
// Convert to JSString to get the view
|
||||||
|
JSC::JSString* const jsString = input.toString(globalObject);
|
||||||
|
RETURN_IF_EXCEPTION(scope, {});
|
||||||
|
|
||||||
|
// Get StringView to avoid joining sliced strings
|
||||||
|
const auto view = jsString->view(globalObject);
|
||||||
|
RETURN_IF_EXCEPTION(scope, {});
|
||||||
|
|
||||||
|
if (view->isEmpty()) {
|
||||||
|
return JSC::JSValue::encode(JSC::jsEmptyString(vm));
|
||||||
|
}
|
||||||
|
|
||||||
|
std::optional<WTF::String> result;
|
||||||
|
if (view->is8Bit()) {
|
||||||
|
result = stripANSI<LChar>(view->span8());
|
||||||
|
} else {
|
||||||
|
result = stripANSI<UChar>(view->span16());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!result) {
|
||||||
|
// If no ANSI sequences were found, return the original string
|
||||||
|
return JSC::JSValue::encode(jsString);
|
||||||
|
}
|
||||||
|
return JSC::JSValue::encode(JSC::jsString(vm, *result));
|
||||||
|
}
|
||||||
|
}
|
||||||
9
src/bun.js/bindings/stripANSI.h
Normal file
9
src/bun.js/bindings/stripANSI.h
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "root.h"
|
||||||
|
|
||||||
|
namespace Bun {
|
||||||
|
|
||||||
|
JSC_DECLARE_HOST_FUNCTION(jsFunctionBunStripANSI);
|
||||||
|
|
||||||
|
}
|
||||||
@@ -2643,7 +2643,7 @@ function formatWithOptionsInternal(inspectOptions, args) {
|
|||||||
}
|
}
|
||||||
return str;
|
return str;
|
||||||
}
|
}
|
||||||
|
const stripANSI = Bun.stripANSI;
|
||||||
const internalGetStringWidth = $newZigFunction("string.zig", "String.jsGetStringWidth", 1);
|
const internalGetStringWidth = $newZigFunction("string.zig", "String.jsGetStringWidth", 1);
|
||||||
/**
|
/**
|
||||||
* Returns the number of columns required to display the given string.
|
* Returns the number of columns required to display the given string.
|
||||||
@@ -2654,24 +2654,9 @@ function getStringWidth(str, removeControlChars = true) {
|
|||||||
return internalGetStringWidth(str);
|
return internalGetStringWidth(str);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Regex used for ansi escape code splitting
|
|
||||||
// Ref: https://github.com/chalk/ansi-regex/blob/f338e1814144efb950276aac84135ff86b72dc8e/index.js
|
|
||||||
// License: MIT by Sindre Sorhus <sindresorhus@gmail.com>
|
|
||||||
// Matches all ansi escape code sequences in a string
|
|
||||||
const ansiPattern = new RegExp(
|
|
||||||
"[\\u001B\\u009B][[\\]()#;?]*" +
|
|
||||||
"(?:(?:(?:(?:;[-a-zA-Z\\d\\/\\#&.:=?%@~_]+)*" +
|
|
||||||
"|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/\\#&.:=?%@~_]*)*)?" +
|
|
||||||
"(?:\\u0007|\\u001B\\u005C|\\u009C))" +
|
|
||||||
"|(?:(?:\\d{1,4}(?:;\\d{0,4})*)?" +
|
|
||||||
"[\\dA-PR-TZcf-nq-uy=><~]))",
|
|
||||||
"g",
|
|
||||||
);
|
|
||||||
const ansi = new RegExp(ansiPattern, "g");
|
|
||||||
/** Remove all VT control characters. Use to estimate displayed string width. */
|
|
||||||
function stripVTControlCharacters(str) {
|
function stripVTControlCharacters(str) {
|
||||||
if (typeof str !== "string") throw new codes.ERR_INVALID_ARG_TYPE("str", "string", str);
|
if (typeof str !== "string") throw new codes.ERR_INVALID_ARG_TYPE("str", "string", str);
|
||||||
return RegExpPrototypeSymbolReplace(ansi, str, "");
|
return stripANSI(str);
|
||||||
}
|
}
|
||||||
|
|
||||||
// utils
|
// utils
|
||||||
|
|||||||
@@ -130,23 +130,14 @@ var getStringWidth = function getStringWidth(str, removeControlChars = true) {
|
|||||||
return internalGetStringWidth(str);
|
return internalGetStringWidth(str);
|
||||||
};
|
};
|
||||||
|
|
||||||
// Regex used for ansi escape code splitting
|
const stripANSI = Bun.stripANSI;
|
||||||
// Adopted from https://github.com/chalk/ansi-regex/blob/HEAD/index.js
|
|
||||||
// License: MIT, authors: @sindresorhus, Qix-, arjunmehta and LitoMore
|
|
||||||
// Matches all ansi escape code sequences in a string
|
|
||||||
var ansiPattern =
|
|
||||||
"[\\u001B\\u009B][[\\]()#;?]*" +
|
|
||||||
"(?:(?:(?:(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]+)*" +
|
|
||||||
"|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]*)*)?\\u0007)" +
|
|
||||||
"|(?:(?:\\d{1,4}(?:;\\d{0,4})*)?[\\dA-PR-TZcf-ntqry=><~]))";
|
|
||||||
var ansi = new RegExp(ansiPattern, "g");
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove all VT control characters. Use to estimate displayed string width.
|
* Remove all VT control characters. Use to estimate displayed string width.
|
||||||
*/
|
*/
|
||||||
function stripVTControlCharacters(str) {
|
function stripVTControlCharacters(str) {
|
||||||
validateString(str, "str");
|
validateString(str, "str");
|
||||||
return RegExpPrototypeSymbolReplace.$call(ansi, str, "");
|
return stripANSI(str);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Constants
|
// Constants
|
||||||
|
|||||||
@@ -25,6 +25,7 @@
|
|||||||
"@testing-library/react": "16.1.0",
|
"@testing-library/react": "16.1.0",
|
||||||
"@verdaccio/config": "6.0.0-6-next.76",
|
"@verdaccio/config": "6.0.0-6-next.76",
|
||||||
"acorn": "8.15.0",
|
"acorn": "8.15.0",
|
||||||
|
"ansi-regex": "6.1.0",
|
||||||
"astro": "5.5.5",
|
"astro": "5.5.5",
|
||||||
"aws-cdk-lib": "2.148.0",
|
"aws-cdk-lib": "2.148.0",
|
||||||
"axios": "1.6.8",
|
"axios": "1.6.8",
|
||||||
@@ -871,7 +872,7 @@
|
|||||||
|
|
||||||
"ansi-escapes": ["ansi-escapes@4.3.2", "", { "dependencies": { "type-fest": "^0.21.3" } }, "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ=="],
|
"ansi-escapes": ["ansi-escapes@4.3.2", "", { "dependencies": { "type-fest": "^0.21.3" } }, "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ=="],
|
||||||
|
|
||||||
"ansi-regex": ["ansi-regex@6.0.1", "", {}, "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA=="],
|
"ansi-regex": ["ansi-regex@6.1.0", "", {}, "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA=="],
|
||||||
|
|
||||||
"ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
|
"ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
|
||||||
|
|
||||||
@@ -3237,6 +3238,8 @@
|
|||||||
|
|
||||||
"string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
|
"string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
|
||||||
|
|
||||||
|
"strip-ansi/ansi-regex": ["ansi-regex@6.0.1", "", {}, "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA=="],
|
||||||
|
|
||||||
"strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
|
"strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
|
||||||
|
|
||||||
"strip-literal/acorn": ["acorn@8.12.0", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-RTvkC4w+KNXrM39/lWCUaG0IbRkWdCv7W/IOW9oU6SawyxulvkQy5HQPVTKxEjczcUvapcrw3cFx/60VN/NRNw=="],
|
"strip-literal/acorn": ["acorn@8.12.0", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-RTvkC4w+KNXrM39/lWCUaG0IbRkWdCv7W/IOW9oU6SawyxulvkQy5HQPVTKxEjczcUvapcrw3cFx/60VN/NRNw=="],
|
||||||
|
|||||||
481
test/js/bun/util/stripANSI.test.ts
Normal file
481
test/js/bun/util/stripANSI.test.ts
Normal file
@@ -0,0 +1,481 @@
|
|||||||
|
import { heapStats } from "bun:jsc";
|
||||||
|
import { describe, expect, test } from "bun:test";
|
||||||
|
import stripAnsi from "strip-ansi";
|
||||||
|
|
||||||
|
describe("Bun.stripANSI", () => {
|
||||||
|
test("returns same string object when no ANSI sequences present", () => {
|
||||||
|
var input = "hello world";
|
||||||
|
const stripANSI = Bun.stripANSI;
|
||||||
|
const numStrings = heapStats().objectTypeCounts.string;
|
||||||
|
const result = stripANSI(input);
|
||||||
|
// Make sure the string wasn't modified
|
||||||
|
expect(result).toBe(input);
|
||||||
|
// Verify it's the same object, not a copy
|
||||||
|
expect(heapStats().objectTypeCounts.string).toBe(numStrings);
|
||||||
|
});
|
||||||
|
|
||||||
|
test("returns new string when ANSI sequences are removed", () => {
|
||||||
|
const input = "\x1b[31mhello\x1b[0m world";
|
||||||
|
const result = Bun.stripANSI(input);
|
||||||
|
expect(result).toBe("hello world");
|
||||||
|
// Verify it's a different object
|
||||||
|
expect(result === input).toBe(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
// Tests of the form [input, expected] are used when strip-ansi's behavior
|
||||||
|
// is incorrect or undesirable.
|
||||||
|
const testCases: (string | [string, string])[] = [
|
||||||
|
// Basic colors
|
||||||
|
"\x1b[31mred\x1b[39m",
|
||||||
|
"\x1b[32mgreen\x1b[39m",
|
||||||
|
"\x1b[33myellow\x1b[39m",
|
||||||
|
"\x1b[34mblue\x1b[39m",
|
||||||
|
"\x1b[35mmagenta\x1b[39m",
|
||||||
|
"\x1b[36mcyan\x1b[39m",
|
||||||
|
"\x1b[37mwhite\x1b[39m",
|
||||||
|
|
||||||
|
// Background colors
|
||||||
|
"\x1b[41mred background\x1b[49m",
|
||||||
|
"\x1b[42mgreen background\x1b[49m",
|
||||||
|
|
||||||
|
// Text styles
|
||||||
|
"\x1b[1mbold\x1b[22m",
|
||||||
|
"\x1b[2mdim\x1b[22m",
|
||||||
|
"\x1b[3mitalic\x1b[23m",
|
||||||
|
"\x1b[4munderline\x1b[24m",
|
||||||
|
"\x1b[5mblink\x1b[25m",
|
||||||
|
"\x1b[7mreverse\x1b[27m",
|
||||||
|
"\x1b[8mhidden\x1b[28m",
|
||||||
|
"\x1b[9mstrikethrough\x1b[29m",
|
||||||
|
|
||||||
|
// 256 colors
|
||||||
|
"\x1b[38;5;196mred\x1b[39m",
|
||||||
|
"\x1b[48;5;196mred background\x1b[49m",
|
||||||
|
|
||||||
|
// RGB colors
|
||||||
|
"\x1b[38;2;255;0;0mred\x1b[39m",
|
||||||
|
"\x1b[48;2;255;0;0mred background\x1b[49m",
|
||||||
|
|
||||||
|
// Cursor movement
|
||||||
|
"\x1b[2Aup",
|
||||||
|
"\x1b[2Bdown",
|
||||||
|
"\x1b[2Cforward",
|
||||||
|
"\x1b[2Dback",
|
||||||
|
"\x1b[Hhome",
|
||||||
|
"\x1b[2;3Hposition",
|
||||||
|
|
||||||
|
// Erase sequences
|
||||||
|
"\x1b[2Jclear",
|
||||||
|
"\x1b[Kclear line",
|
||||||
|
"\x1b[1Kclear line before",
|
||||||
|
"\x1b[2Kclear entire line",
|
||||||
|
|
||||||
|
// Combined sequences
|
||||||
|
"\x1b[1;31mbold red\x1b[0m",
|
||||||
|
"\x1b[1;4;31mbold underline red\x1b[0m",
|
||||||
|
"\x1b[31;42mred on green\x1b[0m",
|
||||||
|
|
||||||
|
// Nested sequences
|
||||||
|
"\x1b[31mred \x1b[1mbold\x1b[22m red\x1b[39m",
|
||||||
|
"\x1b[31m\x1b[32m\x1b[33myellow\x1b[39m",
|
||||||
|
|
||||||
|
// OSC sequences
|
||||||
|
["\x1b]0;window title\x07text", "text"],
|
||||||
|
["\x1b]0;window title\x1b\\text", "text"],
|
||||||
|
"\x1b]8;;https://example.com\x07link\x1b]8;;\x07",
|
||||||
|
|
||||||
|
// Other escape sequences
|
||||||
|
"\x1b(Btext",
|
||||||
|
"\x1b)Btext",
|
||||||
|
["\x1b*Btext", "text"],
|
||||||
|
["\x1b+Btext", "text"],
|
||||||
|
"\x1b=text",
|
||||||
|
"\x1b>text",
|
||||||
|
"\x1bDtext",
|
||||||
|
"\x1bEtext",
|
||||||
|
"\x1bHtext",
|
||||||
|
"\x1bMtext",
|
||||||
|
["\x1b7text", "text"],
|
||||||
|
["\x1b8text", "text"],
|
||||||
|
["\x1b#8text", "text"],
|
||||||
|
["\x1b%Gtext", "text"],
|
||||||
|
|
||||||
|
// No ANSI codes
|
||||||
|
"plain text",
|
||||||
|
"",
|
||||||
|
"hello world",
|
||||||
|
|
||||||
|
// Partial sequences
|
||||||
|
["text\x1b", "text"],
|
||||||
|
["text\x1b[", "text"],
|
||||||
|
"text\x1b[3",
|
||||||
|
|
||||||
|
// Real world examples
|
||||||
|
"\x1b[2K\x1b[1G\x1b[36m?\x1b[39m Installing...",
|
||||||
|
"\x1b[32m+ added\x1b[39m\n\x1b[31m- removed\x1b[39m",
|
||||||
|
"\x1b[1A\x1b[2K\x1b[32m████████\x1b[39m 100%",
|
||||||
|
|
||||||
|
// Unicode handling
|
||||||
|
"\x1b[31m你好\x1b[39m",
|
||||||
|
"\x1b[32m😀\x1b[39m",
|
||||||
|
"\x1b[33m🚀 rocket\x1b[39m",
|
||||||
|
|
||||||
|
// SGR parameters
|
||||||
|
"\x1b[0;1;31mtext\x1b[0m",
|
||||||
|
"\x1b[;;mtext",
|
||||||
|
"\x1b[1;;31mtext\x1b[m",
|
||||||
|
|
||||||
|
// Reset sequences
|
||||||
|
"\x1b[0mtext",
|
||||||
|
"\x1b[mtext",
|
||||||
|
"text\x1b[0m",
|
||||||
|
"text\x1b[m",
|
||||||
|
|
||||||
|
// Malformed sequences
|
||||||
|
"\x1b[31text",
|
||||||
|
"\x1b[moretext",
|
||||||
|
["\x1b]incomplete", ""],
|
||||||
|
["\x1b]", ""],
|
||||||
|
"\x1b]i",
|
||||||
|
["\x1b]in", ""],
|
||||||
|
["\x1b]inc", ""],
|
||||||
|
|
||||||
|
// Preserves whitespace
|
||||||
|
"\x1b[31m text \x1b[39m",
|
||||||
|
"\x1b[31m\ttext\t\x1b[39m",
|
||||||
|
"\x1b[31m\ntext\n\x1b[39m",
|
||||||
|
|
||||||
|
// Edge cases
|
||||||
|
"\x1b[mtext",
|
||||||
|
"\x1b[0m\x1b[0m\x1b[0mtext",
|
||||||
|
"text\x1b[31m",
|
||||||
|
"\x1b[31m\x1b[32m\x1b[33m",
|
||||||
|
|
||||||
|
// OSC sequences (Operating System Commands)
|
||||||
|
["\x1b]0;title\x07text", "text"],
|
||||||
|
["\x1b]0;window title\x1b\\text", "text"],
|
||||||
|
["\x1b]2;title\x07", ""],
|
||||||
|
["\x1b]8;;https://example.com\x07link text\x1b]8;;\x07", "link text"],
|
||||||
|
["\x1b]8;;file:///path/to/file\x1b\\clickable\x1b]8;;\x1b\\", "clickable"],
|
||||||
|
|
||||||
|
// C1 CSI sequences (using 0x9B instead of ESC[)
|
||||||
|
"\x9b31mtext\x9b39m",
|
||||||
|
"\x9b2Ktext",
|
||||||
|
"\x9b1Atext",
|
||||||
|
|
||||||
|
// Complex CSI parameters
|
||||||
|
"\x1b[38;5;196mred text\x1b[0m",
|
||||||
|
"\x1b[38;2;255;0;0mrgb red\x1b[0m",
|
||||||
|
"\x1b[48;5;21mblue bg\x1b[0m",
|
||||||
|
"\x1b[1;4;31mbold underline red\x1b[0m",
|
||||||
|
|
||||||
|
// Cursor movement
|
||||||
|
"\x1b[10Atext",
|
||||||
|
"\x1b[5Btext",
|
||||||
|
"\x1b[20Ctext",
|
||||||
|
"\x1b[15Dtext",
|
||||||
|
"\x1b[2;5Htext",
|
||||||
|
"\x1b[Ktext",
|
||||||
|
"\x1b[2Jtext",
|
||||||
|
|
||||||
|
// Save/restore cursor
|
||||||
|
["\x1b[stext\x1b[u", "text"],
|
||||||
|
["\x1b7text\x1b8", "text"],
|
||||||
|
|
||||||
|
// Scroll sequences
|
||||||
|
"\x1b[5Stext",
|
||||||
|
"\x1b[3Ttext",
|
||||||
|
|
||||||
|
// Alternative CSI final bytes
|
||||||
|
"\x1b[?25htext", // show cursor
|
||||||
|
"\x1b[?25ltext", // hide cursor
|
||||||
|
["\x1b[=3htext", "text"],
|
||||||
|
["\x1b[>5ctext", "text"],
|
||||||
|
["\x1b[<6~text", "text"],
|
||||||
|
|
||||||
|
// Prefix characters in sequences
|
||||||
|
"\x1b[?1049htext",
|
||||||
|
["\x1b]#text", ""], // missing ST
|
||||||
|
"\x1b[(text",
|
||||||
|
"\x1b[)text",
|
||||||
|
"\x1b[;text",
|
||||||
|
|
||||||
|
// Multiple parameters with empty values
|
||||||
|
"\x1b[;5;mtext",
|
||||||
|
"\x1b[31;;39mtext",
|
||||||
|
"\x1b[;;;mtext",
|
||||||
|
|
||||||
|
// Large parameter numbers
|
||||||
|
["\x1b[12345mtext", "text"],
|
||||||
|
"\x1b[1234mtext",
|
||||||
|
"\x1b[9999;1234mtext",
|
||||||
|
|
||||||
|
// String terminator variations
|
||||||
|
["\x1b]0;title\x9ctext", "text"], // 0x9C terminator
|
||||||
|
["\x1b]2;test\x07more", "more"],
|
||||||
|
|
||||||
|
// Mixed sequences
|
||||||
|
["\x1b[31m\x1b]0;title\x07\x1b[39mtext", "text"],
|
||||||
|
["\x1b]8;;\x07\x1b[4mlink\x1b[24m\x1b]8;;\x07", "link"],
|
||||||
|
|
||||||
|
// Sequences at boundaries
|
||||||
|
"\x1b[31m",
|
||||||
|
"\x1b[31mtext\x1b[39m\x1b[32m",
|
||||||
|
"start\x1b[31mtext\x1b[39mend",
|
||||||
|
|
||||||
|
// Invalid but should be partially consumed
|
||||||
|
"\x1b[31invalid", // 3 should be consumed as CSI final
|
||||||
|
"\x1b[9invalid", // 9 should be consumed as CSI final
|
||||||
|
"\x1b[Zinvalid", // Z should be consumed as CSI final
|
||||||
|
|
||||||
|
// Very long parameter sequences
|
||||||
|
"\x1b[1;2;3;4;5;6;7;8;9;10;11;12mtext\x1b[0m",
|
||||||
|
"\x1b[" + "1;".repeat(100) + "mtext",
|
||||||
|
|
||||||
|
// Nested-looking sequences (not actually nested)
|
||||||
|
["\x1b[31m\x1b in text\x1b[39m", "n text"], // ESC SP <x> is a two-byte sequence
|
||||||
|
["\x1b]0;\x1b[31mred\x1b[39m\x07text", "text"],
|
||||||
|
|
||||||
|
// Control characters mixed with ANSI
|
||||||
|
"\x1b[31m\x08\x09\x0a\x0d\x1b[39m",
|
||||||
|
|
||||||
|
// Real terminal sequences
|
||||||
|
"\x1b[?1049h\x1b[22;0;0t\x1b[1;1H\x1b[2Jtext",
|
||||||
|
"\x1b[H\x1b[2J\x1b[3J", // clear screen sequence
|
||||||
|
"\x1b[6n", // cursor position query
|
||||||
|
|
||||||
|
// Edge cases with C1 CSI (0x9B)
|
||||||
|
"\x9b31mtext\x9b39m",
|
||||||
|
["\x9b[31mtext", "31mtext"], // 0x9B followed by [ is invalid
|
||||||
|
"\x9bHtext", // Cursor Home
|
||||||
|
"\x9b2Jtext", // Clear Screen
|
||||||
|
|
||||||
|
// OSC sequences with various terminators
|
||||||
|
["\x1b]0;Window Title\x1b\\text", "text"], // ESC \ terminator
|
||||||
|
["\x1b]1;Icon Name\x07text", "text"], // BEL terminator
|
||||||
|
["\x1b]2;Both\x9ctext", "text"], // ST terminator
|
||||||
|
["\x1b]8;;http://example.com\x07", ""], // Hyperlink OSC
|
||||||
|
|
||||||
|
// Invalid OSC sequences (missing terminator)
|
||||||
|
["\x1b]0;title", ""], // No terminator, consumes rest
|
||||||
|
["\x1b]2;test\x1bother", ""], // Incomplete ESC terminator
|
||||||
|
|
||||||
|
// Complex prefix combinations
|
||||||
|
["\x1b[[[31mtext", "[31mtext"], // [ terminates CSI
|
||||||
|
["\x1b]]]]0;title\x07text", "text"],
|
||||||
|
["\x1b()()#;?31mtext", "()#;?31mtext"], // ESC ( <x> is a two-byte sequence
|
||||||
|
["\x1b#?#?[31mtext", "#?[31mtext"], // ESC # <x> is a two-byte sequence
|
||||||
|
|
||||||
|
// CSI sequences with intermediate bytes
|
||||||
|
["\x1b[!ptext", "text"], // DECSTR
|
||||||
|
['\x1b["qtext', "text"], // DECSCA
|
||||||
|
["\x1b[$ptext", "text"], // DECRQM
|
||||||
|
["\x1b[%@text", "text"], // Select UTF-8
|
||||||
|
|
||||||
|
// Private mode sequences
|
||||||
|
"\x1b[?25htext", // Show cursor
|
||||||
|
"\x1b[?25ltext", // Hide cursor
|
||||||
|
"\x1b[?1049htext", // Alternative screen buffer
|
||||||
|
"\x1b[?2004htext", // Bracketed paste mode
|
||||||
|
|
||||||
|
// SGR (Select Graphic Rendition) variations
|
||||||
|
"\x1b[38;5;196mtext", // 256-color foreground
|
||||||
|
"\x1b[48;2;255;0;0mtext", // RGB background
|
||||||
|
"\x1b[38;2;0;255;0;48;5;17mtext", // Mixed RGB and 256-color
|
||||||
|
|
||||||
|
// Function key sequences
|
||||||
|
"\x1b[11~text", // F1
|
||||||
|
"\x1b[24~text", // F12
|
||||||
|
"\x1b[1;5Ptext", // Ctrl+F1
|
||||||
|
|
||||||
|
// Cursor movement sequences
|
||||||
|
"\x1b[10;20Htext", // Cursor position
|
||||||
|
"\x1b[5Atext", // Cursor up
|
||||||
|
"\x1b[3Btext", // Cursor down
|
||||||
|
"\x1b[2Ctext", // Cursor right
|
||||||
|
"\x1b[4Dtext", // Cursor left
|
||||||
|
|
||||||
|
// Erase sequences
|
||||||
|
"\x1b[0Ktext", // Erase to end of line
|
||||||
|
"\x1b[1Ktext", // Erase to beginning of line
|
||||||
|
"\x1b[2Ktext", // Erase entire line
|
||||||
|
"\x1b[0Jtext", // Erase to end of screen
|
||||||
|
"\x1b[1Jtext", // Erase to beginning of screen
|
||||||
|
"\x1b[2Jtext", // Erase entire screen
|
||||||
|
"\x1b[3Jtext", // Erase scrollback buffer
|
||||||
|
|
||||||
|
// Save/restore cursor
|
||||||
|
["\x1b[stext\x1b[u", "text"], // Save and restore cursor
|
||||||
|
["\x1b7text\x1b8", "text"], // Save and restore cursor (alternate)
|
||||||
|
|
||||||
|
// Scroll sequences
|
||||||
|
"\x1b[5Stext", // Scroll up
|
||||||
|
"\x1b[3Ttext", // Scroll down
|
||||||
|
"\x1bMtext", // Reverse line feed
|
||||||
|
"\x1bDtext", // Line feed
|
||||||
|
|
||||||
|
// Tab sequences
|
||||||
|
"\x1b[3gtext", // Clear tab stop
|
||||||
|
"\x1b[0gtext", // Clear tab stop at cursor
|
||||||
|
"\x1bHtext", // Set tab stop
|
||||||
|
|
||||||
|
// Insert/delete sequences
|
||||||
|
["\x1b[5@text", "text"], // Insert characters
|
||||||
|
"\x1b[3Ptext", // Delete characters
|
||||||
|
"\x1b[2Ltext", // Insert lines
|
||||||
|
"\x1b[4Mtext", // Delete lines
|
||||||
|
|
||||||
|
// Mode setting sequences
|
||||||
|
"\x1b[4htext", // Insert mode
|
||||||
|
"\x1b[4ltext", // Replace mode
|
||||||
|
"\x1b[20htext", // Automatic newline
|
||||||
|
"\x1b[20ltext", // Normal linefeed
|
||||||
|
|
||||||
|
// Device status report
|
||||||
|
"\x1b[5ntext", // Device status report
|
||||||
|
"\x1b[6ntext", // Cursor position report
|
||||||
|
"\x1b[?15ntext", // Printer status report
|
||||||
|
|
||||||
|
// Character sets
|
||||||
|
"\x1b(Atext", // UK character set
|
||||||
|
"\x1b)Btext", // US character set
|
||||||
|
["\x1b*0text", "text"], // DEC special character set
|
||||||
|
["\x1b+Btext", "text"], // G3 character set
|
||||||
|
|
||||||
|
// Double-width/height sequences
|
||||||
|
["\x1b#3text", "text"], // Double-height line (top half)
|
||||||
|
["\x1b#4text", "text"], // Double-height line (bottom half)
|
||||||
|
["\x1b#5text", "text"], // Single-width line
|
||||||
|
["\x1b#6text", "text"], // Double-width line
|
||||||
|
|
||||||
|
// Malformed sequences that should partially match
|
||||||
|
"\x1b[31", // Incomplete CSI (no final byte)
|
||||||
|
["\x1b[31;", ""], // Incomplete parameters
|
||||||
|
"\x1b[31;4", // Incomplete parameters
|
||||||
|
["\x1b]0;title", ""], // Incomplete OSC
|
||||||
|
["\x1b]0;title\x1b", ""], // Incomplete OSC terminator
|
||||||
|
|
||||||
|
// Sequences with invalid parameters
|
||||||
|
["\x1b[99999mtext", "text"], // Parameter too long (>4 digits), but strip anyway
|
||||||
|
"\x1b[;;;;;mtext", // Multiple empty parameters
|
||||||
|
"\x1b[1;2;3;4;5;6;7;8;9;10;11;12;13;14;15;16;17;18;19;20mtext", // Many parameters
|
||||||
|
|
||||||
|
// Mixed valid and invalid sequences
|
||||||
|
"\x1b[31mred\x1binvalid\x1b[39mnormal",
|
||||||
|
"\x1b]0;title\x07\x1binvalid\x1b[32mgreen",
|
||||||
|
|
||||||
|
// Unicode content in sequences
|
||||||
|
["\x1b]0;タイトル\x07text", "text"], // Japanese in OSC
|
||||||
|
["\x1b]2;🚀 rocket\x07text", "text"], // Emoji in OSC
|
||||||
|
"\x1b[31m🌈 rainbow\x1b[39m after",
|
||||||
|
|
||||||
|
// Zero-width sequences
|
||||||
|
"\x1b[0mtext", // Reset all attributes
|
||||||
|
"\x1b[mtext", // Reset all attributes (no parameters)
|
||||||
|
"\x1b[;mtext", // Reset with empty parameter
|
||||||
|
|
||||||
|
// Application keypad sequences
|
||||||
|
"\x1b=text", // Application keypad mode
|
||||||
|
"\x1b>text", // Numeric keypad mode
|
||||||
|
|
||||||
|
// Bracketed paste sequences
|
||||||
|
"\x1b[200~pasted\x1b[201~text",
|
||||||
|
|
||||||
|
// Focus events
|
||||||
|
"\x1b[Itext", // Focus in
|
||||||
|
"\x1b[Otext", // Focus out
|
||||||
|
|
||||||
|
// Multiple sequences of varying lengths
|
||||||
|
"\x1b[31m\x1b[32m\x1b[33m\x1b[34m\x1b[35m\x1b[36m\x1b[37mtext", // 7 short sequences
|
||||||
|
"\x1b[38;5;196m\x1b[48;5;21m\x1b[1m\x1b[4mtext\x1b[0m", // Mixed length sequences
|
||||||
|
"\x1b[31mred\x1b[32mgreen\x1b[33myellow\x1b[34mblue\x1b[39mnormal",
|
||||||
|
|
||||||
|
// Long sequences (>16 characters)
|
||||||
|
"\x1b[38;2;255;128;64;48;5;196;1;4;9;7mtext", // Very long CSI with many parameters
|
||||||
|
["\x1b]0;This is a very long window title that exceeds 16 characters\x07text", "text"], // Long OSC
|
||||||
|
"\x1b]8;;https://very-long-domain-name.example.com/path/to/resource\x07link\x1b]8;;\x07", // Long URL in OSC
|
||||||
|
"\x1b[38;2;255;255;255;48;2;128;128;128;1;3;4;9mstyledtext\x1b[0m", // RGB colors with attributes
|
||||||
|
|
||||||
|
// Multiple long sequences
|
||||||
|
[
|
||||||
|
"\x1b]0;Window Title\x07\x1b[38;2;255;0;0;48;2;0;255;0mcolorful\x1b[0m\x1b]8;;https://example.com\x07link\x1b]8;;\x07",
|
||||||
|
"colorfullink",
|
||||||
|
],
|
||||||
|
"\x1b[38;5;196;48;5;21;1;4;9mstyle1\x1b[38;5;46;48;5;201;22;24;29mstyle2\x1b[0m",
|
||||||
|
|
||||||
|
// Sequences with maximum parameter counts
|
||||||
|
"\x1b[1;2;3;4;5;6;7;8;9;10;11;12;13;14;15;16;17;18;19;20;21;22;23;24;25;26;27;28;29;30mtext",
|
||||||
|
"\x1b[255;255;255;255;255;255;255;255;255;255;255;255;255;255;255;255;255;255;255;255mtext",
|
||||||
|
|
||||||
|
// Mixed short and long sequences in succession
|
||||||
|
"\x1b[31m\x1b[38;2;255;0;0;48;2;0;255;0;1;4;9m\x1b[32m\x1b[38;5;196;48;5;21;22;24mtext",
|
||||||
|
"\x1b[H\x1b[2J\x1b[38;2;255;255;255;48;2;0;0;0;1;3;4;7;9;53mstyledtext\x1b[0m\x1b[K",
|
||||||
|
|
||||||
|
// Long OSC sequences with various terminators
|
||||||
|
["\x1b]0;Title with special chars !@#$%^&*()_+-=[]{}|;:,.<>?\x07text", "text"],
|
||||||
|
"\x1b]8;;https://user:pass@subdomain.example.com:8080/path/to/resource?query=value#fragment\x07hyperlink\x1b]8;;\x07",
|
||||||
|
["\x1b]2;Icon name with unicode: 🚀🌈⭐💎🎯\x1b\\text", "text"],
|
||||||
|
|
||||||
|
// Sequences that span SIMD boundaries (assuming 16-byte chunks)
|
||||||
|
"\x1b[31m123456789012345\x1b[32mtext", // Crosses 16-byte boundary
|
||||||
|
"12345678901234567\x1b[31mtext", // ANSI starts after 16 bytes
|
||||||
|
"123456789012345\x1b[38;2;255;0;0mtext", // Long sequence after 15 chars
|
||||||
|
|
||||||
|
// Multiple sequences with content between that crosses SIMD boundaries
|
||||||
|
"\x1b[31m12345678901234567890\x1b[32m12345678901234567890\x1b[33mtext",
|
||||||
|
"prefix\x1b[31m12345678901234567890\x1b[32mmiddle\x1b[33m12345678901234567890suffix",
|
||||||
|
|
||||||
|
// Very long content with scattered sequences
|
||||||
|
"a".repeat(100) + "\x1b[31m" + "b".repeat(50) + "\x1b[32m" + "c".repeat(100),
|
||||||
|
"\x1b[31m" + "x".repeat(200) + "\x1b[32m" + "y".repeat(200) + "\x1b[0m",
|
||||||
|
|
||||||
|
// Complex mixed sequences with varying parameter lengths
|
||||||
|
"\x1b[1m\x1b[38;5;196m\x1b[48;2;255;255;255m\x1b[4;9;53mcomplex\x1b[22;24;29;49;39mtext",
|
||||||
|
"\x1b]0;\x07\x1b[31;32;33;34;35;36;37mcolors\x1b[0m\x1b]8;;\x07",
|
||||||
|
|
||||||
|
// Alternating short and long sequences
|
||||||
|
"\x1b[31m\x1b[38;2;255;0;0;48;2;0;255;0m\x1b[32m\x1b[38;5;196;48;5;21;1;4mtext",
|
||||||
|
"\x1b[H\x1b[38;2;255;255;255;48;2;0;0;0;1;3;4;7;9mstyle\x1b[K\x1b[38;5;46mmore\x1b[0m",
|
||||||
|
|
||||||
|
// Strip a single escape character
|
||||||
|
["\x1b", ""],
|
||||||
|
];
|
||||||
|
|
||||||
|
for (const testCase of testCases) {
|
||||||
|
let input;
|
||||||
|
let expected;
|
||||||
|
if (testCase instanceof Array) {
|
||||||
|
[input, expected] = testCase;
|
||||||
|
} else {
|
||||||
|
input = testCase;
|
||||||
|
expected = stripAnsi(input);
|
||||||
|
}
|
||||||
|
test(JSON.stringify(input), () => {
|
||||||
|
const received = Bun.stripANSI(input);
|
||||||
|
expect(Bun.stripANSI(input), `${JSON.stringify(expected)} != ${JSON.stringify(received)}`).toBe(expected);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
test("long strings", () => {
|
||||||
|
const longText = "a".repeat(10000);
|
||||||
|
const withAnsi = `\x1b[31m${longText}\x1b[39m`;
|
||||||
|
expect(Bun.stripANSI(withAnsi)).toBe(stripAnsi(withAnsi));
|
||||||
|
});
|
||||||
|
|
||||||
|
test("multiple sequences in long string", () => {
|
||||||
|
const parts = [];
|
||||||
|
for (let i = 0; i < 1000; i++) {
|
||||||
|
parts.push(`\x1b[${30 + (i % 8)}mword${i}\x1b[39m`);
|
||||||
|
}
|
||||||
|
const input = parts.join(" ");
|
||||||
|
expect(Bun.stripANSI(input)).toBe(stripAnsi(input));
|
||||||
|
});
|
||||||
|
|
||||||
|
test("non-string input", () => {
|
||||||
|
expect(Bun.stripANSI(123 as any)).toBe("123");
|
||||||
|
expect(Bun.stripANSI(true as any)).toBe("true");
|
||||||
|
expect(Bun.stripANSI(false as any)).toBe("false");
|
||||||
|
expect(Bun.stripANSI(null as any)).toBe("null");
|
||||||
|
expect(Bun.stripANSI(undefined as any)).toBe("undefined");
|
||||||
|
});
|
||||||
|
});
|
||||||
@@ -30,6 +30,7 @@
|
|||||||
"@testing-library/react": "16.1.0",
|
"@testing-library/react": "16.1.0",
|
||||||
"@verdaccio/config": "6.0.0-6-next.76",
|
"@verdaccio/config": "6.0.0-6-next.76",
|
||||||
"acorn": "8.15.0",
|
"acorn": "8.15.0",
|
||||||
|
"ansi-regex": "6.1.0",
|
||||||
"astro": "5.5.5",
|
"astro": "5.5.5",
|
||||||
"aws-cdk-lib": "2.148.0",
|
"aws-cdk-lib": "2.148.0",
|
||||||
"axios": "1.6.8",
|
"axios": "1.6.8",
|
||||||
@@ -66,6 +67,7 @@
|
|||||||
"mysql2": "3.7.0",
|
"mysql2": "3.7.0",
|
||||||
"node-gyp": "10.0.1",
|
"node-gyp": "10.0.1",
|
||||||
"nodemailer": "6.9.3",
|
"nodemailer": "6.9.3",
|
||||||
|
"p-queue": "8.1.0",
|
||||||
"pg": "8.11.1",
|
"pg": "8.11.1",
|
||||||
"pg-connection-string": "2.6.1",
|
"pg-connection-string": "2.6.1",
|
||||||
"pg-gateway": "0.3.0-beta.4",
|
"pg-gateway": "0.3.0-beta.4",
|
||||||
@@ -90,7 +92,6 @@
|
|||||||
"string-width": "7.0.0",
|
"string-width": "7.0.0",
|
||||||
"strip-ansi": "7.1.0",
|
"strip-ansi": "7.1.0",
|
||||||
"stripe": "15.4.0",
|
"stripe": "15.4.0",
|
||||||
"p-queue": "8.1.0",
|
|
||||||
"superagent": "10.2.2",
|
"superagent": "10.2.2",
|
||||||
"supertest": "6.3.3",
|
"supertest": "6.3.3",
|
||||||
"svelte": "5.20.4",
|
"svelte": "5.20.4",
|
||||||
|
|||||||
Reference in New Issue
Block a user