A party is placed even when the engine cannot seat it together: the booker is told how close it managed rather than being refused, because a worse seat is a disappointment and only the booker can judge whether to take it. That sentence is a notice on the page that placed them, and a notice is easy to miss. Nothing asks the booker to confirm it, and nothing stops an order of scattered places reaching payment.
The plan does show a booker the places they hold, so they can see those places are apart. Only if they look at the plan, though, and only if they can read seats drawn on it, which a screen reader user cannot.
Proposed resolution
A required acknowledgement on the cart page, shown only for an event whose places are not side by side, refusing to go on until it is ticked.
- Asked where the booker commits, which is the cart. The payment page comes after the registration form, so a question there would have them fill their details in and only then learn their seats are apart; and a booking that owes nothing never reaches a payment step at all.
- Asked per event, inside that event's own card. The rule hangs on a resource, so a basket holding two evenings in two houses may be asked about one of them, about both in different words, or about neither, and a booker seated apart at two houses ticks two boxes.
- Nothing new is stored. The answer is derived from the order's place lines and their section, row and position, reusing the adjacency the seating strategies already apply, so the notice on the picker and the question at the cart cannot disagree about what side by side means.
- A constraint policy carries it, attached to a resource or to its type, so a house that wants it says so and a house that does not never sees it. Being asked and being enforced are one setting: there is no second place to configure and no second thing to forget.
- The seam is an interface any policy may implement, so another rule can put its own question in the booker's way without the cart learning what it is about.
- One setting decides who is asked: everybody whose places ended up apart, or only a booker the house placed.
- The sentence follows who chose: the places you chose, against the places given to you. A mixed order counts as placed.
- The Checkout button is held out of reach until every question is answered. Client-side only, so a booker with no JavaScript is refused on the server rather than locked out.
- A party of one, and a line holding no place at all, have nothing to acknowledge and see nothing.
- The refusal is attached to the checkbox itself, not printed as a loose banner above the page.
- The seat map's own Checkout goes. The cart is the one place a basket is committed, because it is the one place a rule gets to stand in the way, and a second way to commit would be a way around it.
Remaining tasks
Docs and the French translation in the same commit. Tests covering a scattered event, an adjacent one, a party of one, two evenings in one basket, and the cart page itself.
User interface changes
A required checkbox in an event's card on the cart page, present only when that event's places are apart, with the Checkout button held back until it is ticked. The seat map offers Go to cart and no longer offers Checkout.
AI-Generated: Yes (Claude Code wrote the code and ran it, and helped draft this issue summary.)
Issue fork yoyaku-3616324
Show commands
Start within a Git clone of the project using the version control instructions.
Or, if you do not have SSH keys set up on git.drupalcode.org:
Comments
Comment #3
mably commentedComment #4
mably commentedComment #6
mably commented