Napisałem klasę autoryzacji użytkownikó. Reguła jest taka że powinna ona pozwalać na:
--- dodawanie ról
--- dodawanie zasobów
--- dzielenie zasobów na akcje
--- zasoby mogą być dziedziczone w linii prostej
--- role mogą dziedziczyć po sobie również w linii prostej
Narobiłem się przy tym jak wół dlatego bardzo proszę o pomoc w testowaniu. Klasa zawiera funkcję drop() która wyświetla całą tabelę. Powinno pomóc. Dla wytrwałych proponuję w zamian działającą klasę. Na pewno się przyda jeśli nie teraz to może w przyszłości (IMG:
style_emoticons/default/smile.gif)
//authorization
$auth->addRole('guest');
$auth->addRole('user', 'guest'); // user dziedziczy po guest
$auth->addRole('moderator', 'user'); // moderator dziedziczy po user
$auth->addRole('moderator2', 'user');
$auth->addRole('administrator', 'moderator');
//-----------------
$auth->addResource('article', array('view', 'edit', 'delete')); //nowy zasób artykuł z 3 akcjami view edit i delete $auth->addResource('backend', array('view', 'edit', 'delete')); $auth->addResource('structure#1', array('view', 'edit', 'delete'), 'backend'); $auth->addResource('structure#2', array('view', 'edit', 'delete'), 'structure#1'); // struktura#2 dziedziczy po strukturze#1 $auth->addResource('structure#3', array('view', 'edit', 'delete'), 'structure#1'); $auth->addResource('structure#4', array('view', 'edit', 'delete'), 'structure#2'); $auth->addResource('structure#5', array('view', 'edit', 'delete'), 'structure#2'); //-----------------
$auth->allow('administrator'); // ten zapis oznacza ze admin ma prawa do wszstkiego
$auth->allow('moderator', 'backend'); // moderator ma prawo do wszystkiego w backend
$auth->allow('moderator', 'structure#5', array('edit', 'view')); // moderator ma prawo edytowac i edytowac strukture#5 $auth->deny('moderator', 'structure#5', 'edit');
$auth->allow('moderator2', 'structure#2', 'delete');
$auth->deny('moderator', 'backend');
$auth->deny('administrator', 'structure#2', 'delete');
<?php
class User_Authorization
{
private $roles = array(); private $resources = array();
public function addRole($name, $parent = null)
{
$this->roles[$name] = array('name' => $name, 'parent' => $parent); }
public function addResource
($name, $actions = array(), $parent = null) {
$this->resources[$name] = array('name' => $name, 'actions' => $actions, 'parent' => $parent); }
public function allow($role, $resource = null, $actions = null)
{
$this->acl[] = array('access' => true, 'role' => $role, 'resource' => $resource, 'actions' => $actions); }
public function deny($role, $resource = null, $actions = null)
{
$this->acl[] = array('access' => false, 'role' => $role, 'resource' => $resource, 'actions' => $actions); }
private function _getRoleBloodline($role)
{
$i = 0;
$bloodline = array($this->roles[$role]['name']=>array
('name' => $this->roles[$role]['name'], 'level' => $i++)); while ($parent = $this->roles[$role]['parent']) {
foreach ($this->roles as $r) {
if ($r['name'] == $parent) {
$bloodline[$r['name']] = array('name'=>$r['name'], 'level'=>$i++); $role = $r['name'];
}
}
if (in_array($this->roles[$role]['parent'], $bloodline) || !$this->roles[$parent]) { break;
}
}
return $bloodline;
}
private function _getResourceBloodline($resource)
{
$i = 0;
$bloodline = array($this->resources[$resource]['name'] => array('name' => $this->resources[$resource]['name'], 'level' => $i++)); while ($parent = $this->resources[$resource]['parent']) {
foreach ($this->resources as $r) {
if ($r['name'] == $parent) {
$bloodline[$r['name']] = array('name'=>$r['name'], 'level'=>$i++); $resource = $r['name'];
}
}
if (in_array($this->resources[$resource]['parent'], $bloodline) || !$this->resources[$parent]) { break;
}
}
return $bloodline;
}
public function isAllowed($role, $resource, $action = null)
{
$roleBloodline = $this->_getRoleBloodline($role);
$resourceBloodline = $this->_getResourceBloodline($resource);
$isAllowed = false;
$isAllowedPoints = 100;
if ($action === null) {
$isAllowed = false;
foreach ($this->resources[$resource]['actions'] as $a) {
if (!$isAllowed = $this->isAllowed($role, $resource, $a)) {
break;
}
}
} else {
foreach ($this->acl as $ac) {
if ($roleBloodline[$ac['role']] && $resourceBloodline[$ac['resource']]) {
if ($isAllowedPoints >= $roleBloodline[$ac['role']]['level'] + $resourceBloodline[$ac['resource']]['level'] / 100) {
if ($ac['access']) {
if (is_array($ac['actions']) && in_array($action, $ac['actions']) || $action == $ac['actions'] || !$ac['actions']) { $isAllowed = true;
}
} else {
if (is_array($ac['actions']) && in_array($action, $ac['actions']) || $action == $ac['actions'] || !$ac['actions']) { $isAllowed = false;
}
}
$isAllowedPoints = $roleBloodline[$ac['role']]['level'] + $resourceBloodline[$ac['resource']]['level'] / 100;
}
} else if ($roleBloodline[$ac['role']] && !$ac['resource']) {
if ($ac['access']) {
$isAllowed = true;
} else {
$isAllowed = false;
}
}
}
}
return $isAllowed;
}
}
?>
to się nie zmieściło do posta....
public function drop()
{
echo "<style type=\"text/css\">\n"; echo "\t#userAuthorizationTableTitle {float:left; color:#516c7d; border:0px dashed #666; font-size:12px; font-family:tahoma; padding:0px 10px 0px 10px; background-color:#fcc; margin:0px; border:1px dashed #666; border-bottom:0px; margin-top:10px;}\n"; echo "\t#userAuthorizationTable {border-collapse:collapse; clear:both; border-top:1px dashed #666; border-left:1px dashed #666; font-size:12px; background-color:#fcc; font-family:tahoma; color:#666; width:100%; margin-bottom:0px;}\n"; echo "\t#userAuthorizationTable tr{border-collapse:collapse; border:0px dashed #666; font-size:12px; font-family:tahoma; color:#666;}\n"; echo "\t#userAuthorizationTable tr th{padding:0px; border-collapse:collapse; vertical-align:top; background-repeat:no-repeat; padding-left:20px; border-right:1px dashed #666; border-bottom:1px dashed #666; text-align:left; color:#516c7d; background-color:#fbbbbb}\n"; echo "\t#userAuthorizationTable tr td{border-collapse:collapse; border-right:1px dashed #666; border-bottom:1px dashed #666; color:#666; padding-left:5px;}\n"; echo '<h1 id="userAuthorizationTableTitle">User authorization table </h1>'; echo '<table id="userAuthorizationTable" cellspacing="0" cellpadding="0">'; $width = 100
/ (count($this->roles) + 1
); echo '<td width="'.$width.'%"></td>'; foreach ($this->roles as $role) {
echo '<th style="background-image:url(\'edc_application/System/Images/UserIcon.gif\'); padding-left:15px;" width="'.$width.'%">'; if ($role['parent']) echo ' (' . $role['parent'] . ')'; }
foreach ($this->resources as $resource) {
echo '<th style="background-image:url(\'edc_application/System/Images/ResourceIcon.gif\')">'; if ($resource['parent']) echo ' (' . $resource['parent'] . ')'; foreach ($this->roles as $role) {
$c = 0;
foreach ($resource['actions'] as $action) {
if ($this->isAllowed($role['name'], $resource['name'], $action)) {
}
}
if ($this->isAllowed($role['name'], $resource['name'])) {
}
}
}
}