我想限制我的用户只编辑/删除他们添加的评论。我在youtube上找到了一个名为intergral30的人并按照他的指示操作的例子。现在我的管理员帐户可以编辑/删除所有内容,但我的用户无法访问自己的评论。
这是代码: 资源
class Application_Model_CommentResource implements Zend_Acl_Resource_Interface{
public $ownerId = null;
public $resourceId = 'comment';
public function getResourceId() {
return $this->resourceId;
}
}
作用
class Application_Model_UserRole implements Zend_Acl_Role_Interface{
public $role = 'guest';
public $id = null;
public function __construct(){
$auth = Zend_Auth::getInstance();
$identity = $auth->getStorage()->read();
$this->id = $identity->id;
$this->role = $identity->role;
}
public function getRoleId(){
return $this->role;
}
}
断言
class Application_Model_CommentAssertion implements Zend_Acl_Assert_Interface
{
public function assert(Zend_Acl $acl, Zend_Acl_Role_Interface $user=null,
Zend_Acl_Resource_Interface $comment=null, $privilege=null){
// if role is admin, he can always edit a comment
if ($user->getRoleId() == 'admin') {
return true;
}
if ($user->id != null && $comment->ownerId == $user->id){
return true;
} else {
return false;
}
}
}
在我的ACL中,我有一个名为setDynemicPermissions的函数,它在访问检查插件的preDispatch方法中调用。
public function setDynamicPermissions() {
$this->addResource('comment');
$this->addResource('post');
$this->allow('user', 'comment', 'modify', new Application_Model_CommentAssertion());
$this->allow('admin', 'post', 'modify', new Application_Model_PostAssertion());
}
public function preDispatch(Zend_Controller_Request_Abstract $request)
{
$this->_acl->setDynamicPermissions();
}
我正在从我的评论模型中调用ACL-s isAllowed方法,我返回一个评论对象列表。
public function getComments($id){
//loading comments from the DB
$userRole = new Application_Model_UserRole();
$commentResource = new Application_Model_CommentResource();
$comments = array();
foreach ($res as $comment) {
$commentResource->ownerId = $comment[userId];
$commentObj = new Application_Model_Comment();
$commentObj->setId($comment[id]);
//setting the data
$commentObj->setLink('');
if (Zend_Registry::get('acl')->isAllowed($userRole->getRoleId(), $commentResource->getResourceId(), 'modify')) {
$commentObj->setLink('<a href="editcomment/id/'.$comment[id].'">Edit</a>'.'<a href="deletecomment/id/'.$comment[id].'">Delete</a>');
}
$comments[$comment[id]] = $commentObj;
}
}
谁能告诉我,我做错了什么? 或者如果我想让我的管理员有权发起帖子而其他用户有权评论他们,我该怎么用。每个用户都应该有机会编辑或删除自己的评论,管理员应该拥有所有权利。
答案 0 :(得分:5)
您似乎以错误的方式使用动态断言,因为您仍然将roleId
传递给isAllowed()
。
这些动态断言真正做的是获取一个完整的对象并使用它。 Zend将通过在您的对象上调用getResourceId()
和getRoleId()
来确定必须使用哪条规则。
所以你要做的就是将对象而不是字符串传递给isAllowed()
:
public function getComments($id){
//loading comments from the DB
$userRole = new Application_Model_UserRole();
$commentResource = new Application_Model_CommentResource();
$comments = array();
foreach ($res as $comment) {
$commentResource->ownerId = $comment[userId];
$commentObj = new Application_Model_Comment();
$commentObj->setId($comment[id]);
//setting the data
$commentObj->setLink('');
// This line includes the changes
if (Zend_Registry::get('acl')->isAllowed($userRole, $commentResource, 'modify')) {
$commentObj->setLink('<a href="editcomment/id/'.$comment[id].'">Edit</a>'.'<a href="deletecomment/id/'.$comment[id].'">Delete</a>');
}
$comments[$comment[id]] = $commentObj;
}
}
您不必实施全新Application_Model_CommentResource
,而是可以使用您的实际Application_Model_Comment
:
// we are using your normal Comment class here
class Application_Model_Comment implements Zend_Acl_Resource_Interface {
public $resourceId = 'comment';
public function getResourceId() {
return $this->resourceId;
}
// all other methods you have implemented
// I think there is something like this among them
public function getOwnerId() {
return $this->ownerId;
}
}
Assertion然后将使用此对象并检索所有者以将其与实际登录的人进行比较:
class Application_Model_CommentAssertion implements Zend_Acl_Assert_Interface {
public function assert(Zend_Acl $acl, Zend_Acl_Role_Interface $user=null,
Zend_Acl_Resource_Interface $comment=null, $privilege=null){
// if role is admin, he can always edit a comment
if ($user->getRoleId() == 'admin') {
return true;
}
// using the method now instead of ->ownerId, but this totally depends
// on how one can get the owner in Application_Model_Comment
if ($user->id != null && $comment->getOwnerId() == $user->id){
return true;
} else {
return false;
}
}
用法是这样的:
public function getComments($id) {
//loading comments from the DB
$userRole = new Application_Model_UserRole();
$comments = array();
foreach ($res as $comment) {
$commentObj = new Application_Model_Comment();
$commentObj->setId($comment[id]);
//setting the data
$commentObj->setLink('');
// no $commentResource anymore, just pure $comment
if (Zend_Registry::get('acl')->isAllowed($userRole, $comment, 'modify')) {
$commentObj->setLink('<a href="editcomment/id/'.$comment[id].'">Edit</a>'.'<a href="deletecomment/id/'.$comment[id].'">Delete</a>');
}
$comments[$comment[id]] = $commentObj;
}
}