mirror of
https://github.com/stablyai/orca.git
synced 2026-10-31 17:17:38 +00:00
4d22306d259a9c2b94c8ec6d120e673f2e5b00a4
22
Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
e268135719 |
feat(native-chat): chat agents are offered wherever their chat program runs, not only where their CLI is installed (#28709)
* feat(acp): ACP agents can declare a managed runtime installed on first chat start An ACP launch spec may name a pinned runtime Orca installs under its locked data folder. The stock lookup searches it last (Command, PATH, install directories, managed folder); a start whose lookup missed installs it under the acquisition's signal, then resolves the launch again. A Command setting, restart-recovery reads and catalog probes never install. The pinned-runtime materializer can now publish a verified multi-member folder: extract once into staging, check each member's sha256, rename into place, with a per-asset download size limit. Node's runtime path is unchanged. * Fix ACP managed runtime lookup precedence * feat(acp): ACP agents can run with a private per-process temp folder * feat(acp): old managed runtime versions are removed at host start Once per host start, the ACP registration removes every version beside an agent's current managed runtime folder, and staging left by an earlier process. One host owns the data root and ACP servers are never reattached across host runs, so nothing runs from them. This process's own staging is kept (a publish may be in flight). Best effort: a failure is logged and never holds up a launch. * feat(acp): a sign-in prompt on an ACP agent's stderr ends the start or turn signed out An agent that waits for a browser sign-in prints a link on stderr and blocks for minutes. A launch spec can now name that line (signInPrompt); the connection then closes with a typed sign-in failure through the existing process owner, so a start reads notSignedIn and a running turn fails signed out instead of settling unknown. The matched line, which carries the sign-in URL, never enters the retained stderr tail, errors or diagnostics. * Prevent sign-in URLs leaking from long stderr lines * feat(acp): an agent can enforce the permission mode itself through a session config option An optional launch-spec field names the session config option and its ask/full values. Every new or reopened session gets the value for the chat's full-access posture before it is exposed, and a refusal fails the start. With the field present Orca no longer answers permission requests for the person. No agent sets it yet. * fix(acp): reject unconfirmed permission mode during acquisition * feat(acp): an agent enforcing the permission mode itself runs the chat's own mode The launch spec maps each chat permission mode to its session option value; a start sets the value for the mode the host launches with (ask when it names none), replacing the global Agent Permissions full-access read. A mid-chat change takes effect through the host's existing restart of a child launched with another mode before the next send. * Keep ACP session acquisition within the line limit * feat(acp): open Antigravity in the Chat UI over its ACP server With the experimental chat setting on, Antigravity chats run Google's Antigravity ACP server, which Orca installs on the first chat start: a pinned 1.3.0 release whose archive and both executables are verified by hash (macOS arm64/x64, Linux x64/arm64). Each host keeps one private sign-in folder for these chats under Orca's data folder, made owner-only before every start; the server keeps its sign-in there as a file. A chat signs in with the server's Google method through the existing auth-required retry; with no saved sign-in the server's sign-in prompt ends the chat signed out. The Agent Permissions setting maps to the server's own mode, and a question the server asks shows as a question that takes one of its choices, never auto-answered. A chat reopens its session with session/resume. * fix(acp): separate Antigravity chat command and require pinned host * test(acp): assert Antigravity launch arguments across hosts * feat(acp): Antigravity chats offer Ask, Accept edits and Full access per chat Each mode maps to the server's own (default, auto_edit, yolo). No Approve for me: the server has no automatic reviewer. Accept edits gets its own description, since auto_edit approves file edit tools only. * feat(native-chat): offer host-provided chats without their CLI detected A host now marks each agentSession.agents row whose chat program Orca provides there (an ACP managed runtime with a pinned build on this host). With Chat UI on, the tab-bar picker, the empty-workspace default chat and the new-agent shortcut offer those agents beside the detected ones when the launch opens as a chat. Terminal launches still follow detection, and an older host that sends no mark keeps today's detection-only offer. * Fix CLI-free chat fallback and picker updates * Fix admission refusal reason test expectation * feat(native-chat): the host health snapshot says whether each chat's program is on the machine Antigravity's chat runs Orca's own download of Google's ACP program, not the agy CLI, so clients could not tell from CLI detection whether it can open as a chat. Each snapshot row now carries an optional chatProgram (available, installable, missing, unknown), found through the agent's own launch resolver without spawning anything, and re-derived after a managed runtime install or removal. Health state and reason are unchanged, so older clients decode the frame as before. * feat(native-chat): one renderer reading of whether an agent can open as a chat on its host Pickers asked CLI detection whether an agent can open as a chat, which is wrong for Antigravity, whose chat runs a program Orca downloads. This module answers from the host's published chat program fact, and for hosts that publish none, from the host's managed-runtime mark and install capability or else CLI detection. Facts not yet learned read as unlearned, not as no. * fix(native-chat): a declined chat opens its agent's terminal only where the CLI is installed Once a chat can be offered without its CLI, a host refusal used to fall back to a terminal that runs a CLI that is not there. The one admission boundary now reports the host's refusal instead when the workspace host's detected agents lack the CLI, for new-tab, work-item and workspace creation launches alike. A caller's own fallback, like the empty workspace's shell, still opens. * feat(native-chat): the + menu and Settings offer a chat wherever its program runs With Chat UI on and no agy CLI, Antigravity had no chat row in the + menu (or a disabled 'Not installed' one when switched on), because both read CLI detection. The menu now reads the host's chat-program answer: a chat row where the program runs or installs from the chat, no '(CLI)' row or terminal button without the CLI. A failed CLI check no longer keeps the menu from learning that answer. Settings shows an unchosen provider on when its CLI or the program Orca runs for it (downloaded or found outside Orca) is installed, and holds the switch until that is known. A saved default that opens as a chat no longer says it is not detected. * feat(native-chat): a default agent that opens as a chat starts without its CLI An empty workspace and the new-agent shortcut skipped a default agent whose CLI is not detected, even when it opens as a chat on that host (Antigravity without agy). Both now honor that default, waiting briefly for the host's chat facts when they are not known yet, while the automatic pick with no default still chooses only detected agents. Blank and the shell fallback are unchanged. * feat(native-chat): new workspaces, work items, continuations and the dashboard offer chat-only agents The new-workspace composer, work-item launches, session continuation and the dashboard launcher listed only agents whose CLI is detected, so an agent that opens as a chat without its CLI could not be picked, and an explicit pick of it was dropped. They now also offer agents that open as a chat on the workspace's host, keep such an explicit choice, and the dashboard republishes when the host's chat facts arrive. Automatic picks still choose only detected agents. * feat(native-chat): Source Control and Fix Checks accept a chosen agent that opens as a chat The Source Control action dialog, its saved auto-start, the checks panel, recovery launches and Fix Checks (before and after its workspace exists) rejected a saved or default agent whose CLI is not detected, even where it opens as a chat. They now accept it there and list it, through the shared source-control pick, while the automatic pick still chooses only detected agents. * fix(native-chat): an empty workspace does not wait on chat facts for a Claude or Codex default Claude and Codex have no program Orca downloads, so without their CLI only the host's own answer could offer them as a chat; holding the workspace empty for the host's agent list could not change that. * test(native-chat): pin the chat-program fact, cold explicit defaults and the CLI-less decline Covers the host's program lookup and its re-read after an install, older and unknown snapshot values falling back to the managed mark and install capability of the same host, an explicit default opening as a chat with CLI detection failed while automatic and blank picks stay on detected agents, kept composer and saved Source Control choices, and a declined chat reporting the refusal instead of opening a terminal for a missing CLI on both launch paths. * refactor(source-control): the action dialog's agent list lives in its own hook The dialog hook was over the file-length limit after it learned which agents open as a chat without their CLI; detection and that offer now live together in use-source-control-launchable-agents. * fix: typed test mocks and record the dialog's pre-existing reset effect The Source Control dialog's open-cycle reset effect was already on main; the changed-code gate reported it because the effect now also learns which agents open as a chat. * fix(native-chat): a declined chat refuses its terminal only when the CLI is known to be missing When a host declines a chat, Orca falls back to that agent's terminal. A chat can now be offered without its CLI, so the fallback must not open a terminal that cannot start. But a failed or still-pending CLI check is not proof the CLI is missing: treating it that way blocked a working terminal fallback (for example an OpenCode version that runs in a terminal but not as a chat). Each detection producer (local, paired server, SSH) now records the outcome of its latest attempt for the exact target, next to the IDs it already keeps. The decline check refuses the terminal only when the same host's latest attempt succeeded and did not list the CLI; pending, failed or unresolved outcomes keep the existing fallback, and a caller's own shell fallback is untouched. * fix(native-chat): every launch surface learns whether a chat opens before it decides A chat whose program runs on the host without its CLI (for example Antigravity) could be missing, greyed out or swapped for another agent depending on which surface launched it: the composer dropped an explicit pick while the host was still answering, Fix Checks and the Checks panel refused a saved chat agent, an inactive paired host was never asked about its chats, the Providers switch flashed off, and session continuation auto-picked an agent that was only offered. One lease per host, runtime and pairing now acquires the host's agent list and health stream for whoever needs it: the + menu, composers, Settings, the dashboard and its pop-out, Source Control and Checks, Fix Checks, work items, shortcuts and continuation. Actions wait for those facts within one bounded deadline (ordinary CLI detection keeps its own wait), cancel when the workspace's host is genuinely replaced, and re-read settings before launching. A saved, default or explicit choice may open as a chat without its CLI; automatic picks still come only from detected agents. Pending or unknown facts never erase a choice or flash a switch off. The dashboard's holds are reconciled by the publishers that read them, and a hold that notifies while it is being created no longer leaks a second stream holder. * fix: the new-workspace composer memoizes its launch workspace from its own fields * fix: a declined chat reads the launch host's own agent inventory; test fixtures match their types * fix: work-item launches detect before waiting on chat facts; the composer and Source Control list agents from one owner The composer card no longer holds its own chat-facts lease beside its modal's, Source Control reads agent inventory only while its dialog is open, and a work-item launch keeps the new workspace's own detection when the store has not loaded that workspace yet. * fix(native-chat): keep acquisition tied to the current host resource * fix(native-chat): verify the current acquisition before returning choices * fix(i18n): retain legacy terminal-list English entries in the runtime catalog * fix(native-chat): the dashboard republishes launch options when the active workspace's host changes Both dashboard publishers now watch the active workspace and its selected host, which own its launch options. Two QuickLaunchButton tests assert the current "couldn't list terminal agents" wording. Restores base forms and drops a duplicate workspace helper to stay inside the change budget. * test: the dashboard publisher test reads its watched state from the function it tests * fix(native-chat): dashboards watch one checked route-input view; saved Source Control discovery settles every outcome Both dashboard publishers observe and derive launch options from one exhaustive, compiler-checked view of the store slices the launch-route readers take, so a route input can no longer be missed by one list. A saved Source Control action's discovery now ends as success, cancelled or failed; only success can auto-start, and a cancelled or failed attempt reveals the editable dialog instead of launching on a replacement runtime. Restores base forms and shares one worktree workspace helper to stay inside the change budget. * style: format the runtime metadata resolver * fix: merge duplicate imports the code-quality gate rejects * test: the dashboard watch fixture seeds every route-input field * test: the dashboard watch fixture is fully typed without a cast * fix: an unknown agent scan stays unknown for Fix Checks and recovery, and a saved Checks agent keeps its message * fix: the action-first chat path asks the same missing-CLI check before opening a declined terminal; compact to the size cap * refactor: compact the chat-program changes to the size cap after merging main * Pickers list an agent that can't open here as disabled with its reason instead of hiding it The Create workspace and continuation pickers only searched the agents the caller could launch, so an enabled agent with no chat on this host (for example Antigravity when the host can't run it) lost its disabled row, while the + menu showed it. * Continuation test accepts more than one disabled subfolder row now that disabled rows are listed * Re-run CI: the code scan was cancelled across the repository * test: cover chat selection without terminal CLI * test: compact host chat program fixtures |
||
|
|
c089ca5812 |
fix(ci): preserve rename boundaries in React Doctor gate (#32159)
* fix(ci): preserve rename boundaries in React Doctor gate * fix(ci): retain coverage and reject inconsistent audit reports * test(ci): update Git status fixture for rename-aware ranges |
||
|
|
2004d0c7d1 |
perf: batch changed-code quality baseline reads (#29435)
Co-authored-by: OrcaWin <293788423+OrcaWin@users.noreply.github.com> |
||
|
|
31b2b17d9b |
refactor(wsl): move the WSL guest bundle sources out of src/relay (#27174)
* refactor(wsl): move the WSL guest bundle sources out of src/relay The WSL hook relay and WSL browser network relay are built from src/relay but are not part of the SSH relay. Move them, and the 46 relay modules the hook relay bundles, to src/wsl-guest so the SSH relay can be deleted on its own. Pure renames; the built bundles are byte-identical. Adds a boundary test so nothing outside src/relay imports it except relay tests. * fix(ci): exempt renamed files' existing lint debt in the changed-lines gate * test(relay): keep the cast suppression on the wrapped line * test(relay): only parse files that mention relay in the import boundary check --------- Co-authored-by: m4air <m4air@Mac.localdomain> |
||
|
|
4a5f00f46f |
Normalize base source once while checking changed-code diagnostics (#24557)
Reuse the exact existing moved-code matching algorithm with run-local lazy normalization of immutable base source blocks across diagnostics. |
||
|
|
eb44511992 |
fix(jira): discard detail replies after closing an issue (#24835)
Co-authored-by: OrcaWin <293788423+OrcaWin@users.noreply.github.com> |
||
|
|
080c562898 |
perf(ci): diff against the merge commit's first parent so PR checkouts can be shallow (#23562)
Every changed-path gate asked git for `--merge-base "$BASE_SHA" "$HEAD_SHA"`, which needs the event payload's base SHA to be in the local graph. That is the only reason two jobs cloned all 8127 refs' history. On a pull_request checkout HEAD is already the merge commit, so its first parent is the base side and no merge base has to be computed. config/scripts/git-pull-request-diff-base.mjs resolved that for the two Node gates; the workflow's inline gates now use the same helper through a small CLI rather than open-coding it. code_paths gates all 22 jobs, so its checkout is charged to the start of every one of them: measured 20.7s to 1.6s, keeping blob:none because its sparse tree is ~7 files and leaves no blobs to refetch. Static analysis drops the filter instead, since populating all 30,226 files makes blob:none force a second promisor fetch: 23s to ~11s. Verified on a real merge ref. At depth 50 the old and new forms produce identical changed-file sets. At depth 2 the new form still works and the old one fails with `fatal: bad object`, which is the failure a stale base would have caused once the checkout stopped being complete. Also drops the dead resolveBase + merge-base prelude in the changed-code gate, whose result resolvePullRequestDiffBase already discarded on every PR. |
||
|
|
fbe7b194b8 |
fix(quality-gate): let the changed-code gate see the focused import plugins (#20912)
import/no-duplicates was reachable only through the repo-wide CI audit, so an author's first signal was a red static analysis job after push. |
||
|
|
22ce8d69a1 |
fix(lint): enable anti-slop/no-module-mocking (#20783)
The rule rejects `vi.mock` / `vi.doMock` / `vi.unstable_mockModule` and the
`jest` equivalents, on the argument that a test which rewrites the module graph
asserts against a stand-in the production code never sees. It is already off for
`**/*.test.{ts,tsx}`, `**/*.spec.{ts,tsx}`, `tests/**` and `**/__mocks__/**` via
the existing override in config/oxlint-anti-slop.json; that override is
unchanged here. What the rule actually catches is module mocking that has drifted
out of a spec and into a first-party `.ts` support module, where nothing marks it
as test-only.
73 violations at baseline, all of them in test-support code. 9 were relocated
back into spec files the override already exempts; the remaining 64 sit in 10
files that are test-only but do not match the override globs, and carry a
file-level disable naming the rule and the reason.
Relocated:
- terminal-hydration-store-test-bootstrap.ts: the sonner / sync-runtime-graph /
pty-transport `vi.mock` calls moved into the two specs that import it
(terminals-hydration-canonical-rows, terminals-hydration-canonical-pty-overlap).
Vitest hoists `vi.mock` inside a test file, so registration is strictly earlier
than the previous module-eval-time call; the bootstrap keeps only the preload
API proxy. Both importers were updated.
- ipc-events-ssh-authority-test-fixtures.ts: the 6 direct-ssh `vi.doMock` calls
moved into useIpcEvents-agent-status-ssh-authority.test.ts as a local
`stubDirectSshModules()` helper, which also de-duplicates the three copies the
spec already had inline. The fixture now returns the store state and coordinator
doubles it builds, typed via the exported DirectSshReconnectCoordinatorDouble.
Suppressed, with justification (each is `/* oxlint-disable
anti-slop/no-module-mocking -- ... */`, rule named, no blanket disable):
- config/scripts/headless-serve-shutdown-matrix.test.mjs (1) - a genuine Vitest
spec that the override misses only because its globs say {ts,tsx}. The script
under test is a top-level CLI module; the alternative is spawning real docker.
- src/main/codex-accounts/runtime-home-service-test-harness.ts (1) - stubs one
probe predicate in ../pty/shell-startup-env, imported directly by several
main-process readers; 17 specs share it.
- src/main/computer/desktop-script-provider-test-harness.ts (2) - stubs
child_process/fs-promises for a provider that shells out; 8 specs share it.
- src/main/github/work-item-search-test-harness.ts (4) - one consumer lives in
tests/e2e, where the relative mock ids resolve differently, so moving the calls
into the specs would silently stop mocking there.
- src/renderer/src/components/automations/automations-page-test-harness.tsx (14)
- the mount rig for 10 AutomationsPage specs.
- src/renderer/src/components/terminal-pane/remote-runtime-pty-transport-test-harness.ts
(1) - stubs refreshWebRuntimeSessionTabsSnapshot, imported directly by several
renderer runtime modules; 18 specs share it.
- src/renderer/src/hooks/ipc-events-agent-status-window-test-fixtures.ts (7) -
stubReactSyncEffect/stubAuxiliaryModules, shared by 11 specs.
- src/renderer/src/hooks/ipc-events-close-routing-test-harness.ts (11) - stubs
and hook invocation are one unit; 4 specs share it.
- src/renderer/src/hooks/ipc-events-terminal-create-test-harness.ts (13) - its
only spec is at 799 of an 800 max-lines budget.
- src/renderer/src/hooks/ipc-events-test-harness.ts (10) - shared by 8 specs.
No violation was converted to real dependency injection, and no max-lines disable
was added.
Verified: the audit command exits 0 with no output (and reports errors on a
planted probe, so the rule is live); node config/scripts/run-typecheck-projects-in-parallel.mjs
exits 0; 354 spec files / 2506 tests covering every importer of every touched
file pass. No mobile/ file was touched.
The changed-code quality gate's root Oxlint scan runs without --config so it never
loads the anti-slop JS plugin, which made all 10 of those file-level suppressions
read as "Unused oxlint-disable directive". check-changed-code-quality.mjs now
exempts directives naming an anti-slop rule from that unused-directive warning,
the same carve-out isCastingDirectiveUnusedWarning already makes for the casting
suppressions the casting config enforces. Such a directive can never suppress a
root-config rule, so nothing the root scan would otherwise report is hidden;
audit:anti-slop remains the scan that enforces the rule.
|
||
|
|
b61a2347b9 |
feat(design-system): gate renderer UI with @shadcn/lint (#20731)
* feat(design-system): gate renderer UI with @shadcn/lint Wires shadcn-ui/lint's Oxlint plugin into the two places this repo already ratchets: the changed-lines PR gate for rules the renderer can't satisfy today, and `pnpm lint` for the one that is already at zero. - config/oxlint-design-system.json: no-restyle (layout allowed), no-raw-colors, require-static-classes -- scoped to src/renderer/**/*.tsx, run over added lines only. Measured at 10 findings across the last 60 commits (771 changed files), so it holds the line without a migration. - config/oxlint-dead-classes.json: no-unknown-classes repo-wide, with the renderer's plain-CSS hook namespaces allow-listed. Now at zero. - no-inline-styles and no-arbitrary-values stay off; STYLEGUIDE says why. Fixes the three live bugs the linter found: - `--editor-surface` never reached `@theme inline`, so `bg-editor-surface` generated no CSS -- 12 editor/artifact/notebook panes fell through to the page background instead of #1e1e1e in dark mode. - `scrollbar-none` is not a Tailwind utility and was declared nowhere, so the remote file browser breadcrumbs showed the scrollbar they meant to hide. Declared as a real `@utility`. - Notebook markdown cells used `markdown-preview-body`, which no stylesheet defines; the styled class is `markdown-body`. They rendered unstyled. * ci: run the dead-class gate in PR CI `pnpm lint` gained check:dead-classes, and pr-workflow-lint-parity requires every `pnpm lint` step to have a matching step in pr.yml. * fix(notebook): keep markdown theme selectors working |
||
|
|
182cd4c2f7 |
Add code quality lint for type assertions (#19462)
* Add casting code quality lint scan Enforce type assertion style by adding a new oxlint scan with `typescript/consistent-type-assertions` rule. Requires using `as const`, type annotations, or `satisfies` instead of raw type casts, with documented `SAFETY:` exceptions for unavoidable cases. * fix minor issue |
||
|
|
c37413271e |
perf(mobile): open a session with parallel startup RPCs and a pre-warmed terminal engine (#19260)
Startup RPCs now fan out in parallel and the xterm engine pre-warms inside the real terminal frame while they are in flight, so the first pane inherits a warm WebView and an already-measured viewport instead of paying a round trip for it. The pre-warm opens its engine before measuring: web-ready only reports that the bundle loaded, and the WebView answers a measure with null until a terminal exists. It also pre-warms at the user's saved text size, because cell size is what the frame height gets divided by. Host writes such as worktree.activate wait for an evaluated status.get reply. Navigation still fails open when a host cannot answer one, but that fallback no longer reads as a passing compatibility verdict. |
||
|
|
3eec77c11a |
chore(cloud): add the relay fence broker, ops console, Terraform root, scripts, and 24 cloud-* workflows (#18413)
Phase 6 of the relay split: the relay's deploy/operate surface moves under cloud/ with 24 cloud-* workflows gated on ORCA_CLOUD_OPERATIONS_ENABLED, the Cloud SQL rollout lease action, the relay Terraform root (dual-accept identities for both repositories), scripts, docs, CODEOWNERS, and a terraform validate job in Cloud Verify. |
||
|
|
3ae51076b1 |
fix(tooling): run oxlint gates without a Windows .cmd shim (#17894)
* fix(tooling): run oxlint gates without a Windows .cmd shim
`check:code-quality:changed` spawned `pnpm.cmd` without a shell, which Node
refuses under the CVE-2024-27980 mitigation, so the gate died with EINVAL
before linting anything. Resolve oxlint's own Node bin and run it under this
process's node instead — no shim, no shell, no quoting question — and add a
ratchet so the idiom cannot spread back into config/scripts.
* fix(tooling): validate the react-doctor diff base and widen the shim ratchet
`base` reaches cmd.exe unquoted on the shell fallback, so reject anything
outside a git revision before spawning. The ratchet matched only a handful of
runner names, which let `vitest.cmd` through even though config/scripts already
spawns vitest, playwright and electron-builder; match any batch-shim literal
instead, walk subdirectories, and cover tests/tools.
* docs(tooling): state what the shim ratchet and diff-base check miss
Both comments read as complete accounts of their guard's coverage. The revision
class rejects reflog syntax like HEAD@{1}, deliberately, since braces have no
business in a cmd.exe-bound argument; the ratchet misses a drive-lettered
literal because a colon is not in its class. Say so beside the template-literal
ceiling already noted.
---------
Co-authored-by: Orca Worker <orca-worker@localhost>
|
||
|
|
b94a65a4fc |
fix(lint): preserve TaskPage effect suppressions after split
(cherry picked from commit
|
||
|
|
b3912ebed2 |
Split up combined-diff viewer into feature-organized modules (#17341)
* Reorganize combined-diff components into feature-organized structure Splits flat combined-diff files into feature-focused subdirectories (browse-files, load-sections, resolve-changes, review-controls, scroll-viewport) to improve code organization and reduce clutter in the editor directory. Groups related logic by concern for easier navigation and maintenance. * Split up combined-diff viewer into feature-organized modules Decompose the 221-line monolithic CombinedDiffViewer into smaller, focused modules organized by feature: entry resolution, section loading, view state memory, file tree navigation, review controls, and scroll viewport handling. Main component now composes these hooks to orchestrate the combined-diff view. * fix(combined-diff): prevent replayed preference writes Move preference write outside state updater callback since React may replay state updaters, causing multiple writes. Add sideBySide to dependency array. * fix(combined-diff): re-resolve sections by key to handle list rebuilds The section list can rebuild while a write is pending (due to rebase, file changes, etc.); re-resolve by key instead of stale index to apply updates to the correct section. - Convert skipped conflicts message to structured i18n plural forms - Add oldPath field to git status signature for rename tracking * Suppress react-doctor diagnostics in combined-diff feature Add suppressions for react-doctor diagnostics that are necessary patterns for the combined-diff implementation, configured in both the quality check script and package.json. |
||
|
|
e361da7fb7 |
Deleting skill (#16357)
* Add skill deletion with cross-platform transaction safety Implements end-to-end skill removal with placement enumeration, dependency guards, and transactional recovery. Covers native, WSL, and remote hosts; users can delete canonical directories and alias placements (symlinked directories or files) in a single atomic batch. Includes UI selection flow, preview, confirmation, and results band. Block reasons (bundled, plugin, unowned, stale) gate deletions that would fail or contradict user intent. * Organize IPC handlers into module subdirectories Move register-core-handlers and skill-delete-ipc-handlers into dedicated subdirectories for improved code organization and to reduce the flat structure in src/main/ipc/. * Make skill deletion recovery transactions idempotent Defer journal cleanup until both staging removal and receipt cleanup succeed, leaving the journal in place for startup to retry if either operation fails. This ensures the recovery process is safe to run multiple times without leaving partially-deleted skills. * Consolidate skill-delete files into dedicated module Reorganize skill deletion functionality into a modular structure under `src/main/skills/skill-delete/` with simplified file names. Remove the redundant `skill-delete-` prefix from file names since they now live in the dedicated directory. Update all import paths throughout the codebase to reflect the new structure, including imports from IPC handlers and RPC methods. * Fix broken import paths and add deletion robustness improvements Import paths using `..//'` were invalid and broken. Replace with explicit module names (`skill-discovery-sources`, `skill-install-filesystem`, etc.) to clarify dependencies. - Bind WSL filesystem methods to preserve `this` context - Keep recovery journal when rollback rename fails, so startup can retry - Skip symlink-based tests on Windows where they cannot run - Only treat ENOENT/ENOTDIR as empty directories; propagate other errors - Fix cross-platform path parent calculation to handle drive roots - Replace shared constant with localized string for user-facing message - Use `runProcess` for WSL integration test instead of bare `execFile` * Add batch limit for skill deletion and improve host availability checkin - Limit concurrent deletions to prevent remote host overload - Add retry logic for capability probing to handle transient unavailability - Add reprobe() method to recheck capability after errors or user refresh - Fix status logic: receipt cleanup is best-effort, completion depends only on content removal - Improve error message for unreachable hosts |
||
|
|
6faaf3af74 |
fix(lint): match moved code by ordered near-match, not strict contiguity (#16385)
A diagnostic's span often reaches past the block a split moved — most commonly to a hook dependency array, which legitimately grows when closure variables become props. Requiring every line of the span to match contiguously reported the moved body as new. The block must still start at the same line in the base and appear in order, and >=90% of it must be present. Genuinely new code shares neither the anchor nor the ordering. |
||
|
|
33c9353f29 |
fix(lint): exempt verbatim-moved code from the changed-lines quality gate (#16359)
A file-splitting refactor makes every line of the new module an added line, so pre-existing lint debt in code that merely moved starts failing the gate. The only way to satisfy it is to edit the moved code, which is what a behavior-preserving refactor must not do. Exempt a diagnostic when its highlighted lines already existed verbatim and contiguous in the base revision. |
||
|
|
89f32a121b | fix(lint): restore nested config discovery in changed-code gate (#11130) | ||
|
|
e551d3ec0d |
perf(lint): consolidate code-quality gates into Oxlint (#11117)
Consolidate standalone code-quality scanners into Oxlint, preserve focused native/type-aware enforcement, add custom plugin coverage, and harden deferred PTY test cleanup. |
||
|
|
12ef12c55b |
chore(quality): ratchet Oxlint, React Doctor, and Zustand performance (#11034)
* chore(quality): ratchet lint and Zustand performance * fix(ci): stabilize React peer lock snapshot * fix(ci): isolate PR diff and React Doctor CLI |