Changelog

All the latest updates, improvements, and fixes to Decal

Saved Carts, Rescheduling From Your Cart & Payout Method Clarity

Saved Carts

Customers can now keep items in their cart for a week and come back later to finish.

Held appointment times still expire after ten minutes, which keeps them available to everyone else. When one does, the item stays in the cart, marked as needing a new time and showing the time originally wanted. Checkout waits until every booking has a time held, and says how many still need one.

Rescheduling From Your Cart

Customers can pick a new time for a cart item without leaving their cart. An item whose held time expired shows a Pick a new time button, which opens the same picker as rescheduling an appointment and updates the item in place. With several expired items, the picker walks through them one after another.

Items with a time still held get a Change time option. If the new time turns out to be taken, the original time is kept.

Payout Method Clarity

Getting paid to a bank account is now the direct path. Merchants without a settlement wallet of their own go straight into the bank payout flow, and those who have one see both options, bank first. A disabled stablecoin option now says what's actually wrong, and an organization with no payout destination at all says so.

Backing out of a payout is recorded as Canceled rather than failed. Closing the dialog, or letting the authorization time out, leaves a muted Canceled row in your activity feed and returns your funds to your available balance. A payout that genuinely broke shows a red badge.

Minor Improvements

  • Your customer list stops doubling up. A number typed as 415-555-1212 and the same one from Square as +1 415 555 1212 now match one customer. International numbers sync to Square too.
  • An invite link that no longer works says why. Already joined, already used, canceled, expired and not found each get their own screen naming the organization.
  • Treasury transfers that hit a problem stay on your Finances page, with a plain explanation and a link to the details.
Read more →

Self-Serve Cancellations, Applied Booking Policies & Booking Page Location Details

Self-Serve Cancellations

Customers can now cancel their own appointment from their booking page, and the refund your cancellation policy calls for is issued automatically as store credit If the customer is not eligible for a refund at time of canceling, they can still cancel and the page says so before they confirm.

The cancel dialog on a customer's booking page, showing the store credit refundThe cancel dialog on a customer's booking page, showing the store credit refund

Bookings with no cancellation policy, and anything Decal can't refund automatically, still show the customer a "contact the business" message so your staff can cancel and refund manually as needed.

Applied Booking Policies

The dashboard's booking details page now shows which of your policies apply, in plain language, and flags any policy you've changed since, so you can see the terms the customer actually agreed to next to your current ones. Opening a policy's terms takes you straight to editing that policy.

Policy terms now read in neutral third person, "up to 24 hours before the appointment", so the same sentences work at checkout and in the dashboard. This changes the wording customers see.

Booking Page Location Details

The booking page for a single service or class now shows your location details below the time picker: map, address, phone, directions and opening hours. The location name links back to that location's full list of bookable services.

Those pages are listed in search results now too! A location page is titled with its location and city, each service page with its own name, duration and price, and both publish structured data so search engines can show them as rich results. Your cart, checkout and your customers' own orders stay out of search, as before.

Minor Improvements

  • Booking pages no longer offer dates inside your minimum notice. Where one can still be picked, the page names your real notice, "48-hour notice required", right away.
  • Customers land on their receipt after paying, and held times that expire during checkout are re-held automatically. A customer whose time was taken is told which one.
  • Cancelling one appointment on a multi-appointment order refunds that appointment's own price, including after it's been rescheduled.
  • Treasury funds held for you always appear on your Finances page, even when the transfer that started them failed partway, and an unfinished withdrawal can be claimed again from there.
  • Failed transfers explain themselves consistently everywhere they appear, including whether your funds moved. An expired payout now reads in a neutral color rather than red.
  • Transaction pages lead with the amount, "$42.00 Payment received", and link to the customer and order.
Read more →

Self-Serve Rescheduling, Customer Booking Pages & Improved Special Hours

Self-Serve Rescheduling

Customers can now move their own appointment. Signed in on their booking page, they get a Reschedule button that opens your real availability, in whichever timezone they've chosen, and confirming moves it on the spot. They get the usual reschedule email, and the freed slot returns to your open availability for other customers to book.

Choosing a new time on a customer's booking pageChoosing a new time on a customer's booking page

Your reschedule policy decides whether they can or cannot reschedule. Inside your notice window the button opens a Contact us to reschedule dialog with the terms that customer agreed to upon booking.

Customer Booking Pages

Customers now have a Bookings page listing every appointment they've made with you, upcoming ones soonest first, each row linking to their respective appointment. Cancelled and no-show appointments stay in the past list rather than disappearing.

Times show in the customer's own timezone by default, and a picker in the page header switches to each appointment's location timezone or any other.

Improved Special Hours

Every Special Hours entry now names its own effect: the date leads, a badge says whether the day is closed or open on different hours. Both notes are labelled by audience, Customers see: and Internal:, so the customer-facing message is no longer the unmarked one.

Removing an entry asks first and names the date it clears. Entries that have already ended are tucked behind Show past, and closing the offering wizard with an unsaved entry now warns you.

Minor Improvements

  • Booking failures say what happened. A service pulled from a location says so, a full cart tells the customer to check out first, and only a genuine clash with another customer says a time was just taken.
  • Picking a payout wallet takes one click, with each wallet's name above its address and the default marked.
  • Treasury states correct status: in cooldown, ready to claim, queued, or moving.
Read more →

Bank Payouts, Cancellation Policies & Terms at Checkout

Bank Payouts

Merchants can now pay out from their Decal balance straight to a bank account. Pick an amount, link your bank once inside the payout widget, and the money leaves your balance directly. Bank payouts have a $2 minimum to cover the processing fee.

Cancellation & Reschedule Policies

Your cancellation and reschedule terms now live in one library. A new Policies page under Organization settings lets you create, rename, edit, and archive them, then attach one to any offering from its Policies tab. Set a default per type for your whole business, and override it on any location.

Policy Terms at Checkout

Customers read an appointment's terms before they pay, on the payment step, and again on their booking page afterwards. Each policy opens in plain language: "A full refund up to 24 hours before your appointment. A 50% refund up to 2 hours before. No refund after that."

At checkout these are the exact terms about to be attached to the booking. On the booking page they're the terms in force when it was made, so tightening a policy never changes the deal for existing bookings.

Minor Improvements

  • Developer Mode is a new add-on. Turn it on for a Developers area holding your API keys and webhooks.
  • Pay links preview with your name. A shared link reads "Pay Acme Coffee" now, and the amount is deliberately left off.
  • A dashboard balance that can't be read shows a dash, not $0.00, with a notice that your funds are safe. A genuine zero still shows $0.00.
Read more →

Classes on Your Booking Calendar, Class Rosters & Improved Checkout

Classes on Your Booking Calendar

Classes show up on your booking calendar as soon as you schedule them. Each one is a single block carrying its seat count, so an empty class still holds its room and time. A class whose bookings were all canceled stays on the calendar too.

A Group Fitness Class block on the booking calendar showing "1 of 35 spots" with its roster openA Group Fitness Class block on the booking calendar showing "1 of 35 spots" with its roster open

When you change a class's schedule after people have booked, the old time is flagged Schedule changed and says what happened: the bookings are still active, the attendees haven't been told, and you can keep the session or reschedule them from the roster.

Class Rosters

Clicking a class on the calendar opens its roster, and a View button there opens a dedicated class page. An Overview tab covers the location, time, and seats booked; a Roster tab gives the attendee list a full-width, searchable table. Canceled attendees stay listed, and you can add an attendee from either tab.

The Roster tab of a class page with a searchable attendee table, Status and Payment filters, and a confirmed attendeeThe Roster tab of a class page with a searchable attendee table, Status and Payment filters, and a confirmed attendee

Each attendee's payment status sits alongside their booking status, and you can filter by it. A booking with no order behind it, a comp, a free session, or someone paying in person, is marked No order rather than counted as unpaid.

Improved Checkout

Paying an unpaid order now uses the same layout as the cart, with the order summary alongside the payment step. Details you require before payment (name, email, phone) are collected on the page itself rather than in a pop-up.

Choosing a payment method selects it, and the Pay button starts the payment and shows the amount being charged. Name, email, and phone can now be collected on any order, including in-person purchases, where they're optional.

Minor Improvements

  • Cancelling from the booking calendar now offers refund controls. The Cancel button opens the same cancel-and-refund flow as the booking page: reason, refund amount, refund method. Past a cancellation window you can override the policy and cancel anyway, with your reason recorded.
  • Booking times are right the first time they appear, instead of showing in UTC for a moment before switching to the customer's own timezone.
  • A new Security page under Account lists every device signed in to your dashboard, and ends any of them or all your other sessions at once.
  • Connecting Square or Lightspeed reports its real outcome. A connection that had succeeded used to report a failure and skip the import of your locations.
  • Confirmation dialogs can't be dismissed while they're working, so a refund or a cancellation can't be abandoned halfway through.
  • Email capitalization no longer matters for signing in, team invites, or matching customers.
Read more →

Booking Reminders and Configurable Homepages

Booking Reminders

Reminder emails now go out ahead of every appointment, on every account running Bookings. There's nothing to turn on.

Customers control their own reminders from their notification settings on your site, alongside confirmations, cancellations, and reschedules. Reminders are the one they can switch off completely.

A customer booking reminder email showing the date, time, and locationA customer booking reminder email showing the date, time, and location

Booking confirmation and reschedule emails now carry one-tap Add to Calendar buttons for Google Calendar, Apple Calendar, and Outlook. Each with its own icon, plus a link to view the appointment online. The links resolve live, so a link in an older email always adds the appointment's current time even after rescheduling.

Add to calendar links for Google, Apple, and Outlook above a Manage appointment buttonAdd to calendar links for Google, Apple, and Outlook above a Manage appointment button

Configurable Homepages

Your site's homepage now matches what you sell. If you take bookings, visitors land on your bookable services and can pick a time without signing in first. Merchants running customer balances keep the homepage they have today, and if you run both, bookings takes it.

You can set this yourself under Website → Settings. Every option says what a visitor lands on, Auto tells you which page it currently resolves to, and options that need an add-on turned on first say which one. Saving takes effect on your live site right away.

Minor Improvements

  • Booking emails link to your notification preferences and published policies at the bottom. Nothing appears for a policy you haven't published.
  • Taking your site online or offline moved to the actions menu on Website → Settings, with a Live or Offline badge beside the title. Both directions confirm first and say what happens.
Read more →

Stored Value Preset Names, In-Place Editing & Consistent Amount Formatting

Named and Editable Preset Amounts

Merchants can now give every Stored Value top-up/reload amount an optional name, so a $210 reload is presented as "10-Session Pack" alongside the dollar figure. Add one from Stored Value → Settings in the Preset Amounts card. Click any preset there to load its amount and name back into the form, change either one, and hit Update. Re-entering an amount you already have renames it in place, and renaming works even when your list is full.

The Preset Amounts card with named reload amounts including $210 Class 6-pack and $900 60-min PT 10-packThe Preset Amounts card with named reload amounts including $210 Class 6-pack and $900 60-min PT 10-pack

Customers see the name wherever they pick an amount: on your balance page, in the add funds widget on your homepage, and in the top-up grid at checkout. It sits above the dollar figure on the amount buttons, and beside it in the dropdown when you offer a longer list of amounts.

A customer's Add funds to your balance sheet with the amount dropdown open, every amount listed with its nameA customer's Add funds to your balance sheet with the amount dropdown open, every amount listed with its name

Consistent Amounts and Bonus Copy

Whole-dollar amounts drop the trailing cents everywhere they appear, so your settings page reads $10 $25 $50 $100 and the bonus preview beside it reads "Get a $5 bonus when you load $25". Amounts that carry real cents still show them, so a $12.50 preset is unchanged. Order lines, receipts, balances, and the "added to your balance" confirmation all keep exact cents.

