开发者

How to represent user rights in a elegant way?

Here is the table of user rights

Post
        Guest User                      Admin 
Create    N     Y                         Y
Read      Y     Y                         Y
Update    N   Their own post ONLY        All
Delete    N     N (yes, user can't del)   Y

And here is the situation. I am thinking putting all the validating user rights in one single class to handle开发者_JAVA技巧. And all the action have a defined name, for example: create_post, read_post. Also, have a user_role to pass in, let say: role_guest, role_user. And the validation class do all the magic. What do you think of this design? Thank you.


You could use a bitmask.

If all your permissions are (or can be generalised to) a set of yes/no conditions, it's quite easy.

In your example, you have Create, Read, Update and Delete. That's 4 bits, so you need a 4-bit number to store permissions. (0000 to 1111 in binary = 0 to 15 in decimal)

Someone who can only read would have permissions 0100 (4 in decimal), and someone who can create/read/update would have persmissions 1110 (14 in decimal). Administrators who have full access would have persmissions 1111 (15 in decimal).

The way you would check these in PHP would be with the bitwise OR operator |.

For example

// you could write a function getUserPermission($strUsername)
// which returns a permission number, say 10 (1010 in binary)
// which means he/she can create/update but not read/delete
$userPermissions = getUserPermission("TedWong");

$permissionCreate = 8; // 1000;
$permissionRead   = 4; // 0100;
$permissionUpdate = 2; // 0010;
$permissionDelete = 1; // 0001;

if ($userPermissions | $permissionCreate)
{
  //user has permission to create
}

if ($userPermissions | $permissionRead)
{
  //User has permission to read
}

if (!($userPermissions | $permissionDelete))
{
  //User doesn't have permission to delete
}

if ($userPermissions | $permissionUpdate &&
    $userPermissions | $permissionCreate)
{
  //User has permission to create and update.
}

If you want more permissions, you just need to introduce more bits.

As for your update all posts/delete own posts in your example, I would have a 5-bit permission structure: Create, Read, Delete, UpdateOwn, UpdateAll.

You can have many permissions, but would be limited by the data structure storing them. For example, if you are storing the permission mask in a 32-bit integer, then you can only have up to 32 permissions.

here is a full list of 4-bit permissions for your example:

0000 //  0: No Permissions
0001 //  1: Delete
0010 //  2: Update
0011 //  3: Delete + Update
0100 //  4: Read
0101 //  5: Read + Delete
0110 //  6: Read + Update
0111 //  7: Read + Delete + Update
1000 //  8: Create
1001 //  9: Create + Delete
1010 // 10: Create + Update
1011 // 11: Create + Delete + Update
1100 // 12: Create + Read
1101 // 13: Create + Read + Delete
1110 // 14: Create + Read + Update
1111 // 15: Create + Read + Delete + Update

So that means the INTEGER 6 (which in BINARY is equal to 0110) gives permissions Read/Update but not Create/Delete. In the same way each integer has a set of permissions associated with it. You can store up to as many permissions in the integer as many bits there are that represent that integer (usually 32).

So you can see that with a 4-bit integer (decimal numbers 0 to 15) can give you 4 yes/no permissions. If you use a 32-but integer then you can have up to 32 yes/no permissions.

Check the PHP documentation on how to determine the maximum size of your integers. (It depends on the platform you're running your PHP parser on). I think generally speaking a 32-bit system/OS will allow for 32-bit integers, and 64-bit system/OS will allow for 64-bit integers.

Check these other threads on SO for discussions on pros/cons of using bitmasks vs other methods.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