Security is Layered
The truth of the mater is that Bad People™ will try and by pass your security.
By adding security you want to make it as genuinely difficult as possible for someone who is not there legitimately to do anything, while also reducing the amount of being in the way experienced by people who legitimately use the system everyday.
Boundaries
Your picture isn't entirely accurate, it looks more like:
DB -> Repository -> Controller -> User
The ->
are the boundaries. Even though that is still a simplification, we could through networks and other issues in.
The point is that each boundary needs to allow the good stuff through, while making the bad stuff difficult/impossible to do.
You could place all of your security between the user
and the controller
, but if someone bypassed that, then they would have a field day.
Similarly you can't just place all of the security between the Database
and Repository
. It's already to late as the service itself is exposed, and any data being passed to it, must presumably be available to anyone using it. Which probably isn't reasonable to expect.
DB -> Repository
The actual Database Engine needs to enforce permissions, to the Repository
. Obviously the Repository
can't just do anything:
- creating/dropping tables,
- adding indices,
- updating rows in these tables,
- inserting rows to these other tables,
- etc...
The Engine should give exactly the rights needed for that repository, and no more.
Repository -> Controller
The Repository similarly needs to ensure that a controller can't just do anything with it:
- Delete a customer record, especially if it is linked to other records
- Insert Multiple Payments against an already paid order
- Permit the viewOrder controller to insert User Records.
This is partly done by implementing business sanity checks, and partly done by checking to see if the Controller has the right to do so. This is usually implemented by some form of whitelist checking that the caller is on the list, and has the required rights, or by some permissions object that can itself be verified.
Controller -> User
The Controller itself has to establish that the user has the required permissions. Usually done by some login method, or certificate. If the login/certificate passes muster, the users permissions are checked to see if they can access the controller.
This provides layers of security.
If for example an admin account got breached, and the used the OrderViewController
with some sort of exploit, then the repository will reject odd requests, as the controller only has privilege X, Y, Z.
If they bypassed the controller and somehow got to within the repository, then they can't just drop all the data, or use it for storing their own in an easy way.