Minor Improvements

  • One bonus callout on the add funds sheet, not two. It follows the amount your customer picks, pointing at the next tier and then confirming the bonus once the amount qualifies.
  • Customers can see where a balance spends. A note under the amount picker names your balance and your business, so it's clear the balance covers anything you sell.
  • Section headings read as headings. Select amount and Select Payment Method are larger and marked up properly, so a screen reader can move through the sheet section by section.
  • Amount buttons and the named-preset dropdown are taller, which makes them easier to read and tap on a phone.
  • Issue credits limits are described in the right units. The minimum read "at least $1.00" for a one-cent floor and the maximum read "cannot exceed $100,000.00" for a $1,000 ceiling. They read $0.01 and $1,000 now.
Read more →

Location Special Hours, Vacation Closures & Booking Page Messages

Location-Wide Special Hours

Merchants can now set Special Hours for any location to better control their availability across every bookable service or class at that location. Mark a single date Closed, set Different hours for a day, use Closed for a range for a vacation, or Block a time range inside a day. Dates and times are stored and shown in the location's own timezone.

Setting Special Hours for a locationSetting Special Hours for a location

The controls on an individual offering are called Special hours & closures now too, so both places use the same standard language of "special hours" (as opposed to "date exceptions" previously).

Customer Messages on Closed Dates

Every special hours entry has an optional Customer message field to display a custom message directly on your booking page for those dates. Customers see it on the date in the picker, and again when they select a date for both closed days or modified hours.

The old Reason field is relabeled to Internal note for clarity. It is still only shown to you and your staff, never customers.

Minor Improvements

  • Sign-in failures say what happened. You get a plain message above the sign in field, too many attempts or we couldn't reach the sign in service, instead of a stuck form or a raw string like "Request failed with status code 403".
  • Character counts appear as you type. Fields with a length limit show how much room is left, and going over shows the count in red instead of quietly cutting your text short. It's on the special hours customer message and internal note, your balance name and description, and your sign-up page headline, subheading, and bullet points.
  • Sign-up bullet points enforce one limit. They accepted 200 characters when only 120 could be saved. Both the counter and the check are 120 now.
  • The balance name's 100-character limit fails with a readable message in the setup wizard and on the settings page, rather than a raw validation error.
  • Opening the signup page while already signed in takes you to your dashboard. Invite links are unaffected, so a signed-in account can still join another business.
  • Reloading right after you sign up no longer asks you to confirm leaving the site.
Read more →

Stored Value and Custom Websites Are Now Available to Everyone

Stored Value Is Open to Every Merchant

Stored Value is out of early access. Turn it on from Add-ons → Stored Value & Customer Balances, name the balance your customers will see, and launch your program. From there customers can preload funds and pay from their balance at checkout.

The Products & Add-ons page showing Custom Website and Stored Value & Customer Balances available to activateThe Products & Add-ons page showing Custom Website and Stored Value & Customer Balances available to activate

Naming the balance is the one decision worth thinking about, so there are quick-pick suggestions like "Store Credit" and "[Your Business] Cash" to start from, whether you're setting it up for the first time or renaming it later.

Custom Websites, Out of Beta

The Custom Website add-on is now available to every merchant. Turn it on from Add-ons → Website and you get a branded storefront at <your-handle>.decal.site.

Nothing switches on by itself. The add-on stays off until you enable it, and merchants already using it are unaffected. Custom domain support for your Decal Site is on the roadmap and will roll out to select merchants in private beta soon.

Booking Availability Comes From One Place

A time your booking page shows as available is now a time that actually books. The times it lists, the times the dashboard offers when you book someone in by hand, and the check that runs at Add to cart and again just before payment are all the same calculation. They used to be separate, and separate implementations can disagree, which is how a class could show seats free and then get refused at checkout.

One behavior follows from that merge. An offering at a location with no business hours configured is now closed everywhere. It already showed no times on your booking page, and it now refuses the booking too, rather than accepting any time of day.

The booking page's date list and its dimmed-day prediction come from the same place as everything else now. Which dates are offered hasn't changed, but the two can no longer drift apart, which would have looked like a date quietly missing from the picker.

Your Notice and Advance Windows Apply Everywhere

Your minimum booking notice and maximum advance window now hold wherever a booking can be made, not only over the times your booking page lists. A customer who left the page open until their chosen time fell inside your notice window used to be able to add it to their cart and only hear about it at payment. They're told at Add to cart now, in words that point at the fix: pick a later time.

The advance window was only ever applied to what the booking page showed, so a booking made any other way could land years out. It now holds at add-to-cart, at checkout, and on a reschedule.

Booking from the dashboard is unaffected. Both limits are policy for your customers, so booking someone in for tomorrow morning, or a year out, still works.

Revenue Stops Counting Balance Twice

Your revenue figures now reflect money you actually collected. A customer's balance load was being counted as revenue when they bought it and counted again each time they spent it down, which overstated revenue for any merchant running a stored value program. The revenue chart matches the card now.

Average order value measures what customers bought per order and no longer includes balance loads, which are deposits rather than purchases. Total orders and total customers are unchanged, since a load is still a real order from a real customer. Each card names which basis it's on, so it's clear why average order value isn't revenue divided by orders.

The figures are computed from your order history on every page load, so corrected numbers appear retroactively across every period, trend comparisons included.

Minor Improvements

  • Old decalpassport.com links land where they should. Apex, www, and every merchant subdomain redirect permanently to the matching page on decal.site, keeping the full path and query, so bookmarks, printed QR codes, shared links, and search results all still work.
  • Tables that show every row stopped after the tenth. Website Pages, Website Domains, and your saved payout wallets among them had no page controls and no way to see the rest. They show everything they hold now.
  • Site metadata errors appear under the field they belong to instead of in a toast, and Save stays disabled until you've actually changed something.
  • Records report a version over the API and in webhooks. Customers, orders, and locations now carry a counter that goes up only when the record actually changed, so if two webhook deliveries arrive out of order you can tell which describes the newer state. A re-sync that rewrites a record with identical data reports the same version rather than looking like a fresh edit.
  • A balance program left unnamed no longer produces a nameless line on a receipt. Programs now require a name, and any that were missing one are renamed to "[your business] Balance".
Read more →

Guided Registration for New Merchants

A Setup Checklist Instead of an Empty Dashboard

New accounts now land on a checklist that walks through getting your business ready, starting with your first location, and shows how far along you are. It replaces the dashboard full of zeros a brand new account used to open on.

The setup checklist on a new merchant's dashboard, with the first location ticked off and steps remaining for a service, Square, and brandingThe setup checklist on a new merchant's dashboard, with the first location ticked off and steps remaining for a service, Square, and branding

The list is tailored to what you told us at signup. Say Square is what you run on today, or ask for it during setup, and Connect Square appears as a step and ticks itself off once you've connected. Turn on Bookings and the checklist covers everything needed to take a real booking: a location first, then a service or class customers can pick.

Optional steps like adding your branding can be dismissed by an owner or admin, and stay dismissed everywhere you sign in. Once your setup is done the checklist disappears for good and your revenue metrics take its place. Accounts that have already taken a payment never see it at all.

Your Progress Follows You Around the Dashboard

While setup is unfinished, a slim strip sits at the top of every page showing how far along you are, with a link back to the checklist. Finishing a step like adding your first location no longer leaves you stranded on a settings page with no way back to what's left.

On phones the strip stays put. The header above it still slides out of the way as you scroll, but the strip does not, because it's the way back.

Signup Asks What You Want to Set Up

Pick Bookings at signup and it's switched on before you reach your dashboard. Pick Square integration, or tell us Square is what you use today, and your dashboard home offers you the connect step on arrival. Picking nothing keeps the flow exactly as it was. The same question appears when you complete setup from an invitation, and means the same thing there.

That step also asks what you run your business on today, and leaves room to tell us anything else about it, so we can point you at the right setup. Both answers are optional. Stripe joins Square, Clover, Toast, Lightspeed, Shopify, and WooCommerce in the list of platforms you can tell us about, here and on the application form.

Signup copy now describes the whole platform rather than only stablecoin payments, and tells you upfront that setup takes about three minutes.

A dashboard link now opens in the recipient's own organization. A URL like dashboard.usedecal.com/home/settings/locations goes straight there for merchants with one organization, and offers a picker labelled with the destination for merchants with several. Query strings and anchors survive sign-in and organization selection.

Signing in from a link that points at a specific page now takes you to that page even if you were already signed in. The destination used to be dropped and you landed on the dashboard home.

Switching organizations from the sidebar keeps you in the same section. Viewing Orders in one organization and switching takes you to Orders in the other. Links to a specific record fall back to that record's section, since records belong to a single organization.

Pages That Tell You What to Do Next

These pages now introduce themselves and open the right flow, instead of opening on an empty table with nothing to act on:

  • Settlement Wallets walks you through connecting a wallet you already own: what settles into it, and what verifying it costs (one signature, no keys shared).
  • Settings → Team shows what a teammate gets, their own login, role-based permissions, and their own activity history, with a button that opens the invite dialog. It goes away once you've sent an invite or added a second member.
  • Bookings prompts you to create your first bookable service and opens the wizard right there.
  • Locations explains what locations are for and opens the location wizard.

Bookings now asks for a location before anything else, because a booking can't exist without one. The bookings overview and the calendar both explain why and open the location wizard directly. The overview used to skip this check, so a merchant with no locations could add a service that was bookable nowhere.

Creating a location no longer throws you onto that location's detail page. You stay where you were, so adding a location from the bookings pages drops you back into setting up bookings.

Minor Improvements

  • Products & Add-ons leads with what you can turn on today. Anything still in beta or being built is grouped under a "Coming soon" heading further down the page, and every add-on card carries the same icon its sidebar link uses once you enable it.
  • Your names are capitalized for you. Type "acme coffee co" at signup and your organization shows up as "Acme Coffee Co", and the same applies to your own first and last name. A name you deliberately cased, like "eBay", "McKayla", or "van der Berg", is kept exactly as typed. You can change either one later from settings, where whatever you enter sticks as-is.
  • The user menu shows your name, not your email address. It was falling back to your email after signing up, completing an invite, or logging back in.
  • Turning on an add-on puts it in your dashboard navigation straight away, instead of on your next click. This applied to every add-on you enable, including ones you turn on long after signup.
  • Invited merchants see their own timezone, detected from their browser, rather than UTC pre-selected as though someone had chosen it.
  • The invite dropdown says what each role can do. No more guessing between Admin, Member, and Viewer, or reopening the dropdown to recheck the one you're not currently on.
  • The sole owner of an organization no longer sees "Leave organization" on the team page or their own member page. Transferring ownership first is a prerequisite that doesn't need a dead-end dialog to explain it.
  • Every page in an organization has a header on mobile. Square integration settings, Finances, Website, Products, and your business profile had none at all, leaving no way to reach the menu without scrolling back to the top. Customer detail pages no longer render two.
  • Three signup fixes. The page itself failed to load in production, because its social share card pulled fonts and artwork the moment the page rendered. The email field turned red with "Email is required" the moment you clicked anywhere else, before you'd typed anything. And the step indicator sat crooked on phones when a step name wrapped onto two lines.
  • Legal entity types are spelled out rather than abbreviated, so "Limited Liability Company (LLC)" is no longer easy to confuse with a Limited Liability Partnership.
Read more →

Free Items, Branded Customer Emails, and Fixed Booking Availability Exceptions

Branded Customer Notification Emails

Booking emails sent to your customers now lead with your business name and logo. Decal gets one small line in the footer. Set both under Settings → Branding and they carry through to every one of these emails. The booking emails Decal sends you are unchanged and still clearly come from Decal. All emails got a visual glow-up pass too: Decal's real brand colors and standard button appearance.

A rescheduled booking email leading with the merchant's logo and business nameA rescheduled booking email leading with the merchant's logo and business name

Logos are stored as PNG images to support transparency consistently across email clients.

Free Items Check Out Like Anything Else

An item priced at $0.00 can now be booked and checked out. When an order comes to $0.00, checkout skips payment selection and completes the booking right there. Your customer still gives their name and email, so you know who's coming. A cart that mixes a free item with a paid one checks out the usual way.

This works everywhere a customer can buy: your checkout page, an order link, and hosted checkout.

$0.00 prices read as FREE on booking pages, in the cart, at checkout, and on order confirmations, so a free intro session looks intentional rather than like a price you forgot to set.

