Changelog
ShippedBackend

One product, one outcome, whichever button they clicked

A payment tells us which product was bought. It never tells us which buy button, paywall or pricing column it was bought from, because that is not in the webhook. So there can only be one answer to the question "what happens in Ghost when somebody buys this". Until today the same product could carry a different answer for each widget it appeared in, and a purchase applied all of them in the order they happened to be stored. Nobody lost access, everybody got that, but whether the buyer was subscribed to your newsletter and which label they were given depended on which widget you had saved last. That is now impossible rather than merely avoided: the database refuses a second answer for the same product. The rule is also written by the server as part of saving the widget, so a widget that takes money without granting anything is no longer a state that can exist.

  • One rule per product, enforced by the database rather than by whichever editor happens to be saving
  • Saving a widget writes its rule in the same step, so the two can never disagree
  • Product Mapping now says what a purchase does, in a sentence, and lists every widget offering that product
  • The check for the paywall script now confirms the script belongs to your publication, instead of accepting any PayGlue script it finds
  • Blog articles no longer scroll sideways on a phone, and one article can no longer end up with a different text size than the rest