My site is giving me the exception “Policy for CakeDC\Users\Model\Table\UsersTable
has not been defined.”. How do I have to define the second parameter in the policy so that it receives the table of the SimpleCrudTrait?
This is the code for index action in SimpleCrudTrait:
public function index()
{
$table = $this->loadModel();
$tableAlias = $table->getAlias();
$this->paginate = [
'contain' => ['Enterprises'],
];
$this->set($tableAlias, $this->paginate($table));
$this->set('tableAlias', $tableAlias);
$this->set('_serialize', [$tableAlias, 'tableAlias']);
$user = $this->request->getAttribute('identity');
$canDelete = $user->can('delete', $table);
$this->set('canDelete', $canDelete);
}
And this is the code of UsersTablePolicy:
<?php
declare(strict_types=1);
namespace App\Policy;
use CakeDC\Users\Model\Table\UsersTable;
use Authorization\IdentityInterface;
/**
* Users policy
*/
class UsersTablePolicy
{
/**
* Check if $user can delete Users
*
* @param \Authorization\IdentityInterface $user The user.
* @param \App\Model\Entity\Users $users
* @return bool
*/
public function canDelete(IdentityInterface $user, UsersTable $users)
{
return $user->role == "superuser";
}
}
You basic setup looks ok. The problem probably comes from the fact that your table belongs to a plugin.
Are their any details in the docs that discuss integrating with plugins?
The OrmResolver class (part of the Authorization plugin) chooses the policy class to run based on the fully qualified class name of the object it receives (the second argument, $table in your case).
It does a string manipulation of this name and calculates the name of the policy class to run. This is the Authorization\Policy\OrmResolver
code that does that work:
Your plugin table is not in the same namespace as other tables, so it may be calculating this wrong. If so, you may need to change the name of your policy so it matches or there may be some other plugin-specific instructions in the documentation.
As a guess maybe UsersUsersTablePolicy
?
Looking at this documentation… it’s a little confusing to me but I think the second rule:
Plugin resources will first check for an application policy
e.g App\Policy\Bookmarks\BookmarkPolicy
for Bookmarks\Model\Entity\Bookmark.
would apply in your case.
So your policy class would be UsersTablePolicy
and the namespace would be \App\Policy\Users\UsersTablePolicy
?
No, the namespace is App\Policy\UsersTablePolicy, how and in what directory I have to create the policy for cakedc users?
I understand App\Policy\UsersTablePolicy
is where you have created your class. But you also say you are getting an error.
Did you try moving it to the namespace I suggest (based on my reading of those naming rules in the documentation)?
[Edit/Addition]
Running the fully qualified class name of your table through the OrmResolver code, it actually looks like your policy should be at
App\Policy\CakeDC\Users
and be named
UsersTablePolicy
and of course this means you should store the policy class at
src/Policy/CakeDC/Users/UsersTablePolicy.php
I created the Policy directory in root/vendor/cakedc/users/src/Policy/ but it still gives me the exception, in what directory I have to create the policy so that it works?
I would recommend NOT creating it directly in the plugin code-base because you will loose the new files if you ever update the plugin.
I suggest trying this:
This is local to your application and will not get wiped out if you update the plugin
Thank you very much, now is working fine.