Booking Times Hold Up in the Right Timezone

Following on from booking times in your timezone, every location now needs a timezone, and it can't be left blank or cleared later. A location without one used to fall back to UTC without saying so, which threw off booking times, availability, and date exceptions for anyone not on UTC. Locations fall back to your organization's timezone now, and your organization's timezone is required as well, since it also sets the day boundaries in your reporting.

Date exceptions got some bug fixes. Closing a specific date used to save and display it one day off, so the day you picked stayed open and a neighboring day closed instead. An offering's closures and special hours resolve against its location's timezone now, and each exception shows the timezone it applies in.

Two smaller pieces of the same work. Only standard IANA timezones are accepted, so abbreviations like EST that never adjust for daylight saving can't be stored and your booking times stay right year-round. And when a connected point-of-sale sends a timezone we can't read, the location keeps the one it already had, or falls back to your organization's, instead of being handed a value the booking system can't interpret.

Locations created through the API and organizations created from a merchant application pick up the same fallback.

Booking Times Outside Your Regular Business Hours

A bookable time you set deliberately is now what decides when something can be booked, whether that's a class or event running on its own schedule or a date exception with special hours. Your location's regular business hours no longer overrule it.

Anything scheduled outside those hours used to be visible but unbookable. A 6pm bootcamp at a location that closes at 5pm appeared on your booking page with its seat count and then failed on every Add to cart, and a date you opened outside your usual hours behaved the same way. The booking page was showing the right thing all along. The check behind it disagreed and is now fixed.

The error your customers see got fixed with it. "That time was just taken" used to appear for any unavailable time, including ones your own settings had closed, so customers kept retrying a slot that could never work. That wording is reserved for a time someone else genuinely claimed first. A closed time says it's closed, both at add-to-cart and at checkout.

Minor Improvements

  • Team invite emails say when the invite expires. The expiration was already enforced when someone opened the link, but the email gave no hint it existed. The invited role now reads the same way in the email and on the acceptance page, as "with Admin access" or "with Member access". Roles other than Owner and Admin used to get dropped from the email entirely.
  • Buttons stop rendering blank on first paint. On pages that load data before rendering, a dialog, dropdown, tooltip, or popover trigger whose contents included an icon didn't show up until the page finished loading in the browser.
Read more →

Bookings Are Out of Beta, the Wallet Page, and Cleaner Checkout

Bookings Is Out of Beta

Bookings is available to every merchant now! Find it under Products & Add-ons and switch it on to start taking appointments. Customers book from your site whenever suits them, and you manage schedules, staff, and availability from your dashboard.

A customer choosing a date and time on a booking pageA customer choosing a date and time on a booking page

It stays opt-in. Nothing appears on your site until you turn it on, and the add-on clearly spells out what happens if you turn it back off: your booking pages go offline, but your bookings, staff, and availability settings are kept and come back when you re-enable it.

Booking pages for classes and events that repeat on a set weekly schedule also show only the dates they actually run. A weekly Wednesday class lists the upcoming Wednesdays instead of a full week strip where the other six days lead nowhere. That compact list used to appear only for offerings built from individually picked one-off dates. Schedules that run most days of the week keep the week-by-week strip, which is easier to page through and lets customers jump ahead with the calendar.

The Balance Page Is Now the Wallet

Your customers' account page has moved from /balance to /wallet, and reads Wallet in your site's navigation. It's the same page. The new name makes room for everything else a customer will hold with you, not only their balance. Every existing link, bookmark, and QR code pointing at /balance sends people straight to the new page, so nothing you've already printed or shared needs redoing.

Improved Customer Checkout Experience

When a signed-in customer's account was missing part of their name, checkout asked for it and then threw away what they provided, so your dashboard kept showing them as incomplete. Checkout now treats the name as one answer: whenever it asks, both the first and last name go onto the customer's record, replacing whatever partial name was there.

A related problem is fixed too. A customer who signed in with no name on file and then paid for anything had their email address stored as their first name, which is what your dashboard, receipts, and card billing details then showed. Affected records correct themselves the next time that customer checks out and enters a name.

Names provided in lower case are capitalized when they're saved, so "jane doe" is stored and shown as "Jane Doe" on the customer record, the order, and the card billing details. Deliberate capitalization is left exactly as typed, so "McDonald", "van der Berg", and an all-caps entry are never rewritten.

