Skip to content
Merged
Show file tree
Hide file tree
Changes from 49 commits
Commits
Show all changes
53 commits
Select commit Hold shift + click to select a range
347fdfa
Migrate to React
celonymire Dec 10, 2025
bbbecca
Migrate to legend-state observer framework
celonymire Dec 10, 2025
ca4b817
Remove leftover reference of external
celonymire Dec 10, 2025
67e932f
Update instructions to mention React + @legendapp/state
celonymire Dec 12, 2025
b4975f4
Make Rspack alias React and define NODE_ENV to fix React ownership is…
celonymire Dec 12, 2025
0200323
Update instructions to remove TailwindCSS
celonymire Dec 12, 2025
325ff39
Final architecture updates to stylesheets
celonymire Dec 13, 2025
a4dc50a
Ensure TextHandler invariants are maintained in both strings
celonymire Dec 13, 2025
a072b6b
Set acceptedStdout for webview when trigger editing
celonymire Dec 13, 2025
4a1ddfd
Remove duplicate types.ts
celonymire Dec 13, 2025
87b5d14
Initial implementation of new Testcases UI
celonymire Dec 13, 2025
05429e7
Added a view for state of no opened files
celonymire Dec 13, 2025
a83ac19
Update instructions
celonymire Dec 13, 2025
31add23
Initial revamp of Stress Tester UI and added expanding text
celonymire Dec 13, 2025
52089e2
Add comment explaining why we force write newline on accepted stdout
celonymire Dec 13, 2025
b127828
Save the external runtime error from running the command
celonymire Dec 13, 2025
811bb38
Restrict accept icon further
celonymire Dec 13, 2025
9746438
Refactor out chunk callback into another method
celonymire Dec 13, 2025
d083763
Make the textarea stderr variant for certain states in stress tester
celonymire Dec 13, 2025
315fe9d
Add icons for commands that affect all testcases in judge title bar
celonymire Dec 13, 2025
a7fe300
Dual-weird div and textarea implementation to avoid empty trailing ne…
celonymire Dec 13, 2025
4686f6b
Remove unused divider class
celonymire Dec 13, 2025
e604326
Fixed alignment of Next Testcase button
celonymire Dec 13, 2025
028b7fc
Adjust margin of new testcase button icon
celonymire Dec 13, 2025
76e1a35
Implemented visibility change
celonymire Dec 13, 2025
7ab536c
Add back skip and toggle functionality
celonymire Dec 13, 2025
7436999
Allow scrollbar for long horizontal content
celonymire Dec 13, 2025
2c32b1b
Fix condition for accept answer icon
celonymire Dec 13, 2025
1afaa87
Make skipping apply visible opacity effect
celonymire Dec 13, 2025
69bac7e
Add styling to COMPILING status
celonymire Dec 13, 2025
ce538c9
Slightly reduce text size
celonymire Dec 13, 2025
b2e66d6
Refactor terminal handling to ensure readiness before writing output
celonymire Dec 13, 2025
92860a3
Re-implement problem settings (time limit)
celonymire Dec 13, 2025
e1ffa33
Updated view of compile error to be more distinctive
celonymire Dec 13, 2025
1d8c14f
Save compile error state
celonymire Dec 13, 2025
e2ad3e5
Fix linter errors
celonymire Dec 13, 2025
cccc739
Remove leftover debug code
celonymire Dec 13, 2025
30e9b05
Use ===
celonymire Dec 13, 2025
dc21deb
Removed unnecessary from judge view IO clearing upon save
celonymire Dec 13, 2025
9843012
Switch back to testcases view after saving
celonymire Dec 13, 2025
9caa990
Enhance the settings save button in judge settings
celonymire Dec 13, 2025
3b1617b
Add info on 0 value for time limit
celonymire Dec 13, 2025
2945ec0
Merge remote-tracking branch 'origin/ui-revamp' into ui-revamp
celonymire Dec 13, 2025
9d546d3
Don't need to handle enter key for save setting now that we have a bu…
celonymire Dec 13, 2025
e0bf1ad
Increment newline count in TextHandler
celonymire Dec 13, 2025
6c0049d
Remove extra space in class names
celonymire Dec 13, 2025
a121074
Update src/webview/judge/Testcase.tsx
celonymire Dec 13, 2025
8d85e5a
Update src/extension/utils/vscode.ts
celonymire Dec 13, 2025
d378515
Avoid redundant truthiness bypass
celonymire Dec 13, 2025
9ee6026
Make useLayoutEffect depend on value
celonymire Dec 13, 2025
15faac6
Calrify comment about TextHandler even more
celonymire Dec 13, 2025
02eac73
Update to use legend state's For
celonymire Dec 13, 2025
c765b8e
Update documentation to reflect Valibot schema integration and clarif…
celonymire Dec 13, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions .github/copilot-instructions.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,21 @@
This repository contains a VS Code extension that provides two webview-based tools for competitive programming: **Judge** and **Stress**.

