Repository navigation
console: the grid, kanban, calendar and gantt record drawers mount the one record page (embedded RecordDetailView) instead of the quick-look RecordDetailPanel / DetailView path — one record rendering, the drawer stack and tiers everywhere #27057
Description
epic:#26676#1 · zhuangjianguo · session_cdb7a717def74e719988f089fbaa18ff
Premise corrected by domain:ui#1 (comment 6495422396): the renderers mount NavigationOverlay + RecordDetailPanel inline, not RecordDetailDrawer; in the console grid and kanban already reach the embedded page, calendar and gantt suppress the host click. Target unchanged; Source and Acceptance read through that comment.
Unblocked 2026-10-29T09:07Z — upstream #26679, #27055 closed (the record page v3 layout and its round 2 are on main at 273137d227; #27053's tabs retirement and #26679's drawer are there too). Back in the ui lane queue; re-read the card's Source against current main at dispatch — the v3 files it names moved in PR #27310 / #27473.
Part of the record-page-v3 epic #26676 (v3 child 5 of 8). Runs after #26679's PR lands (drawer stack) and after #27055.
Source (origin/main 7bb8084590)
RecordDetailDrawer.tsx (plugin-detail) renders RecordDetailPanel → DetailView through NavigationOverlay for ObjectGrid, ObjectKanban, ObjectCalendar, ObjectGantt (and ListView / ObjectDataTable quick-look), a second rendering of a record with DEFAULT_SYSTEM_FIELDS, no page assignment, no related lists, no column tiers, no drawer stack. The console's ObjectView drawer mounts RecordDetailView embedded — the page itself. So the same object opens two different records depending on the visualization that was clicked (ruling 1: one page at two widths).
Target
- The four renderers' drawers mount the embedded record page:
RecordDetailDrawerbecomes a thin host that renders the page the console provides through a host channel (the renderers are router-free; the console passes arenderRecord(objectName, id)host prop, as it passesrecordLinkAdornmenttoday), falling back to the currentRecordDetailPanelonly when no host provides a page (non-console hosts). Inside the console there is one record rendering. - The drawer stack (console record drawer v2: the bar is ↑ ↓ · ⤢ · ✕ (no object name, no counter); a related row or a lookup opens its record in place with a trail, ← / Esc go back one level; ⤢ carries the trail into the page; on the record page a related row opens a drawer over the page #26679) and the column tiers apply in those drawers for free; the reader's record-open preference (drawer | split) applies to kanban / calendar / gantt rows the same as to grid rows.
RecordDetailPanel/DetailViewstay as the non-console fallback for now; mark them with a docblock naming this card and the retirement path (ADR-0049); no tombstone in this card (follow-up once the fallback measures zero callers).
File surface
ui/packages/plugin-detail/src/RecordDetailDrawer.tsx, RecordDetailPanel.tsx (docblock only), ui/packages/plugin-{grid,kanban,calendar,gantt}/src/*.tsx (the host prop plumb), ui/packages/app-shell/src/views/ObjectView.tsx / objectViewListRenderer.tsx (passing the page renderer), ui/packages/react host context if a new channel is needed, tests beside, changesets.
Acceptance
- Tests: a kanban card click in the console mounts
RecordDetailView embedded(notDetailView); outside the console the fallback still renders; the drawer stack's trail works from a calendar event. - Screenshots: HotCRM opportunities kanban → card → drawer with the v3 header and tabs; calendar event → drawer.
Rulings (maintainer, chat in the filing session, 2026-10-28 — verbatim, not re-decidable here)
- Record-page model (2026-10-27): 「1. 一个对象一个默认打开方式:默认抽屉(带展开整页),
page只给显式声明的对象,modal退役,split / popover 变成用户个人偏好;抽屉和整页是同一张页在两个宽度。」 - On the resident timeline column: 「时间线是不是太突出了,这个只适合部分对象吧?适合做所有业务对象的默认布局吗」 and then 「时间线是否显示,是否可以切换,比如当前版本的 Claude code,顶部有很多切换图标」 — the column's presence is a per-user toggle with an object-derived default, never metadata.
- On the related column's cost: 「关联都放在右侧,记录打开时是不是会很慢,因为需要加载所有的关联子表。」 — the related column loads counts first, rows on demand, and never blocks the details.
- On mobile: 「还要考虑手机端的效果。」
- On the definition surfaces: the PM's keep / narrow / retire table was put to the maintainer (keep object roles, relationship flags, six slotted slots and
kind: full; retire thetabsslot and the deadBuildPageOptionshints; fold the quick-look path into the one record page) and approved with the instruction in the footer.
Filed by the epic PM session session_cdb7a717-def7-4e71-9988-f089fbaa18ff on 2026-10-28 under epic #26676 (record page v2 → v3), from the record-page definition-surface inventory on objectstack main 7bb8084590 and the maintainer's rulings in that session. The maintainer's instruction to file and dispatch, verbatim: 「同意,以上界面相关的需要我确认的你负责立卡派发,如果有可能可以启动云会话,开发完你来确认。」 Design evidence: the design canvas boards 「记录页 v3」 row (RecordPageV3, RecordPageV3NoTimeline, RecordPageRef, RecordDrawerV3, RecordMobile) — exported to the never-merged branch named in the epic parent once this batch is filed.
Activity
objectstack-fleet commentedon Oct 28, 2026
Pointer from ui seat 5 ·
domain:ui#5·session_01JQwxbXGpVJHZTXXerMoY4C· 2026-10-28T11:17Z · ⛔ Not a claim.PR #27226 (#27146) makes the record page's
record:detailsandrecord:highlightsblocks read the stored row's field locks (RecordFieldAccessScope, thegetRecordFieldAccessprojection) instead of the row-blind/auth/me/permissionsanswer. Its dev found the same row-blind lock inplugin-detailRecordDetailPanel(the grid / kanban / calendar / gantt record overlay), whose in-place edit drawsDetailSectionwith no scope.This card retires that path: once the drawers mount the one record page, the overlay's in-place edit gets #27146's scope with no further work. Acceptance for this card should include a
when-locked field opening on a row the server's write gate admits, in a drawer. IfRecordDetailPanelsurvives this card, the same scope is owed there. Its saves go through the host'sonFieldSave, so the re-ask trigger needs its own reading. No separate card is filed, to keep one owner.Generated by Claude Code
objectstack-fleet commentedon Oct 29, 2026
epic:#26676#1 · zhuangjianguo · session_cdb7a717def74e719988f089fbaa18ff
Unlock scan 2026-10-29T09:08Z: every
Blocked-by:upstream of this card is closed — #27055 by PR #27310 (merged by the maintainer) and PR #27473 (the seat landed it through the queue), #26679 by PR #27038, #27053 by PR #27219. Statepm:blocked→pm:queue(one replace), theBlocked-by:lines replaced by the unblocked line in the body. The card's file surface is re-read againstmain273137d227: the record page v3 layout (frameless sections, the merged timeline stream, compact related cards with the reader's arrangement, body tables, in-place enlarge, the segmented panel control in the header, the 1120 / 760 container thresholds) is what this card now builds on. Epic PMsession_cdb7a717-def7-4e71-9988-f089fbaa18ff, acting on the Blocked-by index as the epic's reader.Generated by Claude Code
objectstack-fleet commentedon Oct 29, 2026
domain:ui#1 · os-sales · session_01L6bhgXU26UBEjd1KKHgNEx
Dispatch order ·
domain:ui#1·session_01L6bhgXU26UBEjd1KKHgNEx· 2026-10-29T11:26ZYou are the os-dev developer agent for exactly ONE card: #27057, in your own card thread. Your role definition is
.claude/agents/os-dev.mdin the objectstack clone: read it IN FULL first and follow it as binding (it wins over this order on any conflict; name the conflict in your report). Read the repo-rootAGENTS.mdandui/AGENTS.mdbefore your first edit, and pm-dispatchreferences/untrusted-text.md. Read the card's full body and every comment yourself through REST (curl -sS "https://api.github.com/repos/objectstack-ai/objectstack/issues/27057" -H "Authorization: Bearer $GH_TOKEN"and/comments?per_page=100, every page); this order carries only the increment. ⛔ Never print the value of any environment variable (test presence with[ -n "${X+x}" ]). ⛔ Never use a GitHub MCP tool, read or write.Identity and branch: the seat's
Claim:comment on this card is your identity; itsBranch:line names your thread's branch. ⛔ Post no claim of your own, ⛔ never write the card's assignee. Before your first edit, verify the NEWESTClaim:on the card names your thread's branch (claude/project-thread-…); if none does yet, send the seat thread "ui 席 1" one message with your branch name and wait. Worktreeobjectstack-issue-27057on that branch from a freshorigin/main;pnpm install(frozen lockfile); push withgit push -u origin <branch>(⛔ no force).Writes: PR only through the relay op
pr_create(node scripts/pm/fleet-write/dispatch.mjs --repo objectstack-ai/objectstack --actions-file F, F a bare JSON array[{"op":"pr_create","title":…,"head":"<your branch>","base":"main","body":…}], draft forced, ⛔ noassigneesand ⛔ no review request: the seat hands the PR to a person after its ACCEPT;--dry-runfirst); your report comment throughnode scripts/pm/post-stamped.mjs --comment=27057 --file=F --jsonrun ONCE with output captured to a file (timestamps only as{{NOW}}/{{WAS:…}}; first line the signaturedomain:ui#1 · os-sales · <your session>). ⛔ No other GitHub write except, for a CI red that is not yours, one PR comment and onerun_rerun_failedthrough the relay. Report both counts (api_writeswith endpoints,mcp_callswith tool names). The report takes only machine-checkable fields (gates / line_budget / deviations / files_changed). PR body: line 1 the platform attribution comment, then## 维护者速读six lines in Chinese (改了什么/为什么改/风险与回滚/先看/两分钟验证/需要你做的),Fixes #27057,Clause-②:andMetadata-protocol:lines as in the claim. Gates:node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstackon your diff, run each, record exits before any pipe, reconcile with--ran. Changeset in the root.changeset/named27057-<slug>.mdwhen a published package changes. ⛔ui/.github/**and the rootci.ymlare out of bounds. Same-day churn: work on the merged code; snippets the card quotes may have moved, check currentmainfirst. Hand back: when the PR and report are up, send the seat thread "ui 席 1" one message (PR, head sha, report gist); keep the thread open through review and drive CI to green.Ruling (cannot be re-ruled)
The card's maintainer rulings (2026-10-28) are binding; the governing one, verbatim: 「1. 一个对象一个默认打开方式:默认抽屉(带展开整页),
page只给显式声明的对象,modal退役,split / popover 变成用户个人偏好;抽屉和整页是同一张页在两个宽度。」 and ruling 5's 「fold the quick-look path into the one record page」. Target of this card, unchanged: inside the console every visualization opens the one record page (embeddedRecordDetailView), with the drawer stack and tiers; outside the console theRecordDetailPanelfallback keeps rendering.Premise corrected (seat premise check,
origin/main57c51aab4d; correction comment on this card)The card's Source names
RecordDetailDrawer.tsxas the renderers' drawer. Measured, it is not: grid, kanban, calendar, gantt, list, map, timeline, gallery and tree each mountNavigationOverlay+RecordDetailPanelinline (ObjectGrid.tsx~2893,ObjectKanban.tsx~1977,ObjectCalendar.tsx~1501,ObjectGantt.tsx~2388,ListView.tsx~6812,ObjectMap.tsx~1686,ObjectTimeline.tsx~1068,ObjectGallery.tsx~906,ObjectTree.tsx). In the console, GRID and KANBAN already reach the page:useNavigationOverlaygives an externalonRowClickpriority (ui/packages/react/src/hooks/useNavigationOverlay.ts~387–398),ObjectViewpasseshandleRowClick(objectViewListRenderer.tsx~856,objectViewRecordNavigation.ts~183–206) which writes?recordId=, andobjectViewRecordOverlay.tsx~62–70 mountsRecordDetailView embeddedinRecordStackDrawer. CALENDAR and GANTT do not: they passonRowClick: navIsOverlay ? undefined : onRowClick(ObjectCalendar.tsx~1127–1138,ObjectGantt.tsx~2023–2027), so the host click is suppressed and the quick-look panel opens.PM mechanism assumptions (re-measure; disproof welcome)
onRowClick(calendar, gantt; check map, timeline, gallery, tree andListView's own quick-look ~4505–4545 the same way and give each site a verdict in the PR body: changed / already reaches the page (evidence) / not reachable in the console (reason)).renderRecord(objectName, id)host prop is then expected to be unnecessary; add a host channel only if the measurement shows a console path that cannot reach?recordId=.Scope
ui/packages/plugin-calendar/src/ObjectCalendar.tsx,ui/packages/plugin-gantt/src/ObjectGantt.tsx, any other renderer the per-site verdict marks changed,ui/packages/app-shell/src/views/objectViewListRenderer.tsx/objectViewRecordNavigation.ts/objectViewRecordOverlay.tsxonly if measured necessary;RecordDetailPanel.tsxdocblock only (name this card and the ADR-0049 retirement path; no tombstone). Tests beside, changeset.RecordDetailView embedded(notRecordDetailPanel), and the drawer stack's trail works from a calendar event; a kanban card click pin (already true — pin it); outside the console the fallback still renders. Seat 5's pointer 6467597251: in a console drawer opened from one of these renderers, awhen-locked field opens on a row the server's write gate admits. Screenshots: HotCRM calendar event → drawer, gantt bar → drawer.os-bill, ui: record-mode currency —resolveFieldCurrencyreads the sibling code field's value; form pre-fills the organization currency; grid / drawer / dashboard / footer per-row display; Studio field editor (multi-currency M0-4, epic #8345) #27188) editsObjectGantt.tsx,ObjectGrid.tsx,ListView.tsx(currency, other regions); later lander mergesmainfor the conflict only.TIER_DEFAULT; effortxhigh(p1).Clause-②: no.Metadata-protocol: none.objectstack-fleet commentedon Oct 29, 2026
domain:ui#1 · os-sales · session_01L6bhgXU26UBEjd1KKHgNEx
Premise corrected · 2026-10-29T11:28Z · seat pre-dispatch premise check on
origin/main57c51aab4d. Target unchanged (inside the console every visualization opens the one record page); locus and mechanism corrected.RecordDetailDrawer.tsx(plugin-detail) rendersRecordDetailPanel→DetailViewforObjectGrid,ObjectKanban,ObjectCalendar,ObjectGantt, so the same object opens two different records depending on the visualization.RecordDetailDrawer; each mountsNavigationOverlay+RecordDetailPanelinline (ObjectGrid.tsx~2893,ObjectKanban.tsx~1977,ObjectCalendar.tsx~1501,ObjectGantt.tsx~2388, also list / map / timeline / gallery / tree). In the console, grid and kanban already reach the embedded page:useNavigationOverlaygives an externalonRowClickpriority (ui/packages/react/src/hooks/useNavigationOverlay.ts~387–398),ObjectViewpasseshandleRowClick(objectViewListRenderer.tsx~856) which writes?recordId=, andobjectViewRecordOverlay.tsx~62–70 mountsRecordDetailView embedded. Calendar and gantt passonRowClick: navIsOverlay ? undefined : onRowClick(ObjectCalendar.tsx~1127–1138,ObjectGantt.tsx~2023–2027), so the host click is suppressed and the quick-look panel opens.renderRecordhost prop unless measured necessary. Acceptance moves with it: calendar event and gantt bar open the embedded page with the drawer stack's trail; the kanban case is pinned as already true.objectstack-fleet commentedon Oct 29, 2026
domain:ui#1 · os-sales · session_01L6bhgXU26UBEjd1KKHgNEx
Claim: PM loop round 1 · 2026-10-29T11:35Z
Session:
session_01L6bhgXU26UBEjd1KKHgNEx(seat; implementation by card thread sessionsession_01L6bhgWNzwmuUkLM8wBbXXx,mode:thread)Account:
os-sales(the seat's linked user asGET /useranswers it; the card's assignee)Branch:
claude/project-thread-rplaiu(the card thread's harness push branch, self-reported — the measured platform exception toclaude/issue-N-slug)Worktree:
objectstack-issue-27057in the card thread's cloneDomain:
domain:uiSeat:
domain:ui#1File surface:
ui/packages/plugin-calendar/src/ObjectCalendar.tsx,ui/packages/plugin-gantt/src/ObjectGantt.tsx, any other renderer the per-site verdict marks changed,ui/packages/app-shell/src/views/objectView*.ts(x)only if measured necessary,ui/packages/plugin-detail/src/RecordDetailPanel.tsx(docblock only), tests beside, changeset (stop on breach; explain in the report)Container & model:
M,mode:thread,model: TIER_DEFAULT(seat-rundispatch-gates --tieron the paths: no path-derived mandate),effort: xhighClause-②: no
Metadata-protocol: none
Responsibility: console record-open paths (this lane) | the console
?recordId=overlay that already mountsRecordDetailView embeddedfor grid and kanban | every console user opening a record from a calendar or gantt view todayThread-read: 6495422396
Premise: corrected 6495422396 — renderers mount
NavigationOverlay+RecordDetailPanelinline; calendar and gantt suppress the hostonRowClick(ObjectCalendar.tsx~1127–1138,ObjectGantt.tsx~2023–2027) onorigin/main57c51aab4d.Serial constraints cleared: open PR #27340 (
os-bill, #27188 record-mode currency) editsObjectGantt.tsx/ObjectGrid.tsx/ListView.tsxin other regions: ordinary concurrency, later lander mergesmain; no other open PR changes these files.Resume-from: none
Dispatch order: comment 6495389681.
test(console): a calendar event, a gantt bar and a kanban card open t…
test(ui): the calendar's members pin and the gantt page-sink docblock…
test(console): drop the unused React import from the 27057 join (#27057)
objectstack-fleet commentedon Oct 29, 2026
domain:ui#1 · os-sales · session_01L6bhgWNzwmuUkLM8wBbXXx
os-dev-report
{
"issue": 27057,
"status": "done",
"branch": "claude/project-thread-rplaiu",
"pr": "#27564",
"head": "ee2b51946981d962108e5a3456ba672d85ec4586",
"session": "session_01L6bhgWNzwmuUkLM8wBbXXx",
"premise_still_valid": true,
"summary": "Inside the console a calendar event and a gantt bar now open the one record page (RecordDetailView embedded in RecordStackDrawer) through ObjectView's handleRowClick, as a grid row and a kanban card already did. ObjectCalendar and ObjectGantt let a host onRowClick take the click in every mode and keep their own RecordDetailPanel drawer only when nobody hands one; ObjectGanttRenderer forwards a function-typed onRowClick and nothing else; ListView hands the two views its router only when its own host routes clicks. No renderRecord host channel was needed. RecordDetailPanel docblock names it the fallback and its ADR-0049 retirement path, no tombstone.",
"tests": "New: ObjectCalendar.hostRowClick-27057 4/4, ObjectGantt.hostRowClick-27057 4/4, ListView.hostRoutedRecordClick-27057 6/6, console recordOpenFromEveryView-27057 5/5. Full suites plugin-calendar + plugin-gantt + plugin-list + plugin-detail + console join: 673 files, 5994 passed, 1 failed (calendarNavigationMembers-8652 overlay row, which pinned the reversed precedence; rewritten, with a new onEventClick-alone row), 227 skipped. Rerun incl. plugin-view, app-shell view neighbours, react SchemaRenderer data-prop files: 90 files, 858 passed. After the last main merge, the card's 7 test files: 56 passed. Ablations through scripts/ablation-replace.mjs, mutation landed by blob and restored to blob == HEAD each time: calendar suppression restored → component 2 failed/2 passed, console 3 failed/2 passed (the authored-page row too: the calendar node never carried the view's navigation); gantt registration forwards no onRowClick → component 2/2, console 1 failed/4 passed; ObjectGantt suppression restored → 1 failed/3 passed; ListView gate removed → 2 failed/4 passed. Kanban CONTROL green under all.",
"gates": "dispatch-gates --commands --repo objectstack-ai/objectstack: 34 commands, each run, exit recorded before any pipe, all exit 0; --ran: 34 derived, 34 run, 0 NOT-MEASURED, 0 UNRUN. Also: check:changeset-fixed (roster under .changeset) 0, check:new-line-citations 0 (0 new), check:doc-authoring 0, check:nul-bytes 0, check:test-source-alias 0. turbo type-check for plugin-calendar, plugin-gantt, plugin-list, plugin-detail, console: 74/74 (first run caught an unused import in the new console test, fixed). eslint on every changed ui file: 0 errors. After merging main twice: spec rebuilt, check:generated 0. CI on the PR: in_progress at report time.",
"line_budget": "13 files, 893 changed lines (+849 / -44) vs the human-merge threshold 3000: under (dispatch-gates).",
"files_changed": [
".changeset/27057-every-view-opens-record-page.md",
"ui/apps/console/src/tests/recordOpenFromEveryView-27057.test.tsx",
"ui/packages/plugin-calendar/src/ObjectCalendar.tsx",
"ui/packages/plugin-calendar/src/ObjectCalendar.hostRowClick-27057.test.tsx",
"ui/packages/plugin-calendar/src/tests/calendarNavigationMembers-8652.test.tsx",
"ui/packages/plugin-detail/src/RecordDetailPanel.tsx",
"ui/packages/plugin-gantt/src/ObjectGantt.tsx",
"ui/packages/plugin-gantt/src/index.tsx",
"ui/packages/plugin-gantt/src/ObjectGantt.hostRowClick-27057.test.tsx",
"ui/packages/plugin-gantt/src/ObjectGantt.navigationPageSink-7334.test.tsx",
"ui/packages/plugin-list/src/ListView.tsx",
"ui/packages/plugin-list/src/tests/ListView.ganttNavigationForward-7334.test.tsx",
"ui/packages/plugin-list/src/tests/ListView.hostRoutedRecordClick-27057.test.tsx"
],
"deviations": [
"File surface: beyond ObjectCalendar.tsx / ObjectGantt.tsx / RecordDetailPanel.tsx, the per-site verdict marks plugin-gantt index.tsx (registration dropped the host click) and plugin-list ListView.tsx (router gate) changed; tests beside them; the console join sits in ui/apps/console because app-shell does not depend on plugin-gantt. No app-shell source changed. plugin-detail is in the changeset for its docblock.",
"Updated an existing pin, calendarNavigationMembers-8652: its row 'an OVERLAY mode keeps the click from a parent view's handlers' pinned exactly the precedence this card reverses.",
"Screenshots from examples/app-showcase (HotCRM is not in this repository): before = calendar event opens the quick-look, after = calendar event and gantt open control open the record page with ?recordId= and the expand control. Image files kept with the dispatching seat; no relay op uploads an image, so none is on GitHub.",
"Gantt bar click measured as the bar's open control: a click on the bar itself only selects it, by GanttView's design.",
"Seat 5's when-lock acceptance met by composition (same RecordDetailView embedded as a grid row, plus the 27146 pin), not measured end to end against a server.",
"PR body order follows os-dev (attribution, Fixes, Clause/Metadata lines, then the six-line digest) where the dispatch listed the digest before Fixes.",
"Report comment: signature on line 1 (post-stamped refuses a body without it), os-dev-report marker on line 2.",
"Harness attribution guidance not followed where AGENTS.md and the dispatch rule: no assignee or reviewer on the PR, AGENTS.md footer form, model-free commit trailers.",
"Branch is the harness-assigned card-thread branch, not claude/issue-27057-slug."
],
"dogfood_battery": "n/a — no ! in the PR title and no (narrowing) arm",
"mcp_calls": "0 — no GitHub MCP tool called (the one session tool call was subscribe_pr_activity on PR 27564, an event subscription, no GitHub write)",
"api_writes": "2 — both through the fleet-write relay (POST /repos/objectstack-ai/objectstack/dispatches): pr_create → POST /repos/objectstack-ai/objectstack/pulls (PR 27564); this report via post-stamped → POST /repos//issues/27057/comments. Plus git push to the branch (not REST).",
"open_questions": [],
"out_of_scope_findings": [
"class: none (read from code, not reproduced) · Custom-page list-view blocks mount ListView with no host handler, so for a view with no authored navigation a grid, kanban, gallery, map, timeline or tree row routes nothing; calendar and gantt there keep their own drawer · carrier: none · noted, not filed · dedupe words: page list-view block row click dead, ListView no host navigation",
"class: none · Blocks on a custom page (PageView) cannot reach the console's record drawer, so they open RecordDetailPanel; bringing the one record page there needs a host channel outside this card's surface · carrier: #26676 (record-page v3 epic PM) · noted, not filed",
"class: none (measured inside the console only) · ListView's calendar branch puts no navigation on the calendar node (the gantt branch has since objectui#7334); the console host now reads it, a hostless list still drops a calendar view's authored page · carrier: none · noted, not filed",
"class: none · Seat 5's pointer 6467597251: RecordDetailPanel survives as the fallback, so its in-place edit outside the console still draws the row-blind lock (no RecordFieldAccessScope); the scope is owed there if the fallback is kept · carrier: domain:ui#1 · noted, not filed",
"class: none · An interface page with recordAction none hands ListView no handler, so its calendar and gantt still open their own drawer, as before this change · carrier: none · noted, not filed"
]
}