Appointments Reference Public

Packages & Memberships

End-user documentation for the ERPat Appointments module (spa / salon / clinic booking).

Guide version: r1 Module version: 1.0.0 Updated: 2026-07-22 Estimated time: 16 min 1 views
Catalog & Setup

Packages & Memberships

Packages let you sell prepaid bundles of services — a one-off Package (e.g. "5 Massages") or a Membership plan — to your customers. Selling a package gives that customer a running balance of sessions per service (their entitlements), which the front desk can later spend to cover a service at Checkout so it drops off the bill.

Manager Front desk Admin
ℹ️
Where this lives Open it from the left menu at Appointments → Packages (route /appointment_packages). The Appointments module must be enabled, and you need the Packages permission to open the page. Building the catalog and selling happen here; spending a session happens on the appointment Checkout screen. Customers never operate this screen — staff sell packages to them.

What packages & memberships are

A package bundles one or more services with a session count for each (e.g. 3 × Facial + 1 × Massage), an optional price, and an optional validity period. Selling it to a customer provisions entitlements — a per-service balance of how many sessions they have left. When that customer later comes in for one of those services, the front desk can "cover" the service line at checkout by drawing one session from the matching entitlement, and the covered service is excluded from the invoice (they already prepaid).

Package vs. Membership

TypeWhat it isBilling period
Package A one-off, prepaid bundle of service sessions (e.g. "5-Session Facial"). Bought once; sessions draw down as they are used. Not applicable.
Membership A membership plan. Structurally the same as a package (services + session counts), but tagged as a membership and carrying a billing period. None / Monthly / Yearly — informational only in this version.
????
Memberships do not auto-charge The Billing period (Monthly / Yearly) on a membership is a label only — this version does not run automatic recurring billing. Do not rely on it to charge customers on a schedule; you sell and take payment for each membership manually, exactly like a package.

The two panels on one page

The Packages page is split into two lists side by side:

????
Packages (left panel — the catalog)

Every package/membership you offer. Columns: Name, Type, Price, Services (count of included services), Validity, Status, and an actions column. Header has a + Add Package button (shown only with create permission).

????
Sold Packages (right panel — read-only log)

Every package a customer has bought. Columns: Package, Customer, Type, Remaining (shown as "remaining / total"), Expiry, and Status. There is no edit or void action here — it is a record only.

Per-row actions (catalog)

Each catalog row exposes small action icons, each hidden unless you hold the matching permission:

IconDoesPermission
???? Shopping cartSell Package — opens the Sell modal to sell this package to a customer.Packages · Sell
✏️ PencilEdit — opens the Add/Edit modal pre-filled with the package and its included services.Packages · Update
✖ Times / XDelete — soft-deletes the package (catalog entry only).Packages · Delete
????
Build services first The included-services dropdown lists only Active services. Create and activate the services you want to bundle before building the package, otherwise they won't be selectable. See Services & Staff.

Building a package (SOP)

Building the catalog is a Manager / front-desk task. A package needs a name and — before it can ever be sold — at least one included service with a session count.

SOP · Create a package or membership

Actor: Manager / front desk (needs the Packages · Create permission).

  1. Open the Packages page

    Left menu → Appointments → Packages (route /appointment_packages).

  2. Click "+ Add Package"

    The button sits at the top-right of the left panel. The Add/Edit modal opens blank, with the Name field autofocused.

  3. Enter the Name

    Required — for example 5-Session Facial or Gold Membership.

  4. Choose the Type

    Package (one-off bundle) or Membership (a plan with a billing-period label). Defaults to Package.

  5. Set the Price

    The sale price of the whole package. Leave it 0 if you don't want an invoice raised when it's sold (a comp/gift). A price > 0 raises an unpaid invoice for that amount on sale — see Selling a package.

  6. Set Validity (days)

    How many days after purchase the package and all its sessions stay usable. Enter 0 for never-expires (shown as ∞). See Validity & expiry.

  7. (Membership only) Set the Billing period

    None / Monthly / Yearly. This is informational only — it does not trigger recurring billing.

  8. Add the included services

    In the Included services repeater, pick a Service (active services only) and set its Qty (min 1). Click + Add Service to add more rows (e.g. 3 × Facial + 1 × Massage). See Included services & session counts.

  9. Set Status, Public, and Description

    Leave Status as Active to use it, or set Inactive to hide it. Optionally tick Public and add a Description.

  10. Save

    Click Save. The catalog row appears (or updates), and you'll see the "record saved" confirmation.

