Racketeer: Organised RacketRacket source debugging and editing for VS Code. By Eric Parsonage. Racketeer is the only Racket extension for VS Code that debugs Racket source: set breakpoints, step through expressions and inspect live values in the editor, as with any other VS Code language. Racketeer's DAP server provides expression breakpoints, stepping across files and packages, live lexical inspection and evaluation. Run a source file to see text and images beside the editor, or debug it with breakpoints and stepping. Bundled language tools, testing and package commands complete the development workflow. Requires the full Racket 9.1 or newer distribution. Minimal Racket alone
does not include all the standard libraries and documentation used by the
language server. No separate Install and start
If Racket is not on PATH, set DebuggingFor a reusable launch configuration:
The root module loads first, then its By default, the session ends after the entry action and GUI work complete;
visible windows, timers and queued callbacks keep GUI programs alive. With With Breakpoints and exceptionsClick the gutter to the left of a line number, press F9 or right-click
and choose Add Breakpoint. These controls work in the captured source tab
opened by the debugger as well as in the source file. Press F9 again to remove
the breakpoint. A normal session exits when the program finishes; enable
The bundled language server supplies semantic highlighting and documentation
for ordinary files and matching captured debugger sources. For example,
Breakpoints bind to expressions beginning on the selected line, preferring the outermost expression. Use an inline breakpoint to select a later expression on the line. An inline breakpoint on a non-tail expression's final character stops after it returns. Racket: Continue to Cursor runs to one selected boundary once while retaining ordinary breakpoints. A breakpoint stays pending until its module is loaded; if there is no expression at that location it remains unverified with an explanation. Breakpoints do not silently move into another function. A breakpoint added to an already loaded, uninstrumented dependency needs a fresh launch. Right-click a breakpoint to add a condition or hit count:
Use Uncaught Racket exceptions (enabled by default) in the Breakpoints pane to stop at an
uncaught runtime error. Call Stack, lexical variables, Exception scope and exception details
remain available. Continue propagates the same exception: a script usually ends,
while an interactive console call reports the error and leaves the module loaded.
The program's error display and escape handlers retain their original context;
a custom Stepping and evaluationThe default launch's To inspect initialisation before reaching VS Code keeps its native Continue, Step Into, Step Over and Step Out controls. These correspond to DrRacket's Go, Step, Over and Out respectively. Call Stack, Variables and Watch also keep their native VS Code names. Step Into visits expression starts and completions. Step Over can stop at an
expression's completion. When a function returns, this completion stop remains
at its call site, so its return values can be inspected before advancing to the
next expression. The Return values scope includes a count, such as Return
values (0), Return values (1) or Return values (2); zero values and one
Call Stack distinguishes Before evaluation from Returned N values. At a return stop the marker moves to the expression's closing parenthesis; open Return values to inspect its values. Waiting for return identifies a caller whose calculation is still pending. Stepping is by expression, so several stops can share a source line. Expanded forms can also share a larger source range, which currently makes some stops highlight a whole function. Captured debugger sources support hover, Go to Definition and Find References through the language server. Navigation opens current project files. These features require the captured source to match the current file and are disabled for that view if its file changes or the debug session ends. Select a frame in Call Stack to inspect its lexical variables in
Variables → Locals, or evaluate a Racket expression in the Debug Console,
for example The editor context menu and Command Palette provide Skip Expression before
an expression, Change Return Values and Print Return Values to Console
after it, plus Print Variable Value to Console and Set Variable Value
(set!) for the variable at the cursor. Variable actions use the selected stack
frame. Expression actions use the executing frame. Replacement expressions can
return Run Racket: Cancel Evaluation to interrupt a blocked console, watch, condition or logpoint evaluation. The session and paused frames remain usable when cancellation succeeds. Cancellation is cooperative: code that disables or catches breaks may keep running; Stop still terminates the worker. Effects that already happened are not rolled back. When a console call is paused and another evaluation runs inside that stop, Cancel targets the inner evaluation. Lists, vectors, hashes and inspector-visible structures show bounded contents
in their previews. Pairs, vectors, boxes, hashes and visible structure fields
can be expanded. Syntax objects show a datum preview and expand to the datum
and source coordinates; procedures expand to show arity. Procedure names appear
when they can be obtained without invoking program callbacks; other procedures
can remain Automatic inspection does not force promises, call custom writers or invoke wrapped accessors. Wrapped values retain conservative previews; use explicit console evaluation to run their code. A stopped program's source remains available even if its file is edited; start a fresh session to debug the edited version. Language toolsThe bundled upstream racket-langserver
provides completion, hover documentation, definition, references, rename,
diagnostics, symbols, semantic tokens, signature help, inlay hints and code
actions. Support varies with the program's Cold startup loads the bundled source packages and can take longer on a busy
machine. Startup has a three-minute deadline by default; set
Magic Racket is not required. If its language client is enabled, this extension defers language-server startup to it to avoid duplicate providers. Disable Magic Racket and reload the window to use this extension alone. No other extensions or global Racket packages are disabled or changed automatically. Module dependenciesUse Racket: Browse Module Dependencies on the current named source file, or from its Explorer context menu. The Racket Dependencies tree shows imports, their phase shifts and submodules. Select an entry to open its source file; expand it to follow dependencies. Repeated modules stop expanding within a branch. Open Racket/Rhombus buffers, including unsaved dependency edits, participate in analysis without being saved. The tree refreshes after source changes; its Refresh button retries failed branches. Compilation runs readers and compile-time code in a trusted workspace. Analysis uses public Racket APIs without a DrRacket dependency. A phase label gives an import's shift relative to its parent module, not a phase
accumulated from the root: phase 0 is an ordinary import, phase +1 a compile-time
import and label phase a Lambda insertionPress Alt+\ (Option+\ on macOS) in an editable Racket buffer to insert
Macro expansionRacket: Open Line or Selection in Macro Stepper (Alt+Shift+Enter) opens complete selected forms, or the current line, in Racket's macro-stepper window. Fragments use a fresh Racket namespace. Racket: Open File in Macro Stepper expands the entire module with its own imports and macro definitions. Both use the current buffer, including unsaved edits. Expansion runs compile-time code, but does not execute the module's runtime body. These commands use the full Racket installation's public macro-debugger library and require a graphical desktop. The stepper is a separate window; startup and expansion errors appear in its terminal. Close the stepper window to finish, or close its Racket Macro Stepper terminal to cancel. Inspection does not save the buffer. Rhombus editingOpen a Automatic Rhombus formatting is disabled because the bundled default formatter handles Racket S-expressions. Rhombus uses its own basic indentation rules. Rhombus support covers editing. Rhombus source debugging, Debug REPL and Test Explorer compatibility are not established by these checks. Running, testing and REPL
Set The default, The editor toolbar has Run, Debug and File Actions… controls. File Actions also offers testing and both kinds of REPL. Test ExplorerOpen VS Code's Testing view to discover workspace Results include logged check counts, test output and clickable failure
locations for direct RackUnit checks and cases inside discovered suites.
Explicitly run suites also contribute their RackUnit counts; custom runners
that replace the reporting hooks may provide details only in test output.
Teaching-language checks such as Configure Use VS Code's Run Tests with Coverage controls to see executed and unexecuted
expressions in the Test Coverage view and editor. Coverage combines completed
tests and their loaded dependencies under Debug REPLRacket: Run in Interactions loads the saved root module into a fresh session
and opens its Interactions view beside the source. Text and image results appear
automatically, including expressions at the top level of the file. Try
Enter expressions at the prompt and press Enter; Shift+Enter inserts a newline.
Up/Down recalls previous expressions. Interrupt cancels evaluation or image
conversion. Run again saves the file and starts a fresh session; Stop
leaves its output visible. Program input supplies lines or EOF to Errors include clickable source locations when the evaluator has retained the
relevant source. Try Malformed input links to the entered text. Submitted expression opens the whole expression when no exact location within it is available. Context: labels approximate stack locations. Arbitrary error-message text is never parsed as a file link. Each error retains at most eight locations and 1 MiB of captured source, counted within the transcript limit. Omissions caused by these limits are reported. Locations in uncaptured libraries or embedded WXME editors may be unavailable. The normal error formatter and debugger exception controls remain in effect. Racket: Load Current File in Debug REPL reuses this file's session and
Interactions view. These commands do not execute Change or remove the shortcut in VS Code's Keyboard Shortcuts editor by
searching for Racket: Evaluate Selection in Debug REPL, or use Both selection commands support multiple selections. Select complete expressions; they run from top to bottom, ignoring empty cursors. The Debug REPL prints each result and stops the batch if an expression fails or is cancelled. Each file has its own Debug REPL. Loading again reuses it. Use Racket: Restart Debug REPL for Current File to load saved edits into a fresh session. Restart and Stop affect that session only. With several sessions open, use the Debug Console's session selector to choose where manually typed expressions go. Selection commands always target the source file's Debug REPL. Cancel Evaluation interrupts evaluation in the active Racket debug session; Stop ends the session. Plain REPL terminals continue to run ordinary Racket through For a saved WXME source file, use Open With → Racketeer WXME Viewer to read text and embedded bitmap images in source order. The viewer is read-only and does not run the program. Ordinary Racket files still open in the text editor. Nested editors, comment boxes, XML boxes and Racket boxes retain their boundaries and contents. XML labels show the whitespace mode; Racket labels distinguish single values from splicing. Other object classes are reported as unsupported. A changed file is marked in the view; close and reopen it to refresh. Unsaved text edits must be saved or reverted before viewing. Choose Open With → Racketeer WXME Editor to edit text around embedded images and inside nested editors or comment boxes. It supports VS Code's Undo, Redo, Save, Save As, Revert and unsaved-document recovery. Use the toolbar to insert a PNG image, comment box or nested editor at the cursor. Selecting text before inserting a box moves that text inside it. The × button removes an object and its contents; Undo restores them. XML and Racket boxes support text editing, insertion and removal. Box controls change XML whitespace handling or Racket splicing, with normal Undo/Redo. Their original object types and nested contents survive saving. The writer uses Racket's public editor libraries and does not require DrRacket. Unsupported box versions, other object classes and linked or missing images cannot be edited. PNG imports are limited to 8 MiB and 4096 pixels in either dimension. Save As opens its destination in the configured default editor. Use Open With to continue in the WXME editor if needed. Editing requires the full Racket installation's GUI libraries and a working graphical display on the extension host. It opens inside VS Code; no separate Racket window is shown. The read-only viewer also works without a display. Saving preserves supported objects and unchanged text styles through Racket's editor codec and can change the file's binary representation. Text placed in a comment box takes the framework's standard comment-box style. If the file changes externally, use Revert to reload it or Save As to keep the edited version. Racket: Run Current File and Racket: Debug Current File save and launch the active WXME document from either the editor or viewer. A dirty editable view of the same file is saved before launch. Debugging opens a read-only source snapshot with an object replacement character (U+FFFC) for each image or box. Use that snapshot for breakpoints and stepping through the surrounding source text. The program executes from the original WXME bytes; the snapshot remains fixed if the file is edited during a stop. Language services, breakpoints in the custom editor and locations inside embedded boxes are not yet available. The Interactions view draws returned and printed image values automatically.
For the native Debug Console, after an expression returns an image, choose Racket: View Image from the
Command Palette or the preview button on the debug toolbar.
It opens a PNG snapshot in VS Code's built-in image editor. Use Racket: Save
Image As… from that editor to keep a copy. Try While paused, right-click an image in Variables and choose Racket: View Image. This also works for image fields inside expanded structures and images in the Return values scope. It uses the selected value directly, without evaluating an expression or changing the last console result. Previews share one editor group so opening several images keeps the source visible. Viewing converts the retained value; it does not evaluate the expression again. Conversion can execute the value's code: use Racket: Cancel Evaluation to interrupt it. The live result expires when another interaction starts or the program resumes. A rendered snapshot remains available until its last tab is closed or the editor reloads. PNG previews are limited to 8 MiB. Inline image output is provided by the Interactions view; the native Debug Console remains textual. For a live value returned by Opening a view uses the retained value without reevaluating the expression.
Copying may execute user code; Racket: Cancel Evaluation interrupts opening.
Close a plot window to release that view. Stopping or restarting its debug
session closes all its plot windows. Subsequent REPL evaluations leave open
windows available. Racket GUI libraries and a working display on the Racket
host are required; these windows are separate from VS Code's image editor.
In a plain terminal REPL, The workflow follows Racket's picture-value model using the public conversion protocol. Interactions displays these values inline, with a native image preview available by clicking the picture. Application logsChoose Racket: Show Application Log, or Logs in Interactions, to open a session's messages in the native Output panel. If several sessions are available, choose one by its file and session number. Racket: Set Application Log Filter… changes capture for a running session. Racket: Clear Application Log clears its retained messages. The default filter is Try Capture uses the public Racket logging API for the program's current logger and descendants, including child threads and REPL evaluations. Loggers detached from that hierarchy and other processes are outside this stream. Existing stderr logging remains active. Opaque log data is not inspected or printed. Terminal-only runs use Racket's own logging facilities; this view belongs to debugger-backed sessions, including Interactions and tests. Adapter clients can select an initial PackagesUse Racket: Manage Packages to install, link, update, remove, build, test
or open package source. Management changes use user scope for the configured
Racket installation. Dependencies, locking and package test metadata are
handled by the native Use Racket: Choose Packages to Debug to include installed or linked package
source outside the workspace in Debug, Debug Test and Debug REPL. This sets
Racket: Test Package honours Current limitsThis remains a development release. Runtime debugging is tested with
Caught-exception tracing, transformer-phase stepping, arbitrary-process attach, reverse execution, full TTY input and DrRacket's graphical source editor are outside this release. Local syntax transformers are not reconstructed for console evaluation. Standard text sources are used in VS Code. A breakpoint stops only the triggering Racket thread. Other threads continue; shared values can change. Pause can interrupt a blocked primitive while retaining live frames; its location is marked approximate in the stop description. If a break arrives without an instrumented frame, stopping waits for the next source expression. Code that disables breaks defers interruption. Source files under the workspace folder are instrumented by default; collection dependencies normally run without instrumentation. GUI callbacks continue to dispatch while an interactive session waits for console input. The debugger's expression instrumentation and frame/binding support are under
Copyright © 2026 Eric Parsonage. Racketeer's original code and documentation
are licensed under Apache-2.0 OR MIT, at the licensee's option. The extension includes
Building applicationsUse Racket: Create Launcher… or Racket: Build Executable… with a source module open, choose Console or GUI mode and select the output path. Use Racket: Create Distribution… on an executable to collect its runtime dependencies. Builds run as native VS Code tasks; Tasks: Terminate Task cancels them. A launcher needs its original source and Racket installation; an executable embeds code but can still need runtime files. Distributions target compatible operating systems and architectures and may need system libraries. The Workspace referencesRacketeer analyses unopened Racket module files in trusted workspaces using a separate indexing service. It works with either the bundled or installed language server, reusing the bundled analysis libraries. Find All References waits for the current analysis pass and can be cancelled. Unsaved editor buffers remain authoritative for their own source files; closing a buffer returns that file to disk analysis. Dependencies are loaded from disk, so save changes to imported modules before relying on dependent analysis. The status bar shows indexing progress and warns when references are partial. Use Racket: Refresh Workspace References after external package changes or to retry failed analysis. Rename Symbol uses the same workspace scope and previews binding-checked edits across unopened files. It preserves explicit import aliases, nested prefixes and prefixes around selective imports. Selectors over composed imports, phase-shifted uses and selectors shared by multiple export phases may be refused. Files that fail analysis make the index partial; rename refuses incomplete or stale snapshots. Background diagnostics are not part of this feature. Settings under Changes within watched workspace directories conservatively restart analysis,
including non-Racket files that readers or macros may use. Dependencies outside
those directories, excluded files, environment changes and nondeterministic
macros require a manual refresh. Initial indexing can take time, especially
when dependencies are not compiled. These limits bound work and retained facts;
they are not a total process memory limit. Both language tools use Racket's
compilation cache under the Racket addon directory's |