Repository navigation
Description
Product discovery from an internal demo production run (video-studio #151), recorded here unassigned per repo convention — not claiming, not proposing a specific fix.
Observed (HotCRM carrier app, dev server, 2026-08-29): a custom React page created and published through the metadata API renders correctly at its direct URL, but:
- it appears in no navigation group — all 26 app navigation links were scanned with every group expanded;
- the command palette search cannot find it (searching by page name returns nothing);
- the only way to reach it is a direct link.
Root cause established (code-level evidence, 2026-08-29 follow-up) — an agent cannot register the nav entry itself, even if asked to:
GET /api/v1/meta/types— theapptype carriesallowRuntimeCreate=true,allowOrgOverride=false,supportsOverlay=true.GET /api/v1/meta/app/crm_enterprise— this app'spackageIdisapp.objectstack.hotcrm, i.e. a code package.- Overlay writes are gated on
OVERLAY_ALLOWED_TYPES= types whoseallowOrgOverrideis true —appis not among them. - Platform's own refusal text:
[not_overridable] … is provided by a code package and the type has not opted into per-org overlay writes (allowOrgOverride=false). Edit the source artifact and redeploy, or set OS_METADATA_WRITABLE … - Second gate behind it:
namedBase && !isWritablePackage(engine, packageId)→readOnlyBaseOverrideError.
So app can be created at runtime but its code-package instance cannot be overlaid. HotCRM's navigation lives in src/apps/crm.app.ts (code package), so the only sanctioned path is "edit source and redeploy". The nearest runtime-only approximation is for the agent to create its own app and put the page in that app's navigation ({id, type:'page', pageName, label, icon} is a valid shape; nav_account_workbench is an existing example) — but that is a different application in the launcher, not an entry in the CRM the team already uses.
Why it matters: in the "AI builds a page into your running app" flow, the page an agent publishes is unreachable for end users, and the agent has no in-protocol way to fix that. Either publishing should be able to register a nav entry for the target app, or published pages should at least be findable in palette search.
⚠ Evidence level, stated honestly: the above is code-level (platform decision functions and verbatim refusal text). A live confirmation — one ?mode=draft overlay write against crm_enterprise, which would prove the refusal without taking effect — was blocked by the session permission gate and not worked around, so there is no live receipt.
Related but distinct: #3371 covered palette record-search hits; this is about published pages being undiscoverable and un-registerable.
Activity
huangyiirene commentedon Aug 29, 2026
分诊:入决策箱 + 四棱块
needs-user-decision·priority:p1· typeTask。⛔domain:*刻意未打 —— 见文末路由段,不是漏标。<!-- os-decision-facets -->
一句话问题:通过元数据 API 发布的页面,对终端用户不可达 —— 不在任何导航组(26 条导航链接全展开扫过)、命令面板搜不到,只有直链能进。⇒ 在「AI 把一个页面建进你正在跑的应用」这条流程里,agent 的交付物对用户等于不存在。
选项 × 真实客户可感成本
(A 与 B 不互斥;B 是 A 的下位保底。)
四棱
① 长远合理性:页面与导航分离是合理的元数据建模(一个页面可以被多处引用、也可以刻意不挂导航)。⇒ C 最省心但最伤模型;A/B 是在不破坏模型的前提下补可发现性。
② 业务拉动 ⭐ 本轮最强的一条:这不是推演 —— 是内部演示生产环境实测(video-studio #151,HotCRM 承载应用)。而且它咬的正是本平台的旗舰叙事:「AI 把页面建进你正在运行的应用」。⇒ 演示观众看到的是「什么都没发生」。本席位这两天定的所有卡里,这一维是最硬的。
③ 防 AI 犯错:⭐ 反向的一维 —— 这里出错的不是 AI 写错代码,而是 AI 正确完成了工作,而系统没有让结果可见。一个 agent 无法从任何反馈里得知它的交付物不可达(发布成功、页面能渲染、直链有效)。⇒ 这是成功回执形状的又一种:所有信号为绿,用户拿不到东西。
④ 不扩散:B 最省(一处搜索源扩展);A 中等;C 最重且引入导航布局规则;D 零成本但不解决。
推荐:⛔ 不裁 —— A/B/C/D 之间是产品决定(页面与导航该不该自动耦合),正是人工地板要你回答的。只指出一点:B 是最便宜的止血,且与 A、C 任何一条都不冲突;若要选一条先做,B 的代价最小、可逆性最好。
⭐ 置信缺口
没人测过「发布」这个动作今天究竟有没有导航注册的入口。 卡面只测了结果(不在导航、搜不到),没测元数据 API 的发布流里是否已存在一个可选的导航注册参数、或 Setup 里是否有手工挂载入口。⇒ 这决定 A 的性质:
⇒ 建议裁前先查这一条。
domain:*为什么空着两条候选补救落在不同仓,且落点由裁决决定:
⇒ 按本席位「落点不明留分诊首触、⛔ 不猜」的纪律,不预打
domain:*,也不预打repo:*。裁决落下后本席补齐路由。⛔ 这是刻意留白,不是漏标 —— 与 #13037 那次预登记条件改判同一纪律。低摩擦裁决格式:回「先查发布流有无导航入口」(推荐)/「B」/「A」/「A+B」/「C」/「D」。
Generated by Claude Code
huangyiirene commentedon Aug 29, 2026
补车道:
domain:engine(priority:p1·needs-user-decision不变)。⛔ 这张卡此前只有
priority:*与needs-user-decision、没有domain:*—— 那是我这个席位的漏项,一张 p1 决策卡在决策箱里躺着却没有归属车道,裁完也不知道该由谁执行。本轮开轮扫描时补上。落点从代码锚定,⛔ 未按标题猜:
⇒ 本仓车道表
domain:engine覆盖metadata*⇒domain:engine。卡里点名的那两道闸门(OVERLAY_ALLOWED_TYPES过滤、namedBase && !isWritablePackage→readOnlyBaseOverrideError)都在这两个包里。packages/metadata-core/metadata-protocol的 overlay 策略(app是否 opt-inallowOrgOverride)domain:engine(本卡)domain:ui⇒ 第二条不在本卡车道内。若裁决选它,本卡需拆出一张 objectui 卡;⛔ 我不预先拆,因为在裁之前拆是猜。
app类型改成allowOrgOverride=true是安全/权限边界的改动——它决定一个代码包提供的应用能否被按组织覆写。⛔ 这不是"加个开关",ADR-0005 的 org-scoped overlay 模型整体依赖这个标志的取值。⭐ 立卡人自己标注的证据等级值得保留:根因是代码级(平台决策函数 + 逐字的拒绝文本),而一次
?mode=draft的活体确认被会话权限闸门挡住且未绕过 ⇒ 没有活体回执。⛔ 请不要在引用本卡时把它说成"已在运行环境验证"。Generated by Claude Code
yinlianghui commentedon Aug 29, 2026
Follow-up evidence (read-only, 2026-08-29): we also checked the two plausible runtime alternatives to app-nav overlay, and neither closes the gap. Recording so the fix discussion starts from the full map.
1. The
viewdoor is open — but has no shape for a custom page. Of 30 registered metadata types only 5 carryallowOrgOverride=true;viewis one of them (allowRuntimeCreate=true / allowOrgOverride=true / supportsOverlay=true), and platform guidance even points authors there ("author a standalone view through the metadata door (Studio /PUT /api/v1/meta/view), not in stack source"). However theviewschema'stypeenum is closed over declarative renderers —grid | kanban | gallery | calendar | timeline | gantt | map | chart | tree— so a metadata-published React page cannot be mounted as an object view/tab. (page.objectdoesn't help either: its doc says it binds "for Record pages", i.e. record detail, not the list tab bar.)2.
OS_METADATA_WRITABLEis explicitly not this. Percontent/docs/deployment/environment-variables.mdxand the #8146 wording, the hatch is an emergency escape that unlocks the type (treated asallowOrgOverride) but "never a package's writability"; and an org-scoped overlay written through it does not survive boot by design. So it is neither a sanctioned nor a durable way to give a published page a nav entry.Net: a runtime-created page (here in a runtime package,
app.demo.warroom) has no in-protocol path to an end-user entry point — app nav is closed (app.allowOrgOverride=false), object views have no page shape, and the escape hatch is out of scope. Two candidate fixes fall out naturally: apage(orcustom) member in theviewtype enum, or nav registration offered by the page publish flow. Not proposing which — just mapping the closed doors.Generated by Claude Code
yinlianghui commentedon Aug 29, 2026
Closing with a premise correction (maintainer's call, relayed from the demo lane).
This finding was written under a demo-side constraint that forbade touching the carrier app's source at all. Under that constraint the runtime metadata door looked like the only path, and its limits read as a dead end. The constraint has been lifted for this class of demo: editing the app's declarative source (e.g. adding the nav item in
src/apps/crm.app.ts) and redeploying is the platform's sanctioned path, and it works — for anyone (human or agent) with code access, which describes the developer audience this platform targets. So "published page is unreachable" is not a defect: it is by-design behavior with a documented resolution.What survives as a genuine product question — whether the no-code/runtime path (Studio / metadata API authors without code access) should be able to give a published page an entry point, and whether published pages should appear in palette search — is tracked as a feature proposal in #13216, which awaits a human product decision. Closing this one as the record of the evidence trail; nothing further to act on here.
Generated by Claude Code
fix(spec): a retired-key prescription is the top-level message at PUT…