⚠️
Editing replaces the whole service set When you edit a package and Save, the entire included-services set is rebuilt from the rows currently in the form: the old items are soft-deleted and only the rows you left in are re-inserted. Removing a row on edit removes that service from the package. It does not touch entitlements already sold.

Package form fields

FieldRequiredNotes
NameYesDisplay name of the package/membership. Autofocused.
TypeYesPackage or Membership; defaults to Package. Any other value falls back to Package.
PriceNoDefaults to 0. Currency formatting is stripped on save. 0 = no invoice is raised on sale.
Validity (days)NoDefaults to 0 (never expires, shown as ∞). If > 0, expiry = purchase time + that many days.
Billing periodNoNone / Monthly / Yearly. For memberships; informational only — no recurring billing.
Included services (Service + Qty rows)Yes to sellAt least one valid row (active service + Qty ≥ 1) is needed before the package can be sold. Rows with a blank service or Qty ≤ 0 are silently skipped on save.
StatusNoActive or Inactive; defaults to Active.
PublicNoCheckbox; defaults to unchecked. Stored on the package.
DescriptionNoFree-text, 2-row textarea.

Included services & session counts

The Included services repeater is the heart of a package: it defines which services the package grants and how many sessions of each. Each row is one service plus a quantity — for example a "Pamper Pack" might be 3 × Facial + 1 × Massage, which is two rows.

Repeater controlWhat it does
Service dropdownPicks the service to include. Lists Active services only — inactive/deleted services can't be added.
QtyHow many sessions of that service the package grants (minimum 1). This becomes the entitlement's total on sale.
Remove (X)Deletes that row from the form.
+ Add ServiceAdds another included-service row.
????
At least one service — or you can't sell it A package with no included services cannot be sold. The Sell action refuses with "Add at least one included service to this package first." Always add at least one Service + Qty row before you try to sell.
ℹ️
Silent skips are intentional Rows with a blank Service or a Qty of 0 or less are silently dropped when you Save — they don't raise an error, they just aren't stored. If a service you expected doesn't appear on the package, check that its row had both a service and a Qty ≥ 1.

Selling a package (SOP)

Selling records the sale to a named customer inside one transaction: it creates the customer's package instance, one entitlement per included service (total = the row's Qty), and — only if the package price is greater than 0 — an unpaid invoice for the price, linked back to the customer's package. The sale is stamped with source "staff".

SOP · Sell a package to a customer

Actor: Front desk / manager (needs the Packages · Sell permission).

  1. Find the package in the catalog

    On the Packages page, locate the package row in the left panel.

  2. Click the shopping-cart (Sell) icon

    The Sell Package modal opens, showing the package name in bold, its price, and a read-only Included services list (a green check with "N × Service" per item).

  3. Pick the Customer

    Choose the buyer from the Customer dropdown (required). It lists all customers as "First Last (email)" — use the email to disambiguate customers with the same name.

  4. Click "Sell Package"

    The system provisions the customer's entitlements (and, if priced, raises the invoice). You'll see "Package sold and entitlements provisioned.", the Sold Packages panel refreshes, and the modal closes.

  5. If priced — collect payment

    A priced package creates an unpaid invoice (status not paid, note "Package: <name>"). Take payment through the normal invoicing flow — see Checkout & Payments. The sale itself does not mark the invoice paid.

ℹ️
What "Sell" creates behind the scenes One customer package instance (stamped with purchase time, expiry, status, and source "staff"), one entitlement per included service (each with its own remaining balance and expiry), and — only when price > 0 — a linked unpaid invoice. Expiry is stamped from the package's Validity at the moment of sale.
⚠️
Price 0 means no invoice If you expect an invoice for the sale, make sure the package has a Price > 0 before selling. With a price of 0 the sale only provisions entitlements — no invoice is created, so there's nothing to collect against.

Entitlements & remaining sessions

An entitlement is the customer's per-service session balance, created when the package is sold. Each entitlement tracks:

  • Total — sessions granted (the included-service Qty at sale time).
  • Used — sessions consumed so far.
  • Remaining — total − used; this is what can still be spent.
  • Its own expiry and status (inherited from the package's validity at sale).

"Available now" — what shows at checkout

Only an entitlement that is available now — meaning active, unexpired, and with remaining sessions > 0 — is offered in the checkout "Apply package…" dropdown. Exhausted or expired entitlements simply stop appearing; there is no separate "expired" badge on the checkout line.

Viewing remaining sessions

There are two easy places to check how many sessions a customer has left:

????
Sold Packages panel

On the Packages page, the right-hand Sold Packages table's Remaining column shows "remaining / total" (e.g. 3 / 5) — the sum of remaining vs. total across all of that sold package's entitlements. The quickest at-a-glance check.

????
Customer History

Open an appointment's Customer History to see the customer's Active packages list (name + expiry) alongside visits, spend, and loyalty. Great for spotting a usable package before you upsell. See Customer History.

????
Check before you upsell Peek at Customer History before recommending a treatment — if the customer already has an active package for it, you can apply a session at checkout instead of charging again.

Applying a package to an appointment (SOP)

Sessions are spent on the appointment Checkout screen, in its Package coverage section. This section only appears while the appointment has a customer and no invoice yet. Applying a package "covers" a service line so it is excluded from the invoice, and consumes (claims) one session from the matching entitlement.

SOP · Apply a package session to a booking

Actor: Front desk (on the Checkout modal; needs the Checkout permission).

  1. Open Checkout before invoicing

    From the appointment card click Checkout while the appointment still has a customer attached and no invoice.

  2. Find the service line in "Package coverage"

    The Package coverage section lists each service line on the appointment. Uncovered lines with usable sessions show an "Apply package…" dropdown; lines with no available sessions show no control (they'll be billed normally).

  3. Choose the entitlement

    In the "Apply package…" dropdown, pick the package to draw from. Each option shows the package name and remaining count, e.g. "Glow Facial x5 (3 remaining)". Selecting it applies immediately.

  4. Confirm the coverage badge

    The line switches to a blue Covered by package badge and drops off the billable list; one session is claimed (used +1).

  5. Create the invoice for what remains

    Proceed to Create Invoice for the remaining (uncovered) billable lines. See Checkout & Payments.

Removing / undoing coverage

Applied the wrong session? While the appointment is still uninvoiced, click the red X next to the blue Covered by package badge. This releases the session back to the customer's balance (used −1, floored at 0) and the line becomes billable again — then apply the correct one.

????
Coverage locks in once invoiced Package coverage can only be applied or removed before the invoice is created. Once you click Create Invoice, the coverage controls disappear and the covered service was already excluded from that invoice — you can't cover, uncover, or refund the session afterward here.

If two staff apply the last session at once

Claiming a session is atomic — it only succeeds if the entitlement is active, unexpired, and still has a balance. If two people race for the last session, only one wins; the loser sees "That package session is no longer available." Re-check the customer's remaining balance and pick a different session (or bill the line).

Automatic release on cancellation

When an appointment is cancelled, any package sessions applied to it are automatically returned to the customer's balance — but only if no invoice was created yet. If an invoice already exists, the covered service was already excluded from that invoice, so the session is not refunded automatically; adjust manually if needed. (This mirrors the cancel behavior on the Calendar.)


Validity & expiry

Validity (days) controls how long a sold package and its sessions stay usable. It is set on the package in the catalog but stamped onto the customer's package at the moment of sale.

Validity valueMeaningShown as
0Never expires. The package and every session stay usable indefinitely.∞ (infinity) in the catalog and, as a null expiry, in Sold Packages.
> 0 (e.g. 90)Expiry = purchase time + that many days. After that date the sessions stop being offered.The concrete expiry date in the Sold Packages Expiry column.
⚠️
Changing validity doesn't extend sold packages Validity is stamped at the moment of sale. If you later change the package's Validity (days), it only affects future sales — already-sold customer packages keep the expiry they were stamped with. To give an existing customer more time you'd need to sell them a fresh package.
ℹ️
Expired sessions just disappear from checkout An expired or exhausted entitlement simply stops appearing in the checkout "Apply package…" dropdown — there's no error and no "expired" badge on the line. If a customer's package won't offer at checkout, verify it isn't past its expiry or already fully used (check "remaining / total" in Sold Packages).

Tips & gotchas

Everything below is scoped to Packages. Expand each item for the detail.

"Add at least one included service to this package first."

You tried to sell a package that has no included services. Edit the package, add at least one Service + Qty row (with Qty ≥ 1), Save, then sell again. A package with no services can't provision any entitlements, so the sale is refused.

"That package session is no longer available."

At checkout, the entitlement you tried to apply was exhausted or expired — often because another staffer claimed the last session at the same moment, or it just crossed its expiry. Re-check the customer's remaining balance (Sold Packages / Customer History) and either apply a different session or bill the line normally.

Only ACTIVE services can be bundled

The included-services dropdown (and the checkout coverage dropdown) only list Active services. If a service is inactive or deleted you can't add it to a package. Activate the service first on the Services page.

Editing a package replaces the whole service set

On Save, the old included-services are soft-deleted and only the rows currently in the form are re-inserted. Removing a row on edit removes that service from the package. It does not change entitlements customers already bought.

Price 0 = no invoice on sale

Selling a package priced at 0 provisions entitlements but does not create an invoice — there's nothing to collect. For paid packages, set a Price > 0; the sale then raises an unpaid invoice you collect via the normal invoicing flow.

Sessions are only spent at Checkout — before invoicing

The Package coverage section appears only while the appointment has a customer and no invoice yet. Apply coverage before you click Create Invoice; once the invoice exists the coverage controls are gone and coverage is locked in.

Cancelling refunds sessions only if not yet invoiced

Cancelling an appointment returns any applied sessions to the customer — unless an invoice was already created (the covered service was already excluded from that invoice). Invoiced-then-cancelled does not auto-refund sessions; adjust manually if needed.

Deleting a package doesn't revoke sold sessions

Deleting a package from the catalog is a soft delete of the catalog entry only. Customers who already bought it keep their entitlements — the delete does not retroactively revoke sold packages or sessions.

Billing period is just a label

The Monthly / Yearly billing period on a membership is informational in this version. There is no automatic recurring billing — sell and collect for each membership manually.

Where do I see a customer's leftover sessions?

Fastest: the Remaining column ("3 / 5") in the Sold Packages panel. Richer: the Active packages list in Customer History, with expiry dates.

Quick tips

  • Build and activate the underlying services before creating a package — only active services can be added as items.
  • Use Validity = 0 for gift-style packages that should never expire; the catalog and Sold Packages show ∞ for these.
  • When selling a priced package, remember it creates an unpaid invoice — go collect payment via Checkout; the sale doesn't mark it paid.
  • At checkout, apply all package coverage first, then Create Invoice — it keeps covered services off the bill and correctly draws down the sessions.
  • If you applied the wrong session, click the red X on that line to return it (before invoicing), then apply the correct one.

Legend · package & coverage cues

Active Active (package)Package is in normal use and appears in the catalog. The same green label marks an active sold customer package in Sold Packages.
Inactive Inactive (package)Package is hidden from normal use. In Sold Packages, any non-active status is shown as a grey label with the raw status text.
Package Type = PackageA one-off bundle of prepaid service sessions.
Membership Type = MembershipA membership plan; billing period is informational only in this version.
Validity ∞Shown for Validity 0 in the catalog and for a null expiry in Sold Packages — the package/sessions never expire.
Covered by package Covered by packageA checkout service line paid for with a package session (excluded from the invoice). A red X removes it — only before invoicing.
— (em dash)No package coverage is available for that service line; it will be billed normally.

Related pages

Was this guide helpful?

Report a content problem