Rotterdam · 51°55′N · 4°28′O · Atelier nr. 004
1 plek · start Q4 2026Klantportaal →MMXXVI
CaseKlantresultaat · Platform2025

Sessia.
Van nul naar 50.

Een boekingsplatform voor sessie-gebaseerde dienstverlening, ontworpen en gebouwd vanaf nul. Merk, productontwerp en een typed Next.js-implementatie: auth, betalingen, dashboards en marketingsite in één codebase.

Bestek
Type
Opdracht · Platform
Bewijs
Klantresultaat
Jaar
2025
Rol
Merkidentiteit, productontwerp, ontwikkeling en overdracht
Stack
Next.jsTypeScriptSupabaseStripeVercel
Doorlooptijd
8 weken
Opdrachtgever: Eva Möller, oprichter. Opdracht voor een externe opdrachtgever. Het genoemde resultaat komt van de opdrachtgever en is op aanvraag verifieerbaar.
50
Betalende klanten in 8 weken
8 wk
Van schema tot livegang
99
Lighthouse op de marketing-routes
< 200 ms
Time-to-first-byte via Vercel edge
RondleidingZonder login

Wat een gebruiker doorloopt.

De marketingsite van Sessia staat open; de productruimte zit achter een login. Dit is de route die een aanbieder en haar klant afleggen.

sessia.nl
Homepage en dashboard van Sessia: boekingen, betalingen en accounts in één Next.js-platform
Homepage en dashboard, één codebasePlatform · live
  1. Publiek

    Landingspagina en prijzen

    De marketingsite en de prijspagina zijn voor iedereen te openen. Die prijspagina leest dezelfde plans-tabel als de app, dus wat je daar ziet is wat het product hanteert.

  2. Stap 1

    Workspace aanmaken

    Een aanbieder registreert zich en krijgt een eigen workspace. Die workspace is vanaf dat moment de grens van alle data: boekingen, klanten, betalingen.

  3. Stap 2

    Sessies en klanten beheren

    Achter de login staan boekingen, klantbeheer en rapportages, per workspace gescheiden. Van dit deel tonen we geen losse schermen.

  4. Stap 3

    Boeken en betalen

    De klant kiest een sessie en rekent af via Stripe Checkout. Zodra Stripe de betaling bevestigt staat de boeking vast en loopt de uitbetaling naar de aanbieder.

Het beeld hierboven is het enige scherm dat we publiek tonen: de rest is de productomgeving van de opdrachtgever, met gegevens van haar klanten. Die stappen staan daarom in tekst.

Opdracht

Eén product, geen stapel tools.

Sessia verkoopt sessies: boekingen, betalingen, klantbeheer, programma's en rapportages. De oprichter wilde dat als één product, niet als vijf abonnementen die elkaar half verstaan.

De harde eis was multitenancy met data-isolatie per workspace. Off-the-shelf boekingstools bieden dat niet, of alleen als enterprise-optie met een prijs die niet past bij een startende aanbieder. Dus: zelf bouwen, met de isolatie in de database in plaats van in de applicatiecode.

  • 01Boekingen, betalingen en klantbeheer in één workspace per aanbieder.
  • 02Harde data-isolatie op databaseniveau, geen if-statements per klant.
  • 03Marketingsite en app in dezelfde repo, zodat prijzen en product tegelijk live gaan.
  • 04Overdracht waarmee de oprichter het product zelf kan onderhouden.
AanpakDrie sleutelmomenten

Waar het project gewonnen werd.

Week 1–3 · Schema-design

Drie weken aan het schema, voordat er een scherm bestond.

Multitenancy via Row Level Security in Postgres. Elke tabel kent zijn workspace, en de database begrenst elke query in plaats van een if-statement in de applicatiecode. Dat levert één codebase op zonder klant-specifieke uitzonderingen.

Row-level security is geen garantie. Postgres kent rollen die eroverheen gaan: een superuser, een rol met BYPASSRLS, en de eigenaar van de tabel zolang FORCE ROW LEVEL SECURITY uitstaat. De isolatie is daarom afgegrensd en getest: een policy per tabel op workspace_id, negatieve autorisatietests die controleren dat een sessie van de ene workspace geen rij van de andere terugkrijgt, een applicatierol met alleen de rechten die hij nodig heeft, serviceaccounts daarvan gescheiden en apart beoordeeld, en een periodieke herbeoordeling van de policies. Zo blijft een lek onwaarschijnlijk en aantoonbaar, in plaats van beloofd.

schema.sqlPostgres · RLS
01workspacestenant-root; elke rij in elke tabel draagt workspace_id
02bookingssessie, host, klant, status, betaalreferentie
03paymentsStripe-event gekoppeld aan boeking, idempotent
OKpolicy per tabelusing (workspace_id = current_workspace()), met negatieve tests per rol
Week 3–6 · Eén codebase

