Skip to content

[Frontend][Assignments] A 403 that answers after the board already re-reported write permission locks the field with a release path that has already passed #3042

Description

@Chris0Jeky

MEDIUM declined as out of scope from the fresh-context review of PR #3041 (issue #3017), recorded as
its own slice. Source-traced from the reviewed diff, not runtime-reproduced. Non-blocking: the server
refused the write, the message shown is truthful about what happened, the draft survives
(draftLocked deliberately excludes permissionLost), Clear and Cancel work, and reopening the card
clears the lock.

Gap

CardAssignmentField's readOnly watcher treats a false transition as the authoritative evidence
that write permission was re-read and now allows writing, so it clears saveFailure and releases the
#2982 lock. After #3041 a save settles on its own generation counter, so a 403 that answers after
that transition is no longer discarded — it is applied.

Sequence:

  1. Save starts; the PUT is in flight.
  2. A background board refetch reports canWrite: false, then a later one reports canWrite: true.
    The watcher fires on the second, clears saveFailure and reloads participants.
  3. The PUT — refused during the downgrade window — answers 403. Nothing bumped saveGeneration, so
    saveFailure = 'permission' is applied and the sticky lock goes back on.
  4. The copy says the selector and Save "stay locked until this board reports write permission again
    or you reopen the card". The board already reported it, at step 2. No further readOnly
    transition is coming, so the only remaining release is reopening the card.

Before #3041 this 403 was swallowed entirely by the intervening load() — but that same swallowing
was #3017: it latched saving true and left the editor un-closable, which is strictly worse.
Applying the refusal is the right half of the trade; the release path is the half left open.

Why this belongs with #3021

#3021 already owns "drive the post-403 lock and its explanation from an authoritative permission
read" rather than from a readOnly edge. An authoritative read at the moment the 403 lands resolves
this case directly: the board says writable, so the lock either releases in place or is replaced by a
permission answer that is actually current. This issue is the concrete ordering that makes the
edge-triggered release provably insufficient, not a separate mechanism.

Acceptance

Related: #3017 / PR #3041 (which introduced this ordering), #3021, #3037.

Activity

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

    Priority IIThe active direction's next tranche: wedge capabilities, significant defects, near-term hardening.bugSomething isn't workingfrontendPrimary implementation impact in Vue/TypeScript UI and client runtime.

    Projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions