You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Add Playground v2 with TS7, multifile, and more - #3653
This is an all new playground, which began as just making something to support TypeScript v7, but has turned into a feature-rich replacement with multiple files, real tsconfigs, multi file output, and more.
Build a static Monaco 0.56 playground against the local wasip1 compiler API. Support Twoslash type queries, diagnostics, JavaScript emit, standard library types, and a browser console API without playground plugins.
Make the playground deployable from a standalone website checkout by committing the wasip1 API packages, standard libraries, WASM module, version metadata, and legal notices. Brand the route as /play/7/.
Force-add the generated API package output and wasip1 module because the website's global dist ignore otherwise omits the files required by a fresh checkout.
Port the browser WASI and Monaco LSP transport from the 2026 GopherCon talk. Serve the playground directly at /play/7/ so its service worker can establish cross-origin isolation for SharedArrayBuffer.
Keep the synchronous compiler API authoritative for diagnostics, Twoslash, emit, and window.ts while LSP provides completion, hover, signature help, navigation, references, rename, and related editor features.
Set an explicit /play/7/ base in production so Azure's slashless /play/7 route resolves scripts, styles, workers, libraries, and the service worker from the playground directory.
Canonicalize Azure's slashless /play/7 URL before the scoped cross-origin isolation service worker starts. This lets the worker control /play/7/ after its activation reload without repeatedly registering.
Add a virtual project with editable tsconfig.json and multiple source files. Drive native compilation from the config and show all emitted files together in a highlighted, non-Monaco output pane.
Restore Run with captured CommonJS console output and reuse the existing playground loading grid while the compiler API and LSP initialize.
Add a collapsible file tree with nested file creation and default to src/index.ts. Persist the complete project and active file in an old-playground-style compressed #code URL.
Enable declaration emit by default, trim display-only trailing newlines, remove Twoslash and WebAssembly branding, and provide local JSON Schema completion, hover, and validation for tsconfig.json and jsconfig.json.
Ignore trailing commas and suppress SchemaStore enum diagnostics when TypeScript accepts the value with different casing. Migrate projects saved before the src directory change so their config includes the moved files and enables declaration emit.
Stream the compiler, libraries, and config schema with real byte progress. Show WebAssembly compilation as indeterminate, report library mounting by file count, and finish with the actual LSP startup stages.
Reuse the downloaded libraries in the LSP worker, add a Reset control for non-emitting saved projects, and explicitly route Ctrl/Cmd-click through go to definition.
Store the compiler WASM, library bundle, and config schema in a content-versioned browser cache. Refreshes now read those artifacts locally and new compiler artifacts automatically use a new cache namespace.
Remove the implementation-detail message about WebAssembly compile progress while keeping that phase honestly indeterminate.
Enable Monaco semantic highlighting and add explicit theme colors for TypeScript semantic token kinds. Recognize bundled library URIs so definitions such as console.log open the read-only lib.dom.d.ts model.
Replace the full-screen loading blocker with a compact translucent progress card. Keep the file tree, Monaco editor, emit pane, and Run output visible and editable throughout compiler and LSP startup.
Register the ^? inlay provider for JavaScript and build a supplemental allowJs program for source models outside the configured project. This matches LSP inferred-project hover behavior without changing tsconfig-driven emit.
Update the playground to the current wasip1 compiler, JavaScript API client, standard libraries, and legal notices. Adapt createProgram calls to the new API signature and normalize bundled library definition URIs for Monaco navigation.
Add an in-page compiler selector for Native 7.1, classic stable releases, Nightly, and custom or PR CDN build IDs. Run classic compilers in a dedicated worker with project emit, diagnostics, hover, completion, definitions, references, signature help, Run, and type queries.
Accept old ?ts= and #code/ URLs, migrate @filename multi-file sources and legacy compiler-option parameters, preserve project state while switching backends, and add a Native 7.1 handoff to the classic playground version menu.
Stack the file browser, editor, and output at phone widths so the workspace remains usable without horizontal page scrolling.
Add a collapsible file browser, touch-sized controls, safe-area spacing, and landscape handling.
Make definition jumps reversible so users can inspect project or bundled declarations without losing their previous editor location.
Expose Back and Forward controls and label bundled library files clearly.
Provide an explicit Delete action for the active project file while keeping bundled declarations protected and ensuring the project always retains a fallback file.
Reload after deletion so the WASI language server is rebuilt without stale files from its startup filesystem.
Selecting a classic TypeScript release should not remove the language-service features users expect from the existing playground.
Port Monaco's TypeScript adapters across the Strada worker boundary for rename, formatting, symbols, highlights, quick fixes, inlay hints, and richer completions, with compatibility fallbacks for older compiler APIs.
Inline markers and a toolbar count are not enough when a project has multiple files or configuration diagnostics.
Show a severity-sorted Problems list with file locations and direct navigation for both Native and Strada diagnostics.
Package imports should provide diagnostics, completion, and definition navigation without requiring users to manually copy declaration files into the project.
Reuse the website's existing ATA implementation, cache downloaded declarations, mount them into Native and Strada, and restart Native only when its immutable LSP filesystem needs newly acquired files.
A replacement playground should retain the existing learning entry points without depending on generated website files that are absent from clean package builds.
Bundle the example catalog, load examples as real projects with their compiler settings, and provide responsive help topics written for the unified workspace.
The TS7 playground package must build before repository bootstrap and without generated workspace package outputs.
Bundle the existing ATA runtime, declarations, package metadata, and license with the other static playground dependencies.
Examples and help add useful toolbar actions, but the desktop row can exceed the available width before the phone layout activates.
Allow the toolbar actions to wrap independently while retaining the tablet workspace columns.
The reason will be displayed to describe this comment to others. Learn more.
🔵 Needs a closer look
Unresolved configuration and library-loading issues can produce incorrect editor and compiler results, while completion replacement and counter-overflow defects can duplicate text or disrupt long-running language-server sessions.
Legacy directives such as // @types: node and // @lib: es2020,dom fall through to a raw string here, but those compiler options require arrays. Moving annotated code into v2 therefore produces TSConfig errors instead of applying the settings. Use the option's kind to convert comma-separated lists while retaining support for JSON arrays.
Include imported project files in configured type queries
parsed.fileNames contains configuration roots, not every file in the configured program, so an imported project file can be misclassified as an orphan. Its type queries then run without the entry file and can miss global declarations or augmentations supplied there. Include project source files already present in program in the configured query pass, and reserve the inferred program for files actually absent from it.
Traverse cached libraries to retry missing dependencies
A cached root is skipped even when its referenced libraries are still missing, so a failed dependency download is never retried and an overlapping load can return before the full library graph is available. Both cases can leave compilation or editor requests without required standard-library declarations. Traverse cached libraries' references with the per-call cycle guard so each load waits for all missing dependencies.
Use the compiler's replacement span when converting completions. Always using the current word range loses entry.replacementSpan and result.optionalReplacementSpan; for a string-literal completion containing punctuation, such as completing "foo-" to "foo-bar", the word range starts after the hyphen and accepting the suggestion duplicates the prefix instead of replacing it. Convert the supplied span with spanToRange, falling back to the word range only when neither span is present.
Download libraries referenced by project files and declarations
The download roots omit library references in project files and acquired declarations. For example, with target ES5, /// <reference lib="es2015.promise" /> should make Promise available, but lib.es2015.promise.d.ts is never downloaded and the compiler host cannot read it. Include these directives in the library roots before compilation and language-service requests.
Use TSConfig roots for the configured language service
This gives the language service every source model as a root, even files excluded by TSConfig's files/include/exclude. For example, an excluded file containing a global declaration still contributes that declaration to hover and completion in an included file, while compile() correctly omits it and reports the name as missing. Please use the parsed configuration's root files for the configured language service and handle out-of-project files in a separate inferred service, so editor results agree with the emitted project.
After 2 GiB of cumulative stdin traffic, these Int32Array counters wrap negative, making the available length negative and causing the worker's allocation to throw; negative remainder offsets also break indexing. Use wrap-safe unsigned distances and offsets in both this consumer and RingBufferWorker.#flush in tsgo-lsp.ts so long editing sessions do not lose the language server.
Configuration roots do not enumerate every file in a program. Keep
imported project files in the configured type-query pass so entry-file
globals and augmentations remain available, and infer only true orphans.
Traverse references in cached libraries so retries and overlapping loads
wait for missing dependencies instead of treating cached roots as done.
Include library directives from project files and acquired declarations
when selecting download roots.
Root the configured service in parsed TSConfig files rather than every
editable model, keeping excluded globals out of included source files.
Route imported files through their configured program and retain an
inferred service for documents that are genuinely outside the project.
Preserve compiler-provided replacement ranges instead of relying on
Monaco word boundaries, which split punctuation inside string literals.
Recover literal spans from the selected compiler's syntax tree when
older compilers omit them, including unfinished quoted strings.
Compute circular-buffer distances and offsets as unsigned values on
both sides of the transport so crossing signed and unsigned 32-bit
boundaries does not corrupt stdin or terminate the language server.
The reason will be displayed to describe this comment to others. Learn more.
🟡 Changes recommended
Unresolved defects can break type acquisition and navigation, omit compiler diagnostics, and leave initialization hanging, while repeated full-project synchronization adds unnecessary overhead.
Restrict version annotations to trailing comment tokens
packages/playground-v2/src/ata/discovery.ts:8
The version regex also matches text inside unrelated string literals later on the same line. For example, import "pkg"; const note = "// types: 1.2.3"; assigns the invalid selector 1.2.3"; to pkg, so automatic type acquisition fails despite there being no version annotation. Since both discovery implementations use this helper, associate annotations with actual trailing comment tokens rather than searching the entire remaining line.
This aggregate omits program-wide and global diagnostics, so configurations such as noLib: true can appear problem-free despite missing required global types. Incompatible compiler-option combinations can also go unreported. Include program.getProgramDiagnostics() and program.getGlobalDiagnostics() alongside the existing diagnostics.
Reject pending requests when the worker fails
packages/playground-v2/src/strada.ts:55
If the worker fails to load or emits an uncaught error or messageerror, pending requests never settle, so initialization can leave the loading overlay active indefinitely. Handle both events by rejecting and clearing pending requests and retaining the failure so subsequent requests reject immediately. Also terminate the worker when initialization fails, following NativeBackend.
Deduplicate concurrent declaration model creation
packages/playground-v2/src/strada.ts:533
The model-existence check happens before an asynchronous worker request. Concurrent definition/reference requests for the same unopened declaration file can both pass that check, then both call createModel; the second throws because Monaco already has that URI, causing navigation to fail. Recheck for an existing model after readFile resolves, or deduplicate in-flight model creation by URI.
Use each compiler's statement boundaries and comment ranges rather than
searching arbitrary remaining line text for version annotations.
Keep reference-directive annotations bounded by their real comment line,
including CR-only line endings.
Reject pending and future requests after worker errors or undecodable
messages instead of leaving initialization and editor requests hanging.
Terminate failed initialization, ignore late progress after failure, and
clear pending requests when disposing the backend.
Skip unchanged snapshots and send only changed or deleted files before
editor requests. Queue updates against the last acknowledged snapshot
so concurrent edits remain ordered and failed updates can be retried.
Cache library references per file and reuse parsed configuration instead
of rescanning declaration trees on each request. Keep script versions
monotonic when files are deleted and recreated.
The reason will be displayed to describe this comment to others. Learn more.
🔵 Needs a closer look
Human assessment is needed because subtle import-discovery and compiler-configuration interactions can leave declarations unavailable or unexpectedly change diagnostics and emitted output.
Document scrolling changes page coordinates during a gesture. Track
viewport movement instead so scroll chaining does not distort touch
deltas or inertia, and convert taps back to document coordinates.
Pass vertical movement that the editor cannot consume to the page,
including remaining momentum at either end of the code. Preserve
editor scrolling, taps, and touch interactions in embedded widgets.
Scroll the page, rather than hidden code, when a swipe heads toward an
editor edge outside the viewport. Keep that gesture on the page through
its remaining movement and inertia, preserving the code's scroll position.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
deploy-previewEnables automatic deployments to preview environments on a PR
4 participants
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This is an all new playground, which began as just making something to support TypeScript v7, but has turned into a feature-rich replacement with multiple files, real tsconfigs, multi file output, and more.