Feat/apex test runner - #2005
Conversation
There was a problem hiding this comment.
Pull request overview
Adds the new Apex Test Runner feature to Jetstream (UI + routing + docs), incorporating fixes identified during live-org browser verification (coverage object name, run progress counting, table height behavior, and coverage source modal behavior).
Changes:
- Introduces a new
@jetstream/feature/apex-test-runnerlibrary with test selection, suite management, run monitoring (polling + abort), and coverage viewing (including Monaco line decorations). - Wires the feature into app routing + navigation (web app, desktop client, canvas, and browser extension), plus analytics/constants.
- Adds documentation + landing-page marketing copy and updates e2e routing coverage.
Reviewed changes
Copilot reviewed 48 out of 56 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| tsconfig.json | Adds TS project reference for the new feature lib. |
| tsconfig.base.json | Adds path alias for @jetstream/feature/apex-test-runner. |
| libs/types/src/lib/salesforce/apex.types.ts | Adds strongly-typed Salesforce Tooling API records for test runs/results/coverage/suites. |
| libs/shared/ui-router/src/lib/ui-router.ts | Adds APEX_TESTS route metadata (path, docs link, “new until”). |
| libs/shared/ui-core/src/app/HeaderNavbarItems.tsx | Adds Apex Test Runner to the header “Developer Tools” menu. |
| libs/shared/ui-core/src/app/AppHome/AppHome.tsx | Adds Apex Test Runner to the home page Developer Tools cards. |
| libs/shared/constants/src/lib/shared-constants.ts | Adds IndexedDB key, analytics events, and page title for Apex Tests. |
| libs/features/apex-test-runner/vite.config.mts | Adds Vitest/Vite config for the feature library. |
| libs/features/apex-test-runner/tsconfig.spec.json | Adds TS config for tests. |
| libs/features/apex-test-runner/tsconfig.lib.json | Adds TS config for library build/typechecking + references. |
| libs/features/apex-test-runner/tsconfig.json | Adds base TS project config for the library. |
| libs/features/apex-test-runner/src/useApexTestSuites.ts | Hook for loading/managing test suites + memberships. |
| libs/features/apex-test-runner/src/useApexTestRunsList.ts | Hook for polling recent test runs and merging optimistic rows. |
| libs/features/apex-test-runner/src/useApexTestRun.ts | Hook for polling a single run’s detail + abort/resume behavior. |
| libs/features/apex-test-runner/src/useApexTestClasses.ts | Hook for discovering/caching org test classes + methods via SymbolTable. |
| libs/features/apex-test-runner/src/selection/TestSuiteManagerModal.tsx | UI for creating/renaming/deleting suites and managing memberships. |
| libs/features/apex-test-runner/src/selection/TestClassSelectionRow.tsx | Row UI for selecting a class and (optionally) individual methods. |
| libs/features/apex-test-runner/src/selection/TestClassSelection.tsx | UI for filtering/selecting test classes (including “unknown” classes). |
| libs/features/apex-test-runner/src/selection/RunTestsTab.tsx | “Run Tests” tab: selection + launching runs + suite execution. |
| libs/features/apex-test-runner/src/runs/TestRunsTable.tsx | Runs list table with progress and selection behavior (capped height support). |
| libs/features/apex-test-runner/src/runs/TestRunsTab.tsx | “Test Runs” tab: refresh/pause, selection, and detail display. |
| libs/features/apex-test-runner/src/runs/TestRunResultsTable.tsx | Per-method results table for a selected run. |
| libs/features/apex-test-runner/src/runs/TestRunDetail.tsx | Selected run detail header, abort/resume controls, queue badges, results. |
| libs/features/apex-test-runner/src/runs/TestResultDetailModal.tsx | Modal for full test failure message/stack trace + debug log link. |
| libs/features/apex-test-runner/src/runs/test-run-utils.tsx | Shared status/outcome badge mapping + duration formatting. |
| libs/features/apex-test-runner/src/index.ts | Public export surface for the feature. |
| libs/features/apex-test-runner/src/coverage/useCoverageDecorations.ts | Monaco editor line/gutter decoration management for coverage. |
| libs/features/apex-test-runner/src/coverage/CoverageTable.tsx | Coverage aggregates table with quick-filter support. |
| libs/features/apex-test-runner/src/coverage/CoverageTab.tsx | “Code Coverage” tab: org-wide + per-class coverage listing + refresh. |
| libs/features/apex-test-runner/src/coverage/CoverageSourceModal.tsx | Fetches and displays source + line-level coverage, with stale-row guidance. |
| libs/features/apex-test-runner/src/coverage/coverage-utils.ts | Coverage percentage calculation helper. |
| libs/features/apex-test-runner/src/ApexTestRunner.tsx | Feature page container (tabs + optimistic run handling + route wiring). |
| libs/features/apex-test-runner/src/apex-test-runner-types.ts | View models and selection/cache types. |
| libs/features/apex-test-runner/src/apex-test-runner-symbol-table.utils.ts | SymbolTable distillation into cached test metadata. |
| libs/features/apex-test-runner/src/apex-test-runner-data.utils.ts | Tooling API query builders + fetch/mutate helpers (runs, suites, coverage, abort). |
| libs/features/apex-test-runner/src/tests/coverage-utils.spec.ts | Unit tests for coverage percentage helper. |
| libs/features/apex-test-runner/src/tests/apex-test-runner-symbol-table.utils.spec.ts | Unit tests for SymbolTable distillation behavior. |
| libs/features/apex-test-runner/src/tests/apex-test-runner-data.utils.spec.ts | Unit tests for payload building + SOQL builder behavior. |
| libs/features/apex-test-runner/README.md | Nx-generated library README. |
| libs/features/apex-test-runner/project.json | Nx project definition for the new feature library. |
| libs/features/apex-test-runner/.babelrc | Nx React Babel preset config for the library. |
| apps/landing/components/landing/feature-data.ts | Updates landing-page developer tooling bullets/cards to include test runner. |
| apps/jetstream/tsconfig.app.json | Adds reference to apex-test-runner lib for the main app build. |
| apps/jetstream/src/app/AppRoutes.tsx | Adds lazy-loaded route for /apex-tests in the main app. |
| apps/jetstream-web-extension/tsconfig.app.json | Adds reference to apex-test-runner for extension build. |
| apps/jetstream-web-extension/src/pages/app/App.tsx | Adds extension route for Apex Test Runner. |
| apps/jetstream-web-extension/src/components/SfdcPageButton.tsx | Adds extension quick link to Apex Test Runner. |
| apps/jetstream-e2e/src/tests/app/routing.spec.ts | Adds routing test case for Apex Test Runner menu item. |
| apps/jetstream-desktop-client/tsconfig.app.json | Adds reference to apex-test-runner for desktop client build. |
| apps/jetstream-desktop-client/src/app/AppRoutes.tsx | Adds lazy-loaded route for Apex Test Runner in desktop client. |
| apps/jetstream-canvas/tsconfig.app.json | Adds reference to apex-test-runner for canvas build. |
| apps/jetstream-canvas/src/app/AppRoutes.tsx | Adds lazy-loaded route for Apex Test Runner in canvas app. |
| apps/docs/sidebars.ts | Adds Apex Test Runner doc page to Developer Tools sidebar. |
| apps/docs/docs/developer/apex-tests.mdx | Adds end-user documentation for running tests, suites, runs, and coverage. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 48 out of 56 changed files in this pull request and generated no new comments.
Suppressed comments (5)
Previously missed (3) — in code that hasn't changed since the last review.
libs/features/apex-test-runner/src/runs/TestRunResultsTable.tsx:113
- Row selection in the results table is click-only for keyboard users: the wrapper has role="button" with tabIndex={-1} and no Enter/Space handling.
libs/features/apex-test-runner/src/runs/TestRunsTable.tsx:107 - The clickable cell wrapper is not keyboard-accessible: it uses role="button" with tabIndex={-1} and has no Enter/Space handler, so users who rely on keyboard navigation can’t select a row.
libs/features/apex-test-runner/src/useApexTestRunsList.ts:121 - Polling error cutoff is off by one:
intervalDelaystops polling only whennumPollErrors.current > MAX_POLL_ERRORS, meaning it will continue polling at exactly the max error count. If the intent is to stop after hitting the maximum, this should use>=.
libs/features/apex-test-runner/src/runs/TestRunsTable.tsx:113
columnsis memoized with an empty dependency array but closes overonRowSelection. If the parent ever passes a new handler, the table will keep calling the stale one. IncludeonRowSelectionin the dependency list and remove the exhaustive-deps suppression.
libs/features/apex-test-runner/src/runs/TestRunResultsTable.tsx:119columnsis memoized with[]but referencesonRowSelection, so the click handler can become stale ifonRowSelectionchanges. AddonRowSelectionto the dependency array and drop the eslint suppression.
|
Went through Copilot's suppressed (low-confidence) comments — one was valid:
The keyboard-accessibility comments on the two tables don't apply — the grid's built-in keyboard navigation activates |
6ebef03 to
265b880
Compare
265b880 to
8f28a02
Compare
New features-apex-test-runner lib with a placeholder tabbed page at /apex-tests, wired into the route registry, all four app routers, the Developer Tools navbar menu, and the home page card. Feature work lands in follow-up commits. Refs #1256
Tooling API access for runTestsAsynchronous, run/queue/result polling queries, coverage aggregates, suite CRUD, and abort (queue items PATCHed to Aborted). Test-class discovery distills SymbolTables to method lists; null SymbolTables (class needs recompile) fall back to class-level runs. Verified live against a dev org: runTestsAsynchronous returns a bare JSON-quoted job id, and compile failures surface as a CompileFail result row with MethodName "<compile>". Refs #1256
Runs list polls all users' ApexTestRunResult rows (5s while a run is active, 30s idle) so runs started from Dev Console, VS Code, or CI are visible while in progress. Selecting a run polls status, per-class queue progress, and per-method results with backoff, stops after a terminal status, and pauses with a resume button rather than erroring if the run outlives the polling window. Abort PATCHes remaining queue items. Refs #1256
Test classes are discovered from a cheap ApexClass manifest query plus chunked SymbolTable fetches for new/changed classes only, distilled to method lists and cached per-org in IndexedDB. Classes with a null SymbolTable (need recompile) allow class-level runs from a collapsed section. Launching inserts an optimistic Queued row, switches to the Test Runs tab, and swaps to the real run record once polling finds it. Refs #1256
Suites and memberships come from ApexTestSuite/TestSuiteMembership tooling CRUD; membership edits are applied as a composite diff. The manager modal supports create, rename, delete, and class membership; the Run Tests toolbar gains a suite picker that runs via suiteids. Refs #1256
Coverage table computes per-class percentages from ApexCodeCoverageAggregate (line detail excluded from the list query to keep the payload small) alongside the org-wide percentage. Clicking a row opens the class/trigger source in a read-only Monaco editor with covered/uncovered whole-line decorations plus gutter bars for color-blind redundancy — decorations are net-new in this repo via createDecorationsCollection, themed off the slds-color-scheme body class like MonacoEditor itself. Refs #1256
- The org-wide coverage tooling object is ApexOrgWideCoverage, not
OrgWideApexCoverage (query 400'd against a real org).
- MethodsCompleted already includes failed methods, so progress no
longer double-counts failures ("3 of 2 methods run").
- The capped runs table now disables fillHeight — its viewport-based
min-height beats max-height in CSS, pushing run detail off screen.
- The coverage source modal explains when Salesforce returns empty
covered/uncovered line arrays for stale aggregate rows, and shows the
freshly fetched aggregate counts instead of the possibly-stale table
row.
Verified end-to-end in the browser against a live org: run launch,
polling, failure detail, abort path, suite create/membership/run, and
green/red coverage line decorations.
Refs #1256
8f28a02 to
f835a5c
Compare
- Select All checkbox (tri-state) above both the test class list and the suite membership list, applying only to the visible filtered rows. - Run options: stop-after-N-failures (maxFailedTests) and skip code coverage, passed to runTestsAsynchronous for class and suite runs. - Suite names validated against Salesforce API-name rules (letters/ numbers/underscores, starts with a letter, no trailing or double underscore, unique) with inline errors. - Suite rename tunnels PATCH through POST ?_HttpMethod=PATCH — some orgs reject a direct PATCH on ApexTestSuite with "MediaType of 'json' is not supported" (Dev Console tunnels for the same reason). - Suite list uses the standard List component (full-row click, standard selected styling) and auto-selects the first suite; Manage Suites is disabled while suites load after an org change. - Runs tables: Failures column red/green via slds text color classes, Test Time widened, Message column widened with wrapped text and dynamic row height via getWrappedTextRowHeight. Refs #1256
f835a5c to
be07b7b
Compare
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 52 out of 60 changed files in this pull request and generated 3 comments.
Suppressed comments (1)
libs/test/e2e-utils/src/lib/pageObjectModels/QueryPage.model.ts:34
- Playwright Locator.filter() does not support a
{ visible: true }option, so this will not compile / will fail at runtime. To scope to the currently visible field list, use a:visibleselector (or another supported visibility filter).
|
Went through Copilot's suppressed (low-confidence) comments from the 8/26 review — the three that never resurfaced as review threads all check out fine against the current branch, so no changes needed:
The remaining suppressed items duplicated review threads that are already resolved. |
…etch A slow, superseded fetch failing after a newer one succeeded could bump the error counter toward the polling cutoff. Also reword the allOrNone comment - atomicity is per 25-item batch, not across the whole diff. Refs #2005
fix(apex-tests): correct issues found during live browser verification
OrgWideApexCoverage (query 400'd against a real org).
longer double-counts failures ("3 of 2 methods run").
min-height beats max-height in CSS, pushing run detail off screen.
covered/uncovered line arrays for stale aggregate rows, and shows the
freshly fetched aggregate counts instead of the possibly-stale table
row.
Verified end-to-end in the browser against a live org: run launch,
polling, failure detail, abort path, suite create/membership/run, and
green/red coverage line decorations.
Refs #1256