Skip to content

Commit f544617

Browse files
flowglad-sync[bot]subsetpark
authored andcommitted
merge(upstream): just-bash@2.14.5
2 parents 88edd83 + 2bbbfaf commit f544617

13 files changed

Lines changed: 596 additions & 60 deletions

File tree

examples/website/app/opengraph-image.tsx

Lines changed: 31 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -28,15 +28,21 @@ export default async function Image() {
2828
alignItems: "flex-start",
2929
justifyContent: "flex-start",
3030
fontFamily: "IBM Plex Mono",
31-
padding: "60px 80px",
31+
padding: "60px 200px",
3232
}}
3333
>
34-
<pre
34+
<div style={{ display: "flex", marginLeft: "-135px", marginTop: "10px" }}>
35+
<svg width="56" height="49" viewBox="0 0 112 98" fill="none" xmlns="http://www.w3.org/2000/svg">
36+
<path fill-rule="evenodd" clip-rule="evenodd" d="M56 0L112 98H0L56 0Z" fill="white" />
37+
</svg>
38+
</div>
39+
40+
<pre
3541
style={{
3642
color: "#fff",
37-
fontSize: "28px",
43+
fontSize: "32px",
3844
lineHeight: "1.2",
39-
margin: 0,
45+
margin: "-50px 0 0 0",
4046
whiteSpace: "pre",
4147
}}
4248
>
@@ -53,42 +59,45 @@ export default async function Image() {
5359
>
5460
<div
5561
style={{
56-
color: "#888",
57-
fontSize: "24px",
62+
color: "#7d7d7d",
63+
fontSize: "31px",
64+
lineHeight: "1.2",
65+
textAlign: "center",
66+
display: "flex",
67+
flexDirection: "column",
68+
alignItems: "center",
69+
justifyContent: "center",
5870
}}
5971
>
60-
A sandboxed bash interpreter for AI agents
72+
A sandboxed bash interpreter for AI agents.
73+
<br />
74+
Pure TypeScript with in-memory filesystem.
6175
</div>
6276
<div
6377
style={{
6478
display: "flex",
65-
alignItems: "center",
6679
gap: "12px",
67-
marginTop: "8px",
80+
marginTop: "20px",
81+
fontSize: "31px",
82+
lineHeight: "1.2",
83+
flexDirection: "row",
84+
alignItems: "center",
85+
justifyContent: "center",
86+
flexGrow: 1,
87+
width: "800px",
6888
}}
6989
>
70-
<span style={{ color: "#666" }}>$</span>
90+
<span style={{ color: "#FFF" }}>$</span>
7191
<span
7292
style={{
7393
color: "#0AC5B3",
74-
fontSize: "32px",
94+
fontSize: "31px",
7595
}}
7696
>
7797
npm install just-bash
7898
</span>
7999
</div>
80100
</div>
81-
<div
82-
style={{
83-
position: "absolute",
84-
bottom: "50px",
85-
left: "80px",
86-
color: "#555",
87-
fontSize: "18px",
88-
}}
89-
>
90-
Pure TypeScript | In-memory filesystem
91-
</div>
92101
</div>
93102
),
94103
{

package.json

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,5 +30,10 @@
3030
"@changesets/changelog-github": "^0.6.0",
3131
"@changesets/cli": "^2.31.0"
3232
},
33+
"pnpm": {
34+
"overrides": {
35+
"postcss@<8.5.10": "^8.5.10"
36+
}
37+
},
3338
"packageManager": "pnpm@10.33.2+sha512.a90faf6feeab71ad6c6e57f94e0fe1a12f5dcc22cd754db40ae9593eb6a3e0b6b12e3540218bb37ae083404b1f2ce6db2a4121e979829b4aff94b99f49da1cf8"
3439
}

packages/just-bash/CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,12 @@
99
payload forms such as `--data-urlencode @file` and `-d @file` remain
1010
intentionally unsupported and now fail clearly.
1111