Card billing names stay separate from the customer record. The name on the card can belong to someone else (a spouse's card, for instance), so only the name entered in checkout's personal information is saved to the customer.

Customers signing in used to see two competing sets of legal links: Decal's Terms of Service and Privacy Policy, followed by a second copy of yours in the same sentence. Every checkout and sign-in surface now shows a single line: "By continuing, you agree to the Terms of Service and Privacy Policy."

When both Decal and your business have a document for one of those, clicking the link opens a short list so your customer can pick either one. When only one exists, the link opens it directly. Checkout shows this line even if you have no policies configured, where it previously showed nothing at all.

More Room and More Time for Bank Verification

Following on from the bank verification work, the verification step during card checkout now waits a full 30 seconds before offering the manual Continue button, so a customer still typing in a one-time code isn't prompted to skip ahead mid-verification. When the button does unlock, it says why: "This is taking longer than expected. If you finished verifying with your bank, continue here."

The verification window is noticeably larger on desktop, giving the bank's page more room, and Cancel sits beside the primary button on one line rather than stacked underneath, which hands that vertical space to the bank's page as well.

On a phone, the bank's page runs edge to edge. On screens too narrow to fit it, the page scales down just enough to fit, so pages built for a desktop browser no longer get cut off on the right with the Submit button stranded off-screen. Screens wide enough for the page are left alone.

Small Treasury Balances Start Earning

Treasury auto-deposit moves small balances now instead of leaving them idle. With rewards switched on you could sit indefinitely with a few dollars in your wallet and nothing happening, because anything under $5 was held back by a conservative platform minimum that wasn't shown anywhere. That minimum now matches the actual deposit minimum, so those balances start earning.

The Treasury settings page states the minimum directly, so a balance too small to move is explained rather than silent.

Business Details Are Quicker to Fill In

Your business profile's dropdowns are searchable. Type to filter entity type, country, tax ID type, account purpose, source of funds, and owner role or title instead of scrolling a long list.

The MCC and secondary industry code pickers are searchable too, with curated code lists behind them. The secondary code list follows your country of incorporation (NAICS, UK SIC, or free text), and the label in the review summary changes to match.

Your tax ID has a show and hide toggle. Dropdown placeholders read in the muted color rather than looking like answers you already gave, and review card rows line labels up with the top of multi-line values.

Decal Logos and Colors in One Place

There's a public branding page at usedecal.com/branding with downloadable Decal logos, click-to-copy color values, and naming guidelines. Send that one link to a partner, a payment processor, or press instead of assembling assets by hand. Dark-mode logo, lockup, and wordmark variants ship alongside the existing light-mode files, in SVG and PNG.

Minor Improvements

  • Teammates show by name or email. Activity, API key, and wallet lists identify a teammate without a display name by their email address instead of an auto-generated handle. Team settings, invite emails, invite links, and the sidebar account menu do the same, so auto-generated handles no longer turn up anywhere in team management.
  • Enabling an add-on checks your website pages first. Turning one on from Products & Add-ons runs the same page-conflict check the rest of the dashboard already did.
  • The Checkout button on booking pages shows a loading state while the cart page loads, matching the cart page's own Checkout button.
Read more →

Bank Verification for Card Payments, Faster Card Checkout, and Booking Email Improvements

Card Payment Stops Asking for Details You've Already Given

When a name and email are already known, either typed into checkout moments earlier or saved on your customer's account, the card form shows them as a short summary instead of empty inputs. That leaves only the card details to fill in, plus a billing address where your processor requires one. A Change link is there for anyone paying with a card in someone else's name.

The card payment sheet showing the customer's billing details as a summary with a Change link, leaving only the card number to fill inThe card payment sheet showing the customer's billing details as a summary with a Change link, leaving only the card number to fill in

This applies to checkout, the order payment page, and balance top-ups. A top-up link shared with someone else still collects that payer's own details.

Where a name genuinely is missing, checkout asks for it now instead of moving straight to payment with nothing on file. Their known email is shown read-only rather than collected again. Relatedly, a customer with no name saved no longer sees their email address sitting in the First name field on their account page, or repeated back to them as their name in the checkout Paying as summary.

Card Payments That Need Bank Verification Now Go Through

Some banks want a second confirmation from the cardholder before they'll approve a charge. Until now those payments failed outright, and your customer saw a generic failure message with nothing useful to act on.

Checkout now shows the bank's verification step right in the payment sheet and finishes the payment once the bank approves it. The step opens full-screen, so there's room to read and tap through the bank's page, which matters most on a phone. This works everywhere your customers pay by card: the checkout page, an order's payment page, and a payment session in the pay app.

A few things keep it from turning into a dead end:

  • Backing out cancels the attempt cleanly, so your customer can try the same card again or pay another way.
  • The screen says what it's waiting on. A "Waiting for bank approval" indicator replaces what looked like a frozen page, and it turns into a button your customer can tap to confirm they're finished as soon as it looks like they are.
  • Reloading mid-verification warns first, since a reload would lose the payment and mean starting over.
  • Payments finish regardless of which bank issued the card. Banks report a completed verification in more than one way, and only one of those was recognized before.

If a verification is started and then abandoned, that attempt gets cleared on its own, so you're not left with a payment that looks like it's still in progress. Anything that may have been charged is flagged for review rather than cleared.

Clearer Reasons When a Card Doesn't Work

A declined card now tells your customer why, in plain language, along with whatever next step the processor suggests. Before, most of these arrived as the same generic failure, and the ones that did carry a reason showed it in the processor's own Title Case wording.

  • A bank asking for verification says so, with the option to retry or use a different payment method.
  • A flat rejection from the bank shows that reason instead of a catch-all failure.
  • Retrying a card too quickly asks your customer to wait a few minutes and try again, rather than telling them to contact support.
  • A verification page that can't load securely gets the same clear message and retry option, instead of leaving them looking at a blank screen.

Balance Top-Ups Show Up in Your Orders

Every balance top-up your customers buy is now recorded as a real order, so top-up revenue appears in your orders list and your reporting alongside everything else you sell. This is on for all merchants now, finishing the top-up work from a few weeks ago. Nothing changes for your customers: same sheet, pick an amount and a payment method, then Continue.

Top-ups bought from a mobile wallet pass go through that same order payment flow, which retires the old standalone top-up links. One upside for your website: the /topup page slug is free now, so you can use it for a page of your own.

Stored Value top-up amounts also sort correctly on the item page, where $10 could previously land after $100.

Booking Emails Sound Like Your Business

Booking notifications used your location's name wherever your business name belonged. If your location was called "Gym", customers got "You're confirmed at Gym" and "How was your visit to Gym?".

Customer emails now use your business name in the message itself and show the location in the Where details, where it belongs. They arrive from your business name too, and so do your own booking alerts, which used to come from "Decal".

Other changes across every booking email:

  • Your alerts lead with the location and time. "New booking · Gym · Sat, Aug 1 at 2:00 pm" reads at a glance in a notification, where "New booking at Gym" didn't.
  • A cancellation reads as a cancellation. Both versions now lead with "Booking canceled". A customer-initiated one used to say "Your cancellation is confirmed" in the subject and the heading, which is easy to skim as a confirmation.
  • A booking canceled automatically is labeled that way, so nobody assumes a teammate did it.
  • The inbox preview line shows the date, time, and location instead of repeating the subject.
  • A booking with no customer account attached says "A guest" rather than "A customer".
  • Multi-item bookings read properly throughout, including the thank-you email, which used to list every booked item as one long run-on.
Read more →

Itemized Card Fees, Clearer Refunds, and Booking Timezone Improvements

Itemized Cart Processing Fees

Card payments may carry a processing fee that the card processor bills on top of your order total. Checkout was showing that fee correctly, but nothing saved it. A $19.99 order paid by card recorded no fee at all, and the fee vanished from the customer's receipt the moment the page reloaded.

The charged total is now the recorded source of truth for what the customer paid. The payment summary on an order spells out the full breakdown:

  • Order total, what you charged.
  • Processing fee, paid by the customer to the card processor. It is not deducted from your payout.
  • Charged to card, what the customer actually paid.

An order's Payment Summary showing the order total, processing fee, and charged to cardAn order's Payment Summary showing the order total, processing fee, and charged to card

The order's payment summary also shows how much of the order has been refunded to date, and the payment status badge moved into its header. On your customer's side, the fee stays on their receipt after a reload, not only in the seconds right after they pay.

Every fee the processor bills is captured now, not only the credit card fee, and the portion you absorb is left out so the recorded fee is the customer's share. Transaction records show the correct charged amount too, which was previously off by 100x on the source amount.

Reimburse the Processing Fee When You Refund

You can now choose to reimburse the processing fee when you issue a refund.

That fee went to the card processor rather than to you, so reimbursing it comes out of your own funds. The refund dialog says exactly that, shows the amount, and leaves the box unchecked by default. It's available on a full refund of an order that hasn't been refunded before, and when it isn't available the dialog explains why.

Consistent Appointment Timezones

Booking times on the cart page and in the payment success headline were rendering in the location's timezone with nothing on screen to say so. Cart, checkout, the success headline, and the order receipt now all show a booked appointment the same way: converted to the viewer's timezone and labeled with its abbreviation.

If an order has bookings at more than one of your locations, each line now shows its own location. Before, every line took whichever single location the checkout page happened to resolve.

A Real Starting Point for an Empty Catalog

A merchant opening Catalog for the first time got an empty table with column headers, pagination controls, and "No catalog items found." That's now a setup card explaining what the catalog is for, with an Add Item button that opens the item wizard.

The card only appears when you genuinely have nothing. The catalog list defaults to showing active items, so an organization whose only items were archived used to look identical to a brand new one. It gets the table now, and can clear the status filter to find its items. Filtering or searching down to zero results keeps the table too, and says "No catalog items match your filters." instead of implying nothing exists.

Minor Improvements

  • The card form adds up out loud. The fee breakdown reads "$0.20 + $0.37 processing fee" so it's clear which part is the order and which is the fee.
  • Balance top-ups lead with the billed amount. The top-up sheet shows what the card will actually be charged, matching order checkout, rather than the amount before the fee.
  • Improved error messages in card payment forms.
  • Add-ons switch on right away. When we turn on an add-on or integration for you, it shows up on your site within seconds instead of taking up to five minutes.
Read more →

Booking Windows, Checkout Top-Ups, and a Cleaner Stored Value Setup

Booking Notice and Booking Window

Bookings has a Settings page now, with two rules you set yourself.

Minimum booking notice is how far in advance a customer has to book. Set it to two hours and nobody can book a time slot starting in ninety minutes. This replaces a hardcoded ten-minute floor, and the default is no minimum, so nothing changes until you set one.

Booking window is how far out customers can book. Set it to 30 days, or 90, or 7, replacing the fixed 30-day limit that used to apply to everyone.

Both rules are checked again at the moment a booking is being confirmed, not only when the customer first sees the time picker. A customer who put a time slot in their cart before you set a two-hour notice can no longer check out past it. Manual bookings you make in the dashboard are unaffected, since you can always manually override your own rules.

Failed Payments No Longer Hold Your Calendar

This one was costing merchants real availability. When a customer clicked Pay, the time slot was reserved before the card was ever sent to the processor. Every declined card left a booking sitting on that slot for up to 40 minutes, blocking customers who would have paid.

Bookings are now created only after payment succeeds. A declined card, an abandoned checkout, a wallet form that gets opened and closed: none of them leave anything behind on your calendar.

  • If you book a time yourself via the dashboard while a customer is mid-checkout on it, your booking wins and that customer is told the time is gone instead of being charged for it.
  • A completed payment now always produces a confirmed booking and clears the customer's cart. There was a case where a customer could pay, have the order marked paid, and end up with no booking. No longer!
  • Cancelled bookings no longer show on the calendar, so a freed-up time reads as free. The all-bookings table can be filtered to Pending.

Two customers still can't pay for the same time slot. The slot is re-checked before any money moves.

Stored Value: Top Up at Checkout, Set Up in One Step

Customers can now add a balance top-up while they pay at checkout, not only from inside the "pay with balance" flow. The page shows a nudge to load funds, with a low-balance alert when their balance is running down. Offered amounts come from the top-up presets you configured, and the top-up credits their balance, plus any bonus you set, once payment completes. Adding or removing one updates their cart properly now, so it survives a change to their booking and shows the right total.

Setting up Stored Value is a guided wizard. It creates your program, turns on Treasury rewards, and launches it in one pass, with no separate activation checklist.

Catalog Is Now Available to Everyone

Decal Catalog is out of early access and shows in the sidebar for every merchant.

Item pricing now lives on the item's variant. Nothing changes about how you set a price in the dashboard, but the item detail page shows each variant's billing type (e.g. one-time, recurring, etc) and price right in the Variants table, replacing the old "Default Price" card. Order line items also record which catalog item and variant they were sold from, and link to that item's page from the order, improving dashboard navigation.

Booking Emails From Your Own Name

Booking notification emails now send from your own handle on a dedicated notifications domain, so a customer sees Acme Corp <acme@notifications.mail.usedecal.com> instead of a shared no-reply address.

Login-code emails moved to their own sending domain too, which should get verification codes into inboxes more reliably.

Payouts Explain What They Need

A payout could previously be submitted, queued, and then fail in the background with an unexplained policy violation. The payouts page checked only the wallet payout policy, while a payout that converts stablecoins first also needs the token swap policy, and nothing on the page said so.

Payouts now check every policy the payout will use, up front, so you get a readable error immediately instead of a failure later. When a policy needs your review, the page shows a banner naming it and walks you through each one in turn. Your payout history stays on screen the whole time, and if no payout policy is active at all, the page tells you.

A Steadier Checkout

Customers were getting interrupted by a spurious "Your order was updated" dialog that didn't say what had changed, sometimes on pressing Pay and sometimes after leaving the page open for a while. That cluster is fixed. Several batches of improvements were made to improve order modification detection and presentation, improving stability and user experience during checkout. The dialog appears only on a real change and describes it correctly.

A balance top-up is no longer deleted when a customer's account gets linked to their order, and when a top-up genuinely can't be paid for, the customer is told which reason applies. A booking's date, time, and variant stay in the order summary through a refresh, and the hold countdown re-syncs after a top-up changes rather than counting down a deadline that had already been extended.

Minor Improvements

  • Confirm before you refund. Refunding an order, and cancelling or refunding a booking, now ask for confirmation first.
  • Checkout works at Decal-only locations. A location with only Decal payment methods and no external POS was incorrectly showing "Payment Not Available".
  • Reconnect and team actions work again. Square and Lightspeed reconnect, plus team management, were failing with a connection error from a URL redirect rule that caught more than it should have.
  • Website domain actions work again. "Set as primary", "Verify now", "Remove domain", and the redirect toggle failed with a generic "Invalid input" for any domain that wasn't already primary.
  • Phone numbers read like phone numbers, formatted consistently across the dashboard, with malformed values hidden instead of shown as a bare "+".
  • Mailing address on your policies. Decal-hosted Terms, Privacy, and Refund pages show your business mailing address in its own labeled section when you've set one.
  • Clearer cart messages. The cart says when an item hasn't been priced for online purchase yet, rather than a generic "couldn't hold that time", and an item that becomes unavailable while sitting in a cart is removed with a notice instead of vanishing.
  • Booking form polish. Duration uses the same quick-select presets as the catalog item form, order status badges show on mobile, and the "Create booking" wizard says "Add at least one service" instead of "undefined".
Read more →

Book and Pay Online, Automatic Booking Emails, and Store-Credit Refunds

Customers Can Book and Pay Online

Building on last cycle's customer booking pages, where customers could browse your services and pick a time, they can now finish the booking and pay online.

Customers add one or more of your services or classes to a cart, held together under a single countdown, and check out on a cleaner two-column checkout page: contact details and a desired payment method. Signed-in customers are recognized automatically, and guests enter their details once, which creates an account they can sign into later to see their history. An order is created only when a customer goes to pay, so revisiting, reloading, or going back never creates a duplicate. Each time slot is locked the instant before payment, and the booking is confirmed the moment payment succeeds. If someone takes the slot first, the customer is told directly at the payment step and can pick another, with no charge made.

The online booking checkout page with contact details and payment methodsThe online booking checkout page with contact details and payment methods

Customers can also book across more than one of your locations in a single checkout, for example a session at one studio and a class at another, paid once as one order. Each booking is still made at its correct location and shows in that location's timezone on the receipt.

Automatic Booking Emails

Bookings now keep both sides in the loop by email, from the first booking to the follow-up:

  • Confirmations go to the customer as soon as a booking is confirmed, and you get a new-booking alert.
  • Cancellations and reschedules notifies the customer and you. Reschedule notifications show both the previous time (now free) and the new one, so you don't have to cross-reference your calendar to see what opened up.

The confirmation email is redesigned into clear "When" and "Where" sections. The date is spelled out in full ("Saturday, August 1, 2026") and shown prominently, the location's full street address and formatted phone number appear, and "Get directions" is a proper button. Cancellation emails now show the reason in its own card below the booking details, so it reads clearly instead of a small line above them.

Customers control what they hear from you. A new Notifications page in a customer's account groups booking emails so they can toggle confirmations, cancellations, and reschedule notifications on their own. Confirmations, cancellations, and reschedules always keep email on, so customers always keep a record of their bookings.

Refunds as Store Credit

You can now refund a customer as store credit even before they've joined your stored value program. The customer's wallet is created automatically behind the scenes and the balance is waiting the first time they sign in.

Cancelling a paid appointment now opens a cancellation wizard where you can more easily refund in the same step, choosing the refund method and amount. The amount defaults to that booking's share of the order, so cancelling one booking of a multi-booking order doesn't over-refund, and the wizard shows how much of the order has already been refunded.

A refunded order also shows a proper refunded receipt on the customer-facing order page. The items and totals stay visible under a clear "Refunded" or "Partially Refunded" header and the refunded amount.

A Cleaner Merchant Site

  • Desktop navigation. Your site now shows a proper desktop navigation bar with inline links, keeping the mobile menu for smaller screens. "Show Member ID" is now available from the account menu.
  • Location booking pages. Each location's booking page now shows its address, a map, opening hours, and phone number.
  • Browse everything in one place. Customers can browse everything you offer to book from a single /book page. Picking a service offered at more than one location opens a location selector.
  • Back to where you were. After signing in, customers return to the page they originally opened instead of the home page.

Minor Improvements

  • Choose where each item sells. Picking which locations a catalog item is available at is now generally available, right in the catalog item wizard and on the item detail page. Leave it unset to keep an item available at every current and future location.
  • Smoother sign-in at checkout. Fixed a sign-in issue where verifying your identity, including when paying with a stored-value balance, could get stuck asking you to verify again or briefly flash a "wallet unavailable" error while loading.
  • Cart clears after mobile wallet payment. After paying with a mobile wallet and returning to the original browser tab, the cart now correctly empties along with the confirmation instead of lingering.
  • Refresh-safe confirmation. Refreshing the checkout page right after paying now reliably lands on your order confirmation instead of an empty cart.
  • Jump to the order from a booking. The booking detail page now has an "Order" button when a booking has a linked order.
Read more →

Customer Booking Pages, Treasury Automation & Smarter Scheduling

Customers Can Book Right on Your Site

Building on the customer booking beta, customers can now browse a merchant's bookable services and classes directly on their site at /book. Each offering gets its own page showing the name, description, price, duration, and real available times in the location's timezone, so a customer can find a service and pick an open slot without calling ahead.

Select a date and time for a booking on the merchant's siteSelect a date and time for a booking on the merchant's site

Faster, Smarter Booking Pages

The public booking experience is quicker and clearer. Availability now loads a full week at a time instead of one day per click, so flipping between days you've already looked at is instant with no loading spinner. Booking date pickers dim days the location is closed or a class isn't offered and explain why on tap or hover, so a customer never picks a day that turns out to have no times. When a day has nothing open, the empty state names the reason (closed, not offered, or fully booked) instead of a generic "no times available." Offerings bookable on only a handful of specific dates now show a compact list of just those dates rather than an almost-empty calendar. Open booking pages also keep availability current in the background: while a customer is deciding, a slot taken by someone else quietly disappears, and a selected time that gets booked away is cleared with a gentle notice.

Both booking flows now share a cleaner date-strip picker, a month and year header with week navigation over a row of day cards, and tapping the month opens a full calendar so customers can jump straight to a far-future date.

Multi-Service Appointments & Timezone-Aware Views

Merchants can now book multiple services in a single appointment from the dashboard. Search and add a haircut and a color to one booking, pick a single start time, and each service is scheduled back-to-back automatically. The calendar and bookings list show every service on the appointment instead of just the first.

The bookings calendar and all-bookings list now display in your own timezone by default, with a control to switch to a location's timezone or any timezone you choose. Booking times also show their zone (for example "EDT" or "PST"), so appointments at the same clock time in different locations are no longer indistinguishable. And for solo-operator businesses, booking one service now blocks that same time across your other bookable offerings at that location, so you can't get double-booked across multiple locations at the same time for single staff businesses.

Automatic Treasury Deposits

Merchants can now put idle balances to work automatically. A new Treasury settings page (Finances then Settings) lets you enable automatic Treasury deposits, set an operating buffer to keep on hand, and choose a target tier. Once enabled, idle balances above your buffer are swept into Treasury to earn yield on a recurring schedule. It stays off unless you turn it on, deposits respect your existing payout rules, and anything deposited remains withdrawable through the usual Send to Balance flow. Automated deposits show up in your finances activity with a clear "System" label so it's obvious when the system automation acted on your behalf versus a team member.

Enable automatic Treasury deposits from the Treasury settings pageEnable automatic Treasury deposits from the Treasury settings page

You can also now see your all-time Treasury earnings on the Finances overview and on Stored Value program pages, instead of a placeholder dash.

Add Customers Without Leaving the Page

Adding and editing customers now happens in a slide-over wizard, consistent with catalog items, bookings, and locations. You can also create a customer inline while booking or while creating an order: "Add new customer" opens the customer form over your current work and pre-selects the new customer when you save.

Minor Improvements

  • More reliable checkout notifications. Checkout webhooks still fire immediately, but are now retried automatically (up to five attempts with increasing delay) if the first attempt fails, instead of being dropped.
  • Treasury "Max" withdrawals fixed. Full-balance and dust-sweep Treasury withdrawals no longer fail with a false "insufficient balance" error, and a stale "reserved by a pending transfer" notice no longer lingers after a transfer has settled.
  • Proper 404 pages in the dashboard. Unmatched URLs under an organization now show a "Page Not Found" inside the dashboard chrome, and visiting an organization you don't have access to shows a clear "Organization Not Found" page instead of a bare error.
  • Class size is now intentional. Creating or editing a class requires you to set the number of seats per session rather than defaulting to a single seat capacity.
  • Tidier date displays. Dates now read "Jul 6, 2025" (unpadded day) and relative times read "1 hour ago" instead of "about 1 hour ago" across the platform.
  • Cleaner wizard dialogs. Removed a large empty gap above the title in the customer, booking, location, and catalog dialogs.
Read more →

Booking Management, Order Invoicing & Stored-Value Insights

Manage Bookings from Your Dashboard

Merchants can now run their entire appointment schedule from the dashboard. A new Bookings section gives you a live calendar board you can view by day, by week, or across a custom number of days, with a current-time indicator and appointments that refresh on their own. Click an open time to book, or click an appointment to view it, reschedule, or cancel, all without leaving the calendar. Next to the calendar is a filterable, sortable bookings list you can narrow by location and by date range.

Booking calendar view in the dashboardBooking calendar view in the dashboard

Creating a booking works from anywhere: the list, the calendar (pre-filled with the day you clicked), or a customer's profile. On a single screen you pick the offering and location, enter a start time and length (with a live heads-up if the time falls outside business hours or is already taken), and choose an existing customer or add new contact details inline. From a booking's detail page you can edit the customer, notes, or time, mark it completed or no-show, or cancel it, with your cancellation, no-show, and reschedule policies applied automatically. When you need to act outside a policy window, a one-off override with a recorded reason keeps things clean.

Flexible Scheduling for Services and Classes

Offerings can now be scheduled with far more control. A service or class can have different start times on different days (for example Mon and Wed at 6pm, Fri at 5pm), repeat on a custom interval, and include one-off sessions on specific dates, all on the same offering. You can also set special hours or closures to close an offering for a day, restate that day's hours for a holiday, or block out a range for a vacation or closure.

Any catalog item can be made bookable as a Service (one-to-one) or a Class (a group session with a capacity you set), and each item chooses the locations it's available at. That one selection is the single source of truth for where an item is sold and where it can be booked, so a multi-location merchant can't accidentally create a booking at the wrong place. Booking times are now stored and shown in each location's real timezone across the wizard, list, calendar, and detail page, matching how orders and receipts already show appointment times.

Booking management is rolling out to select merchants. Reach out if you'd like it enabled for your account.

Create and Invoice Orders

Merchants can now create an order directly from the Orders page. A wizard captures line items and an optional customer, then generates a checkout link you can copy and send. The order stays open until it's paid or cancelled. You can edit an open order (line items, customer, due date) from the order page at any time, and the checkout link you already shared updates automatically. The order detail page shows the invoice's checkout link and whether it's been paid, so you can re-copy the link or check its status without recreating anything.

Browse and Manage Your Catalog

The dashboard now has a catalog you can browse, search, and filter. It shows your active items by default, with archived items available from the status filter. You can create and edit both physical items and services from a single-step wizard, including pricing and categories. New items are active the moment you create them, with no separate draft or publish step. This is rolling out to merchants gradually.

Stored-Value Activity Chart

The Stored Value program overview now includes a daily Activity chart showing customer top-ups, customer spend, and bonus value issued over a period you choose (7 days, 30 days, 3 months, or year to date). Toggle each series on or off to focus on the activity you care about.

Stored-Value Activity ChartStored-Value Activity Chart

Merchants can now set their Terms of Service, Privacy Policy, and Refund Policy from the new Policies tab on Settings, General. Link your own pages, or use a Decal-hosted template filled in with your business details. Your policies are then published on your Decal site for customers to read.

Accurate Timezones for Revenue Reporting

Locations now record their real timezone from the connected point of sale (e.g. Square, Lightspeed, etc) instead of defaulting to UTC, which keeps revenue reporting dated correctly. Existing Square locations are corrected automatically on the next sync. The locations list and detail pages now flag any location whose timezone couldn't be read, so you can set it yourself, and the timezone picker is now a searchable dropdown that shows each zone's current UTC offset.

Minor Improvements

  • Cleaner links in the address bar. Order, transaction, location, customer, loyalty, and stored-value pages now show short, readable IDs. Older or shared links still resolve automatically.
  • "Order Not Found" fix on Square checkout. Open orders pulled from Square are now saved as soon as they're listed, so selecting one reliably opens its order page.
  • Clearer customer labels on orders. Order details now distinguish "No customer attached" from a guest contact and from a linked customer.
  • Jump to Square from a customer. A customer's linked accounts now include an "open in Square" link to the matching record.
  • Friendlier date and time pickers across business setup, availability, and location hours, plus a fix for payment-link expiration dates showing in the wrong local time.
  • Appointment durations read naturally on the public booking site (for example "2 hrs" and "45 mins").
Read more →

Appointment Booking (Beta), Store-Credit Refunds, and Customer Management

Appointment Booking (Beta)

Customers can now book and pay for a merchant's services directly on the merchant's Decal site. They browse the bookable services, open one to see available times for a day in the merchant's timezone, and pick a slot. The chosen day stays in the page URL, so reloading or sharing a link keeps the selected date. Picking a time takes the customer straight to the order page, where the appointment summary, the payment options (card, stablecoin, or stored balance), and any required contact details all appear together. Signed-in customers pay right away without re-entering their details; guests are asked for an email inline only when they go to pay. On payment, the appointment is added to the merchant's connected calendar and the confirmation appears in place, with no separate review screen.

Nothing is created in the merchant's point of sale while a customer browses or changes times. The order is held on Decal until payment, so abandoned or re-timed selections leave nothing behind.

Appointment booking is in beta for select merchants while we put it through production use. If you'd like early access for your services, reach out and we'll enable it for your account.

Refund Orders to Store Credit

Merchants can now refund a paid order right from the order page. The new Refund order action opens a dialog to pick a method and amount (full or partial); today the available method is store credit through the merchant's stored-value program, shown by name. For a card order that was settled through Square, refunding as store credit returns the value without card fees and credits the customer's balance instead.

A few things this handles cleanly:

  • Partial refunds add up correctly. An order that was already partially refunded can be refunded again up to its full paid amount, and is marked fully refunded once the refunds reach that total.
  • Mixed orders are handled. When an order includes both a regular item and a balance top-up, only the purchased portion is refundable (the top-up was already received as balance), and the dialog shows the excluded amount.
  • Appointment orders are refundable too. Bookings that settle through Square can now refund as store credit just like a point-of-sale order.

Issue Store Credit Directly

Merchants can now grant store credit to a program member straight from the dashboard, for comps, promotions, or goodwill, without the customer making a payment. The credit appears in the member's balance immediately and is recorded as a grant rather than revenue, so lifetime revenue volume stays accurate.

A Customer Hub

The dashboard customer pages got a lot more useful:

  • Add and edit customers from the Customers page, with duplicate-email and duplicate-phone protection. New and edited customers sync to connected platforms like Square within seconds.
  • Orders and Transactions tabs on each customer page, both filterable and sortable.
  • A Linked Accounts card showing the customer's accounts on connected platforms, with the external customer id and reference id, each copyable, plus when each account last synced.
  • The Orders table now links to the customer and shows the linked customer's name rather than a stale order snapshot.

Every order now has a short, stable link at /orders/{id} on the merchant's site. Old checkout links and QR codes resolve to it automatically, and typed or Square order ids redirect to the same canonical URL.

Minor Improvements

  • Stablecoins turn on automatically for new merchants. Newly provisioned merchants have stablecoin payments enabled in both test and live mode, so the method is selectable at checkout immediately. It can still be disabled from the dashboard.
  • Clearer payment errors. Payment failures now show a specific reason when one is available (for example, "Your balance is $0.02 short of the $0.02 required"), and the generic message is friendlier and no longer mentions a point of sale.
  • Richer order details for appointments. Appointment line items now show the booked date, time, and duration, and the payment summary shows which method paid the order.
  • Balance link appears only when ready. The "Balance" link on a merchant site now shows only once an active stored-value program exists, so it no longer leads to an unavailable page.
  • Fewer unexpected sign-outs. Brief network hiccups during a session check no longer sign you out; the app retries automatically and stays signed in.
  • Receipt and layout fixes. Long item names no longer break order tables, appointment durations read naturally ("1 hour 30 mins"), and dashboard pages have more breathing room on mobile.
Read more →

Stored Value Insights, Customer Sync & Faster Dashboard Tables

Clearer Stored Value Revenue

Stored Value program reporting now separates what customers actually paid from what you gave away. The program overview breaks out All time bonus value issued alongside Total value issued since inception and All time customer spend, so bonuses are no longer counted toward revenue you earned. The members table gains a Granted column, and each customer's page shows a relevant card, making it clear at a glance how much free balance each member has received.

Stored Value program metrics in the Decal DashboardStored Value program metrics in the Decal Dashboard

Two-Way Customer Sync

Building on last week's near-real-time point-of-sale sync, your customer records now stay in step across Decal and your connected point of sale, in both directions.

  • Edits flow both ways. When you update a customer in Decal, the change pushes to your connected systems within seconds. When a customer is added or edited in Square, it reflects on Decal just as quickly.
  • Birthdays sync. Customer birthdays now sync between Decal and Square in both directions, including month-and-day-only birthdays (common in Square).
  • More than one system? A customer connected to multiple systems now resolves to a single Decal profile instead of being overwritten.
  • Sync without waiting. "Sync customers now" from your Square integration settings now runs in the background, so importing a large customer base no longer times out, and you can navigate away while it runs.

Membership ID QR Codes

A customer's Membership ID QR now carries the value your point of sale can resolve against your loyalty program. If you already use a membership ID scheme, Decal reads in your existing ID and preserves it, so it's never overwritten. If you don't, Decal assigns one so QR scans work immediately at the register.

Searchable, Paginated Dashboard Tables

Your Transactions, Orders, Customers, Loyalty Members, Stored Value Members, Finance Activity, and Webhooks pages now page through your full history rather than just the most recent records, with filtering, sorting, and search across your entire history, not just the page you're looking at. Your current view (filters, sort, search, page) is captured in the URL, so it survives a reload and can be shared with a teammate. Search now also treats characters like % and _ as literal text instead of wildcards.

Smoother Sign-In on Your Website

Signing in on your customer-facing website is smoother and more reliable. The verification screen now keeps a loading spinner up until the sign-in page is ready instead of flashing a blank panel, and the Cancel button eases in a moment after the step starts rather than appearing instantly, while still giving customers a way out if the page is slow to load.

These improvements carry through to Stored Value sheets (top-up, balance, and checkout add-ons), where already-signed-in members are no longer asked to re-verify, and the account setup screen no longer hangs on a "Setting up your account…" spinner.

Minor Improvements

  • Orders link to the right customer. Orders completed by a signed-in customer, whether on Decal or paid at a connected Square register, are now reliably attributed to that customer.
  • Bonus callouts match your brand. The top-up bonus message now uses your storefront's brand color instead of a fixed green.
  • Cleaner reconnect prompts. When an integration needs reattention, its settings are disabled with a clear Reconnect notice so you can't kick off a sync against a connection that needs reconnecting.
  • More reliable Square sync. A fix to how inbound Square updates are verified restores point-of-sale order and customer sync that could previously stall.
Read more →

More Ways to Get Paid: Cards, Wallets & Docs

Card Payments Are Now Available to Every Merchant

Following last week's card payments work, card payments are now available to every merchant to set up from the payment methods settings page, no longer limited to a small group. The setup flow adapts to where your organization is:

  • Not set up yet? Instead of a dead, disabled button, you'll see a Request card payments dialog. Submitting it lets the Decal team provision your card payment provider and follow up with you.
  • Already provisioned? Enable card payments yourself in one click.
  • Provider still being set up? Enabling is blocked with a clear message rather than quietly turning on a method that would fail your customers at checkout.

To be clear: card payments aren't switched on automatically. Every merchant can now start the setup themselves.

More Wallet Options at Checkout

Customers now have more ways to pay with crypto. MetaMask is available in the wallet connect sheet, and Jupiter is available on mobile, so customers can complete a payment straight from the wallet they already use. New to paying this way? Our guide to crypto and blockchain breaks down the basics.

When a wallet app isn't installed, checkout now detects it and falls back gracefully with a copy-link option instead of getting stuck.

Complete Business Verification In-Dashboard

Merchants can now complete business verification from a dedicated Business section in the dashboard: fill in your business profile, add beneficial owners, upload compliance documents, and submit for review, with a guided step-by-step setup and a clear overview of what's done. The flow tailors itself to your country of incorporation, so you only see the entity types and tax-ID options that actually apply.

This is rolling out in beta for select merchants today. General availability is expected to follow shortly.

Decal Docs Are Now Public

Our documentation site at docs.usedecal.com is open to everyone, with no more access request or email code to get in. Browse guides, concepts, and the full API reference directly.

Faster Point-of-Sale Sync

Sales, customers, and locations from your connected point of sale now sync to Decal in near-real time instead of waiting for a periodic refresh:

  • When you create or update an order on your Square device, it reflects on the matching Decal order within seconds. Customer adds, edits, and removals, and changes to your locations, sync in seconds too.
  • If a customer opens a Decal checkout link but pays at the register instead, the order is reconciled automatically so it isn't left looking unpaid.

This is enabled for a controlled set of merchants while we verify it in production. We're also expanding our Lightspeed Retail integration in beta: connected merchants can sync their outlets as locations and let customers pay open Lightspeed sales with stablecoins through the Decal checkout. And stale, abandoned orders can now be auto-cancelled across both Square and Lightspeed locations so they don't pile up.

Clearer Checkout Messages

When something goes wrong at checkout, customers now see a clear, friendly message instead of a generic server-error page. A temporarily-unavailable point-of-sale connection shows a "Connection Problem" notice, and specific situations, an order that's no longer open or a payment method that's unavailable, each explain what to do next and never expose raw technical details.

Minor Improvements

  • Sign-in is snappier. The email form renders instantly with no flash on load, the verification code field auto-focuses when it appears (even when you switch back to the tab), and the theme toggle no longer flickers.
  • Newly launched merchant sites look right immediately. A brand-new site now goes live with sensible default branding and your organization's name the moment your website is activated, instead of showing a generic "Welcome to Decal" page.
  • Stored Value opens reliably. Merchants with the Stored Value add-on can now open an existing program from the dashboard without hitting a incorrect "not found" error.
  • Cleaner cooldown cards. Removed a redundant status row from in-progress withdrawal claims.
  • Fresh from the blog. Decal was featured by Para (read the press post), and blog posts now sort correctly by date.
Read more →

Treasury Goes GA, Plus Reliable Payouts & Checkout Status

Treasury Is Now Live for Every Merchant

Treasury is out of early access. Every merchant can now earn yield on idle balances directly from the Finances dashboard. The Treasury balance card, Send to Treasury / Send to Balance actions, and the cooldown list are no longer gated to a small set of organizations.

Click the Earn rewards button in the Balance card to see the current rewards rate and immediately deposit your idle balance.

Live Operation Tracking Across the Dashboard

Every Treasury deposit and withdrawal (and wallet payouts) now reports its progress in real time, so you're never left wondering whether a submission is still working:

  • A persistent background-work indicator sits in the bottom-right corner and shows in-flight deposits and withdrawals at a glance. Click it to see what's running and jump straight into any transfer's details. It fades out gently after a transfer finishes, with a green check on success and a red X on failure, with no more identical-looking end states.
  • Completion alerts follow you across the app. After you submit a deposit or withdrawal, a toast fires when it completes or fails no matter which page you're on. Watched transfers persist across page reloads, so slow ones are never lost.
  • Balance, Treasury, and Cooldown cards update instantly the moment a transfer is confirmed, with no multi-second wait while the dashboard re-fetches. Confirmations also land 1 to 3 seconds sooner than before.
  • Cooldowns read as scheduled, not stuck. A withdrawal in its cooldown window now shows a clock and a relative countdown ("Available in ~23h") instead of a perpetual spinner, and a transfer that's genuinely taking too long turns amber with a Check status link.

See Your Real Available Balance Before You Send

The Send to Treasury and Send to Balance dialogs now show your available balance, your total minus anything already committed to a pending transfer, so the Max button reflects what you can actually spend right now. When funds are reserved by an in-flight transfer, a clear notice tells you how much is held and what's left, and the Balance and Treasury cards show an "X of Y available" line. Attempts to send the same dollars twice are now blocked outright instead of silently accepted.

More Reliable Payouts

Payouts got a reliability and UX pass:

  • The New Payout dialog is now always available, including bank and card payouts, which don't require a settlement wallet. The prompt to add a settlement wallet now appears only inside the stablecoin payout step, and only when you don't already have one.
  • A payout request no longer fails when your available funds need to be consolidated first. The system handles the conversion behind the scenes so the payout goes through.
  • Payouts now show reserved funds and block submission when your available balance is zero, matching the Send to Treasury and Send to Balance dialogs, and a duplicate-submission guard prevents the same payout from being sent twice.

Clearer Checkout Session Status

Checkout sessions now expose a typed status (pending, processing, completed, failed, expired, completed_externally) on API responses and checkout.session.* webhook payloads, a precise replacement for the older active boolean (which is preserved but now deprecated). Sessions are reliably marked completed after a payment, and a stale browser tab can no longer re-submit against a finished session.

Stale sessions are also automatically marked expired once their window passes, and merchants subscribed to checkout.session.expired receive a webhook within five minutes. Previously, an abandoned session sat at pending indefinitely. The published checkout and webhook docs have been corrected to match the real response shape end-to-end.

Account Settings & a Personalized Home

Custom websites & apps got several updates!

Account settings now has a proper sidebar (desktop) / picker (mobile) layout, and the Profile page is a stack of per-section cards (Email, name, date of birth, postal code), each with its own Save button, so editing one field no longer overwrites the others.

The merchant home page now adapts to who's viewing it: guests see a branded login form, signed-in customers with a stored value account see their balance and top-up options, and customers who haven't joined yet see an onboarding prompt.

Minor Improvements

  • Confirm before disabling an add-on. Disabling an add-on now opens a confirmation dialog that spells out exactly what changes (e.g. Loyalty programs will be hidden; gift cards stay redeemable when re-enabled).
  • Faster Treasury & Payouts pages. Yield rates now load from a short-lived cache, trimming page load time.
  • Consistent metric cards. Dashboard metric cards now share the same footer treatment, so sibling cards on a page no longer look mismatched.
Read more →

Treasury Deposit Overhaul, Member ID QR Codes & Card Autofill Fixes

Treasury Deposit Overhaul

Sending funds to Treasury now feels like a single guided action instead of a black-box request. The Send to Treasury dialog shows a progress view while the deposit executes, with a clear Done button on success and an inline Retry button if anything fails. A new toast confirms the final amount and discloses any drift if the deposited amount differs from the requested one by $0.50 or more.

When a deposit takes longer than expected or the browser temporarily loses connection, the dialog now shows a "still working" state with a link to the activity feed. Merchants can close the dialog and check back later while the deposit continues in the background. Plans that hang for more than 10 minutes are automatically marked as failed by a periodic sweep, so a stuck dialog can't trap a deposit indefinitely.

Under the hood, transient errors from the yield provider and brief network hiccups now auto-retry up to three attempts before failing the merchant. Most short-lived blips are now invisible.

The amount input is also smarter:

  • Available to deposit is now the system's routable cash, what can actually reach the provider once conversions are applied, with an info popover explaining when small amounts in certain currencies aren't yet convertible.
  • The dialog enforces the provider's minimum (currently $1) with a clear Alert explaining what to add when balance is below threshold.
  • Sub-cent precision drift no longer rejects valid $1.00 deposits or renders $0.99 anywhere in the app. USD amounts now truncate consistently instead of rounding up.
  • When a typed amount would strand a sub-$1 sliver, the dialog upsizes the deposit and explains with a clear message similar to "We'll deposit $1.40. Your remaining $0.39 balance can't be deposited later." The submit button shows the actual amount that will be sent.

Yield Tiers: Basic and Pro

The two yield tiers are now named Basic and Pro across the dashboard, replacing the previous mismatched Protected/Boosted labels. The new names are clearer for merchants weighing the tradeoff between immediate access and higher-rate cooldown access.

Behavior is unchanged. Basic still settles immediately, Pro still has a cooldown window. Only the labels changed consistently across the platform.

Member ID QR on Custom Websites

Custom merchant websites now have a burger menu in the header with quick links to Account, Balance, and a Show Member ID action. Tapping it opens a bottom sheet with a scannable QR code so a customer can identify themselves at the counter, no app required.

The QR encodes the merchant's custom external ID when one is set; otherwise it falls back to the customer's Decal member ID. Both values appear as plain text below the QR for staff who'd rather read than scan.

Card Checkout Upgrades

The card payment form was upgraded and fixes several stubborn issues:

  • Autofill works. Cards saved in the browser or password manager now populate cleanly without rendering glitches or browser crashes.
  • Theme matches the merchant's palette. The card input inherits the merchant's primary, background, input, and text colors from the active theme, including custom palettes.
  • Retry after a failed payment works. Clicking Try Again after a card rejection no longer fails immediately with a "transaction is no longer valid" error; the form now re-initializes a fresh card session on retry.

Card payments are also now supported in the pay app's session checkout (pay.usedecal.com/s/…), matching the existing custom-website card flow.

Critical: Percentage Discount Fix

A bug in percentage discount computation was causing the full item subtotal to be applied as the discount amount instead of the correct percentage. For example, a 10% discount on a $13.00 order was applying $13.00 off instead of $1.30. This has been fixed!

Percentage discount amounts also used to go stale when an order's items changed without the discount being replaced, for example when items were updated via the API or when a top-up line item was added or removed. The recompute now lives inside the order totals path, so every caller gets up-to-date discount amounts against the current item subtotal.

Faster Top-Ups

A few rough edges on the balance top-up flow are smoothed out:

  • The on-page balance now updates immediately after a successful card top-up. The count-up animation runs against the new balance instead of remaining stale until a polling round-trip.
  • Hard-refreshing the balance page right after a top-up now shows the new balance immediately instead of taking up to a minute.
  • The success ("Done!") step of the top-up sheet no longer shows a back button. Users can only close from the success screen.
  • Customer sign-in feels snappier: the "Verifying your account" indicator appears immediately once the email verification code is accepted, instead of waiting for a verification poll.

Custom Website Balance Page

The Balance link in the burger menu and header, and access to /balance, now follows the merchant's stored value toggle in the dashboard. Toggling stored value on or off invalidates the public site's cache and updates nav visibility within seconds.

The link is also now visible to signed-out visitors when stored value is enabled, so they can land on the page and sign in to load funds.

Minor Improvements

  • Login returns you where you came from. After signing in, you're taken back to the page you originally tried to access instead of the dashboard home.
  • Admin-enabled add-ons appear enabled. Add-ons enabled by Decal support for your org now consistently show as enabled across the dashboard instead of an "early access" prompt.
  • Friendlier add-on pages. Add-on pages show a friendly prompt when the feature isn't provisioned yet, instead of a generic 404.
  • Branded error pages in the pay app. Custom error and 404 pages now match the rest of the platform.
  • Mobile sheet/dialog polish. A 1px right border / backdrop bleed on mobile overlays is fixed.
  • Tables no longer flash raw headers. Tables across Finances, Loyalty, Transactions, Orders, Customers, Wallets, and Settlement Wallets no longer flash raw column headers during initial page load.
Read more →

Webhook Visibility, Location Management & Friendlier Errors

Webhook Delivery Inspector

A new Webhooks view under Settings → Connections lets merchants see exactly what happened to every outgoing webhook. Filter by status and event type, drill into any individual delivery to view the request body, response body, headers, response code, and duration as code blocks, and read the error details for failed attempts (DNS lookup failed, HTTP error, request timed out, etc.) right at the top of the page.

Every webhook attempt is now persisted with full forensics, so a failure that happened overnight is 'still inspectable the next morning, with no more guessing whether the endpoint was reachable.

Manual Locations

Locations no longer require a Square integration. A unified location form covers name, description, street address, phone, email, timezone, and recurring business hours, and works whether the location was created manually or imported from Square.

For merchants who do use Square, sync precedence is now snapshot-based: Square only overwrites a field if the merchant hasn't changed it since the last sync. Edit business hours, fix a typo in your address, or update a phone number directly in Decal without worrying that the next Square sync will clobber it.

Custom Sign-Up Bonus Messages

Merchants running Stored Value programs can now write their own first-top-up bonus message. The dashboard Sign-Up Bonus settings tab adds a formatting toolbar (bold, italic, center alignment), a 140-character counter, and a one-click Remove button to return to the default. The phone mock preview updates live as you type so you can see exactly what first-time top-up customers will see at checkout.

Friendlier API Errors

Errors returned from the API now carry through the actual reason instead of a generic "An unexpected error occurred" fallback. Auth flows in particular (invalid OTP, expired challenge, fingerprint mismatch, hourly refresh limit) now surface real messages to integrators and apps. The HTTP status code and error code contract is unchanged; only the user-facing message is more useful.

Minor Improvements

  • Square order-not-found shows the right page. Checkout sessions for missing Square orders now display the order-not-found message instead of a generic server error.
  • Payment page production crash fixed. Resolved a minor error that could surface on the payment page in production for some wallets.
  • "Required information" heading hidden when not needed. The checkout page no longer shows the Required information heading if you haven't configured any required customer input fields on the checkout session.
  • Branded merchant sites are more resilient. Custom domain sites now tolerate transient database hiccups instead of bubbling to an error page, with a friendlier in-page recovery state when something does fail.
Read more →

Decal Treasury, Finances Overview & the Add-ons Hub

Decal Treasury

The Finances overview is now live. At a glance it shows your idle Balance available to allocate, funds currently in Decal Treasury with a per-tier yield breakdown, and funds available to transfer back to Balance. When funds are sitting idle, the Balance card surfaces a quick action to allocate them to your Treasury account directly, no separate flow required. Tap the yield badge to expand the full tier-by-tier breakdown.

Transferring funds from Treasury to Balance is done from the Payouts page. Timing depends on your tier:

  • Basic-tier funds transfer to Balance instantly.
  • Pro-tier funds enter a ~24-hour unlock window. A live Cash Unlocking callout will display on the Payouts page with a countdown timer and a batch-claim button once the window closes.

The Balance card shows only the portion of your funds that can be allocated to Treasury today, with a secondary line for your "additional balances." Support for those is coming soon for Treasury yield.

Yield is generated through managed treasury strategies and is not guaranteed. Decal is a payments platform, not a bank.

Products & Add-ons

A new Products & Add-ons page gives merchants a single place to discover and enable optional features. Each add-on card shows whether the feature is generally available, in early access, or coming soon. One click enables or disables it.

The dashboard sidebar and pages update automatically: enabling an add-on unlocks its section in the nav; disabling one hides it cleanly without affecting your data.

Website Pages

The website area now includes a Pages view that lists every page your customer website responds to. Alongside the built-in pages (/, /login), any add-on you enable surfaces its pages here. For example, Stored Value adds /balance and /topup. Each row shows the path, title, live status, and a View live link to the page on your primary domain.

Minor Improvements

  • Branding saves no longer auto-publish your custom site. Saving your logo, theme color, or display name no longer accidentally brings a draft site online. Publishing remains an explicit action under Website → Settings.
  • Friendlier domain conflict errors. If a domain is already in use by another organization, the dialog now says so with a clear message instead of a generic failure.
  • Canonical URLs across custom website pages. All public merchant site pages now set correct canonical URLs and page titles for consistent SEO.
Read more →

Invite Your Team, Checkout API Upgrades & Payouts GA

Team Invites

Merchants can now invite teammates end-to-end from Team settings. Enter a name, email, and role (Admin or Owner), and the invite is sent by email automatically, with a copyable invite link for sharing outside of email.

  • Resend email is available from the pending invites menu, so a lost email isn't a dead end
  • Leave Organization is now a first-class action from your own member profile, with a safety guard that prevents the last owner from leaving without first transferring ownership
  • Remove Member and Change Role actions are live in member detail page as well
  • Invitee display name is set automatically from the name fields the inviter provides

Checkout API Upgrades

Following the Checkout Sessions and Orders API launch last week, a batch of upgrades aimed at integration reliability.

Top-level externalId on POST /v0/checkout/sessions and POST /v0/orders. Pass your own order identifier (cart ID, POS ticket, order number) directly on the order and retry safely. A second create call with the same externalId returns 409 Conflict with a DUPLICATE_EXTERNAL_ID error code. Built-in idempotency key that makes flaky network calls safe to retry.

Required fields at checkout. Create a session with requiredFields set to phone, shippingAddress, and/or location, and Decal's hosted checkout page will collect the missing information from the customer during the payment collection. Any fields you pre-fill at session creation allow the skipping those fields entirely.

{ORDER_ID} URL template. successUrl and callbackUrl now support {ORDER_ID} alongside the existing {SESSION_ID}. Substitution uses the formatted typed IDs (cs_<mode>_<cuid>, ord_<mode>_<cuid>), so the URLs your handlers receive are ready to plug straight back into the API.

Metadata limits. Orders and order items now have metadata shape constraints: max 50 keys, keys up to 40 characters, string values up to 500 characters, flat primitive arrays only. Keeps row sizes, response payloads, and webhook deliveries tidy. Well-formed existing metadata is unaffected.

Live Session Expiry Countdown

Checkout sessions now show a live countdown timer when less than 10 minutes remain, and transition gracefully to the expired or cancelled page mid-checkout, no page reload required. Whichever fires first (the timer hitting zero or the order polling detecting expiry) wins, so the customer always lands on the right page.

Saved Customer Payment Methods

Card and wallet details are now persisted after each successful payment. This enables returning-customer detection by card fingerprint, groundwork for faster repeat checkout flows.

Payouts for All Merchants

The Payouts page is now available to every organization. Previously it was gated behind a feature flag.

Submitting a stablecoin payout updates the available balance and payout activity in-place. The active payout shows a spinner until it confirms (usually within sub-second), and failures surface inline with a clickable error badge. No more full-page reloads on submit.

Manual Wallet Connect

Wallets that don't publish a deep link scheme (e.g. Jupiter) can now be connected via a guided manual flow. A Don't see your wallet? entry appears at the bottom of the wallet list and opens a sheet with step-by-step instructions and a copy button, with no auto-redirect or auto-copy.

Wallet sort order also updated so Mobile Wallet Adapter appears after named wallets but before Brave.

Minor Improvements

  • QR codes canonicalized to pay.usedecal.com. Scan-to-pay QR codes and wallet deep links now route through the pay app redirect, so customers always see and share pay.usedecal.com/loc/{id} URLs regardless of your merchant handle or site configuration. Printed QRs keep working across handle and location status changes.
  • Dashboard time range sync. Changing the chart period now updates all four metric cards to the same window, and the selection is preserved in the URL so it survives refresh and can be shared. Adds Year to date as a fourth option.
  • Payment destination fix. paymentDestination set on a checkout session now correctly routes funds to the specified wallet instead of the merchant's default orchestration wallet.
  • Checkout polling on tab return. Returning to the browser tab after a wallet deep-link now immediately triggers an order status check, regardless of whether the wallet sheet is still open.
  • Dashboard sign-in fix. Resolved a schema validation error that could reject valid emails on the sign-in screen, plus a layout fix to the error alert on dashboard, passport, and admin login screens.
Read more →

Checkout Sessions API, Manually Adding Wallets & More

Developer API: Checkout Sessions and Orders

The Checkout Sessions API and Orders API are now available to merchants in closed-beta.

Checkout Sessions let you create a hosted payment page with a single API call. Pass your order details, get back a URL, and redirect your customer. Decal handles the checkout UI, payment collection, and order tracking.

curl -X POST https://api.usedecal.com/v0/checkout/sessions \
  -H "Authorization: Bearer sk_live_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "items": [{ "name": "Cold Brew", "quantity": 1, "unitPrice": 550 }],
    "successUrl": "https://yoursite.com/confirmed?session={SESSION_ID}"
  }'

