Veiligheidsrisico
Opgelost
Medewerkers hadden onbedoeld toegang tot billing en gebruikersbeheer. Nu krijgt iedereen precies wat zijn taak vraagt.
Case study · toegangsbeheer · restaurantplatform
Veiligheidsrisico
Opgelost
Medewerkers hadden onbedoeld toegang tot billing en gebruikersbeheer. Nu krijgt iedereen precies wat zijn taak vraagt.
Toegangsbeheer
Per actie
Reservaties beheren, instellingen wijzigen en billing inzien zijn nu strikt van elkaar gescheiden.
Uitbreidbaarheid
Eenvoudiger
Nieuwe medewerkers of functies toevoegen zonder risico op onbedoelde toegang tot gevoelige data.
Probleem
In het platform had een gebruiker vaak wel toegang nodig tot reservaties, maar niet tot instellingen, gebruikersbeheer of billing. Toch werd die toegang lang bepaald door één brede restaurantrol. Dat werkte initieel, maar werd snel een bron van uitzonderingen en ongewenste macht.
Waarom dat gevaarlijk werd
Zodra één rol te veel acties afdekt, ontstaat sluipende privilege-uitbreiding. Dan ben je geen toegang meer aan het modelleren, maar uitzonderingen aan het stapelen.
Analyse
Meerdere restaurants per gebruiker.
Verschillende werkrollen binnen hetzelfde restaurant.
Acties met uiteenlopende gevoeligheid, van reservaties bekijken tot billing beheren.
Backward compatibility met de bestaande Restaurant-owner setup.
Mijn standpunt is hier eenvoudig: zodra verschillende gebruikers verschillende acties uitvoeren binnen hetzelfde domein, volstaan roles niet meer als eindmodel. Ze blijven nuttig, maar enkel als grof startpunt.
Oplossing
Het systeem werkt nu met twee lagen: rollen als grove groepering (manager, medewerker), en voor elke specifieke actie een aparte toegangscontrole. Wie geen expliciete toestemming heeft, krijgt geen toegang.
Elke actie heeft een eigen toestemming
Reservaties bekijken, instellingen aanpassen, gebruikers beheren en billing inzien zijn nu vier aparte bevoegdheden — niet gebundeld in één brede restaurantrol.
Geen toegang tenzij expliciet toegekend
Ontbreekt een toestemming? Dan is het antwoord automatisch nee. Dat voorkomt dat nieuwe functies onbedoeld openstaan voor de verkeerde mensen.
Roles vs. Permissions
| Actie | Manager (rol) | Medewerker (rol) | Permission (nieuw) |
|---|---|---|---|
| Reservaties beheren | ✓ | ✓ | ManageReservations |
| Instellingen wijzigen | ✓ | ✓ | ManageSettings |
| Gebruikersbeheer | ✓ | ✓ | ManageUsers |
| Billing inzien | ✓ | ✗ | ViewBilling |
Vóór: Medewerker had door zijn rol ongewild toegang tot instellingen én gebruikersbeheer.
Na: Elke actie wordt getoetst op een specifieke permission — deny by default.
Security principle
Belangrijk detail in de implementatie: als er geen expliciet recht is, is het antwoord gewoon false. Dat voorkomt impliciete toegang en maakt nieuwe features veiliger uitbreidbaar.
Waarom dit beter is
Beveiliging faalt hier naar gesloten toestand. Dat is voorspelbaarder dan permissies achteraf dichtzetten wanneer een feature al live staat.
Trade-off
Voordelen
Nadelen
Backward compatibility
We hebben de bestaande owner-setup niet abrupt gebroken. Accounts die al actief waren, bleven gewoon werken tijdens de overstap. Dat is praktisch voor migratie, maar precies daarom moet je het ook benoemen als tijdelijke maatregel en niet als permanent ontwerp.
Waarom dit werkt
De overstap naar het nieuwe model hoeft niet alles op één dag te veranderen. Bestaande gebruikers blijven werken, nieuwe functies worden meteen correct beveiligd. Zo migreer je zonder operationele onderbreking.
Resultaat
Reservaties wijzigen, instellingen aanpassen en gebruikers beheren kregen elk hun eigen permission.
Een medewerker kan nu reservaties beheren zonder impliciet toegang te krijgen tot alle restaurantinstellingen.
Controlleracties zijn leesbaarder geworden doordat ze expliciet de vereiste toestemming vragen.
Het autorisatiemodel is beter uitbreidbaar per feature zonder nieuwe rol-explosie.
Een actie als ToggleReservatiesActief hoeft daardoor niet langer “restaurantbreed” beschermd te worden, maar kan exact gekoppeld worden aan de juiste permission voor die functionaliteit.
Lessons learned
Start met een kleine permission set en laat ze groeien op basis van echte use cases.
Hou backward compatibility expliciet in het oog als bestaande accounts al actief zijn.
Centraliseer authorization in een service in plaats van logica te verspreiden over controllers.
Test per actie en per permission, niet alleen per rolnaam.
Gebruik deny-by-default als veilige basisregel.
Ik zou dit patroon niet aanraden voor een zeer klein team met een triviale adminomgeving. Maar in een platform waar meerdere gebruikers verschillende taken uitvoeren binnen één restaurant, is dit de juiste balans tussen veiligheid en werkbaarheid.
Takeaway
Gebruik roles als grouping en permissions als beslissingslaag. Dat maakt restaurantbeheer veiliger, duidelijker en veel beter schaalbaar in onderhoud, zonder in vage enterprise-complexiteit te vervallen.
Voor de technisch geïnteresseerde
De onderstaande codevoorbeelden tonen hoe het toegangsmodel concreet is uitgewerkt in C# met een enum, servicecontract en fallback-logica.
Permission enum — alle beschikbare rechten
public enum RestaurantPermission
{
ViewReservations,
ViewStatistics,
ViewSettings,
EditReservation,
ManageOpeningHours,
ManageTables,
ManageUsers,
ManageBilling,
ManageContract
}Servicecontract
Task<bool> HasPermissionAsync(string userId, string restaurantId, RestaurantPermission permission);
Task<IEnumerable<RestaurantRole>> GetUserRolesForRestaurantAsync(string userId, string restaurantId);Fallback voor bestaande owner-accounts (tijdelijk)
if (userId == restaurantId)
{
return RolePermissions.HasPermission(RestaurantRole.Owner, permission);
}
Plan een vrijblijvende digitale kennismaking met Mitch en ontdek wat wij voor jouw organisatie kunnen betekenen.