12+
- [#214](https://github.com/vercel-labs/just-bash/pull/214) [`da58f4f`](https://github.com/vercel-labs/just-bash/commit/da58f4f523c5e9c1c444106a0f2a7777a59fb618) Thanks [@subsetpark](https://github.com/subsetpark)! - jq: accept control characters inside JSON strings
13+
14+
- [#221](https://github.com/vercel-labs/just-bash/pull/221) [`a835686`](https://github.com/vercel-labs/just-bash/commit/a835686c97f5cac2e5b94bd551d996079a33dfc2) Thanks [@cramforce](https://github.com/cramforce)! - upgrade deps
15+
16+
- [#218](https://github.com/vercel-labs/just-bash/pull/218) [`13d78b2`](https://github.com/vercel-labs/just-bash/commit/13d78b2876d7ac7b6bc3a6eacfa3937bbb79665f) Thanks [@Hazzng](https://github.com/Hazzng)! - grep: 5-123x faster pattern matching via RE2 matcher reuse and literal pre-filter
17+
1218
## 2.14.4
1319

1420
### Patch Changes

packages/just-bash/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@
126126
"dependencies": {
127127
"seek-bzip": "^2.0.0",
128128
"diff": "^8.0.2",
129-
"fast-xml-parser": "5.3.3",
129+
"fast-xml-parser": "^5.7.3",
130130
"file-type": "^21.2.0",
131131
"ini": "^6.0.0",
132132
"minimatch": "^10.1.1",

packages/just-bash/src/commands/grep/grep.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,7 @@ export const grepCommand: Command = {
206206

207207
let regex: UserRegex;
208208
let kResetGroup: number | undefined;
209+
let preFilter: import("../search-engine/regex.js").PreFilter | undefined;
209210
try {
210211
const regexResult = buildRegex(pattern, {
211212
mode: regexMode,
@@ -215,6 +216,7 @@ export const grepCommand: Command = {
215216
});
216217
regex = regexResult.regex;
217218
kResetGroup = regexResult.kResetGroup;
219+
preFilter = regexResult.preFilter;
218220
} catch {
219221
return {
220222
stdout: "",
@@ -235,6 +237,7 @@ export const grepCommand: Command = {
235237
afterContext,
236238
maxCount,
237239
kResetGroup,
240+
preFilter,
238241
});
239242
if (quietMode) {
240243
return { stdout: "", stderr: "", exitCode: result.matched ? 0 : 1 };
@@ -361,6 +364,7 @@ export const grepCommand: Command = {
361364
afterContext,
362365
maxCount,
363366
kResetGroup,
367+
preFilter,
364368
});
365369

366370
return { file, result };
Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
import { describe, expect, it } from "vitest";
2+
import { Bash } from "../../Bash.js";
3+
4+
// Real jq accepts JSON containing literal control characters inside strings,
5+
// even though RFC 8259 forbids them. Real-world inputs (webhooks, copy-paste
6+
// from terminals, log lines piped through `jq`) frequently contain unescaped
7+
// tabs and newlines, so matching jq's permissive behavior here avoids
8+
// surprising failures when our jq is dropped into existing pipelines.
9+
describe("jq permissive control chars in JSON strings", () => {
10+
it("accepts a literal newline inside a string value", async () => {
11+
const env = new Bash({
12+
files: { "/payload.json": '{"body":"first\nsecond"}\n' },
13+
});
14+
15+
const result = await env.exec("jq -r '.body' /payload.json");
16+
17+
expect(result.stderr).toBe("");
18+
expect(result.stdout).toBe("first\nsecond\n");
19+
expect(result.exitCode).toBe(0);
20+
});
21+
22+
it("accepts a literal tab inside a string value", async () => {
23+
const env = new Bash({
24+
files: { "/payload.json": '{"body":"col1\tcol2"}\n' },
25+
});
26+
27+
const result = await env.exec("jq -r '.body' /payload.json");
28+
29+
expect(result.stderr).toBe("");
30+
expect(result.stdout).toBe("col1\tcol2\n");
31+
expect(result.exitCode).toBe(0);
32+
});
33+
34+
it("accepts a literal carriage return inside a string value", async () => {
35+
const env = new Bash({
36+
files: { "/payload.json": '{"body":"a\rb"}\n' },
37+
});
38+
39+
const result = await env.exec("jq -r '.body' /payload.json");
40+
41+
expect(result.stderr).toBe("");
42+
expect(result.stdout).toBe("a\rb\n");
43+
expect(result.exitCode).toBe(0);
44+
});
45+
46+
it("preserves a real escape sequence next to a literal control char", async () => {
47+
const env = new Bash({
48+
files: { "/payload.json": '{"body":"line1\\nline2\nline3"}\n' },
49+
});
50+
51+
const result = await env.exec("jq -r '.body' /payload.json");
52+
53+
expect(result.stderr).toBe("");
54+
expect(result.stdout).toBe("line1\nline2\nline3\n");
55+
expect(result.exitCode).toBe(0);
56+
});
57+
58+
it("does not rewrite control characters that appear outside strings", async () => {
59+
const env = new Bash({
60+
files: { "/payload.json": '{\n "a": 1,\n "b": 2\n}\n' },
61+
});
62+
63+
const result = await env.exec("jq -c '.' /payload.json");
64+
65+
expect(result.stderr).toBe("");
66+
expect(result.stdout).toBe('{"a":1,"b":2}\n');
67+
expect(result.exitCode).toBe(0);
68+
});
69+
70+
it("handles concatenated JSON values where one contains a literal newline", async () => {
71+
const env = new Bash({
72+
files: {
73+
"/stream.json": '{"a":"x\ny"}{"a":"z"}\n',
74+
},
75+
});
76+
77+
const result = await env.exec("jq -r '.a' /stream.json");
78+
79+
expect(result.stderr).toBe("");
80+
expect(result.stdout).toBe("x\ny\nz\n");
81+
expect(result.exitCode).toBe(0);
82+
});
83+
});

packages/just-bash/src/commands/python3/worker.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ export interface WorkerOutput {
4242
defenseStats?: WorkerDefenseStats;
4343
}
4444

45+
// @banned-pattern-ignore: worker bootstrap only; Module._load is guarded below and CPython paths are allowlisted
4546
const require = createRequire(import.meta.url);
4647
const CPYTHON_ENTRY_BASENAME = "/vendor/cpython-emscripten/python.cjs";
4748
const CPYTHON_STDLIB_BASENAME = "/vendor/cpython-emscripten/python313.zip";

0 commit comments

Comments
 (0)