The response includes a url to redirect your customer to and the full order object so you have the order ID handy for confirmation.

Orders can also be managed independently: create, retrieve, update, or cancel orders directly without going through a checkout session. Useful for POS integrations or anywhere you're managing order state server-side.

Both APIs:

  • Support taxes and discounts (fixed and percentage)
  • Accept a customer object that will find-or-create a customer record, with externalId support for mapping to your own customer IDs
  • Use test/live mode automatically based on your API key (sk_test_ vs sk_live_)

Webhooks

Checkout sessions now fire a checkout.session.completed webhook to your callbackUrl after a successful payment, before the customer is redirected to your successUrl. This means your server knows about the payment before the customer lands on your confirmation page, eliminating the need to poll for payment status.

Both successUrl and callbackUrl support a {SESSION_ID} placeholder template that gets replaced with the actual session ID at creation time, so you don't need to store the mapping yourself:

{
  "callbackUrl": "https://yoursite.com/webhooks/decal?session={SESSION_ID}"
}

Manual Settlement Wallets

You can now add a settlement wallet by pasting a Solana address directly, without connecting a browser extension. This enables wallet types that can't go through the standard signature flow:

  • Multisig wallets (Squads): add a program-owned address directly
  • Cold storage (Ledger, Keystone, etc): no need to plug in
  • Any externally managed address