- Extension backend code lives under `src/extension/**` and uses the VS Code API. `JudgeViewProvider` and `StressViewProvider` extend `BaseViewProvider`, which handles webview setup, CSP nonce generation, workspaceState storage, and message dispatch.
- Webview frontend code lives under `src/webview/**` and is built with Preact. It talks to the extension only through typed messages defined in `src/shared/*-messages.ts`.
- Webview frontend code lives under `src/webview/**` and is built with React + `@legendapp/state` for reactive state management. It talks to the extension only through typed messages defined in `src/shared/*-messages.ts`.
- Shared enums, message contracts, and types live under `src/shared/**` and define the protocol between extension and webviews (including the `Status` lifecycle and testcase structures).

Build and tooling:

- Use `bun install` to install dependencies.
- Use `bun run watch` during development and `bun run prod` for production builds. The build is two-stage: Tailwind CLI compiles `src/styles/global.css` to `dist/styles.css`, then Rspack bundles the extension and webviews into `dist/`.
- Run `bun run lint` and `bun run format` to apply ESLint (TypeScript + Preact) and Prettier rules.
- Use `bun run watch` during development and `bun run prod` for production builds. Rspack bundles the extension and webviews into `dist/`. Each webview has its own `index.css` stylesheet that is bundled alongside its JavaScript.
- Run `bun run lint` and `bun run format` to apply ESLint (TypeScript + React) and Prettier rules.

Design and implementation guidelines:

- All extension ↔ webview communication must use the discriminated unions and enums in `src/shared/*-messages.ts`. Append to enums instead of reordering to keep numeric values and stored data stable.
- Use `compile()` and `Runnable` from `src/extension/utils/runtime.ts` for running code, and `resolveVariables` / `resolveCommand` from `src/extension/utils/vscode.ts` for safe, cross-platform commands.
- Use `TextHandler` for streamed output; always call `.reset()` for a fresh run and `.write(data, last)` for updates.
- Use `@legendapp/state` for webview state: wrap components with `observer()`, access values via `.get()`, mutate via `.set()`, and use `<Memo>{() => obs$.get()}</Memo>` for direct DOM updates (e.g., streaming text).
- Keep changes minimal and consistent with existing patterns. Prefer reusing the Judge/Stress provider and webview patterns over introducing new architectures.

Additional path-specific details are defined in `.github/instructions/*.instructions.md`, which Copilot uses when working in matching files.
16 changes: 7 additions & 9 deletions .github/instructions/build-and-config.instructions.md
Original file line number Diff line number Diff line change
@@ -1,17 +1,15 @@
---
applyTo: "package.json,rspack.config.ts,eslint.config.ts,tailwind.config.ts,tsconfig*.json"
applyTo: "package.json,rspack.config.ts,eslint.config.ts,tsconfig*.json"
---

This repository uses Bun, Rspack, Tailwind CSS, TypeScript, and ESLint to build and lint the Fast Olympic Coding VS Code extension and its webviews.
This repository uses Bun, Rspack, TypeScript, and ESLint to build and lint the Fast Olympic Coding VS Code extension and its webviews.

When working on the build, config, or tooling files matched by this pattern:

