-
Notifications
You must be signed in to change notification settings - Fork 3.8k
feat(terminal): integrate ghostty-vt for terminal emulation #25539
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
Adds libghostty-vt integration to Bun.Terminal for full VT100/xterm terminal emulation with escape sequence parsing and screen state tracking. ## New API Methods - `terminal.feed(data)` - Feed string/buffer data to VT parser - `terminal.at(x, y)` - Get cell info at position (char, wide, styled) - `terminal.line(n)` - Get line text relative to bottom (0 = bottom) - `terminal.text` - Get full screen content (getter) - `terminal.cursor` - Get cursor position and style - `terminal.clear()` - Clear screen - `terminal.reset()` - Reset terminal state - `terminal.alternateScreen` - Check if in alternate screen mode - `terminal.scrollbackLines` - Get scrollback line count - `terminal.title` - Get terminal title from OSC sequences ## Implementation Details - Lazy VT initialization on first `feed()` call - Uses ghostty's Terminal/Screen/PageList for state management - Parses CSI, OSC, DCS escape sequences - Tracks cursor position, style, and visibility - Supports alternate screen buffer switching - Cell access with wide character and style detection ## Build Integration - CMake target for libghostty-vt static library - Zig build module integration with unicode/symbol tables - Pre-generated lookup tables for unicode properties ## Test Coverage 86 comprehensive tests covering: - Constructor options and validation - feed() with various input types and edge cases - at() bounds checking and cell retrieval - line() bottom-relative indexing - Escape sequence parsing (cursor movement, colors, etc.) - Error handling and invalid inputs - Resource management and cleanup 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
WalkthroughThis PR integrates the Ghostty Terminal VT emulator into Bun's Terminal API. Changes span build configuration (Zig/CMake), Terminal class JavaScript/Zig bindings, and supporting ghostty modules including symbol tables, build options, and comprehensive tests. Changes
Possibly related PRs
Suggested reviewers
Pre-merge checks✅ Passed checks (2 passed)
📜 Recent review detailsConfiguration used: Path: .coderabbit.yaml Review profile: ASSERTIVE Plan: Pro Disabled knowledge base sources:
📒 Files selected for processing (3)
🧰 Additional context used📓 Path-based instructions (3)src/**/*.{cpp,zig}📄 CodeRabbit inference engine (.cursor/rules/building-bun.mdc)
Files:
src/**/*.zig📄 CodeRabbit inference engine (.cursor/rules/building-bun.mdc)
Files:
**/*.zig📄 CodeRabbit inference engine (.cursor/rules/zig-javascriptcore-classes.mdc)
Files:
🧠 Learnings (4)📚 Learning: 2025-10-15T22:03:50.832ZApplied to files:
📚 Learning: 2025-11-24T18:34:55.173ZApplied to files:
📚 Learning: 2025-11-24T18:36:08.558ZApplied to files:
📚 Learning: 2025-10-08T13:56:00.875ZApplied to files:
🔇 Additional comments (1)
Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 4
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
src/bun.js/api/bun/Terminal.zig (1)
637-695: Resize the VT when dimensions change.The
resize()method updatesthis.colsandthis.rows, but doesn't resize theVirtualTerminalif it exists. This causes the VT to have stale dimensions, leading to incorrect rendering and potential out-of-bounds errors when accessing cells or lines.Apply this diff to resize the VT:
this.cols = new_cols; this.rows = new_rows; + // Resize virtual terminal if initialized + if (this.vt) |vt| { + vt.resize(new_cols, new_rows) catch { + return globalObject.throw("Failed to resize virtual terminal", .{}); + }; + } + return .js_undefined; }
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro
Disabled knowledge base sources:
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (8)
build.zig(2 hunks)cmake/targets/BuildBun.cmake(1 hunks)cmake/targets/BuildGhosttyVt.cmake(1 hunks)src/bun.js/api/Terminal.classes.ts(1 hunks)src/bun.js/api/bun/Terminal.zig(3 hunks)src/deps/ghostty/symbols_tables.zig(1 hunks)src/deps/ghostty/terminal_options.zig(1 hunks)test/js/bun/terminal/ghostty.test.ts(1 hunks)
🧰 Additional context used
📓 Path-based instructions (9)
src/**/*.{cpp,zig}
📄 CodeRabbit inference engine (.cursor/rules/building-bun.mdc)
src/**/*.{cpp,zig}: Usebun bdorbun run build:debugto build debug versions for C++ and Zig source files; creates debug build at./build/debug/bun-debug
Run tests usingbun bd test <test-file>with the debug build; never usebun testdirectly as it will not include your changes
Execute files usingbun bd <file> <...args>; never usebun <file>directly as it will not include your changes
Enable debug logs for specific scopes usingBUN_DEBUG_$(SCOPE)=1environment variable
Code generation happens automatically as part of the build process; no manual code generation commands are required
Files:
src/deps/ghostty/terminal_options.zigsrc/deps/ghostty/symbols_tables.zigsrc/bun.js/api/bun/Terminal.zig
src/**/*.zig
📄 CodeRabbit inference engine (.cursor/rules/building-bun.mdc)
Use
bun.Output.scoped(.${SCOPE}, .hidden)for creating debug logs in Zig codeImplement core functionality in Zig, typically in its own directory in
src/
src/**/*.zig: Private fields in Zig are fully supported using the#prefix:struct { #foo: u32 };
Use decl literals in Zig for declaration initialization:const decl: Decl = .{ .binding = 0, .value = 0 };
Prefer@importat the bottom of the file (auto formatter will move them automatically)
Files:
src/deps/ghostty/terminal_options.zigsrc/deps/ghostty/symbols_tables.zigsrc/bun.js/api/bun/Terminal.zig
**/*.zig
📄 CodeRabbit inference engine (.cursor/rules/zig-javascriptcore-classes.mdc)
**/*.zig: Expose generated bindings in Zig structs usingpub const js = JSC.Codegen.JS<ClassName>with trait conversion methods:toJS,fromJS, andfromJSDirect
Use consistent parameter nameglobalObjectinstead ofctxin Zig constructor and method implementations
Usebun.JSError!JSValuereturn type for Zig methods and constructors to enable proper error handling and exception propagation
Implement resource cleanup usingdeinit()method that releases resources, followed byfinalize()called by the GC that invokesdeinit()and frees the pointer
UseJSC.markBinding(@src())in finalize methods for debugging purposes before callingdeinit()
For methods returning cached properties in Zig, declare external C++ functions usingextern fnandcallconv(JSC.conv)calling convention
Implement getter functions with naming patternget<PropertyName>in Zig that acceptthisandglobalObjectparameters and returnJSC.JSValue
Access JavaScript CallFrame arguments usingcallFrame.argument(i), check argument count withcallFrame.argumentCount(), and getthiswithcallFrame.thisValue()
For reference-counted objects, use.deref()in finalize instead ofdestroy()to release references to other JS objectsIn Zig code, be careful with allocators and use defer for cleanup
Files:
src/deps/ghostty/terminal_options.zigsrc/deps/ghostty/symbols_tables.zigbuild.zigsrc/bun.js/api/bun/Terminal.zig
*.zig
📄 CodeRabbit inference engine (.cursor/rules/javascriptcore-class.mdc)
In Zig, declare external C++ functions and wrap them in public methods using the convention
extern fn Bun__ClassName__toJS(...)andpub fn toJS(...)
Files:
build.zig
test/**/*.{js,ts,jsx,tsx}
📄 CodeRabbit inference engine (.cursor/rules/writing-tests.mdc)
test/**/*.{js,ts,jsx,tsx}: Write tests as JavaScript and TypeScript files using Jest-style APIs (test,describe,expect) and import frombun:test
Usetest.eachand data-driven tests to reduce boilerplate when testing multiple similar cases
Files:
test/js/bun/terminal/ghostty.test.ts
test/**/*.test.{ts,js,jsx,tsx,mjs,cjs}
📄 CodeRabbit inference engine (test/CLAUDE.md)
test/**/*.test.{ts,js,jsx,tsx,mjs,cjs}: Usebun:testwith files that end in*.test.{ts,js,jsx,tsx,mjs,cjs}
Do not write flaky tests. Never wait for time to pass in tests; always wait for the condition to be met instead of using an arbitrary amount of time
Never use hardcoded port numbers in tests. Always useport: 0to get a random port
Prefer concurrent tests over sequential tests usingtest.concurrentordescribe.concurrentwhen multiple tests spawn processes or write files, unless it's very difficult to make them concurrent
When spawning Bun processes in tests, usebunExeandbunEnvfromharnessto ensure the same build of Bun is used and debug logging is silenced
Use-eflag for single-file tests when spawning Bun processes
UsetempDir()from harness to create temporary directories with files for multi-file tests instead of creating files manually
Prefer async/await over callbacks in tests
When callbacks must be used and it's just a single callback, usePromise.withResolversto create a promise that can be resolved or rejected from a callback
Do not set a timeout on tests. Bun already has timeouts
UseBuffer.alloc(count, fill).toString()instead of'A'.repeat(count)to create repetitive strings in tests, as ''.repeat is very slow in debug JavaScriptCore builds
Usedescribeblocks for grouping related tests
Always useawait usingorusingto ensure proper resource cleanup in tests for APIs like Bun.listen, Bun.connect, Bun.spawn, Bun.serve, etc
Always check exit codes and test error scenarios in error tests
Usedescribe.each()for parameterized tests
UsetoMatchSnapshot()for snapshot testing
UsebeforeAll(),afterEach(),beforeEach()for setup/teardown in tests
Track resources (servers, clients) in arrays for cleanup inafterEach()
Files:
test/js/bun/terminal/ghostty.test.ts
**/*.test.ts?(x)
📄 CodeRabbit inference engine (CLAUDE.md)
**/*.test.ts?(x): Never usebun testdirectly - always usebun bd testto run tests with debug build changes
For single-file tests, prefer-eflag overtempDir
For multi-file tests, prefertempDirandBun.spawnover single-file tests
UsenormalizeBunSnapshotto normalize snapshot output of tests
Never write tests that check for 'panic', 'uncaught exception', or similar strings in test output
UsetempDirfromharnessto create temporary directories - do not usetmpdirSyncorfs.mkdtempSync
When spawning processes in tests, expect stdout before expecting exit code for more useful error messages on test failure
Do not write flaky tests - do not usesetTimeoutin tests; instead await the condition to be met
Verify tests fail withUSE_SYSTEM_BUN=1 bun test <file>and pass withbun bd test <file>- tests are invalid if they pass with USE_SYSTEM_BUN=1
Test files must end with.test.tsor.test.tsx
Avoid shell commands likefindorgrepin tests - use Bun's Glob and built-in tools instead
Files:
test/js/bun/terminal/ghostty.test.ts
test/**/*.test.ts?(x)
📄 CodeRabbit inference engine (CLAUDE.md)
Always use
port: 0in tests - do not hardcode ports or use custom random port number functions
Files:
test/js/bun/terminal/ghostty.test.ts
**/*.classes.ts
📄 CodeRabbit inference engine (.cursor/rules/zig-javascriptcore-classes.mdc)
**/*.classes.ts: Define JavaScript API using declarative.classes.tsfiles with properties: name, constructor, JSType, finalize, and proto object containing method/property definitions
Use WriteBarrier caching (cache: true) in.classes.tsproperty definitions to enable JSC's garbage-collected value storage for computed or lazily-created properties
Files:
src/bun.js/api/Terminal.classes.ts
🧠 Learnings (26)
📚 Learning: 2025-11-20T19:51:32.288Z
Learnt from: markovejnovic
Repo: oven-sh/bun PR: 24880
File: packages/bun-vscode/package.json:382-385
Timestamp: 2025-11-20T19:51:32.288Z
Learning: In the Bun repository, dependencies may be explicitly added to package.json files (even when not directly imported in code) to force version upgrades on transitive dependencies, particularly as part of Aikido security scanner remediation to ensure vulnerable transitive dependencies resolve to patched versions.
Applied to files:
cmake/targets/BuildBun.cmake
📚 Learning: 2025-11-24T18:36:59.706Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/bun.js/bindings/v8/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:36:59.706Z
Learning: Applies to src/bun.js/bindings/v8/V8*.h : Add BUN_EXPORT visibility attribute to all public V8 API functions to ensure proper symbol export across platforms
Applied to files:
cmake/targets/BuildBun.cmake
📚 Learning: 2025-11-24T18:34:55.173Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/building-bun.mdc:0-0
Timestamp: 2025-11-24T18:34:55.173Z
Learning: Applies to src/**/*.{cpp,zig} : Use `bun bd` or `bun run build:debug` to build debug versions for C++ and Zig source files; creates debug build at `./build/debug/bun-debug`
Applied to files:
cmake/targets/BuildBun.cmakesrc/deps/ghostty/terminal_options.zigbuild.zig
📚 Learning: 2025-11-24T18:36:08.558Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/zig-javascriptcore-classes.mdc:0-0
Timestamp: 2025-11-24T18:36:08.558Z
Learning: Applies to src/bun.js/bindings/generated_classes_list.zig : Include new class bindings in `src/bun.js/bindings/generated_classes_list.zig` to register them with the code generator
Applied to files:
cmake/targets/BuildBun.cmakebuild.zig
📚 Learning: 2025-10-15T22:03:50.832Z
Learnt from: markovejnovic
Repo: oven-sh/bun PR: 23710
File: src/envvars.zig:135-144
Timestamp: 2025-10-15T22:03:50.832Z
Learning: In src/envvars.zig, the boolean feature flag cache uses a single atomic enum and should remain monotonic. Only the string cache (which uses two atomics: ptr and len) requires acquire/release ordering to prevent torn reads.
Applied to files:
src/deps/ghostty/terminal_options.zig
📚 Learning: 2025-10-16T02:17:35.237Z
Learnt from: markovejnovic
Repo: oven-sh/bun PR: 23710
File: src/analytics.zig:15-21
Timestamp: 2025-10-16T02:17:35.237Z
Learning: In src/analytics.zig and similar files using bun.EnvVar boolean environment variables: the new EnvVar API for boolean flags (e.g., bun.EnvVar.do_not_track.get(), bun.EnvVar.ci.get()) is designed to parse and return boolean values from environment variables, not just check for their presence. This is an intentional design change from the previous presence-based checks using bun.getenvZ().
Applied to files:
src/deps/ghostty/terminal_options.zig
📚 Learning: 2025-11-24T18:35:39.205Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/registering-bun-modules.mdc:0-0
Timestamp: 2025-11-24T18:35:39.205Z
Learning: Applies to src/**/index.zig : Create an `index.zig` entry point in your module directory that exports all module functionality
Applied to files:
src/deps/ghostty/terminal_options.zig
📚 Learning: 2025-12-16T00:21:32.163Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-16T00:21:32.163Z
Learning: Code generation happens automatically during the build process - bundled modules can be reloaded without rebuilding Zig by running `bun run build`
Applied to files:
src/deps/ghostty/terminal_options.zigbuild.zig
📚 Learning: 2025-11-24T18:36:08.558Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/zig-javascriptcore-classes.mdc:0-0
Timestamp: 2025-11-24T18:36:08.558Z
Learning: Applies to **/*.zig : Expose generated bindings in Zig structs using `pub const js = JSC.Codegen.JS<ClassName>` with trait conversion methods: `toJS`, `fromJS`, and `fromJSDirect`
Applied to files:
src/deps/ghostty/symbols_tables.zig
📚 Learning: 2025-08-30T09:09:18.384Z
Learnt from: Jarred-Sumner
Repo: oven-sh/bun PR: 22231
File: src/bundler/bundle_v2.zig:48-48
Timestamp: 2025-08-30T09:09:18.384Z
Learning: In Zig, when a module exports a top-level struct, import("./Module.zig") directly returns that struct type and can be used as a type alias without needing to access a field within the module. This is a common pattern in the Bun codebase.
Applied to files:
build.zig
📚 Learning: 2025-11-24T18:36:59.706Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/bun.js/bindings/v8/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:36:59.706Z
Learning: Applies to src/bun.js/bindings/v8/src/napi/napi.zig : For each new V8 C++ method, add both GCC/Clang and MSVC mangled symbol names to the V8API struct in src/napi/napi.zig using extern fn declarations
Applied to files:
build.zig
📚 Learning: 2025-11-24T18:36:59.706Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/bun.js/bindings/v8/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:36:59.706Z
Learning: Applies to src/bun.js/bindings/v8/test/v8/v8.test.ts : Add corresponding test cases to test/v8/v8.test.ts using checkSameOutput() function to compare Node.js and Bun output
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:35:50.422Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/writing-tests.mdc:0-0
Timestamp: 2025-11-24T18:35:50.422Z
Learning: Applies to test/**/*.{js,ts,jsx,tsx} : Write tests as JavaScript and TypeScript files using Jest-style APIs (`test`, `describe`, `expect`) and import from `bun:test`
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:35:50.422Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/writing-tests.mdc:0-0
Timestamp: 2025-11-24T18:35:50.422Z
Learning: See `test/harness.ts` for common test utilities and helpers
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:37:30.259Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: test/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:37:30.259Z
Learning: Applies to test/**/*.test.{ts,js,jsx,tsx,mjs,cjs} : When spawning Bun processes in tests, use `bunExe` and `bunEnv` from `harness` to ensure the same build of Bun is used and debug logging is silenced
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:35:08.612Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/dev-server-tests.mdc:0-0
Timestamp: 2025-11-24T18:35:08.612Z
Learning: Applies to test/bake/dev/css.test.ts : Organize CSS tests in css.test.ts for tests concerning bundling bugs with CSS files
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-10-26T01:32:04.844Z
Learnt from: Jarred-Sumner
Repo: oven-sh/bun PR: 24082
File: test/cli/test/coverage.test.ts:60-112
Timestamp: 2025-10-26T01:32:04.844Z
Learning: In the Bun repository test files (test/cli/test/*.test.ts), when spawning Bun CLI commands with Bun.spawnSync for testing, prefer using stdio: ["inherit", "inherit", "inherit"] to inherit stdio streams rather than piping them.
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:35:08.612Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/dev-server-tests.mdc:0-0
Timestamp: 2025-11-24T18:35:08.612Z
Learning: Applies to test/bake/dev/bundle.test.ts : Organize bundle tests in bundle.test.ts for tests concerning bundling bugs that only occur in DevServer
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-10-19T02:44:46.354Z
Learnt from: theshadow27
Repo: oven-sh/bun PR: 23798
File: packages/bun-otel/context-propagation.test.ts:1-1
Timestamp: 2025-10-19T02:44:46.354Z
Learning: In the Bun repository, standalone packages under packages/ (e.g., bun-vscode, bun-inspector-protocol, bun-plugin-yaml, bun-plugin-svelte, bun-debug-adapter-protocol, bun-otel) co-locate their tests with package source code using *.test.ts files. This follows standard npm/monorepo patterns. The test/ directory hierarchy (test/js/bun/, test/cli/, test/js/node/) is reserved for testing Bun's core runtime APIs and built-in functionality, not standalone packages.
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:37:30.259Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: test/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:37:30.259Z
Learning: Applies to test/**/*-fixture.ts : Test files that spawn Bun processes should end in `*-fixture.ts` to identify them as test fixtures and not tests themselves
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:35:50.422Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/writing-tests.mdc:0-0
Timestamp: 2025-11-24T18:35:50.422Z
Learning: Applies to test/cli/**/*.{js,ts,jsx,tsx} : When testing Bun as a CLI, use the `spawn` API from `bun` with the `bunExe()` and `bunEnv` from `harness` to execute Bun commands and validate exit codes, stdout, and stderr
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-06T00:58:23.965Z
Learnt from: markovejnovic
Repo: oven-sh/bun PR: 24417
File: test/js/bun/spawn/spawn.test.ts:903-918
Timestamp: 2025-11-06T00:58:23.965Z
Learning: In Bun test files, `await using` with spawn() is appropriate for long-running processes that need guaranteed cleanup on scope exit or when explicitly testing disposal behavior. For short-lived processes that exit naturally (e.g., console.log scripts), the pattern `const proc = spawn(...); await proc.exited;` is standard and more common, as evidenced by 24 instances vs 4 `await using` instances in test/js/bun/spawn/spawn.test.ts.
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:37:30.259Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: test/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:37:30.259Z
Learning: Applies to test/**/*.test.{ts,js,jsx,tsx,mjs,cjs} : Always use `await using` or `using` to ensure proper resource cleanup in tests for APIs like Bun.listen, Bun.connect, Bun.spawn, Bun.serve, etc
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:37:30.259Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: test/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:37:30.259Z
Learning: Unit tests for specific features are organized by module (e.g., `/test/js/bun/`, `/test/js/node/`)
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-11-24T18:35:39.205Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/registering-bun-modules.mdc:0-0
Timestamp: 2025-11-24T18:35:39.205Z
Learning: Add tests for new Bun runtime functionality
Applied to files:
test/js/bun/terminal/ghostty.test.ts
📚 Learning: 2025-09-02T06:10:17.252Z
Learnt from: Jarred-Sumner
Repo: oven-sh/bun PR: 22323
File: test/js/web/websocket/websocket-subprotocol-strict.test.ts:80-91
Timestamp: 2025-09-02T06:10:17.252Z
Learning: Bun's WebSocket implementation includes a terminate() method, which is available even though it's not part of the standard WebSocket API. This method can be used in Bun test files and applications for immediate WebSocket closure.
Applied to files:
src/bun.js/api/bun/Terminal.zig
🧬 Code graph analysis (1)
test/js/bun/terminal/ghostty.test.ts (1)
test/harness.ts (1)
bunExe(102-105)
🔇 Additional comments (6)
cmake/targets/BuildBun.cmake (1)
65-65: LGTM!The GhosttyVt dependency is correctly added to the
BUN_DEPENDENCIESlist. This will trigger the inclusion ofBuildGhosttyVt.cmakevia the foreach loop at line 1251.src/deps/ghostty/symbols_tables.zig (1)
1-1808: LGTM - Auto-generated lookup tables.This file contains pre-generated multi-stage lookup tables for symbol/unicode property detection. The comptime-parameterized
Tablesfunction allows the element type to be specified at compile time. Since this is auto-generated data, no manual review of the table contents is needed.src/deps/ghostty/terminal_options.zig (1)
1-28: LGTM - Minimal build configuration for initial integration.The options are appropriately set for a minimal ghostty-vt integration:
- Building as a library (
.lib) is correct for embedding- Disabling C ABI, oniguruma, and SIMD keeps the build simple
- Feature dependencies are correctly handled (kitty_graphics and tmux_control_mode require oniguruma)
This conservative approach is good for initial integration. SIMD could be enabled later if performance optimization is needed for large terminal buffers.
cmake/targets/BuildGhosttyVt.cmake (1)
12-19: The ghostty tag v1.1.3 is valid and cryptographically verified.The v1.1.3 tag exists and is signed with the committer's verified GPG signature, created by the project maintainer. The repository registration follows the same pattern used for other vendored dependencies and the version pinning ensures reproducible builds. The documentation clearly explains the integration approach where the ghostty source is cloned to the vendor path for the Zig build system.
build.zig (1)
846-876: Build system integration for ghostty module is correct.The referenced source files are properly accounted for. The three Bun customization files (terminal_options.zig, unicode_tables.zig, symbols_tables.zig) exist in src/deps/ghostty/. The vendored ghostty files (lib_vt.zig and unicode/props.zig) will be cloned by CMake to vendor/ghostty/ as part of the standard build process—BuildGhosttyVt.cmake registers the ghostty-org/ghostty repository and is included via the dependency loop in BuildBun.cmake.
src/bun.js/api/bun/Terminal.zig (1)
72-77: Verify ArrayList initialization pattern.The
vt_titlefield is initialized with.empty, butstd.ArrayListtypically requires initialization with an allocator via.init(allocator)or= .{}. While.emptymay be a Bun-specific pattern, thedeinit()call at line 965 passesbun.default_allocator, suggesting the ArrayList should have been initialized with that allocator.Run the following script to check if
.emptyis used elsewhere in the codebase for ArrayList initialization:#!/bin/bash # Search for ArrayList initialization patterns in Zig files echo "=== Searching for ArrayList.empty pattern ===" rg -n "ArrayList.*=.*\.empty" --type=zig -C2 echo "" echo "=== Searching for proper ArrayList initialization ===" rg -n "ArrayList.*=.*\.init\(" --type=zig -C1
| test("handles very long string", () => { | ||
| const terminal = new Bun.Terminal({ rows: 10, cols: 40 }); | ||
| const longString = "A".repeat(10000); | ||
| expect(() => terminal.feed(longString)).not.toThrow(); | ||
| terminal.close(); | ||
| }); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧹 Nitpick | 🔵 Trivial
Use Buffer.alloc() for repetitive strings in tests.
The coding guidelines recommend using Buffer.alloc(count, fill).toString() instead of ''.repeat() for creating repetitive strings in tests, as ''.repeat() is very slow in debug JavaScriptCore builds.
Apply this diff:
test("handles very long string", () => {
const terminal = new Bun.Terminal({ rows: 10, cols: 40 });
- const longString = "A".repeat(10000);
+ const longString = Buffer.alloc(10000, "A").toString();
expect(() => terminal.feed(longString)).not.toThrow();
terminal.close();
});As per coding guidelines for test files.
📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| test("handles very long string", () => { | |
| const terminal = new Bun.Terminal({ rows: 10, cols: 40 }); | |
| const longString = "A".repeat(10000); | |
| expect(() => terminal.feed(longString)).not.toThrow(); | |
| terminal.close(); | |
| }); | |
| test("handles very long string", () => { | |
| const terminal = new Bun.Terminal({ rows: 10, cols: 40 }); | |
| const longString = Buffer.alloc(10000, "A").toString(); | |
| expect(() => terminal.feed(longString)).not.toThrow(); | |
| terminal.close(); | |
| }); |
🤖 Prompt for AI Agents
In test/js/bun/terminal/ghostty.test.ts around lines 161 to 166, replace the
slow `"A".repeat(10000)` with a Buffer-based construction per guidelines: create
the longString using Buffer.alloc(10000, "A").toString() so the test builds the
repetitive string efficiently; keep the rest of the test (Terminal creation,
feed call, not.toThrow assertion, and terminal.close()) unchanged.
- Remove unused opts parameter from addGhosttyModule function - Add TODO comment explaining SIMD is disabled for initial integration stability - Replace string.repeat() with Buffer.alloc() for better performance in tests 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
SIMD remains disabled because ghostty's SIMD implementation uses C++ code (vt.cpp) that would need to be built and linked separately. The scalar fallback paths in ghostty provide correct functionality. Added build_options.zig to provide the simd flag that ghostty's simd/vt.zig expects from @import("build_options"). 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
- Build ghostty's C++ SIMD implementation (vt.cpp) using highway - Configure simdutf via webkit wrapper header - Add utfcpp dependency for UTF-8 error handling with replacement chars - Enable exceptions for vt.cpp only (required by utfcpp) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 3
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro
Disabled knowledge base sources:
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (4)
cmake/targets/BuildGhosttyVt.cmake(1 hunks)src/deps/ghostty/build_options.zig(1 hunks)src/deps/ghostty/simdutf.h(1 hunks)src/deps/ghostty/terminal_options.zig(1 hunks)
🧰 Additional context used
📓 Path-based instructions (3)
src/**/*.{cpp,zig}
📄 CodeRabbit inference engine (.cursor/rules/building-bun.mdc)
src/**/*.{cpp,zig}: Usebun bdorbun run build:debugto build debug versions for C++ and Zig source files; creates debug build at./build/debug/bun-debug
Run tests usingbun bd test <test-file>with the debug build; never usebun testdirectly as it will not include your changes
Execute files usingbun bd <file> <...args>; never usebun <file>directly as it will not include your changes
Enable debug logs for specific scopes usingBUN_DEBUG_$(SCOPE)=1environment variable
Code generation happens automatically as part of the build process; no manual code generation commands are required
Files:
src/deps/ghostty/build_options.zigsrc/deps/ghostty/terminal_options.zig
src/**/*.zig
📄 CodeRabbit inference engine (.cursor/rules/building-bun.mdc)
Use
bun.Output.scoped(.${SCOPE}, .hidden)for creating debug logs in Zig codeImplement core functionality in Zig, typically in its own directory in
src/
src/**/*.zig: Private fields in Zig are fully supported using the#prefix:struct { #foo: u32 };
Use decl literals in Zig for declaration initialization:const decl: Decl = .{ .binding = 0, .value = 0 };
Prefer@importat the bottom of the file (auto formatter will move them automatically)
Files:
src/deps/ghostty/build_options.zigsrc/deps/ghostty/terminal_options.zig
**/*.zig
📄 CodeRabbit inference engine (.cursor/rules/zig-javascriptcore-classes.mdc)
**/*.zig: Expose generated bindings in Zig structs usingpub const js = JSC.Codegen.JS<ClassName>with trait conversion methods:toJS,fromJS, andfromJSDirect
Use consistent parameter nameglobalObjectinstead ofctxin Zig constructor and method implementations
Usebun.JSError!JSValuereturn type for Zig methods and constructors to enable proper error handling and exception propagation
Implement resource cleanup usingdeinit()method that releases resources, followed byfinalize()called by the GC that invokesdeinit()and frees the pointer
UseJSC.markBinding(@src())in finalize methods for debugging purposes before callingdeinit()
For methods returning cached properties in Zig, declare external C++ functions usingextern fnandcallconv(JSC.conv)calling convention
Implement getter functions with naming patternget<PropertyName>in Zig that acceptthisandglobalObjectparameters and returnJSC.JSValue
Access JavaScript CallFrame arguments usingcallFrame.argument(i), check argument count withcallFrame.argumentCount(), and getthiswithcallFrame.thisValue()
For reference-counted objects, use.deref()in finalize instead ofdestroy()to release references to other JS objectsIn Zig code, be careful with allocators and use defer for cleanup
Files:
src/deps/ghostty/build_options.zigsrc/deps/ghostty/terminal_options.zig
🧠 Learnings (16)
📓 Common learnings
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/js/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:37:11.466Z
Learning: Write JS builtins for Bun's Node.js compatibility and APIs, and run `bun bd` after changes
Learnt from: theshadow27
Repo: oven-sh/bun PR: 23798
File: packages/bun-otel/context-propagation.test.ts:1-1
Timestamp: 2025-10-19T02:44:46.354Z
Learning: In the Bun repository, standalone packages under packages/ (e.g., bun-vscode, bun-inspector-protocol, bun-plugin-yaml, bun-plugin-svelte, bun-debug-adapter-protocol, bun-otel) co-locate their tests with package source code using *.test.ts files. This follows standard npm/monorepo patterns. The test/ directory hierarchy (test/js/bun/, test/cli/, test/js/node/) is reserved for testing Bun's core runtime APIs and built-in functionality, not standalone packages.
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: test/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:37:30.259Z
Learning: Applies to test/**/*.test.{ts,js,jsx,tsx,mjs,cjs} : When spawning Bun processes in tests, use `bunExe` and `bunEnv` from `harness` to ensure the same build of Bun is used and debug logging is silenced
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/writing-tests.mdc:0-0
Timestamp: 2025-11-24T18:35:50.422Z
Learning: Applies to test/cli/**/*.{js,ts,jsx,tsx} : When testing Bun as a CLI, use the `spawn` API from `bun` with the `bunExe()` and `bunEnv` from `harness` to execute Bun commands and validate exit codes, stdout, and stderr
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/building-bun.mdc:0-0
Timestamp: 2025-11-24T18:34:55.173Z
Learning: Applies to src/**/*.{cpp,zig} : Run tests using `bun bd test <test-file>` with the debug build; never use `bun test` directly as it will not include your changes
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/registering-bun-modules.mdc:0-0
Timestamp: 2025-11-24T18:35:39.205Z
Learning: Add tests for new Bun runtime functionality
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/bun.js/bindings/v8/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:36:59.706Z
Learning: Applies to src/bun.js/bindings/v8/test/v8/v8.test.ts : Add corresponding test cases to test/v8/v8.test.ts using checkSameOutput() function to compare Node.js and Bun output
📚 Learning: 2025-10-01T21:48:38.278Z
Learnt from: taylordotfish
Repo: oven-sh/bun PR: 23169
File: src/bun.js/bindings/Bindgen/IDLTypes.h:1-3
Timestamp: 2025-10-01T21:48:38.278Z
Learning: In the Bun codebase, for `BunIDL*` and `Bindgen*` headers (e.g., BunIDLTypes.h, Bindgen/IDLTypes.h), it's acceptable to rely on transitive includes for standard library headers like <type_traits> and <utility> rather than including them explicitly.
Applied to files:
src/deps/ghostty/simdutf.h
📚 Learning: 2025-11-24T18:36:59.706Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/bun.js/bindings/v8/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:36:59.706Z
Learning: Applies to src/bun.js/bindings/v8/V8*.h : Create V8 class headers with .h extension following the pattern V8ClassName.h that include pragma once, v8.h, V8Local.h, V8Isolate.h, and declare classes extending from Data with BUN_EXPORT static methods
Applied to files:
src/deps/ghostty/simdutf.h
📚 Learning: 2025-11-24T18:36:59.706Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: src/bun.js/bindings/v8/CLAUDE.md:0-0
Timestamp: 2025-11-24T18:36:59.706Z
Learning: Applies to src/bun.js/bindings/v8/V8*.h : Add BUN_EXPORT visibility attribute to all public V8 API functions to ensure proper symbol export across platforms
Applied to files:
src/deps/ghostty/simdutf.h
📚 Learning: 2025-09-20T05:35:57.318Z
Learnt from: pfgithub
Repo: oven-sh/bun PR: 22534
File: src/bun.js/bindings/headers.h:729-731
Timestamp: 2025-09-20T05:35:57.318Z
Learning: symbols.txt in the Bun codebase is specifically for V8 API mangled symbols (without leading underscore), not for general Bun host functions declared with BUN_DECLARE_HOST_FUNCTION. Host functions are handled through different build mechanisms.
Applied to files:
src/deps/ghostty/simdutf.h
📚 Learning: 2025-10-15T20:19:38.580Z
Learnt from: markovejnovic
Repo: oven-sh/bun PR: 23680
File: cmake/targets/BuildBun.cmake:822-822
Timestamp: 2025-10-15T20:19:38.580Z
Learning: In the Bun codebase, FFI is compiled with tcc (TinyCC), which barely supports C99. The headers `src/bun.js/api/FFI.h` and `src/bun.js/api/ffi-stdbool.h` are only used for FFI compilation with tcc, not for the main Bun target. Therefore, C23 compatibility concerns (such as bool/true/false keyword conflicts) do not apply to these FFI headers.
Applied to files:
src/deps/ghostty/simdutf.h
📚 Learning: 2025-11-24T18:36:08.558Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/zig-javascriptcore-classes.mdc:0-0
Timestamp: 2025-11-24T18:36:08.558Z
Learning: Applies to **/*.zig : Expose generated bindings in Zig structs using `pub const js = JSC.Codegen.JS<ClassName>` with trait conversion methods: `toJS`, `fromJS`, and `fromJSDirect`
Applied to files:
src/deps/ghostty/build_options.zig
📚 Learning: 2025-11-24T18:34:55.173Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/building-bun.mdc:0-0
Timestamp: 2025-11-24T18:34:55.173Z
Learning: Applies to src/**/*.{cpp,zig} : Code generation happens automatically as part of the build process; no manual code generation commands are required
Applied to files:
src/deps/ghostty/build_options.zig
📚 Learning: 2025-11-24T18:34:55.173Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/building-bun.mdc:0-0
Timestamp: 2025-11-24T18:34:55.173Z
Learning: Applies to src/**/*.{cpp,zig} : Use `bun bd` or `bun run build:debug` to build debug versions for C++ and Zig source files; creates debug build at `./build/debug/bun-debug`
Applied to files:
cmake/targets/BuildGhosttyVt.cmakesrc/deps/ghostty/terminal_options.zig
📚 Learning: 2025-11-24T18:36:08.558Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/zig-javascriptcore-classes.mdc:0-0
Timestamp: 2025-11-24T18:36:08.558Z
Learning: Applies to src/bun.js/bindings/generated_classes_list.zig : Include new class bindings in `src/bun.js/bindings/generated_classes_list.zig` to register them with the code generator
Applied to files:
cmake/targets/BuildGhosttyVt.cmake
📚 Learning: 2025-11-24T18:34:55.173Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/building-bun.mdc:0-0
Timestamp: 2025-11-24T18:34:55.173Z
Learning: Applies to src/**/*.{cpp,zig} : Run tests using `bun bd test <test-file>` with the debug build; never use `bun test` directly as it will not include your changes
Applied to files:
cmake/targets/BuildGhosttyVt.cmake
📚 Learning: 2025-12-16T00:21:32.163Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-16T00:21:32.163Z
Learning: Run `bun run zig:check-all` to compile Zig code on all platforms when making platform-specific changes
Applied to files:
cmake/targets/BuildGhosttyVt.cmake
📚 Learning: 2025-11-24T18:34:55.173Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/building-bun.mdc:0-0
Timestamp: 2025-11-24T18:34:55.173Z
Learning: Applies to src/**/*.{cpp,zig} : Execute files using `bun bd <file> <...args>`; never use `bun <file>` directly as it will not include your changes
Applied to files:
cmake/targets/BuildGhosttyVt.cmake
📚 Learning: 2025-12-16T00:21:32.163Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-16T00:21:32.163Z
Learning: Code generation happens automatically during the build process - bundled modules can be reloaded without rebuilding Zig by running `bun run build`
Applied to files:
cmake/targets/BuildGhosttyVt.cmakesrc/deps/ghostty/terminal_options.zig
📚 Learning: 2025-11-24T18:35:39.205Z
Learnt from: CR
Repo: oven-sh/bun PR: 0
File: .cursor/rules/registering-bun-modules.mdc:0-0
Timestamp: 2025-11-24T18:35:39.205Z
Learning: Applies to src/**/index.zig : Create an `index.zig` entry point in your module directory that exports all module functionality
Applied to files:
src/deps/ghostty/terminal_options.zig
📚 Learning: 2025-10-15T22:03:50.832Z
Learnt from: markovejnovic
Repo: oven-sh/bun PR: 23710
File: src/envvars.zig:135-144
Timestamp: 2025-10-15T22:03:50.832Z
Learning: In src/envvars.zig, the boolean feature flag cache uses a single atomic enum and should remain monotonic. Only the string cache (which uses two atomics: ptr and len) requires acquire/release ordering to prevent torn reads.
Applied to files:
src/deps/ghostty/terminal_options.zig
🔇 Additional comments (4)
cmake/targets/BuildGhosttyVt.cmake (1)
34-63: LGTM! Well-structured SIMD library configuration.The selective exception enablement for the SIMD source file is appropriate, and the include directory configuration correctly references all necessary dependencies. The use of
HWY_STATIC_DEFINEaligns with the static linkage pattern.src/deps/ghostty/simdutf.h (1)
1-5: LGTM! Clean compatibility wrapper.The header correctly redirects ghostty's expected
<simdutf.h>include to Bun's WebKit-provided SIMDUTF implementation. The approach is clean and well-documented.src/deps/ghostty/terminal_options.zig (2)
1-11: LGTM! Clean artifact configuration.The enum and artifact constant are well-defined for library-mode integration. The
.libartifact type correctly reflects Bun's usage pattern.
12-29: Configuration choices are appropriate for Bun integration.The build options correctly balance functionality and simplicity:
- SIMD enabled for performance (addresses previous review feedback)
- Optional features (oniguruma, kitty_graphics, tmux_control_mode) appropriately disabled for minimal build
- Dependency constraints are satisfied (graphics and control mode require oniguruma, both disabled)
- Runtime safety checks disabled for production
cmake/targets/BuildGhosttyVt.cmake
Outdated
| register_repository( | ||
| NAME | ||
| ghostty | ||
| REPOSITORY | ||
| ghostty-org/ghostty | ||
| TAG | ||
| v1.1.3 | ||
| ) | ||
|
|
||
| # utfcpp - header-only UTF-8 library for error handling in SIMD code | ||
| register_repository( | ||
| NAME | ||
| utfcpp | ||
| REPOSITORY | ||
| nemtrif/utfcpp | ||
| TAG | ||
| v4.0.5 | ||
| ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
🏁 Script executed:
# Verify utfcpp release information and check for CVE advisories
curl -s "https://api.github.com/repos/nemtrif/utfcpp/releases" | jq -r '.[] | "\(.tag_name): \(.published_at)"' | head -20Repository: oven-sh/bun
Length of output: 630
Update ghostty and utfcpp to newer versions.
Ghostty v1.2.3 (released October 23, 2025) is available; the current pin to v1.1.3 is outdated. Ghostty v1.2.0 (September 15, 2025) introduced a security fix where Ghostty now unconditionally asks for permission prior to executing any script or executable, which is not present in v1.1.3.
For utfcpp, v4.0.8 (released September 2025) is the latest available; the current pin to v4.0.5 (released December 2023) is nearly two years old with multiple newer patch releases (v4.0.6, v4.0.7, v4.0.8) available.
🤖 Prompt for AI Agents
In cmake/targets/BuildGhosttyVt.cmake around lines 12 to 29 the repository TAG
pins are outdated; update the ghostty TAG from v1.1.3 to v1.2.3 and update the
utfcpp TAG from v4.0.5 to v4.0.8 to pick up the security and patch fixes, then
run a configure/build and tests to ensure compatibility after the version bumps.
cmake/targets/BuildGhosttyVt.cmake
Outdated
| # Ensure dependencies are built first | ||
| add_dependencies(ghostty-simd clone-ghostty clone-utfcpp) | ||
| if(TARGET highway) | ||
| add_dependencies(ghostty-simd highway) | ||
| endif() | ||
|
|
||
| # Link ghostty-simd into bun | ||
| target_link_libraries(${bun} PRIVATE ghostty-simd) | ||
|
|
||
| # Link highway library | ||
| target_link_libraries(${bun} PRIVATE ${BUILD_PATH}/highway/libhwy.a) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧹 Nitpick | 🔵 Trivial
Consider linking against the highway target instead of hardcoded path.
Line 75 uses a hardcoded path to libhwy.a. If the highway target is available (checked on line 67), linking against the target would be more robust and portable.
Apply this diff to use target-based linking:
# Link ghostty-simd into bun
target_link_libraries(${bun} PRIVATE ghostty-simd)
-# Link highway library
-target_link_libraries(${bun} PRIVATE ${BUILD_PATH}/highway/libhwy.a)
+# Link highway library (if available as a target, use it; otherwise fall back to path)
+if(TARGET highway)
+ target_link_libraries(${bun} PRIVATE highway)
+else()
+ target_link_libraries(${bun} PRIVATE ${BUILD_PATH}/highway/libhwy.a)
+endif()🤖 Prompt for AI Agents
In cmake/targets/BuildGhosttyVt.cmake around lines 65 to 75, replace the
hardcoded link to ${BUILD_PATH}/highway/libhwy.a with target-based linking when
the highway target exists: modify the target_link_libraries call to link PRIVATE
highway if TARGET highway is true (e.g. use if(TARGET highway)
target_link_libraries(${bun} PRIVATE highway) else target_link_libraries(${bun}
PRIVATE ${BUILD_PATH}/highway/libhwy.a) endif()), preserving the existing
add_dependencies so the highway target is built first and falling back to the
file path only when the target is not available.
src/deps/ghostty/build_options.zig
Outdated
| //! Build options for ghostty-vt module. | ||
| //! This provides the build_options that ghostty's SIMD code expects. | ||
|
|
||
| /// SIMD acceleration for optimized UTF-8 and escape sequence parsing. | ||
| /// Uses highway SIMD library with simdutf for fast UTF-8 decoding. | ||
| /// Note: Keep in sync with terminal_options.simd | ||
| pub const simd = true; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧹 Nitpick | 🔵 Trivial
Consider consolidating SIMD configuration to avoid sync issues.
Line 6 notes "Keep in sync with terminal_options.simd", which introduces a manual synchronization requirement. This duplication could lead to configuration drift.
Consider one of these approaches:
- Have one file import from the other:
pub const simd = @import("terminal_options").simd; - Generate both from a single source of truth during the build process
- Document why both are needed if the separation is intentional (e.g., different build phases)
This would eliminate the manual sync requirement and reduce maintenance burden.
This reverts commit 2071742. SIMD cannot be enabled with official ghostty v1.1.3 due to Zig compatibility issues. Ghostty uses Zig syntax that's incompatible with Bun's Zig 0.15.2 (duplicate struct member name errors from usingnamespace patterns). SIMD will need to be re-enabled once a compatible ghostty version is available. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
|
Working on something similar in opentui: sst/opentui#440 I also export stateless functions to convert ANSI to text without a pty and also a way to render the first N lines cheaply without parsing the full terminal output (to show the collapsed bash tool outputs in opencode fast) |
Summary
Bun.TerminalNew API
Implementation
feed()callTest Plan
feed()with various input types (14 tests)at()bounds checking and cell retrieval (12 tests)line()bottom-relative indexing (7 tests)textproperty (4 tests)cursorproperty (7 tests)clear()andreset()(6 tests)alternateScreen,scrollbackLines,titleproperties (7 tests)🤖 Generated with Claude Code