Manually added wallets are tagged with a Manual badge in your wallet list, and adding one requires a confirmation checkbox since funds sent to a wrong address can't be recovered.

Manually add a Settlement WalletManually add a Settlement Wallet

Payment Destination Override

When creating an order or checkout session via the API, you can now specify exactly which settlement wallet receives the funds, overriding the default wallet resolution for that transaction:

{
  "items": [{ "name": "Catering Package", "quantity": 1, "unitPrice": 25000 }],
  "paymentDestination": "sw_live_abc1234567890"
}

Accepts either a typed wallet ID (sw_live_...) or a raw Solana address from your verified wallets.

Stored Value Improvements

A few quality of life improvements for Stored Value programs:

  • No settlement wallet required to activate. The activation checklist is now two steps (balance name + launch). The settlement wallet step was a leftover requirement that didn't actually affect how stored value payments route, so it's gone.
  • Default bonus values. New programs now come pre-filled with bonus configurations ($5 bonus on $25+ first load, $5 bonus on $50+ recurring loads) so you're not starting from a blank slate.
  • Better bonus display. When a top-up added to a checkout qualifies for a bonus, the bonus details appear inline before the customer pays. The balance page now shows the correct bonus type automatically (signup vs topup) without being anchored to a preset amount.
  • Smarter low-balance messaging. First-time customers no longer see a misleading "Low balance" warning. Instead they see a first-topup incentive. Returning customers with a low balance continue to see the existing reload nudge.

