Security 授权系统设计问题

Security 授权系统设计问题,security,active-directory,ldap,authorization,Security,Active Directory,Ldap,Authorization,我正试图想出一个很好的方法来进行身份验证和授权。这是我的。欢迎评论,这也是我所希望的 我在mac服务器上安装了php。 我有微软的用户帐户广告 我使用LDAP在用户登录到Intranet时查询广告 我的设计问题涉及如何处理这些广告信息。一位同事建议在广告中使用命名约定,以避免中间数据库。例如,我有一个网页,personals_payroll.php。我获取url,并使用url和广告用户查询集团人事工资单的广告。如果登录用户在该组中,则他们有权查看该页面。我必须为每个页面设置一个组,或者至少为通用

我正试图想出一个很好的方法来进行身份验证和授权。这是我的。欢迎评论,这也是我所希望的

我在mac服务器上安装了php。 我有微软的用户帐户广告

我使用LDAP在用户登录到Intranet时查询广告

我的设计问题涉及如何处理这些广告信息。一位同事建议在广告中使用命名约定,以避免中间数据库。例如,我有一个网页,personals_payroll.php。我获取url,并使用url和广告用户查询集团人事工资单的广告。如果登录用户在该组中,则他们有权查看该页面。我必须为每个页面设置一个组,或者至少为通用身份验证设置一个用户域用户组

使用页面上的控件会变得更加棘手。例如,假设页面或网格上有一个按钮,只有经理才能看到。在我的广告中,我需要将“人员”\u payroll\u myButton作为一个组。如果用户在该组中,他们将获得该按钮。如果一个页面有多个不同级别的授权,我可以有多个组

是的,我的广告是巨大的,但是如果我不这样做,其他的东西就会出现,无论是MySQL(或其他数据库)、文本文件、httpd.conf等等

我将为传递url或控件名以及经过身份验证的用户的各种项目授权一个通用php函数

使用这样的安全命名约定并使用AD作为存储库是否存在固有的问题?我得把它放在某个地方。为什么不是广告

谢谢你的评论

编辑:您认为这个方案会因为LDAP调用而导致页面速度过慢吗

编辑:我不是第一个想到这个的人。如果您对此有任何想法,我们将不胜感激


编辑:谢谢大家。很抱歉,我不能给你更多的回答分数。我不得不选择一个。

这样你的页面速度会非常慢(在我看来,每次用户导航时,你都会重新查询AD LDAP,以确定他能做什么),除非你实现某种缓存,但是你可能会遇到不稳定的权限问题(在你不知道的情况下,撤销/添加了对AD的权限)


我会将权限等分开,不使用AD作为存储库来管理特定于应用程序的授权。相反,请使用一个单独的存储提供商,它将更易于维护和根据需要进行扩展。

除非您的广告无法扩展,否则使用广告获取权限的想法是没有缺陷的。如果使用本地数据库会更快/更可靠/更灵活,那么就使用它

但是,使用命名约定查找正确的安全角色是非常脆弱的。您将不可避免地遇到自然贴图与真实贴图不一致的情况。愚蠢的事情,比如你希望URL是“finbiz”,但它已经作为“business finance”出现在广告中-你是复制组并保持同步,还是在应用程序中重新映射。。。?有时它就像“FinBiz”和“FinBiz”一样简单

在我看来,最好从一开始就避免这类问题,例如,使用组“185”而不是“finbiz”或“business finance”,或其他一些您可以控制的键

无论您如何获得权限,如果最终不得不缓存它,您将不得不处理过时的缓存数据

如果您必须使用ldap,那么创建权限ou(或“schema”的AD等价物)会更有意义,这样您就可以将任意实体映射到这些权限。缓存该数据,您应该可以

编辑:


部分问题似乎是为了避免中间数据库——为什么不让中间数据库成为主要数据库?定期(通过钩子或轮询)将本地权限数据库同步到AD,您可以避免两个重要问题:1)脆弱的命名约定,2)外部数据源崩溃。

我想知道是否有其他方式来表达和存储权限,从而更干净、更高效地工作

大多数应用程序被划分为功能区域或角色,权限是根据这些[广泛]区域分配的,而不是每页权限。例如,您可能拥有以下权限:

  • 使用应用程序
  • CreateUser
  • 重置其他用户密码
  • ViewPayrollData
  • 修改工资数据
或者,对于角色,您可以有:

  • 应用程序用户
  • 应用管理员
  • 工资管理
角色(可能还有每个功能权限)可能已经映射到存储在Active Directory中的数据,例如现有的广告组/角色。如果没有,它仍然比每页权限更容易维护。权限可以作为用户组(用户在组中,因此有权限或没有权限)进行维护,也可以作为自定义属性进行维护:

dn: cn=John Doe,dc=example,dc=com
objectClass: top
objectClass: person
objectClass: webAppUser
cn: John Doe
givenName: John
...
myApplicationPermission: UseApplication
myApplicationPermission: ViewPayrollData
这有一个优点,即模式更改很少。如果您使用组,AD(以及地球上的所有其他LDAP服务器)已经具有该功能,并且如果您使用这样的自定义属性,则只需要添加一个属性(在上面的示例中可能是
objectClass
webAppUser

接下来,您需要决定如何使用数据。一种可能是在用户登录并将其存储在会话的Web服务器端时,检查用户的权限(找出他们所在的组或授予他们的权限)。这有一个问题,权限更改仅在用户登录时生效,而不是立即生效。如果您不希望权限经常更改(或者当用户同时使用系统时),这可能是一种合理的方法。这有一些变化,例如重新加载用户的许可证
$permMap = array(
    "personnel_payroll" => "ViewPayroll",
    "personnel_payroll_myButton" => "EditPayroll",
    ...
);

function check_permission($elementName) {
    $permissionName = $permMap[$elementName];
    return isUserInLdapGroup($user,$permissionName);
}
<?php
$acl = new Zend_Acl();
$acl->addRole(new Zend_Acl_Role('public'));
$acl->addRole(new Zend_Acl_Role('users'));
$acl->addRole(new Zend_Acl_Role('manager'), 'users');

$acl->add(new Zend_Acl_Resource('about')); // Public 'about us' page
$acl->add(new Zend_Acl_Resource('personnel_payroll')); // Payroll page from original post

$acl->allow('users', null, 'view'); // 'users' can view all pages
$acl->allow('public', 'about', 'view'); // 'public' can only view about page
$acl->allow('managers', 'personnel_payroll', 'edit'); // 'managers' can edit the personnel_payroll page, and can view it since they inherit permissions of the 'users' group

// Query the ACL:
echo $acl->isAllowed('public', 'personnel_payroll', 'view') ? "allowed" : "denied"; // denied
echo $acl->isAllowed('users', 'personnel_payroll', 'view') ? "allowed" : "denied"; // allowed
echo $acl->isAllowed('users', 'personnel_payroll', 'edit') ? "allowed" : "denied"; // denied
echo $acl->isAllowed('managers', 'personnel_payroll', 'edit') ? "allowed" : "denied"; // allowed
?>