Capture review: saving a capture already saved makes a second listing, and a saved one can still be discarded #336
Labels
No labels
accessibility
authentication
breaking change
bug
documentation
enhancement
interface
internationalisation
observability
performance
security
tier
1
tier
2
tier
3
tier/4
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
Postulo/postulo#336
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Found on 2026-09-30, reading
src/postulo/jobs/capture_views.pyat0a5cad587for postulo/postulo-chromium#7. Read from the code; not replayed in a browser.Of the answers a capture can be given, only add to a listing's history checks that the capture is still waiting. Saving it as a listing and discarding it act on a capture in any state.
jobs/capture_views.py:221-233:CaptureReviewView.get_querysetreturns every capture the person owns, whatever its status.get()(:321-324) draws the form for one already saved or discarded.:326-381(post): callscreate_listing, andapply_to_listingwhen I have already applied is ticked, then setsACCEPTED. No check of the status, no lock.:447-452(CaptureDiscardView.post): setsDISCARDEDwhatever the capture was.bind_capture(src/postulo/jobs/history.py:218-224) locks the row and raisesAlreadyDecidedunless it is pending, and the bulk discard (capture_views.py:479) filters on pending.AlreadyDecidedalready carries, and send the person to what the capture became.get()for a decided capture shows that (the listing or the application, or that it was discarded) instead of the form.Done when
Found while filing the extension and DAV plugin improvements of 2026-09-30.
From the read-only review of 2026-09-29 (postulo at
95348908d, checked again at0a5cad587). Three reviewers found this independently; it was not filed again. Two things they add to what is above:CaptureDiscardView.post(jobs/capture_views.py) setsDISCARDEDon an accepted capture and leavespostingset.expire_unconfirmed(jobs/pages.py) keeps a page only forcapture__status=ACCEPTED, so the copy of the advert kept with that capture (#256) is deletedPOSTULO_CAPTURE_PAGE_KEEP_DAYSafter capture, although the listing it belongs to still exists and the docstring promises a saved capture keeps its page for as long as it exists.bind_capture(jobs/history.py) re-reads the capture underselect_for_update()before raisingAlreadyDecided. The two views should do the same inside the request's transaction, or two tabs submitting at once still both pass a plain status check.A test for the first: save a capture that has a kept page, post a discard, run
expire_unconfirmedpast the keep period, and assert the page is still there.