1

我是 cakephp 的新手,我正在尝试从头开始构建一个应用程序。我正在阅读手册,也做了教程。

现在我面临一个关于授权的问题:如何允许用户执行操作(编辑、删除、...),但前提是这是他们自己的事情(发布、事件、...),使用 ActionsAuthorize 和 ControllersAuthorize同时。也许这是一个愚蠢的问题,但作为一个新手,我觉得我错过了一些东西。

如果应用程序更简单,只使用 ControllersAuthorize (isAuthorized()) 就足够了,但我发现 ActionsAuthorize 非常有用。

按照教程(博客)中的示例,每个帖子都有一个作者(用户)并属于一个个人资料(作者,管理员,编辑器,...),一般用户可以编辑帖子($this->Acl->allow ('author','controllers/Posts/edit')) 但只有他们自己的帖子。

到目前为止,我有以下代码:

//User Model
public $actsAs = array('Acl' => array('type' => 'both'));
public $belongsTo = array(
    'Profile' => array(
        'className' => 'Profile',
        'foreignKey' => 'profile_id'
    )
);
//saving the aro alias => username   
public function aftersave($created) {
    if($created) {
        $this->Aro->save(array('alias'=>$this->data[$this->alias]['username']));
    }
}

public function parentNode() {
    if (!$this->id && empty($this->data)) {
        return null;
    }
    if (isset($this->data['User']['profile_id'])) {
        $profileId = $this->data['User']['profile_id'];
    } else {
        $profileId = $this->field('profile_id');
    }
    if (!$profileId) {
        return null;
    } else {
        return array('Profile' => array('id' => $profileId));
    }
}

//Profile Model
public $actsAs = array('Acl' => array('type' => 'both'));
public function parentNode() {
    return null;
}
//savin the aco alias => name
public function aftersave($created) {
    if($created) {
        $this->Aro->save(array('alias'=>$this->data[$this->alias]['name']));
    }
}

//Post Model
public function isOwnedBy($post, $user) {
    return $this->field('id', array('id' => $post, 'user_id' => $user)) === $post;
}

//Post Controller
public function beforeFilter() {
    parent::beforeFilter();
    $this->Auth->allow('index');
}       
public function isAuthorized($user) {
    // All registered users can add posts
    if ($this->action === 'add' && isset($user)) {
        return true;
    }
    // The owner of a post can edit and delete it
    if (in_array($this->action, array('edit', 'delete'))) {
        $postId = $this->request->params['pass'][0];
        if ($this->Post->isOwnedBy($postId, $user['id'])) {
            //after knowing if the post is owned by the user check ACL
            return $this->Acl->check($user['profile_id'],$this->Acl->aco,$this->action);
        }
    }
    return parent::isAuthorized($user);
}

//AppController
public $components = array(
    'Acl',
    'Session',
    'Auth' => array(
        'authenticate' => array('Blowfish'),
        'authError' => 'You are not allow to perform this action, please login',
        'loginRedirect' => array('controller' => 'users', 'action' => 'login'),
        'logoutRedirect' => array('controller' => 'posts', 'action' => 'index')
    )
);
public function isAuthorized($user) {
    // Only admins can access admin functions
    if (isset($user['profile_id']) && isset($this->request->params['admin'])) {
        return (bool)($user['profile_id'] === '1');
    }
    // Admin can access every action
    if (isset($user['profile_id']) && $user['profile_id'] === '1') {
        return true;
    }       
    return false;
}       
public function beforeFilter() {
    $this->Auth->authorize = array('Controller');
    $this->Auth->allow('display');
}  
        // The owner of a post can edit and delete it
        if (in_array($this->action, array('edit', 'delete','view'))) {
            $postId = $this->request->params['pass'][0];
            if ($this->Post->isOwnedBy($postId, $user['id'])) {
                return $this->Acl->check($user['profile_id'],$this->Acl->aco,$this->action);
            }
        }
        return parent::isAuthorized($user);
    }

所以我的问题是我是否以我在 PostController:isAutorized() 中使用它的方式正确使用了授权:首先检查用户是否拥有该帖子,然后检查用户是否允许该操作。是另一种方式吗?这种方式好不好?有更好的方法吗?我错过了什么吗?

非常感谢你!

4

1 回答 1

0

Here's one way to get it done. Edit: Realized you are doing ACL app. This is the answer if you're not. Figured it still might be useful since no else has responded.

public function doStuff(){
      if(AuthComponent::user('role') == 'admin'){
      //do stuff 
      }elseif(AuthComponent::user('id') == $blogpost['Blog']['owner']){ 
      // do stuff 
      }else{ 
      $this->Html->redirect(array('action' => 'elsewhere'));
      }


 }
于 2013-09-11T14:44:31.173 回答