# Versioned Confirmations for Collaborative Photo Selection

A client confirms twelve photographs for retouching. Another person changes the shared favorites moments later. When the photographer opens the project, which twelve images did the confirmation cover?

A mutable selection and a confirmation timestamp cannot answer that reliably.

GalleryDock’s [explanation of shared favorites and selection confirmation](https://gallerydock.com/faq) describes a practical requirement: clients can confirm a selection, reopen it, and confirm again. That behavior raises a useful SaaS architecture question: how should a backend preserve each decision while collaboration continues? The following is a proposed design, not a description of the product’s implementation.

## Separate working state from confirmed state

Keep the editable selection separate from its confirmation history.

The working state contains selected asset IDs and a monotonically increasing revision. Each successful edit increments that revision. A confirmation stores an immutable snapshot containing the selected IDs, source revision, server timestamp, and the available actor or session reference.

Do not store only the number of selected images. Two different selections can contain twelve items.

If media can be replaced, include asset version identifiers too. Otherwise, a stable image ID might later resolve to different content.

## Confirm the revision the client actually reviewed

Send the last observed revision with the confirmation request:

```json
{
  "expectedRevision": 17,
  "idempotencyKey": "confirm-7c82"
}
```

Inside one database transaction, authorize access, lock the selection record, and compare its revision with `expectedRevision`. Every selection mutation must acquire the same lock before changing membership or incrementing the revision.

If they differ, return a conflict response. The interface should refresh the selection and explain that it changed before asking for confirmation again.

If they match, copy the membership into a confirmation record and commit. Downstream retouching jobs reference that confirmation ID rather than reading live favorites.

Scope idempotency keys to the authorized operation. A repeated request with the same payload should return the original confirmation; reuse with a different payload should fail.

## Reopening should preserve history

Reopening creates another editable stage without rewriting the previous snapshot. A later confirmation records a new decision.

This keeps work already started traceable. The interface can show which confirmation a job uses and whether a newer one exists.

A shared gallery password also does not establish an individual’s identity. Record only the identity evidence actually available.

The essential invariant is straightforward: editing today’s selection must never silently change yesterday’s confirmed work order.