Embedded Authentication

Customer authentication now uses inline embedded flows instead of pop-up windows. New users enter their OTP code directly in the app, and returning users authenticate via an embedded iframe. Popups are only used as a fallback for passkey (WebAuthn) auth, with automatic popup blocker detection and Safari-specific recovery instructions.

Minor

  • Stablecoin payment setup streamlined. Enabling a stablecoin payment method is now a single click. The prior flow opened a wallet selection dialog linked to the payment method; that's gone. Payment routing now resolves via orchestration wallets at payment time.
  • Better card payment errors. User-actionable payment errors (invalid zip, declined card) are now shown directly to customers instead of a generic failure message.
Read more →

Finances Dashboard & Stored Value Bonuses

Finances Dashboard

The merchant dashboard now has a dedicated Finances section, consolidating everything related to your money in one place. The new section includes:

  • Payouts: Initiate stablecoin transfers from your Decal-managed wallet to your settlement wallet, with real-time balance visibility.
  • Pay-ins: Coming soon.
  • Accounts: Manage your settlement wallets. Bank accounts coming soon.

Settlement wallet management and payouts have moved out of Settings into this new section. Existing bookmarks and links redirect automatically.

Stored Value Bonuses

Merchants can now configure sign-up bonuses and top-up bonuses for their Stored Value program. Both support fixed-amount or percentage-based bonus credits with tiered spend thresholds, for example, "Load $50, get $5 free" or "Load $100, get 15% bonus."

