What is the best way to handle multiple permission types?
I agree with John Downey.
Personally, I sometimes use a flagged enumeration of permissions. This way you can use AND, OR, NOT and XOR bitwise operations on the enumeration's items.
"[Flags]
public enum Permission
{
VIEWUSERS = 1, // 2^0 // 0000 0001
EDITUSERS = 2, // 2^1 // 0000 0010
VIEWPRODUCTS = 4, // 2^2 // 0000 0100
EDITPRODUCTS = 8, // 2^3 // 0000 1000
VIEWCLIENTS = 16, // 2^4 // 0001 0000
EDITCLIENTS = 32, // 2^5 // 0010 0000
DELETECLIENTS = 64, // 2^6 // 0100 0000
}"
Then, you can combine several permissions using the AND bitwise operator.
For example, if a user can view & edit users, the binary result of the operation is 0000 0011 which converted to decimal is 3.
You can then store the permission of one user into a single column of your Database (in our case it would be 3).
Inside your application, you just need another bitwise operation (OR) to verify if a user has a particular permission or not.
The way I typically go about coding permission systems is having 6 tables.
- Users - this is pretty straight forward it is your typical users table
- Groups - this would be synonymous to your departments
- Roles - this is a table with all permissions generally also including a human readable name and a description
- Users_have_Groups - this is a many-to-many table of what groups a user belongs to
- Users_have_Roles - another many-to-many table of what roles are assigned to an individual user
- Groups_have_Roles - the final many-to-many table of what roles each group has
At the beginning of a users session you would run some logic that pulls out every role they have assigned, either directory or through a group. Then you code against those roles as your security permissions.
Like I said this is what I typically do but your millage may vary.