Marketingsite en app in dezelfde repo.

Geen aparte WordPress voor marketing. De landingspagina en de geauthenticeerde productruimte leven in één Next.js-project, met één design system en één deploy. Een wijziging aan de prijspagina en aan het dashboard gaat in dezelfde commit live, dus er is niets om uit sync te raken.

routesNext.js App Router
/landingspaginastatisch, SEO, Lighthouse 99
/pprijzenleest dezelfde plans-tabel als de app
/appproductruimtegeauthenticeerd, per workspace
/app/*boekingen, klanten, rapportagesserver components, streaming
Week 6–8 · Betalingen

Stripe Connect voor de marketplace-laag.

Elke aanbieder krijgt een Express-account, elke sessie een Checkout die aan de host gekoppeld is, en de uitbetaling loopt zonder handwerk. Stripe Checkout en het Customer Portal nemen facturen, opzeggen en kaartwijzigingen over, zodat daar geen eigen schermen voor gebouwd hoefden te worden.

stripeConnect · Express
01Express-account per hostonboarding via Stripe, geen eigen KYC
02Checkout per sessiebedrag, host en boeking in de metadata
03webhook → boeking bevestigdpayment_intent.succeeded, idempotent verwerkt
OKpayouts automatischCustomer Portal voor facturen en opzeggen
Resultaat

Wat er acht weken na livegang stond.

Eén cijfer komt van de opdrachtgever, met de telwijze erbij. De rest is techniek die dat cijfer mogelijk maakte.

50
Betalende klanten in 8 weken
Sessia, eerste 8 weken na livegang. Telt betalende boekingsklanten van het platform, cijfer van de opdrachtgever, op aanvraag verifieerbaar. Wij bouwden het platform; acquisitie deed de opdrachtgever zelf.
99
Lighthouse performance, marketing-routes
Accessibility, best practices en SEO: 100. Rapport in de repo.
< 200 ms
Time-to-first-byte
Gemeten vanaf Vercel edge, marketing-routes.

Hoe dat cijfer geteld is. Betalende boekingsklanten van het platform, geteld over de eerste acht weken na livegang. Cijfer van de opdrachtgever, op aanvraag verifieerbaar. Wij leverden merk, platform en betalingen; de acquisitie deed de opdrachtgever zelf. Een aanbod dat klanten trekt is dus niet hetzelfde als een platform dat ze kan bedienen: wij bouwden het tweede.

Na livegang was er geen los ontwikkelteam nodig. De oprichter onderhoudt het product zelf, op basis van de overdrachtsdocumentatie en de Loom-sessies uit de laatste week. Code in haar repo, infrastructuur op haar accounts.

Opdrachtgever
Nick herbouwde onze funnel en leverde een Claude-assistent in dezelfde sprint waarin een vorig bureau een contract opstelde.
Eva MöllerOprichter · Sessia

Eva beoordeelt hier de samenwerking als geheel. Deze pagina beschrijft het merk, het boekingsplatform en de betalingen; de funnel en de Claude-assistent die zij noemt vallen buiten wat hier is uitgewerkt en zijn op deze pagina niet onderbouwd.

Stack

Elke laag één keuze, met de reden erbij.

LaagKeuzeWaarom
FrameworkNext.js (App Router)Marketingsite en app in één project, server components voor het dashboard
TaalTypeScriptEén typed model van database tot formulier
Database en authSupabase (Postgres + Row Level Security)Multitenancy afgedwongen in de database
BetalingenStripe Checkout, Connect en Customer PortalMarketplace-uitbetalingen en self-service facturatie zonder eigen schermen
StylingTailwind CSS + eigen design systemEén visuele taal voor site en app
E-mailResend met React-e-mailsTransactiemails in dezelfde componenten als de app
HostingVercelPreview per commit, edge-caching voor de marketing-routes
Geleerd

Voor dit type platform is de keuze voor marketing en app in één repo doorslaggevend. Content en product gebruiken dezelfde tooling, en een wijziging aan de prijspagina gaat samen met de wijziging aan het dashboard live. Het schema drie weken de tijd geven voelde traag; het is de reden dat er daarna geen herbouw nodig was.

Eerstvolgende start: Q4 2026

Plan een vergelijkbaar project.
Van schema tot eerste betalende klant.

Een gesprek van 45 minuten: je hoort of jouw product in 6–10 weken live kan, wat het kost en waar de risico's zitten. Vaste offerte binnen 48 uur.

01SaaS-ontwikkeling: 6–10 weken, vaste prijs na gesprek.
02Code in jouw repo, infrastructuur op jouw accounts.
03Dagelijkse Loom-updates, wekelijkse demo.
04Reactie binnen 24 uur.

Laatst bijgewerkt: 8 september 2026.