2009-01-22 148 views
11

我希望有一些可以帮助我一点,我目前正在使用PHP框架开发我的第一个站点,部分站点溢出到成员区域,这是我混乱开始出现的地方,我希望普通会员能够添加新评论并编辑自己的评论,这足够简单,我可以根据存储在会话中的用户名检查海报名称,但我的混淆之处在于区分“常规” '用户和能够删除和修改任何评论等的更高级别用户,他们也应该能够访问该网站的管理部分。Zend Auth和ACL

我的问题是,所有用户都应该通过同一个Zend_Auth控制器登录,还是应该为每种类型的用户使用Zend_Auth单独控制器,还是可以使用Zend_Acl处理所有这些?任何帮助,建议,文章或教程将非常感激。就我个人而言,我认为Zend文档在某些类中有点生涩。

在此先感谢

sico87

回答

6

是,在大多数情况下,所有的认证应该通过同一个控制器。但是,Zend Auth不是控制器类型。 Zend Auth是一种使用数据库或http等通用身份验证方法的API。它的工作实际上仅仅是编写认证代码的繁重工作。

Zend Acl是您正在寻找的区分正常用户和特权用户的区域。在用户验证并登录之后,您只涉及Zend Acl。

您需要的大部分内容都在ZF文档中。在阅读Auth和Acl之前,我几乎阅读了所有的文档,这对我很有意义。尽管ZF的Auth,ACL,Storage_ *和其他类非常密切地结合在一起,但它们都有着非常不同的目的。有一点时间你会看到他们很好地建立在一起。

的几个环节,让您开始:

Pádraic Brady's ZF Tutorial

Zend's DevZone article on ACL and MVC

18

我推荐曼宁出版的书“Zend框架在行动”作为一个伟大的,跟上时代的,介绍这一点。它的问世为PDF格式下载,这样你就可以拥有它现在:)

但是,为了回答这个特定问题:

让我们先来定义两个关键术语开始。 Zend_Auth中的“身份验证”指身份验证,它证明某人是他们所说的人(即登录)。 Zend_Acl中的“A”是指授权,它证明某人有权做他们想做的事(即访问控制)。

假设用户只有一个角色... 将用户的角色存储在Zend_Auth的一部分“身份”中。 在登录:

$auth = Zend_Auth::getInstance(); 
$identity = new stdClass(); 
$identity->user_pk = $user->getPrimaryKey(); 
$identity->user_name = $user->getName(); 
$identity->role = $user->getRole(); // select * from user_role where user_pk=xxx 
$auth->getStorage()->write($identity); 

在控制器:

$acl->add(new Zend_Acl_Resource('news')) 
->allow('defaultRole', 'news'); 

一切都在默认情况下拒绝,所以你并不真的需要指定:

->deny('defaultRole', 'news', 'add'); 

而且在控制器的代码:

$identity = Zend_Auth::getInstance()->getIdentity(); 
if(!$acl->isAllowed($identity->role, 'news', 'add')) 
{ 
    header('Location: http://www.yoursite.com/error/unauthorized'); 
} 

如果用户的身份不被允许执行“news-> add”,它会将它们重定向到未经授权的页面(假设您已经创建了这样一个页面)。

如果用户具有> 1的角色,您将存储角色数组作为他们的身份。 然后你的支票会去是这样的:

$identity = Zend_Auth::getInstance()->getIdentity(); 
$isAllowed = false; 
foreach($identity->role as $role) 
{ 
    if($acl->isAllowed($role, 'news', 'add')) 
    { 
     $isAllowed = true; 
    } 
} 
if(!$isAllowed) 
{ // if NO ROLES have access, redirect to unauthorized page 
    header('Location: http://www.yoursite.com/error/unauthorized'); 
} 

希望有所帮助。

5

我能理解你为什么会感到困惑。我还是有点困惑。所以,不幸的是我无法直接回答你的问题。但是,为了澄清我脑子里所有这些东西,我正在做的一件事就是用'域对象'而不是数据库记录来思考。

我处理这个问题的策略是创建我自己的Auth适配器,它与用户凭证一起传递'User Base Object'。我的'用户基地'有点像用户的存储库。

因此,Zend Auth留给了其他Zend组件的'接口',而我仍然对我的系统有更多的控制权来存储和访问'用户'。 我的User_Base类可能是一个Zend Db tbl的包装,甚至只是有一些硬编码可用于测试。

所以在中普通

好吧,这就是我要做的。

我不会甚至会打扰Zend ACL,直到我有Auth在我的脑海清楚。


我改造遗留网站并将其转换为Zend的MVC

这些都是一些东西(也许非传统),我不得不去与我的“模型”工作交手。:

  • 一个应用程序可以通过多个“用户群”用户使用 - OpenID的,传统的用户表,新的用户表,转瞬即逝的客人,等
  • 客人的身份可能只是一个哈希创建时,第一到达
  • 而传统用户的身份可能由传统用户表中的ID代表
  • 用户和user_accounts是分开的东西。不要试图将它们混合成一个概念,因为它可能变得复杂。
  • 系统中可能有许多不同类型的帐户。即买家账户与卖家账户。读者_帐户与作家_帐户
  • 帐户'拥有'用户 - '主帐户持有人','管理超级用户'等
  • 用户与帐户之间的关系由'account_users'(本地子集所有用户都有用户)
  • 角色arew连接到account_users(该特定帐户的用户)(而不是角色浮动)
  • 不要害怕在服务器上拥有多个Zend应用程序代表一个网站 - 例如管理员应用程序,会员应用程序,前端应用程序。
  • 不要害怕让这些应用程序使用存储在“共享模型”文件夹中的模型对象,其中只有模型代码与位于/ application/models/foomodel文件夹中的单个应用程序直接相关。
  • 每个应用程序可以有自己的定制验证适配器
  • 管理员身份验证适配器可能只允许从“管理员用户表”的用户,而前端应用程序的验证适配器可能可以从来宾用户群验证用户,员工,或成员用户群。
  • 可能是其中前端的应用程序会话被清除,并且在升降由构件会话replced当构件日志中调校妥当情况。
  • 在任何时间(而不是试图引用每人每Web客户端应用程序
  • 一个用户对象与一个来宾用户和一个成员用户 - 这太复杂了) -
  • 每个应用程序每个用户一个会话(命名空间以避免与其他应用程序可能会在该域中登录的冲突) - (与尝试同时引用'使用它的人'与来宾会议和会员会话再次,这太复杂了)

好吧我开始漫步......但你明白了。不要让你看到的Zend_Auth + Zend Db教程摇摆你自己的模型。他们只是简单的例子。

这份厚礼说

0

我对这段代码

$auth = Zend_Auth::getInstance(); 
    $identity = new stdClass(); 
    $identity->user_pk = $user->getPrimaryKey(); 
    $identity->user_name = $user->getName(); 
    $identity->role = $user->getRole(); // select * from user_role where user_pk=xxx 
    $auth->getStorage()->write($identity); 

    $identity = Zend_Auth::getInstance()->getIdentity(); 

正在user_pk,user_name和角色存储的cookie几个问题吗?是否会有人使用角色名称来访问网站的安全部分?密码(使用md5加密)不应该是身份验证的一部分,因此何时可以验证每个请求的用户名和密码?

+0

为什么这个答案实际上是一个问题? – coderama 2013-07-25 08:28:38