Repository navigation
feat(app-shell,i18n): Setup Packages is the one installed list — Source column, marketplace row actions, ?source= filter (objectui#12675) - #12722
Conversation
…e marketplace row actions The Packages list gains a Source column with the closed values code / marketplace / authored, read from the row's `writable` verdict joined with the marketplace slice's installed list; a row neither signal can place is refused by name. Rows whose Source is marketplace carry the actions the Installed Apps list had (Details, Uninstall) when the install-local capability is present. `?source=` filters the list; an unknown or repeated value is refused. The `marketplace:installed-list` widget and the legacy Installed Apps route now open Packages filtered to Source = marketplace. Claude-Session: https://claude.ai/code/session_01L1BStZ37S5WzHGfEgk5NQJ Co-authored-by: Claude <noreply@anthropic.com>
…s; carry the Installed Apps pins onto them The Installed Apps list's not-loaded, kernel-note and walled-refusal pins now read the Packages marketplace rows; its install-date face and the seven pack keys only it read leave with its body. Claude-Session: https://claude.ai/code/session_01L1BStZ37S5WzHGfEgk5NQJ Co-authored-by: Claude <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01L1BStZ37S5WzHGfEgk5NQJ Co-authored-by: Claude <noreply@anthropic.com>
|
changeset-claim-re-read
|
✅ Console Performance Budget
The eager closure is every chunk the entry reaches through static imports — what the browser fetches and parses before the app renders. The entry chunk on its own is a small fraction of it. 📦 Bundle Size Report
Size Limits
|
Contract reviewServed-tier: Face: narrowing — seven published ① Derived judgmentsNarrowing half
Widening half
② Semver level
③ Boundary flagsFive
Dev flags: the class-a Scope badge finding is filed as objectui#12723 (open); the tolerant Implemented-by: VERDICT: FAIL The code half passes on every derived judgment; the verdict fails on the declaration alone. Rendered 2026-10-16T15:54Z, read-only. Generated by Claude Code |
REWORK round 1 → PR #12722 ·
|
…e installLocal-off Code case (objectui#12675) Claude-Session: https://claude.ai/code/session_01L1BStZ37S5WzHGfEgk5NQJ Co-authored-by: Claude <noreply@anthropic.com>
✅ Console Performance Budget
The eager closure is every chunk the entry reaches through static imports — what the browser fetches and parses before the app renders. The entry chunk on its own is a small fraction of it. 📦 Bundle Size Report
Size Limits
|
Contract reviewServed-tier: Face: narrowing — the PR widens (Source column, marketplace row actions, the Inputs: card #12675 — body, claim Head delta, proven by diff. ① Derived judgmentsAdopted by citation from Spot-checked on this head's tree, read-only, each consistent with the citation: no code, test or doc under Landing note, not a judgment on this head: ② Semver level
③ Boundary flagsFive
Dev flags: the class-a Scope badge finding is objectui#12723 (open, Implemented-by: VERDICT: PASS Rendered read-only on the rework head; the code half stands by citation of Generated by Claude Code |
席位核对 · ACCEPT ·
|
Fixes #12675
Clause-②: yes (narrowing)
Setup → Packages is now the one list of what is installed (ruling B on objectstack-ai/objectstack#23892, record 6216295104).
What changed
Source column. Every row reads Code, Marketplace or Authored, from a closed set (
views/metadata-admin/packageSource.ts). Each value comes from a named signal:writableverdict istrue(objectstack#14375).The list is refused by name, with no rows drawn, in three cases: a row with no boolean
writable, a writable row that the marketplace also lists, and a marketplace list that cannot be read while the capability is on.Marketplace row actions. The Installed Apps list offered two actions: Details and Uninstall (Uninstall on local installs only). Both now sit on Packages rows whose Source is Marketplace, in
console/marketplace/MarketplaceRowActions.tsx. They reuseuninstallLocaland the same pack sentences, and Uninstall asks for confirmation in-app.features.installLocalis on and the viewer is a workspace admin; these are the two gates Installed Apps had.Filter spelling, for cloud-connection: the "Installed Apps" entry opens Setup Packages filtered to Source = marketplace (ruling B on #23892; after the objectui card lands and the pin moves) objectstack#23933 to copy:
/apps/APP/component/developer/packages?source=marketplace. A Setup nav item reaches the same URL with{ type: 'component', componentRef: 'developer:packages', params: { source: 'marketplace' } }, because the sidebar sends a component item's params as the query string. The allowed values arecode,marketplaceandauthored. An unknown, empty or repeated value is refused by name.Installed Apps entries. The
marketplace:installed-listwidget, which the plugin'smarketplace_installedpage renders, now redirects to the filtered Packages URL. So does the legacysystem/marketplace/installedroute. The InstalledList body is gone.Language packs. Seven
marketplace.*keys that only the InstalledList body read are removed from all ten packs. New Packages copy goes in the metadata-admin designer table (en and zh).Untouched: the PackagesPage header (feat(app-shell): one page header for every Setup page — sys_* lists, metadata types, settings and component pages (objectui#12606) #12662 is rewriting it), objectstack's cloud-connection package, and the spec.
Narrowing, declared for contract review
marketplace.installedTitle,installedSubtitle,installedEmpty,installedAt,installedBy,installedPackageIdandcachedAs.marketplace:installed-listwidget and theMarketplaceInstalledPageexport now redirect instead of drawing a list.The follow-up after objectstack-ai/objectstack#23933 retires the widget registration, both routes and the export, and points MarketplacePage's Installed (N) button straight at the Packages URL.
Tests
At head 681c066, after merging origin/main f8267df: app-shell type-check passes, and the vitest run over Packages, the marketplace dir, the i18n package and the route and parity suites gives Test Files 133 passed, Tests 2025 passed, 13 skipped.
New pins:
PackagesPage.source-12675.test.tsx(14 tests): plugin present; plugin absent; non-admin; unknown, conflicting or unreadable origin refused; unknown, empty or repeated filter refused; widget and legacy route redirect.MarketplaceRowActions.installedAppsPins.test.tsx(27 tests): the 11645 not-loaded, 12610 kernel-tooltip and 7611 walled-uninstall pins, carried onto the rows.Ablations, each red and each restored to the HEAD blob:
Builds: the app-shell and console closure builds and the console vite build all pass.
Screenshots
At 1280 px against a published @objectstack 18.0.0-next.2 showcase backend, on branch
claude/issue-12675-evidenceunderevidence/12675/. Thebefore-*files are from main and theafter-*files from this branch. They cover Packages, the marketplace filter, an unknown filter, the plugin's Installed Apps page and the legacy route.Acceptance notes
listLocalInstallsstill treats any failure as an empty list for the marketplace pages. Only the Source read uses the new strictfetchLocalInstalls.Provenance: built by the cloud session
session_01L1BStZ37S5WzHGfEgk5NQJ(claim6217043127) and opened by thedomain:uiseat 1 PM (session_011K9g23W67dy2zwnyzaoB6o) from that session's final message, because a cloud session cannot open a PR from its container. The seat replaced the dev's own footer line with this line.Generated by Claude Code