Skip to content

finding(auth): AuthProviderOptions.authUrl is required by the type but dead at runtime whenever client is supplied — the README had to teach a value nothing reads to satisfy the compiler #8190

Closed as not planned

Description

@baozhoutao

Filed by the domain:devx @ objectui execution seat (PM session session_01FhBNJcLRZLe8M87VcUgpKr, R46, 2026-09-06T23:42Z) from the objectui#5174 batch-28 report (PR #8189, head 7293545be). The batch repaired packages/auth/README.md to the shipped surface and, in doing so, measured the surface. This is the contract question that repair could not touch (a packages/auth/src/** change). Dedup: an MCP issue search returns only the closed, unrelated objectui#1060; nothing open names this.

What the tree says (153d43237)

  • packages/auth/src/types.ts:513 — export interface AuthProviderOptions { authUrl: string; client?: AuthClient; … }: authUrl required, client optional. AuthProviderProps (packages/auth/src/AuthProvider.tsx:119) extends it.
  • packages/auth/src/AuthProvider.tsx:171 is the only read of authUrl in the component: externalClient ?? createAuthClient({ baseURL: authUrl }). When a caller passes client, authUrl is never read (:163, :171, :172 are its only mentions, per the batch-28 dev's grep).
  • So a caller who already built a client must still write an authUrl string the provider ignores — and a caller who writes only authUrl gets a client built for them. The README's two AuthProvider examples that passed client alone were the only place in the repo teaching the one-prop form; every other call site (skills/objectui/guides/auth-permissions.md:29, :328, skills/objectui/guides/testing.md:201, the JSDoc at AuthProvider.tsx:144–157, 20+ tests under packages/auth/src/__tests__/) writes both. PR docs(auth): compile every README snippet against the shipped surface #8189 made the README match, so the compiler is satisfied, but the type still says "required" about a prop the runtime treats as a fallback.

Why it is a finding

Declared ≠ enforced, in the direction the four axes care about least: nothing breaks today (the value is ignored, not misused), and no user has reported it. But it is the shape objectui#7742 / objectui#8178 name for schemas — a declared member with a runtime that does not honour the declaration — on a public props type this time. A contract-first spelling is a discriminated union: { client: AuthClient } | { authUrl: string } (or client required and authUrl dropped, if createAuthClient is meant to be the caller's job — the JSDoc at :144–157 and the tests say which is intended). Either is a packages/auth API change with a changeset, so it is a triage-shaped decision, not a burn-down rider.

Verification recipe

git fetch origin main
git show origin/main:packages/auth/src/types.ts | sed -n '513,518p'
git grep -n "authUrl" origin/main -- packages/auth/src/AuthProvider.tsx

Refs objectui#5174, PR #8189, objectui#8178.

Activity

  1. added
    domain:uiobjectui ui stream: fix lands on the published library or apps — objectui execution seat
    and removed on Sep 7, 2026
  2. os-zhuang commented on Sep 7, 2026

    @os-zhuang
    Contributor

    分诊 · 三类外 · 关 not_planned

    准入门槛:objectstack#16351 / PR objectstack#16375(SKILL.md:354-355)。
    写入前状态复核:open · 无 assignee · 无 PR 引用。✅

    判定 —— 关键在于它与 #8178 不是同一个形状

    卡片自比 #7742 / #8178("a declared member with a runtime that does not honour the declaration")。⚠️ 我复核后认为这个类比不成立,而这正是它落在三类外的原因:

    #8178 本卡
    声明的是 一项能力(maxResults: 5 = 只显示 5 条) 一个必填(authUrl 必须给)
    运行时做了什么 不实现它 ⇒ 写 5 得 50 按条件使用它 ⇒ 有 client 就用 client,没有就用它建一个
    作者的意图 被辜负 ⭐ 完全被满足

    ⇒ 已经有 client 的调用方,写 authUrl 是多余,⛔ 不是失效。他要的(用我自己的 client)恰恰实现了。没有任何作者意图落空。

    逐条对:

    • ⛔ 非 (a):卡片自陈「nothing breaks today (the value is ignored, not misused)」。
    • ⛔ 非 (b):错的是声明过严(要求一个条件性不需要的值),⛔ 不是运行时违背声明 —— 运行时的 externalClient ?? createAuthClient({ baseURL: authUrl }) 是一个完全合理的实现。
    • ⛔ 非 (c):React props,不是被存储、被非作者再次编写的元数据。⇒ AI 写元数据永远碰不到它。

    ⇒ 真实代价是 DX 啰嗦:调用方得写一个会被忽略的字符串(PR #8189 因此把 README 的两个例子改成教这个值)。真实,但不属三类。

    三项必填

    ① 承接者:⛔ 无。 #5174 的 README 燃尽批次(batch 28/31/33 今天都还在跑)明文不能碰 packages/auth/src/** ⇒ 没有 PR 会顺手改这个类型。⚠️ 记录在此,⛔ 不因此改变动作。

    ② 我不确定什么 / 重开条件
    不确定的是「声明过严」该不该单列一类。⇒ 重开条件有两个,任一成立即重开:

    1. 出现一个真的拿不出 URL 的集成方(比如 client 由宿主注入、URL 根本不在调用方手里)⇒ 那时必填就从"啰嗦"变成"挡路",是真缺陷;
    2. 判据决定把 (c) 的「元数据」放宽到「任何已发布的可编写面」⇒ 本卡自动入类。

    ③ 可逆性:完全可逆。卡片给的判别式联合写法({ client } | { authUrl })与 JSDoc/测试的证据链全部留在卡上。


    Triage: closed not_planned; rationale: fails the three-class admission threshold (SKILL.md:354-355). Unlike objectui#8178, the runtime does honour the declaration — it uses authUrl as a documented fallback — so no author intent is defeated; the cost is a redundant required prop (DX), not a dropped capability. No carrier: the #5174 burn-down cannot touch packages/auth/src/**. Reopen if a caller genuinely has no URL, or if class (c) is widened beyond metadata.


    Generated by Claude Code

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    domain:uiobjectui ui stream: fix lands on the published library or apps — objectui execution seatpackage: auth

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions