Subscription Lifecycle

Subscription Lifecycle

Every subscription carries two independent state machines. They’re deliberately orthogonal — a subscription is routinely “in force” and “not yet paid” at the same time, during its grace period. That’s expected, not an error state.

1. Status — is this period in force?

2. Payment status — has this period been paid for?

Pause / resume — the one contract every trigger follows

Whether a pause is customer-initiated, admin-initiated, or automatic (non-payment), the contract is identical:

No wash is ever silently lost to a pause — it’s either restored or replaced by a makeup slot as part of the top-up.

Incidents — a missed wash always gets a retry

If a cleaner can’t complete a wash (car not found, blocked access, weather, etc.), a makeup wash is automatically created for the next available day (skipping days that already have a wash, and never past the period’s end) — except when the customer explicitly asked to skip that day, which doesn’t trigger a retry.

A wash left SCHEDULED with no cleaner activity past its operating day’s close (3 PM Cairo the following day) is automatically marked a no-show and gets the same makeup treatment.