Download Latest Version OpenReceive v0.4.33 source code.zip (14.5 MB)
Home / v0.4.3
Name Modified Size InfoDownloads / Week
Parent folder
openreceive-rails-0.4.3.gem 2026-09-03 59.9 kB
openreceive-server-0.4.3.gem 2026-09-03 69.6 kB
openreceive-0.4.3.gem 2026-09-03 44.0 kB
openreceive-express-0.4.3.tgz 2026-09-03 24.5 kB
openreceive-next-0.4.3.tgz 2026-09-03 23.8 kB
openreceive-node-0.4.3.tgz 2026-09-03 78.0 kB
openreceive-provider-data-0.4.3.tgz 2026-09-03 470.9 kB
openreceive-react-0.4.3.tgz 2026-09-03 75.1 kB
openreceive-svelte-0.4.3.tgz 2026-09-03 23.8 kB
openreceive-vue-0.4.3.tgz 2026-09-03 23.4 kB
openreceive-0.4.3.tgz 2026-09-03 21.9 kB
openreceive-angular-0.4.3.tgz 2026-09-03 32.4 kB
openreceive-browser-0.4.3.tgz 2026-09-03 172.1 kB
openreceive-core-0.4.3.tgz 2026-09-03 48.0 kB
openreceive-elements-0.4.3.tgz 2026-09-03 74.8 kB
openreceive-fastify-0.4.3.tgz 2026-09-03 25.0 kB
openreceive-http-0.4.3.tgz 2026-09-03 59.8 kB
OpenReceive v0.4.3 source code.tar.gz 2026-09-03 3.1 MB
OpenReceive v0.4.3 source code.zip 2026-09-03 3.8 MB
README.md 2026-09-03 5.1 kB
Totals: 20 Items   8.3 MB 0

Four embedding fixes found mounting the drop-in in a 560px card on a 1280px page, plus a quieter server log while a payer waits.

The checkout lays itself out by its own width

Every responsive rule in the checkout used to be a viewport media query (sm: / md: / lg: in orClasses, and vw-based QR widths). The drop-in is an embedded component: the host decides its box, and that box is routinely far narrower than the viewport. In a 560px card on a 1280px page the md: two-column wallet list fired and split 560px into two 234px cards, whose icon-and-name column collapsed to 1.6px — the 28px provider icon was crushed to a sliver and the name truncated to nothing. The same page at a 700px viewport was perfect.

The root (orClasses.root) is now a CSS size query container (container-type: inline-size, named openreceive), and every internal breakpoint is a container query — @sm: / @md: / @lg: / @min-[390px]: — at the SAME rem values as before (40rem, 48rem, 64rem; set in styles.source.css, since Tailwind's container defaults are much smaller). The QR and its caption size in cqw. A checkout mounted in a sidebar, modal or split view lays out like a screen of that width. Container queries and cqw have shipped in every browser since 2023; there is no fallback and none is needed for a payments page.

What this asks of the host: give the root a width. It is block-level, so any normal container does; as a flex or grid item it needs flex: 1 or width: 100%, because an inline-size container cannot size itself from its contents. A host that had widened its page so the two-column layout had room (twotensors' 760px container) can shrink it again.

The pre-create screens are themed

The React "Creating checkout…" spinner and "Could not start checkout." error screens rendered without the resolved data-theme, so both painted the light palette on a dark host — a white flash on every checkout open, and an all-white error screen. They now resolve the theme exactly as the checkout does (lock, ancestor ThemeScope, stored choice, system) and render as the checkout's own root, surface and padding included. The custom element already did this.

The root pads its own surface

daisyUI paints the theme's base-100 on the checkout root, and the root had zero padding: a visible colour slab with the QR, status copy and caption flush against its edges, plain to see on any host whose background is not exactly base-100. The root now pads and rounds itself (p-4, rounded-box) on every stack, including the creating and error screens. A host that draws its own card and wants no second surface sets --root-bg: transparent on [data-openreceive-root], and a host that wants a different inset overrides padding there. Both work because every rule in the shipped stylesheet is :where()-wrapped and carries zero specificity — a host's own selector, however plain, wins on the same property. That is now a documented compatibility promise (docs/guides/frontend-checkout.md, "Layout and surface").

The caption under the QR is money

112,128 sats / $87.0 US is now 112,128 sats / $87.00 USD. Fiat values render at exactly two decimals with thousands grouping through exact bigint math (formatFiatValue in the browser package's checkout formatter), so a Ruby BigDecimal echo of 87.0 and a Node 87.00 print alike, and the dollar carries its ISO code. The same formatter feeds the transaction details' fiat row and the swap limit hints, which already had two decimals.

One line per status poll

payment.reconcile.completed fires on every status poll while a payer waits. On Node it printed ten lines: the console logger passed its fields as a second console.info argument, and Node breaks any object past ~70 characters across lines. createConsoleLogger and createAppConsoleLogger now print one line per event with fields inline as key=value (strings with whitespace JSON-quoted, nested values in single-line inspect form), and the reconcile event's message is the decision itself — 1 pending, 1 settled, 2 pending, 3 pending of 4 attempts when a walk was truncated — with zero-valued extras dropped and the two walk timestamps folded into one window=from..until field. attempt_count, settled_count and pending_count stay as structured fields. The Rails engine's line is the same shape ([openreceive] payment.reconcile.completed: 1 pending attempt_count=1 window=…). A host that also wants Rails' own request logging quiet for the poll route uses Rails' knobs (config.log_level, Rails.logger.silence), which this gem does not touch.

Tests: the e2e suite gained embedded-layout.spec.ts (a 560px host box on a 1280px viewport — provider icons ≥ 24px, names visible, root a query container with ≥ 16px padding, QR in cqw, tutorial modal still covering the viewport, on React and the custom element); React unit tests pin data-theme on both pre-create screens; checkout-format.test.mjs pins the money formatter and the caption.

Source: README.md, updated 2026-09-03