- Use `bun install` to install dependencies. Prefer Bun scripts in `package.json` over ad-hoc commands.
- During development, run `bun run watch` to start Rspack and the Tailwind CLI in watch mode. For production builds, use `bun run prod` to generate minified, no-sourcemap bundles.
- The build is two-stage:
- `build:css`: Tailwind CLI reads from `src/styles/global.css` and writes `dist/styles.css`.
- `build:js`: Rspack bundles the extension backend and webview frontends into `dist/`.
- The Rspack configuration (`rspack.config.ts`) exports two configs: one targeting Node.js/CommonJS for the extension, and one targeting the web/ES modules for the webviews (TypeScript/TSX with Preact). Keep this separation intact when modifying the config.
- During development, run `bun run watch` to start Rspack in watch mode. For production builds, use `bun run prod` to generate minified, no-sourcemap bundles.
- Rspack bundles the extension backend and webview frontends into `dist/`. Each webview has its own `index.css` stylesheet that is bundled alongside its JavaScript.
- The Rspack configuration (`rspack.config.ts`) exports two configs: one targeting Node.js/CommonJS for the extension, and one targeting the web/ES modules for the webviews (TypeScript/TSX with React). Keep this separation intact when modifying the config.
- Type-checking is handled by ForkTsCheckerWebpackPlugin, using `tsconfig.node.json` for the extension and `tsconfig.app.json` for the webviews. Keep these project files aligned with the respective code trees.
- For quality gates, use `bun run lint` (ESLint with TypeScript + Preact rules) and `bun run format` (Prettier). Avoid adding overlapping or conflicting linters/formatters.
- Prefer minimal, focused config changes. Avoid introducing large new toolchains or build systems; extend the existing Rspack + Tailwind + Bun setup instead.
- For quality gates, use `bun run lint` (ESLint with TypeScript + React rules) and `bun run format` (Prettier). Avoid adding overlapping or conflicting linters/formatters.
- Prefer minimal, focused config changes. Avoid introducing large new toolchains or build systems; extend the existing Rspack + Bun setup instead.
3 changes: 2 additions & 1 deletion .github/instructions/extension-backend.instructions.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,11 @@ This repository is a VS Code extension called "Fast Olympic Coding." The `src/ex
When changing files under `src/extension/**`:

- Treat `JudgeViewProvider` and `StressViewProvider` as the main controllers for their respective webviews. They extend `BaseViewProvider`, which encapsulates webview setup, CSP nonce generation, message posting, and workspaceState access keyed by active file path.
- Webviews rely on Codicons for icons; `BaseViewProvider` already whitelists `@vscode/codicons/dist/codicon.css` in local resource roots and injects the stylesheet. Preserve that setup (CSP, resource roots, and link tag) whenever adjusting webview HTML or resource handling so icons keep rendering.
- All extension ⇄ webview communication must go through the discriminated unions and enums in `src/shared/*-messages.ts`. Do not introduce ad-hoc string message types; instead, extend the shared enums and message unions.
- The `Status` enum in `src/shared/types.ts` represents the lifecycle: COMPILING → RUNNING → (AC | WA | RE | TL | CE | NA | EDITING). Preserve existing numeric values and append new states only at the end.
- Persisted testcases and limits are stored in `workspaceState`, with a top-level key per view ("judge" / "stress") and an inner key per absolute file path. Treat the "default" state (no testcases and timeLimit = 0) as "no data" and delete storage entries rather than persisting defaults indefinitely.
- Use `TextHandler` (from the extension utilities) for all streamed output shown in the webviews. Always call `.reset()` before a fresh run and `.write(data, last)` to update output so truncation, batching, and whitespace handling remain correct.
- Use `TextHandler` (from the extension utilities) for all streamed output shown in the webviews. It must keep the full data for comparisons while truncating display output, normalizes CRLF to LF, and ensures a trailing newline on final writes. Always call `.reset()` before a fresh run and `.write(data, last)` to update output so truncation, batching, and whitespace handling remain correct.
- For compilation and execution, use the helpers in `src/extension/utils/runtime.ts`. Specifically, use `compile()` (which caches builds by md5 of the full command) and `Runnable` (which wraps child processes with timing, timeout via `AbortSignal.timeout`, and exit/timeout information) instead of spawning processes manually.
- In the Stress view logic, keep the sequential generator pattern that feeds testcases to the solution and reference solution, and ensure the loop respects both per-test (`stressTestcaseTimeLimit`) and global (`stressTimeLimit`) limits while exiting early on the first mismatch or failure for speed.
- Always resolve command variables via `resolveVariables` / `resolveCommand` from `src/extension/utils/vscode.ts` before spawning external processes. Use built-in variables like `${exeExtname}`, `${path:...}`, and `${fileDirnameBasename}` for cross-platform-safe paths.
Expand Down
14 changes: 11 additions & 3 deletions .github/instructions/webview-frontend.instructions.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,23 @@
applyTo: "src/webview/**/*.ts,src/webview/**/*.tsx"
---

