2010-09-09 140 views
8

设计一个相当复杂的站点,在单个页面上运行大量的Ajax。我已经达到了某些用户需要获得特定许可来执行某些操作的程度,并且需要停止某些操作。我已经在我的数据库中设置了用户角色,并且所有工作都正常,但是我想知道是否有一种更简单/更安全的方法来存储每个权限。存储用户权限的最佳方式是什么?

当前,当用户登录其特定权限时,将从数据库中抓取并加载到会话数组中。要检查用户是否有权限,我只需检查数组中是否包含权限。这似乎很缓慢,几乎就像我错过了一个更好的解决方案。

此外,会话显然可以由用户编辑...有没有更安全的方法?

我曾想过为每个检查运行查询,但这可能会大大增加简单ajax请求的加载时间。

我愿意接受任何想法。谢谢。

回答

20

首先,用户不能编辑会话变量。唯一保存在用户机器上的是会话ID。该ID随后被服务器用于获取仅存储在服务器上的键/值对。从客户的角度来看,不可能随心所欲地改变价值观。

其次,我不会太担心数据库连接。避免重复自己,但不要太担心第一次连接。

最后,我最喜欢的做法是不使用角色创建多个权限,而是使用二进制数学。有些人喜欢这个,有些人不喜欢,但我觉得它很有用。

要使用此方法,成像,我们定义了以下值:

CAN_EDIT_SOMETHING  = 1  // Powers of 2 
CAN_SEE_SOMETHING_ELSE = 2 
CAN_DO_ADMIN_STUFF  = 4 
...      = 8 

给人以多重权限,使用二进制或

PERMISSIONS = CAN_EDIT_SOMETHING | CAN_DO_ADMIN_STUFF 

为了说明这是如何工作的,大家可以看一下位:

0b0001 
OR 0b0100 
--------- 
    0b0101 

要检查是否有人有权限,请使用二进制AND

if(PERMISSIONS & CAN_EDIT_SOMETHING != 0) { 
} 

要看到这是如何工作的,我们在比特再看看

0b0101 
AND 0b0001 
---------- 
    0b0001 // Not equal to 0. They must have that permission! 

这种方法的最终好处是,它可以让你多个权限结合易成“元权限”

// If both EDIT_SOMETHING and ADMIN_STUFF are tasks that an admin 
// can perform, we can combine them easily 
// 
IS_FULL_ADMIN  = CAN_EDIT_SOMETHING | CAN_DO_ADMIN_STUFF 


// We can then use this value exactly as we do any other permission 
// 
PERMISSIONS  = IS_FULL_ADMIN | CAN_SEE_SOMETHING ELSE 

如果你想使用它,但它是一个很好的技巧,在你的武库。

+0

感谢您解释二进制文件,我想在第一次设计角色时使用类似的东西。我最终使用了2个包含用户角色和indv权限的db表,这对我来说更有意义。 我也可以发誓,我看到有些地方可以拉你的会议数据并编辑它,虽然很困难。也许不会。 – 2010-09-09 05:51:30

+0

@Capt奥蒂斯,就像我说过,它在某些情况下,而不是在其他情况下。你比我更了解你的系统。至于会话,这是它如何在PHP中工作,但你应该检查你正在使用的系统。使用Fiddler或Wireshark来检查流量并查看您的用户实际看到的是什么。如果所有来回传递的都是一个ID(当值更改时不会改变),那么你很好。如果您注意到的值比ID更多,或者如果您注意到会话值更改时会话信息发生变化,那么您遇到了麻烦,并且您最好仔细查看会话:) – riwalk 2010-09-09 17:19:19

1

好像对我好!你可以看一些软件来增强你的会话chache性能。

每次查询数据库并不像听起来那么糟!首先,您可能需要连接到数据库,其次,如果您在登录时查询用户权限,那么有可能所有相关的行都坐在缓冲区中,并且不需要IO,第三,查询单个权限单个用户将比针对用户的所有权限的查询轻得多。

-2

您对模型的解释似乎有点困惑。权限是主题授权和对象授权的结果。您是否真的为主题和客体的每个组合存储这些产品?这是一个非常低效的解决方案,很难管理。

而且,会话显然可以由用户编辑的

WTF ????? !!!!

会话数据只能通过您在代码中定义的方法进行更改 - 如果用户能够以任何他们喜欢的方式修改会话数据的任何部分,那么这是您需要解决的第一个问题 - 直到您但是,除非将认证完全移出应用程序代码的域名(顺便说一句:这不是解决问题的正确方法),否则实际上不可能依赖于认证/授权方法的任何部分。

当然,搜索一个非常大的数组(不确定实际断点 - 但在n = 1000的区域 - 但有很多变量影响这个)可能比从数据库中获取结果慢得多。

如果您不了解您当前的系统是如何工作的,那么您很难说出错。是one of these

+0

2 downvotes and no comment? – symcbean 2016-01-08 09:13:44

相关问题