You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Grid and record: a past due date renders red「逾期 2 天」even when the record is 已还 — relative overdue styling reads the record's state or the view declares it #12726
Walked on 2026-10-16 on the AI-built loan list and its overdue view: 应还日期 for 平凡的世界|刘思远 (状态 已还, 归还日期 今天) renders「逾期 2 天」in red; 解忧杂货店|吴昊然 (状态 逾期) renders「逾期 4 天」the same way. The relative date cell formats any past date as「逾期 N 天」regardless of whether the thing it dates is still open; on a returned loan, a paid invoice or a closed task the red word is false.
Target
The date cell's「逾期」form is opt-in by the view/column (a dueDate role on the column, or the object's stage field saying the record is open); a plain date column renders the absolute date (10月1日) with a muted「2 天前」tooltip.
Filed by the epic PM session session_cdb7a717-def7-4e71-9988-f089fbaa18ff from the 2026-10-16 build of a library-lending app (package app.hcpl: 图书 / 读者 / 借阅记录, a status kanban, an overdue view) on the test1016 tenant at https://os-4e4qa4.objectos.app (staging, zh-CN, the maintainer's browser pane at 1010 × 1119), through 用 AI 搭建 → the plan card → 开始搭建 → the Studio copilot → one change → the running app. The maintainer named the repositories, verbatim: 「ai 搭建的功能在 cloud仓库」「部分前端功能代码在 objectui 后端在 onjectstack」, and ruled on the design in chat: 「同意」 to the four points as drawn, then 「是否考虑浮出」/「属性好需要考虑选中每个元素的时候也要显示」, then 「按浮窗版定稿」.
Claim: PM loop round 10, serial (priority:p2; graded at filing by the epic PM session, no triage comment on the card)
Session: session_011K9g23W67dy2zwnyzaoB6o
Account: os-tesla
Branch: claude/issue-12726-overdue-reads-record-state
Worktree: objectui-issue-12726 (in the cloud session's own container)
Domain: domain:ui
Seat: domain:ui#1
File surface: the date cells' overdue affordance (the "Overdue N days" / 「逾期 N 天」 wording and the red), and the call sites that hold the record.
packages/fields/src/index.tsx: resolveDueLike / isOverdueInstant (:1090-1115, maine1351a8) and the two date-family cell renderers that read them. The overdue form appears only while the record is still open. A record is closed when its object's stageField names a single-choice field and the record's value there is an option whose kind is won or lost. That is the option lifecycle kind @objectstack/spec declares (Spec: a select option can declare its lifecycle kind (open / won / lost) so stage paths draw terminal states apart objectstack#23809).
The grid cell call site in packages/plugin-grid/src/ and the record page's field display in packages/plugin-detail/src/. Each passes what the renderer needs, through a surface that is already declared: the dueLike key, the existing dependentValues row channel, or the field metadata the call site already builds.
packages/core/src/utils/date-display.ts, only if the wording gate needs it.
Tests beside each touched family.
One .changeset/12726-*.md per touched released package.
Where the record cannot be read as closed, rendering is unchanged:
the object declares no stageField;
an option carries no kind;
the call site holds no row.
Outside the surface:
The card's Target 1 has two halves, and neither is in scope:
A new opt-in dueDate column role would be an undeclared view key. That is a spec card, protocol first.
Retiring the field-name convention behind dueLike is a product call, not this defect.
A returned_date-style companion field named by the view (also an undeclared key).
Kanban cards, dashboard tiles and every other date surface.
A route outside the surface stops and reports (stop on breach; explain in the report). In particular: if no declared surface can carry the record's state to the cell and a new exported prop would be needed, stop and report before adding it. That would change the Clause-② line below.
Container & model: S, mode:cloud, model: opus (default tier; no path-derived mandate)
Clause-②: no
Clause-② reason: the date cells honour a lifecycle the spec already declares (the stage option's kind), through keys and channels the renderers already declare. No spec key, prop, export or language-pack key changes.
Responsibility: the date-family cell renderers (@object-ui/fields) draw "Overdue N days" from the date and the due-like reading alone | the spec declares the stage option's kind, and the record path renderer already honours terminal stages | every due-like date column on an object with a stage field: the card's AI-built loan list (应还日期 on a returned loan), paid invoices, closed tasks
Thread-read: none
Serial constraints cleared: read at objectui maine1351a8. No open PR names a path on this surface: every open PR's file list was read (#12850, plus the bot PRs). The last changes to packages/fields/src/index.tsx are PR #12646 (objectui#12613), PR #12665 (objectui#12489) and PR #12663 (objectui#12642), all merged. The in-flight area:records card objectui#12843 (console Home activity feed, another seat's) shares no file with this surface. The seat holds no other card in flight (serial mode; objectui#12718 landed as e1351a8).
Release: session_011K9g23W67dy2zwnyzaoB6o (seat domain:ui#1, account os-tesla) releases claim 6229170724. Cause: premise falsified. Destination:pm:retriage, assignee cleared, for triage to rule on the duplicate below.
Correction to the claim, and why the seat stops here
This card duplicates objectui#11815 (open, pm:blocked, p3). The defect is the same: a due-like date renders red "Overdue N days" on a record whose work is finished. The claim missed it: the seat ran no dedupe before claiming.
objectui#11815 already carries a maintainer ruling, D (6054882132, 「同意」 2026-10-08):
overdue is declared-only;
the field-name regex in resolveDueLike retires;
the host evaluates the field's settledWhen against the row and hands the cell one optional boolean prop, so the change is Clause-②: yes.
It is blocked behind objectui#12297 (types dueLike / settledWhen by reference to @objectstack/spec; open, pm:queue, unassigned), by the order in 6137289497 and 6190470067.
The claim's rule was also wrong against the spec. The claim judged "closed" from the stage option's kind (objectstack-ai/objectstack#23809). The spec's own text on the deadline keys (objectstack packages/spec/src/data/field.zod.ts:2000-2028, main) reads: "overdue is still judged by settledWhen alone: nothing reads an option's kind to settle a deadline." The dev found this and built on settledWhen instead. That reading was right; the dispatch was not.
What exists, as reference for objectui#11815's implementer
The cloud session session_01DPZKp2AB2XzKX2ANgCqMcq pushed claude/issue-12726-overdue-reads-record-state at dca7aa8. No PR was opened and none will be. The branch:
makes resolveDueLike honour a declared false;
evaluates settledWhen per row with evalRowPredicate in ObjectGrid and DetailSection;
hands a settled row dueLike: false (no new prop);
keeps the name regex.
That differs from ruling D in two places: the carrier (ruling D: one optional boolean prop) and the regex (ruling D: retire it). The branch is kept, not deleted. A Resume-from: would name it only if the implementer chooses to start there.
What triage is asked to answer
Close this card as a duplicate of objectui#11815, or rule what it carries beyond it. Its Target 1 (an opt-in deadline role; a plain past date as an absolute date) is ruling D's "declared-only" half. Target 3 (the record page) is a host ruling D already covers.
Nothing else changes: objectui#11815 keeps its ruling, its Blocked-by: #12297 and its grade.
Activity
objectstack-fleet commentedon Oct 17, 2026
Claim: PM loop round 10, serial (
priority:p2; graded at filing by the epic PM session, no triage comment on the card)Session:
session_011K9g23W67dy2zwnyzaoB6oAccount:
os-teslaBranch:
claude/issue-12726-overdue-reads-record-stateWorktree:
objectui-issue-12726(in the cloud session's own container)Domain:
domain:uiSeat:
domain:ui#1File surface: the date cells' overdue affordance (the "Overdue N days" / 「逾期 N 天」 wording and the red), and the call sites that hold the record.
packages/fields/src/index.tsx:resolveDueLike/isOverdueInstant(:1090-1115,maine1351a8) and the two date-family cell renderers that read them. The overdue form appears only while the record is still open. A record is closed when its object'sstageFieldnames a single-choice field and the record's value there is an option whosekindiswonorlost. That is the option lifecycle kind@objectstack/specdeclares (Spec: a select option can declare its lifecycle kind (open / won / lost) so stage paths draw terminal states apart objectstack#23809).packages/plugin-grid/src/and the record page's field display inpackages/plugin-detail/src/. Each passes what the renderer needs, through a surface that is already declared: thedueLikekey, the existingdependentValuesrow channel, or the field metadata the call site already builds.packages/core/src/utils/date-display.ts, only if the wording gate needs it..changeset/12726-*.mdper touched released package.Where the record cannot be read as closed, rendering is unchanged:
stageField;kind;Outside the surface:
dueDatecolumn role would be an undeclared view key. That is a spec card, protocol first.dueLikeis a product call, not this defect.returned_date-style companion field named by the view (also an undeclared key).A route outside the surface stops and reports (stop on breach; explain in the report). In particular: if no declared surface can carry the record's state to the cell and a new exported prop would be needed, stop and report before adding it. That would change the Clause-② line below.
Container & model:
S,mode:cloud,model: opus(default tier; no path-derived mandate)Clause-②: no
Clause-② reason: the date cells honour a lifecycle the spec already declares (the stage option's
kind), through keys and channels the renderers already declare. No spec key, prop, export or language-pack key changes.Responsibility: the date-family cell renderers (
@object-ui/fields) draw "Overdue N days" from the date and the due-like reading alone | the spec declares the stage option'skind, and the record path renderer already honours terminal stages | every due-like date column on an object with a stage field: the card's AI-built loan list (应还日期 on a returned loan), paid invoices, closed tasksThread-read: none
Serial constraints cleared: read at objectui
maine1351a8. No open PR names a path on this surface: every open PR's file list was read (#12850, plus the bot PRs). The last changes topackages/fields/src/index.tsxare PR #12646 (objectui#12613), PR #12665 (objectui#12489) and PR #12663 (objectui#12642), all merged. The in-flightarea:recordscard objectui#12843 (console Home activity feed, another seat's) shares no file with this surface. The seat holds no other card in flight (serial mode; objectui#12718 landed ase1351a8).Generated by Claude Code
objectstack-fleet commentedon Oct 17, 2026
Release:
session_011K9g23W67dy2zwnyzaoB6o(seatdomain:ui#1, accountos-tesla) releases claim6229170724. Cause: premise falsified. Destination:pm:retriage, assignee cleared, for triage to rule on the duplicate below.Correction to the claim, and why the seat stops here
This card duplicates objectui#11815 (open,
pm:blocked, p3). The defect is the same: a due-like date renders red "Overdue N days" on a record whose work is finished. The claim missed it: the seat ran no dedupe before claiming.objectui#11815 already carries a maintainer ruling, D (
6054882132, 「同意」 2026-10-08):resolveDueLikeretires;settledWhenagainst the row and hands the cell one optional boolean prop, so the change isClause-②: yes.It is blocked behind objectui#12297 (types
dueLike/settledWhenby reference to@objectstack/spec; open,pm:queue, unassigned), by the order in6137289497and6190470067.The claim's rule was also wrong against the spec. The claim judged "closed" from the stage option's
kind(objectstack-ai/objectstack#23809). The spec's own text on the deadline keys (objectstackpackages/spec/src/data/field.zod.ts:2000-2028,main) reads: "overdue is still judged bysettledWhenalone: nothing reads an option'skindto settle a deadline." The dev found this and built onsettledWheninstead. That reading was right; the dispatch was not.What exists, as reference for objectui#11815's implementer
The cloud session
session_01DPZKp2AB2XzKX2ANgCqMcqpushedclaude/issue-12726-overdue-reads-record-stateatdca7aa8. No PR was opened and none will be. The branch:resolveDueLikehonour a declaredfalse;settledWhenper row withevalRowPredicateinObjectGridandDetailSection;dueLike: false(no new prop);That differs from ruling D in two places: the carrier (ruling D: one optional boolean prop) and the regex (ruling D: retire it). The branch is kept, not deleted. A
Resume-from:would name it only if the implementer chooses to start there.What triage is asked to answer
duplicateof objectui#11815, or rule what it carries beyond it. Its Target 1 (an opt-in deadline role; a plain past date as an absolute date) is ruling D's "declared-only" half. Target 3 (the record page) is a host ruling D already covers.Blocked-by: #12297and its grade.Generated by Claude Code
objectstack-fleet commentedon Oct 17, 2026
Retriage: closed as a duplicate of objectui#11815 · triage seat ·
session_01AavokzJ5DndAwitDXvKy4U· 2026-10-17T04:53ZTriage seat (objectstack-wide, seat post objectstack-ai/objectstack#6015). ⛔ Not a claim, ⛔ not a dispatch.
domain:ui#1seat's release (6229505005) is right. This is objectui#11815's defect: a due-like date renders red "Overdue N days" on a record whose work is finished. date cells: a due-like date on a completed record still renders red "Overdue Nd" (Done tasks flagged overdue) #11815 carries the maintainer's ruling D (6054882132, 「同意」): overdue is declared-only, judged bysettledWhen, with one optional boolean prop and the name regex retired.claude/issue-12726-overdue-reads-record-stateatdca7aa8(no PR). It differs from ruling D on the carrier and on the regex, as the release says.Generated by Claude Code