🌍 English | Español | Português
Open-source business management for service businesses and retail shops.
Self-hosted via Docker or cloud at trypronto.app
Pronto replaces Excel and disconnected apps for small service businesses and retail shops.
Your clients book directly with you — no marketplace commission, no vendor lock-in.
Supported business types:
Salons · Barbershops · Spas · Dental clinics · Fitness studios ·
Auto repair shops · Cafes · Tattoo studios · Retail shops & kiosks
- Online booking page — clients book with name + phone only, no account required
- Drag-and-drop calendar with staff color coding
- Double-booking prevention (PostgreSQL trigger)
- Zero commission — 100% of revenue goes to you
- Client cards with visit history, notes, tags, birthday
- CSV import from Fresha, Vagaro, Booksy, Mindbody, Square
- Fast checkout: services and products in one cart
- Cash, card, transfer payment methods
- Sales history with search by client
- Product catalog with barcode, SKU, category, cost/sell price
- Barcode scanner support (USB/Bluetooth keyboard-wedge mode)
- Manual product grid for cashiers without a scanner
- CSV/Excel import — auto-detects columns, supports
.xlsxand.csv - Excel export for products and sales history
- Low-stock alerts via Telegram, WhatsApp or Email
- Stock movement history per product
- Email (Resend / SMTP)
- Telegram Bot
- WhatsApp (Meta Cloud API)
- Viber Bot
- Auto-events: booking confirmation, 24h reminder, 1h reminder, thank-you, reactivation, birthday, low stock
Enable only what you need:
| Preset | Modules enabled |
|---|---|
| Salon / Barbershop | Bookings + CRM + POS + Inventory + Notifications |
| Shop / Kiosk | POS + Inventory + Notifications (no booking calendar) |
| Cafe | POS + CRM + Inventory + Notifications |
Toggle modules in Settings → Modules — unused tabs disappear from the sidebar.
- Dashboard shows today's revenue with a 7-day sparkline
- Full analytics dashboard (top services/products, client LTV, visit frequency) is cloud-only — see below
- Interface available in English, Spanish (LatAm), Italian, Portuguese (Brazil)
Requirements: Docker, Docker Compose, a free Supabase account.
# 1. Clone the repo
git clone https://github.com/SGrappelli/pronto.git
cd pronto
# 2. Copy environment file and fill in your values
cp .env.example .env
# 3. Disable email confirmation in Supabase (required for self-hosted)
# Dashboard → Authentication → Providers → Email → uncheck "Confirm email" → Save
# 4. Start — migrations run automatically on first start
docker-compose up -d-
Create a project at supabase.com
-
Copy your Database connection string (Session mode, port 5432) from
Project Settings → Database → Connection string and set it asDATABASE_URLin.env
Migrations are applied automatically when you rundocker-compose up -
Create a public storage bucket named
inventoryin
Supabase Dashboard → Storage → New bucket (required for product photos) -
Copy your project URL and anon/service keys to
.env -
Customize email templates (optional) — replace Supabase's defaults with Pronto-branded HTML:
Template in Supabase File Reset Password supabase/email-templates/reset-password.htmlConfirm signup supabase/email-templates/confirm-signup.htmlChange Email Address supabase/email-templates/email-change.html
Start free at trypronto.app — no credit card, no commission.
A few features are cloud-only and not part of the self-hosted core:
- Loyalty points program
- Analytics dashboard
After deploying, log into your Supabase project dashboard and check Advisors → Security Advisor. This project follows Postgres/Supabase RLS best practices in every migration, but Supabase's own advisor is the only way to confirm the live state of your specific database — including any objects that may have existed in your project before running these migrations, or custom changes you've made yourself. Fix anything flagged there before using this in production with real customer data.
Copy .env.example to .env and fill in:
# Supabase (required)
NEXT_PUBLIC_SUPABASE_URL=https://your-project.supabase.co
NEXT_PUBLIC_SUPABASE_ANON_KEY=your-anon-key
SUPABASE_SERVICE_ROLE_KEY=your-service-role-key
# PostgreSQL connection string (for automatic migrations)
# Supabase Dashboard → Project Settings → Database → Connection string (Session mode)
DATABASE_URL=postgresql://postgres.[ref]:[password]@[host]:5432/postgres
# App
NEXT_PUBLIC_APP_URL=http://localhost:3000
# Email notifications (choose one)
RESEND_API_KEY=re_xxxxxxxxxxxx
# or SMTP_HOST / SMTP_PORT / SMTP_USER / SMTP_PASS / SMTP_FROM
# Cron (protects /api/cron/notify)
CRON_SECRET=replace-with-random-stringMessenger credentials (Telegram, WhatsApp, Viber) are configured per-business in
Settings → Notifications — not in environment variables.
| Layer | Technology |
|---|---|
| Frontend | Next.js 14 + Tailwind CSS + shadcn/ui |
| Backend | Next.js API Routes |
| Database | Supabase (PostgreSQL) with RLS |
| Auth | Supabase Auth (Email + Google OAuth) |
| Storage | Supabase Storage (product photos) |
| Notifications | Resend/SMTP + Telegram Bot API + Meta WhatsApp Cloud API + Viber Bot API |
| i18n | next-intl — EN / ES / PT |
| Deployment | Docker Compose |
| Trigger | Who receives it | Channel |
|---|---|---|
| Booking confirmed | Client | Email + WhatsApp |
| Booking confirmed | Business owner | Telegram + Viber |
| 24h before appointment | Client | Email + WhatsApp + Telegram† + Viber† |
| 24h before appointment | Business owner | Telegram + Viber |
| 1h before appointment | Client | Email + WhatsApp + Telegram† + Viber† |
| 1h before appointment | Business owner | Telegram + Viber |
| After visit completed | Client (thank-you + rebook link) | Email + WhatsApp + Telegram† + Viber† |
| 30 days no visit | Client (re-activation) | Email + WhatsApp |
| Birthday | Client | Email + WhatsApp |
| Low stock alert | Business owner | Email + Telegram + Viber |
† Client receives Telegram/Viber notifications only if they have linked their profile via /link {phone} in the bot.
Call this endpoint every 15 minutes from cron-job.org (free):
GET https://yourdomain.com/api/cron/notify
Authorization: Bearer YOUR_CRON_SECRET
Or use the built-in pg_cron scheduler — edit supabase/migrations/007_cron_jobs.sql (replace YOUR_APP_URL and YOUR_CRON_SECRET), enable pg_cron and pg_net extensions in Supabase Dashboard, then run the file via SQL Editor.
- Open @BotFather →
/newbot→ copy the token - In Pronto: Settings → Notifications → paste token → click Connect
- Open your bot in Telegram → send
/start
Owner commands: /today — today's appointments · /help — command list
Clients link their profile by sending /link +12345678900 to the bot (their booking phone number).
⚠️ Since February 2024, new Viber bots require a commercial agreement (~€100/month). This integration works for bots created before February 2024. For new setups, Telegram is recommended (free).
- Sign in to partners.viber.com → copy auth token
- In Pronto: Settings → Notifications → paste token → click Connect
Clients link via /link +12345678900 in the bot.
- developers.facebook.com → create a Meta App → add WhatsApp product
- Copy Phone Number ID and Access Token from WhatsApp → API Setup
- Recommended: create a permanent token via Meta Business Manager → System Users → Generate Token with
whatsapp_business_messaging+whatsapp_business_managementpermissions - Paste credentials in Settings → Notifications → WhatsApp and save
⚠️ Business-initiated messages (reminders, thank-you, birthday) require pre-approved Message Templates submitted through Meta Business Manager. Without them, these messages are silently dropped by Meta. Create templates at business.facebook.com → Account tools → Message templates.
git clone https://github.com/SGrappelli/pronto.git
cd pronto
cp .env.example .env
# Edit .env
docker-compose up -dPoint your domain to the server and set up a reverse proxy (Nginx, Caddy, or Cloudflare Tunnel).
server {
listen 80;
server_name yourdomain.com;
location / {
proxy_pass http://localhost:3000;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
}
}pronto/
├── app/
│ ├── (auth)/ # Login, Register, Check email
│ ├── (dashboard)/ # POS, CRM, Inventory, Booking, Settings, Dashboard
│ ├── api/ # All API routes (notifications, cron, inventory, etc.)
│ ├── onboarding/ # First-run setup wizard
│ └── book/[slug]/ # Public booking page (no login required)
├── components/
│ ├── inventory/ # Import modal, barcode scanner UI
│ ├── layout/ # Sidebar, Header
│ └── ui/ # Button, Badge, Card, DatePicker...
├── hooks/
│ └── useBarcodeScanner.ts # Keyboard-wedge barcode scanner hook
├── lib/
│ ├── modules.ts # MODULES const — sidebar and feature gating
│ ├── plan-limits.ts # All unlimited in self-hosted
│ ├── supabase/ # Client, Server helpers, database types
│ ├── email.ts # Email templates + sending
│ ├── telegram.ts # Telegram Bot API + templates
│ ├── viber.ts # Viber Bot API + templates
│ ├── whatsapp.ts # Meta WhatsApp Cloud API + templates
│ └── utils.ts # Helpers (formatCurrency, formatDate…)
├── messages/
│ ├── en.json # English strings
│ ├── es.json # Spanish strings
│ ├── it.json # Italian strings
│ └── pt.json # Portuguese strings
├── supabase/
│ └── migrations/ # SQL files — applied automatically on first docker-compose up
├── .env.example
└── docker-compose.yml
- Copy
messages/en.jsontomessages/fr.json(or any locale code) - Translate all values
- Update
i18n/request.tsto include the new locale
- POS + CRM + Booking + Inventory
- Omnichannel notifications (Email, Telegram, WhatsApp, Viber)
- Retail / barcode mode with CSV/Excel import-export
- Modular system (enable only what you need)
- Analytics dashboard
- Multi-language: EN / ES / IT / PT
- PWA with offline-capable POS
- Docker one-command install
- Camera barcode scanning (BarcodeDetector API)
- Label printing
- Batch stock receiving
- Open Food Facts integration (auto-fill product names by barcode)
- LINE messenger
- Staff payroll & commissions
- Multi-location support
- AI insights
- API access
Need help getting started?
- Installation & setup — deploy Pronto on your server, configure all integrations ($100–200)
- Customization — custom features, branding, or integrations for your specific business ($150–400)
Contact: ukv2179@gmail.com or open an issue with the services label.
Pull requests welcome. Please open an issue first to discuss major changes.
See CONTRIBUTING.md for guidelines.
MIT — free for personal and commercial use.
Have a feature request? Open an issue