fix(service): My Open Cases lists open cases, not merely unclosed ones - #1539
Merged
Conversation
The tab filtered on `is_closed`, which `case_sla_defaults` derives as `status === 'closed'` and which therefore never flips on `resolved`. A tab labelled "My Open Cases" listed an agent's finished work alongside their live work. It now uses the same predicate the other live-work consumers already state: `status not_in ['resolved', 'closed']`. Measured on the seeded demo population (38 cases): the flag predicate returned 30 rows, 7 of them resolved; the status predicate returns 23. No row is added. `my_open_cases` moves from the boundary roster of test/live-work-predicate-parity.test.ts into its consumer roster, and joins the is_closed offender sweep. `case_escalation_sharing` and `case_director_sharing` stay exactly as declared: the `resolved` to `closed` review window is what those standing grants exist for, and the reasoning is now written beside each rule in the source and in its boundary-roster entry. The `is_closed` retention entry in test/case-create-form-narrowing.test.ts drops `my_open_cases.filter` and keeps `case_workflow.filter`, which is the same fact from the create-form side. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019hUuCQStzXGMFSX4dzww5t
|
The latest updates on your projects. Learn more about Vercel for GitHub. |
This was referenced Sep 3, 2026
os-sales
marked this pull request as ready for review
September 3, 2026 10:45
This was referenced Sep 3, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #1328
Description
Executes ruling B on the decision card (2026-08-31): move
my_open_casesonto the live-work status predicate, keep both critical-case sharing rules and write down why, and reword the view's description in all three doc faces.A tab labelled My Open Cases filtered on
is_closed, whichcase_sla_defaultsderives asstatus === 'closed'— it never flips onresolved. So an agent's "open" queue carried their finished work as well as their live work. It now states the same predicate the other live-work consumers already use:status not_in ['resolved', 'closed'].Type of Change
Related Issues
Ruling and parity guard: #1145 (PR #1323). Boundary-roster precedent: #1325. Neither is touched here.
Changes Made
src/views/case.view.ts—my_open_cases.filtermoves fromis_closed equals falsetostatus not_in ['resolved','closed'], spelled the way the neighbouringsla_at_riskandunassigned_triageviews already spell it, with the reasoning beside it.src/sharing/case.sharing.ts— comments only, zero behaviour change (the diff is 56 added lines, all of them comment lines; bothcondition:lines are byte-identical). Each ofcase_escalation_sharingandcase_director_sharingnow carries a block saying the standing access to resolved critical cases is deliberate, why, and what would have to become true for it to be wrong.test/live-work-predicate-parity.test.ts—my_open_casesmoves from theNOT_LIVE_WORKboundary roster intoLIVE_WORK_CONSUMERS, and joins theis_closedoffender sweep. The two sharing rules stay on the boundary roster, theirwhyrewritten from "out of scope by A resolved unowned case sits in Unassigned — triage forever: the tab filters is_closed, which only flips onclosed#1145" to the ruled keep and its conditions.test/case-create-form-narrowing.test.ts— theis_closedretention entry dropsmy_open_cases.filterand keepscase_workflow.filter. See Bounded in-place fix below.content/docs/service/cases.mdx,.zh-Hans.mdx,.zh-Hant.mdx— the views table row for My Open Cases, all three faces, line 181 in each..changeset/my-open-cases-means-open.md.Measurements
Every claim above was measured against the booted app (memory driver, real seed data, real hooks), not read off the source.
The two predicates do NOT select the same set — this is a behaviour change, not a re-spelling. Over the seeded population of 38 cases:
{"is_closed":false}{"status":{"$nin":["resolved","closed"]}}In A only (rows the rewrite removes): 7, every one of them
status: resolved— CASE-00003, 00011, 00016, 00021, 00026, 00031, 00036. In B only: 0. Controls: aresolvedrow is reported inside A and outside B (the harness can tell them apart); anin_progressrow is reported inside both (it can also report agreement).Only
closedcarries the flag. Everycrm_case.statusoption, written through the real hook and read back from storage:newfalse ·in_progressfalse ·waiting_customerfalse ·waiting_supportfalse ·escalatedfalse ·resolvedfalse ·closedtrue — 7 options, 1 withis_closed: true. There is no third closed-ish status, so the value list in the new predicate is complete.The roster move is real work, not a no-op. With only the view edited, the two expected guards went red and nothing else did:
Bounded in-place fix, declared
test/case-create-form-narrowing.test.tsis not on the claim's declared file surface. ItsLIFECYCLE_MAINTAINEDroster asserted thatis_closedkeepsmy_open_cases.filter, which is the same fact this PR changes seen from the create-form side — the red above is its retention assertion, quoted verbatim. The entry now readskeeps: ['case_workflow.filter'], with a comment naming the reason.case_workflowkeeps the flag deliberately: that kanban is the lifecycle itself andresolvedis a swimlane on it.Testing
pnpm verify— all eight stages green on the pushed tree,3a690f6d:Checklist
Additional Notes
Two things found while measuring, not touched here and reported separately for their own cards:
content/docs/service/sla-and-escalation.mdx:144and its two Chinese faces saycrm_caseships seven views and enumerate them, omitting Unassigned — triage.cases.mdx:170says eight, and eight is right. Stale in three faces.🤖 Generated with Claude Code
https://claude.ai/code/session_019hUuCQStzXGMFSX4dzww5t
Generated by Claude Code