The `src/webview/**` tree contains the Preact-based frontend code for the Judge and Stress webviews. These run in an isolated browser-like environment, not in the VS Code extension host.
The `src/webview/**` tree contains the React-based frontend code for the Judge and Stress webviews. These run in an isolated browser-like environment, not in the VS Code extension host.

When changing files under `src/webview/**`:

- Do not import the `vscode` module here; webview code should communicate with the extension only via the typed message contracts defined in `src/shared/*-messages.ts`.
- Treat the `App.tsx` components under `src/webview/judge/` and `src/webview/stress/` as entry points for each view. They receive initial state and subsequent updates exclusively through message types defined in the shared message unions.
- Codicons are the icon set used across the webviews. The backend already exposes `@vscode/codicons/dist/codicon.css`; prefer the existing `codicon-` classes instead of adding new icon libraries or custom SVG sprite sheets unless strictly necessary.
- When you need new messages or actions from the webview to the extension, first extend the shared enums and message interfaces in `src/shared/*-messages.ts`, then update both the extension providers and the webview components to handle the new types. Avoid magic string message names.
- Assume styles are provided by an external CSS file built from `src/styles/global.css` into `dist/styles.css` via Tailwind CLI. Do not import CSS directly into TypeScript/TSX; the extension side (`BaseViewProvider`) injects the stylesheet as a `<link>` in the webview HTML.
- Prefer the existing lightweight stack (Preact + signals) for state management. Avoid introducing heavier frontend state libraries; instead, follow the current patterns used in the Judge and Stress apps.
- Each webview has its own `index.css` stylesheet (e.g., `src/webview/judge/index.css`, `src/webview/stress/index.css`). Import it in the webview's entry file (`index.tsx`). The CSS is bundled by Rspack alongside the webview JavaScript.
- Use `@legendapp/state` for reactive state management:
- Wrap components with `observer()` from `@legendapp/state/react` for automatic re-rendering.
- Access observable values with `.get()` and mutate with `.set(value)` or `.set(prev => newValue)`.
- Use `<Memo>{() => obs$.get()}</Memo>` for direct DOM updates that bypass VDOM diffing (ideal for streaming stdout/stderr).
- Use `useObservable(value)` for component-local observable state.
- Collections like `Map` and `Set` have fine-grained reactivity; use `state$.map.get(key)` to get an observable for a specific entry.
- Avoid introducing additional state libraries; follow the patterns in the Judge and Stress apps.
- Keep UI logic decoupled from process execution details. The webview should focus on rendering state and sending/receiving typed messages, not on spawning processes or resolving filesystem paths.
- Maintain consistency with existing components such as `AutoresizeTextarea`, `Testcase`, and `State` in terms of props, message handling, and minimal DOM manipulation.
- Keep the file layout lean (e.g., flat component files per view) and avoid introducing extra nested directories unless there's a clear benefit; mirror the existing Judge/Stress structure when adding new pieces.
- Keep changes surgical: avoid large-scale refactors or stylistic rewrites unless they are necessary for a specific task.
5 changes: 3 additions & 2 deletions .vscodeignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
!LICENSE
!media/icon.png
!dist/judge/index.js
!dist/judge/index.css
!dist/stress/index.js
!dist/extension.js
!dist/styles.css
!dist/stress/index.css
!dist/extension.js
Loading