DDD : Authentication and Authorisation, How to achieve?
Tags: ddd, domaindrivendesign, cleanarchitecture, programming
Published: 2023-03-08 15:18:12

This is not just another post however I want like minded persons who have created the system gracefully with a rich domain model that scaled it from modular monolith to micro-services, to discuss their approach, what worked for them and what not, and what was the learning.

Many a times we start small and create a simple MVC CRUD like application using some framework for pilot projects and quick release for market validation. 
Usually developers create a configuration file with some roles and permissions assigned and do a route level check using middleware.  
They make roles like: `users, admin, retailer, customer, internal admin roles, etc`.
and permission like `"create, read, delete, edit"` and pass these permissions to modules or features. 
Developers usually map role collected from user info and pass it to some middleware function as `authorise( "module_feature_name", "[create, read, update, delete]" )`

However this is good for 

- small simple projects, 
- good for learning some framework  
- projects used for internal or personal use.

When we want to create a rich domain model things need to be discussed in much more detail as per use-case and using  domains ubiquitous knowledge. 

**Let's take a scenario in retail:**

**Core Domain:**
A retailer can create bills and share the bills with their customers (one who purchases the product from the shop). A retailer can also assign staff to create bills on their behalf.
....
....other use-cases

**Supporting Domain**
**Customer Support:**
Customer support members will reach out to customers (Here customers for customer support team are retailers), they can take retailers' query and give necessary tele call support..
...
....other use-cases

**Generic Domain**
IAM: User sub domain can be used for authentication and authorisation.

**Use Case: 1**
A retailer can only edit his own bills/Invoice or can allow his selected staff to edit bills/Invoice. Admin can also edit the bills/Invoice for retailers. 

**User Domain:**
What are all the possible roles ?
Retailer, Staff, Admin, Customer Support Member

**There are few questions:**

1. Now who is a customer, a customer (end user one who purchases the product) in the core domain or a retailer in the customer support domain, and what role for two different entity has with same name ? 
2. What are permission levels? It's just the same as `CREATE, READ, DELETE AND UPDATE` or more detailed permissions?
3. Where do these permissions be applied in software: domain, service, controller, core, shared or somewhere else?
4. **How do we start from modular monolith and scale later so that there is not major impact and refactoring and scaling is easy for maintaining the roles and permission **

**A possible solution**

We can have a configuration file based on sub domains or BC we decided.

So we can define roles like:
`iam.billing.retailer
iam.billing.customer
iam.billing.admin
iam.billing.staff
iam.customer-support.customer
iam.customer-support.customer-support-member`

So here `iam.billing.retailer` and `iam.customer-support.customer` can be two different roles being assigned to same `entity`. 

We can define **permissions** to be specific to the domain/bc as per the use-case, 

Like `"generateInvoice", "viewInvoice", "changeInvoice".`

We can assign these permission to different roles from outside and this will make changes more configurable and can be even moved in future to other external service or LDAP.

Then we can call the `authorisationCheck("{activity_name or permission}")` in each use-case instead at router or controller. 
As we can call these application layer use-cases from different event subscribers by by-passing controller which is more based on HTTP concerns only.

For more detailed cases where we need information from the specific domain persistence, we can use that part in domain as these are more close to business logic. 
In domain we can save the duplication of code being done in multiple use-cases which have same BL being used.


**Reference Links:**

[Authorisation based on activity rather than roles-permission match:](https://lostechies.com/derickbailey/2011/05/24/dont-do-role-based-authorization-checks-do-activity-based-checks/)

[Access Control in Domain Driven Design: ](https://stackoverflow.com/questions/23464697/access-control-in-domain-driven-design)