Sign-up bonuses are claimable once per customer. For top-ups, only one bonus tier applies per transaction. Configure both from the Top-Ups tab in your Stored Value program settings.

Non-members and unauthenticated customers now see a signup bonus teaser when viewing a merchant's balance page or the balance top-up addon at checkout. The teaser shows the lowest-threshold bonus tier (e.g. "New member bonus, top up $25 or more to get +$5 free"), giving customers an incentive to join before they reach the amount selection step.

Custom Onboarding Messaging

Stored Value programs now support customizable onboarding content that customers see when signing up. In the dashboard under General > Customer Messaging, merchants can set:

  • A headline shown on the balance page and sign-up sheet (defaults to "Join the {program name} program").
  • A subheadline for a short marketing statement.
  • Up to 6 benefit bullet points highlighting why customers should join.

This gives merchants full control over the first impression their Stored Value program makes.

The Stored Value settings page now also includes a branded phone mock preview, showing a live preview of the customer-facing onboarding screen in merchant brand colors as they edit.

Minor Improvements

  • Organization avatars now display as rounded squares instead of circles, making them visually distinct from user and team member avatars throughout the dashboard.
  • Checkout pages load faster thanks to cached merchant location data, reducing unnecessary database round-trips on repeat visits.
Read more →

Checkout Top-Ups & Stored Value Configuration

Checkout Top-Ups for New Customers

Customers who aren't signed in or enrolled in a merchant's Stored Value program can now tap the balance top-up addon at checkout to sign up and add a top-up in a single inline flow, no navigation away from the order required.

When a customer opens the Stored Value payment sheet with zero or insufficient balance, they now see a contextual top-up amount grid instead of a disabled button. After signing in or completing onboarding, they're correctly registered as a merchant customer and can proceed immediately.

Stored Value Top-Up Configuration

Merchants can now configure custom top-up preset amounts and a low-balance reload reminder for their Stored Value programs. Settings are available in the dashboard under the new Top-Ups tab. The checkout page and balance page respect these settings; programs without custom configuration continue to use platform defaults.

Merchant Branding Fixes

Several branding color issues have been resolved:

  • Merchants using "single" color mode now correctly see their configured scheme regardless of the visitor's OS dark mode preference. Previously, the platform's default dark palette bled through for unconfigured color variables.
  • The branding system now derives and emits all CSS variables used by UI components, eliminating color mismatches caused by variables falling back to dark-mode defaults.
  • The branding editor's phone mock preview now reflects custom colors in real time.
  • Advanced color overrides (primary button text, secondary button text, card background, card text, muted text, input background) are now editable under an "Advanced Colors" toggle.

Minor Improvements

  • Guest customers and unenrolled customers are now protected from inadvertently purchasing balance top-ups at checkout. If a guest attempts to pay an order containing a top-up line item, the item is automatically removed and the customer is shown an updated order.
  • Added checkout auth token for the crypto wallet deep-link wallet flow, preserving top-up items when customers open external wallet apps like Phantom or Solflare.
Read more →

Order Management & Square Integration Settings

Order Management

The merchant dashboard now includes full order management pages. The order listing page supports pagination and filtering by status, payment status, and search by order ID or customer name. Each order detail page shows line items, a financial breakdown, customer info, and timestamps.

Merchants can void open, unpaid orders directly from the dashboard. Cancellation propagates to external POS systems like Square automatically. A stale order detection system alerts merchants when Square locations have lingering open orders, with a bulk void option to clean them up.

Square Integration Settings

The Square integration page now includes a settings panel with toggles for:

  • Location sync. A weekly cron job syncs Square locations, creating new ones, updating metadata, preserving merchant-customized names, and deactivating removed locations. A "Sync now" button is available for on-demand syncing.
  • Customer sync. A daily two-way sync between Decal and Square. Inbound creates or updates Decal customers from Square; outbound pushes new Decal customers to Square. Conflicts resolve via most-recent-update-wins with email-based matching for initial linking.
  • Stale order auto-cancellation. Automatically cancels stale Square orders when enabled. Orders are upserted into Decal first for visibility, then cancelled on Square.

Card Billing Address Configuration

Merchants can now be configured to require either full billing address (address, city, state, zip, country) or minimal card details only for card payments. The checkout form conditionally renders address fields based on the merchant's configuration. Existing merchants default to full address.

Minor Improvements

  • Fixed a critical mode consistency bug where toggling between test and live mode kept the original customer record, allowing a live customer to join a test Stored Value program. Mode toggle now re-resolves the customer in the target mode, with defense-in-depth validation at the database level.
  • Square payments now include the Decal transaction ID as a reference for merchant cross-referencing, with deterministic idempotency keys for retry safety.
  • Fixed card checkout failing with "Order not found" on Square locations due to typed IDs being passed directly to the Square API.
  • Card payment error messages no longer leak internal configuration details. Unknown errors now return a generic fallback message.
  • Fixed tax double-counting when adding a balance top-up to Square orders with additive taxes.
  • Cancelled orders no longer incorrectly trigger the "order details changed" dialog.
  • Empty orders now show a clear "Order Empty" status instead of a broken $0.00 receipt.
  • All open payment sheets close automatically when an order is completed or cancelled via polling.
Read more →

API Keys, Stale Order Protection & Stored Value Management

API Keys

Merchants now have a secure API key system for programmatic access. All keys scoped to your organization.

From the new API Keys settings page, you can create secret keys with an optional name, view existing keys with masked hints and a reveal toggle, see who created each key, and revoke active keys. Keys use the sk_ prefix and include your platform mode (test/live) for safety.

Stale Order Protection

Customers are now protected from paying stale order amounts. The checkout page polls for order changes every second and shows a full-screen dialog when a merchant modifies an order in Square while checkout is open. The dialog highlights exactly what changed: items added or removed and the new total. A server-side fingerprint check also blocks payment if the order data has changed since the customer last reviewed it.

Payment Method Management

Payment method detail pages are now generic and data-driven. Feature flags, setup actions, and settlement wallet management are driven by a single PaymentMethodDefinition config, eliminating method-specific branching. New payment methods work automatically once added to the definitions.

Each detail page now shows the current settlement wallet with a quick action to change it, or fall back to the organization default.

Stored Value Management

Stored Value management has been consolidated into a dedicated dashboard section. The setup wizard, activation checklist, and program editing now live under the Stored Value pages instead of being split across payment method settings.

Minor Improvements

  • OTP verification form now disables on success with a polished animation and redirect message.
Read more →

Card Payments, Integration Health & Improved Authentication

Card Payments

Several card payment improvements shipped this week:

  • Fixed initialization hang. Card payment sessions no longer stall when opening the payment dialog.
  • 4-digit expiration year. Eliminates ambiguous 2-digit year handling that allowed invalid dates to pass validation.
  • Better error messages. User-actionable errors like invalid zip or declined card are now shown directly instead of a generic failure message.
  • Auto-resolved email. Authenticated customers no longer need to re-enter their email in the card form.
  • Hidden zero fees. The "$0.00 processing fee" text no longer appears when there is no fee.
  • Test mode fix. Stablecoin confirm and cancel operations no longer fail in test mode.

Integration Health Monitoring

Integration pages now surface connection health directly in the dashboard. Health badges show auth refresh failures, upcoming expirations, and expired auth tokens at a glance. Detail pages include alert banners with an actionable "Resync Now" button.

Behind the scenes, a daily cron job automatically refreshes expiring OAuth tokens with a 7-day lookahead window. Failed refreshes trigger admin alert emails. The system supports any OAuth integration type automatically.

Improved Customer Authentication

Sign-in now streamlines customer authentication into a single OTP prompt. Customers authenticate once and get both a customer session in a single flow. This fixes the previous scenarios that would require a customer to authenticate twice, reducing friction at login.

Balance Top-Ups

The balance top-up flow has been unified so the guest token experience reuses the same components as the authenticated flow. Card payments are now supported for balance top-ups in addition to stablecoins. Payment method selection is displayed inline and selecting a method immediately opens the payment sheet.

Minor Improvements

  • Session mode is now the single source of truth for all checkout and top-up actions, matching industry standard approaches. Mode is no longer derived from location integrations or passed from the client.
  • Checkout URLs simplified from loc_live_{id} to raw CUIDs, with backwards-compatible redirects for old URL formats, resulting in shorter URLs.
  • Dashboard revenue chart fixed for merchants in non-UTC timezones.
  • Square integration switched to production APIs for both test and live modes, with data isolation handled within the Decal dashboard.
  • Square resync now correctly updates OAuth tokens when the integration has an expired auth token.
  • Test mode banner is now a shared component across apps with improved scroll-hide behavior.
  • Failed top-up transactions can now be retried without creating duplicate records. The existing transaction resets from FAILED to INITIATED.
Read more →