Marketplace SaaS multi-ruolo — RBAC area-based, audit doppio, commissioni, multi-lingua. Tre anni di sviluppo continuo.
Una piattaforma multi-tenant in produzione per un settore regolamentato e high-riskin Svizzera. NDA attivo: il cliente e il verticale restano riservati. L'architettura sotto descritta è invece pubblica e riusabile su qualunque marketplace verticale a quattro ruoli — immobiliare, tutoring, artigiani, classified.
56
Modelli Prisma
3 anni
Sviluppo continuo
1.940
Ore tracciate
4
Ruoli con RBAC
4
Tier abbonamento
5
Lingue native
Il contesto: un verticale high-risk e poco competente
Il cliente operava in un settore regolamentato in Svizzera dove la concorrenza digitale era ferma a un'altra epoca: portali datati in PHP, pagamenti via bonifico, zero verifiche identità, UX da forum del 2010. Una nicchia con ricavi importanti e qualità tecnica fra i più bassi del mercato europeo.
La richiesta era chiara: costruire da zero un marketplace SaaS multi-tenant con qualità da prodotto consumer moderno — verifica identità seria, abbonamenti ricorrenti, sistema commissioni per agenti di vendita, contenuti monetizzabili, multi-lingua nativa, audit completo per le richieste regolatorie. Tutto in conformità nLPD svizzera, con dati e backup esclusivamente in Svizzera.
“Tre anni di lavoro continuo. 56 modelli Prisma. Quattro ruoli, tre livelli di admin, due tabelle di audit. Quello che doveva essere un MVP da sei mesi è diventato un sistema operativo per un'intera categoria di business.”
Quattro ruoli, un solo schema
Il cuore del sistema è un modello Usersingolo che assume comportamenti diversi in base al ruolo. Niente tabelle separate per “professionista” e “cliente”: stessa identità, capability diverse. Questo rende possibile cambiare ruolo (un utente che diventa professionista) senza migrazioni dolorose.
Utente finale
Browse, ricerca filtrata, messaggistica, recensioni, preferiti. Permessi: lettura globale, scrittura sulle proprie risorse.
Professionista
Dashboard editoriale completa: media gallery, storie a tempo, abbonamento attivo, statistiche viste, gestione conversazioni.
Club / multi-account
Profilo contenitore con N profili affiliati. Gestione fatture cumulative, dashboard aggregata, permessi delegati.
Admin (3 livelli)
Super-admin, moderatore, finance. Permessi granulari per area: ban, refund, edit profili, audit completo. Ogni azione tracciata.
Diagramma 01 — Schema dati semplificato (estratto da 56 modelli)
Lo schema completo conta 56 modelli. Il diagramma sopra mostra i quattro pilastri: User al centro, Profile come aggregato di contenuti monetizzabili, Subscription / Commission per il flusso economico, AuditLog per la governance.
RBAC area-based, non page-based
La maggior parte degli RBAC che vediamo in giro è page-based: un middleware controlla chi può accedere a una rotta. Funziona finché l'applicazione è semplice. Quando i ruoli iniziano a sovrapporsi — un admin moderatore può modificare contenuti ma non rimborsare, un club può gestire i propri profili ma non quelli altrui — il page-based diventa un albero di if annidati.
La nostra scelta: RBAC area-based. Una matrice esplicita di (ruolo, area, livello). Le aree sono concettuali (Profilo, Contenuti, Abbonamenti, Moderazione, Sistema), i livelli sono tre (lettura, scrittura sulle proprie risorse, scrittura globale). Ogni endpoint dichiara di che area-livello ha bisogno; il middleware fa il resto.
Il risultato: aggiungere un nuovo ruolo costa 1 riga in matrice, non un refactor. E gli audit di compliance hanno una mappa leggibile in due minuti.
Diagramma 02 — RBAC area-based (4 ruoli × 5 aree)
La matrice reale ha 12 ruoli (4 utente-side + 3 admin × 3 livelli + 2 sales agent) ed è derivata da un singolo file TypeScript con type-safety end-to-end. Il diagramma mostra una versione compressa.
Audit log doppio: utenti e admin non condividono la stessa tabella
Errore comune: una singola tabella audit_logdove finisce qualunque azione, di qualunque attore. Sembra ordinato finché non arriva il primo subpoena con cui devi distinguere “cosa ha fatto questo utente” da “cosa abbiamo fatto noi sull'utente”. A quel punto la tabella unica diventa un incubo di filtri, indici e false positive.
La nostra scelta è stata netta: due tabelle, due pipeline.UserActivityLog ha retention 90 giorni, schema leggero, ottimizzata per analytics. AdminAuditLog ha retention forever, cattura il diff JSON before/after di ogni mutazione, è scritta da un wrapper obbligatorio che falla la build se manca.
Diagramma 03 — Audit log doppio (utente vs admin)
Il wrapper RBAC è non-bypassabile: tutti gli endpoint admin passano da una factory che cattura automaticamente il diff e scrive su AdminAuditLog prima di committare la transazione. Atomicità garantita.
Sistema commissioni e sales agent
Il marketplace ha un canale di acquisizione tramite sales agent geografici: persone reali che firmano clienti su una zona e ricevono una percentuale ricorrente per tutta la durata dell'abbonamento. Sembra semplice. Non lo è quando metti insieme retry su pagamenti falliti, refund parziali, change tier mid-cycle, e una commissione che varia in base al tier acquistato.
La regola d'oro che ci siamo dati: una commissione esiste se e solo se esiste un payment confermato. Niente record speculativi. Le commissioni vengono calcolate al webhook Stripe/TWINT, non in fase di subscription create. Idempotenza sul payment ID: ogni evento processa al massimo una volta, anche su replay.
Il batch payout mensile genera CSV pronto per il bonifico bancario, con tracciamento degli importi pagati. Zero double-spending: una volta marcata paidOut, la commissione non rientra in batch successivi.
Diagramma 04 — Flusso commissioni & sales agent
Verifica identità: il livello di trust che il settore non aveva
Verifica identità in tre passi: documento d'identità, foto vivente con un codice univoco generato server-side al momento dell'upload (anti-foto-recycled), revisione manuale entro 24-48 ore da un team interno di moderazione. Niente provider KYC esterni: i dati restano in Svizzera, l'onboarding costa zero per transazione e il team può escalare senza dipendere da un'API di terze parti.
Il badge “verificato” è una proprietà del profilo, non un campo testo. Compare in tutta la UI come segnale di trust ed è il prerequisito per accedere ai tier più alti. Quando un documento scade, il sistema flagga automaticamente il profilo per re-verifica.
Sicurezza, privacy e compliance svizzera
In un settore regolamentato non ci sono opzioni: o hai compliance documentabile, o non sei un fornitore serio. Quattro pilastri non negoziabili.
Dati in Svizzera (nLPD)
Hosting e DB su datacenter CH. Per il settore di applicazione la residenza dati non è preferenza, è obbligo.
KYC con revisione manuale
Documento ID + foto vivente con codice univoco generato server-side. Approvazione 24-48h da un team interno, non automatica.
Moderazione attiva + DMCA
Coda di segnalazioni con priorità, takedown notice in 24h. Watermark non rimovibile sui media caricati.
PCI-DSS by proxy
Zero card data sui nostri server. Stripe e TWINT gestiscono il PCI scope. Webhook firmati e replay-protected.
Cinque lingue native, non plug-in
La Svizzera è quattro lingue ufficiali più l'inglese di servizio. Un Weglot o un traduttore automatico non bastano: i contenuti monetizzabili, le email transazionali, i template legali e l'onboarding del professionista devono essere localizzati frase per frase. Abbiamo usatonext-intl con bundle separati per locale e routing dedicato (/fr/...,/de/...).
Anche i campi user-generated supportano traduzioni multiple sullo stesso record (es. una bio in IT + DE + FR), con fallback intelligente sulla lingua preferita dell'utente che legge.
Cosa abbiamo imparato
Tre anni su un singolo prodotto cambiano il modo in cui pensi alle architetture. La lezione più importante non è tecnica, è strategica: i settori high-risk sono sotto-serviti dal punto di vista tecnico. Adult tech, gambling, classified, exchange crypto — sono mercati pieni di ricavi e vuoti di sviluppatori seri, perché molti studi “perbenisti” ci girano alla larga.
Tecnicamente, le scelte che hanno retto bene tre anni di evoluzione sono tre: schema Prisma normalizzato (no shortcut su tabelle “event blob”), RBAC esplicito anziché if annidati, audit log separato per attore. Quelle che invece abbiamo dovuto rifare almeno una volta: la pipeline upload media (passata da S3 diretto a Cloudflare R2 con CDN edge) e la gestione storie/contenuti effimeri (initially in DB, oggi su storage object con scadenza nativa).
Sul piano del business: una piattaforma multi-ruolo con verifica identità, abbonamenti ricorrenti e sistema commissioni è uno schema riusabile. Lo stesso scheletro può servire un marketplace immobiliare, una rete di tutor, una directory di artigiani, un classified verticale. Il valore non è il dominio: è la capacità di reggere quattro tipi di utenti, tre livelli di permessi e un flusso pagamenti senza buchi.
Stai costruendo un marketplace multi-ruolo?
Tre anni di esperienza concreta su uno stesso schema architetturale. RBAC area-based, audit doppio, pipeline pagamenti, KYC interno, multi-lingua. Lo schema è trasferibile a qualunque verticale — immobiliare, tutoring, artigiani, classified. Possiamo discutere la tua piattaforma senza vincoli, sotto NDA.
Parliamone sotto NDADettagli Progetto
Cliente
Riservato (NDA)
Periodo
3 anni · in corso
Categoria
Web App · SaaS Multi-tenant
Verticale
Settore regolamentato CH
Mercato
Svizzera (5 lingue)
Volume
1.940 ore tracciate
Ruoli gestiti
Utente / Pro / Club / Admin
Tecnologie
Cosa abbiamo costruito
Lo Stack Tecnologico
Stack scelto con un solo criterio: ogni componente deve reggere tre anni di evoluzione senza essere riscritto.
Next.js 14
App Router, SSR, ISR
Prisma + PostgreSQL
56 modelli, migration-driven
NextAuth + RBAC
Sessions JWT, area-based
Stripe + TWINT
Pagamenti ricorrenti, webhook
Cloudflare R2 / S3
Media storage, presigned URL
next-intl
5 lingue native, locale routing
WebSocket
Messaggistica real-time
Sharp + AVIF/WebP
Resize on-the-fly
Tiptap
Editor moderazione e blog
Playwright + Vitest
E2E + unit, CI bloccante
Creiamo Qualcosa di Grande Insieme!
Hai un progetto in mente? Parliamone. La prima consulenza è gratuita.