我正在为我的项目开发一个访问控制库,我正在寻找最佳解决方案:
我将所有访问列表从数据库获取到数组。结果它看起来像这样:
$array = array(
'*' => array('administrator' => TRUE),
'frontend/*' => array(
'user' => TRUE,
'unregistered' => TRUE
),
'backend/*' => array(
'user' => FALSE,
'unregistered' => FALSE
),
'backend/user/*' => array(
'moderator' => FALSE,
'supermoderator' => TRUE,
),
'backend/article/*' => array(
'supermoderator' => TRUE
),
'backend/article/add/new' => array(
'moderator' => TRUE
)
);
“*”表示此用户可以访问所有相关选项后端/ article / *表示该组可以访问所有文章选项(文章/添加,文章/删除,...)。
如您所见,backend/article/add
中没有超级模拟器的项目,但它具有对所有文章页面的主访问权。
检查这个的最佳方法是什么?我试过array_walk()
,但我想它不会帮助我。
感谢您的建议......
如果你愿意,我可以分享我的整个代码。
*编辑*
我存储错误吗?如果您有更好的解决方案来存储它,我将很高兴听到它。
感谢您提出建议
答案 0 :(得分:0)
无论这是一个复杂的算法,简单的array_walk
都不会。除非有人感到特别慷慨并会为你写一个,我建议你雇用一个程序员。
我存储错误吗?如果您有更好的解决方案来存储它,我将很高兴听到它。
这完全取决于你的算法。您可以编写一个使用当前数据格式的文件。如果更改数据格式,也可以编写更简单的文件。但是,你的数据格式应该是什么样的,那对于程序员来说,这是一项工作。
答案 1 :(得分:0)
我自己找到了答案:
让我们说用户试图访问超级模拟器组中的backend/article/add/new
和此用户。所以我需要寻找backend/*
,backend/article/*
,backend/article/add/*
。 array_slice()
和for()
足以满足此要求:
我顺便使用CodeIgniter。我修改了一点来分隔前端和后端控制器。我没有使用application/controller
目录。我正在为控制器使用application/backend
和application/frontend
目录。
所以uri模式就是这样:http://site.com/[backend]*/[directory]*/class/method
// This is the page that user trying to reach
$requested_page = "backend/article/add/new";
// pharsing...
$x = explode('/', $requested_page);
// this is needed to cut last 3, 2, 1 items of $x
$i = count($x) > 3 ? -4 : -count($x);
for (; $i < 0; $i++) {
$resource = implode('/', array_slice($x, 0, $i)) . '/*';
// echoing for debug
echo $resource;
}
// Outputs:
// backend/*
// backend/article/*
// backend/article/add/*
答案 2 :(得分:0)
function userHasPermissions($permissionsArray, $user, $path) {
// Check exact
if(isset($permissionsArray[$path]) &&
isset($permissionsArray[$path][$user])) {
return $permissionsArray[$path][$user];
}
// Check lower and lower
$partArr = explode('/', $path);
for($i = substr_count($path, '/'); $i >= 0; $i--) {
if($i > 0) {
$choppedPartArr = array_slice($partArr, 0, $i);
$newPath = implode($choppedPartArr, '/') . '/*';
} else {
$newPath = '*';
}
if(isset($permissionsArray[$newPath]) &&
isset($permissionsArray[$newPath][$user])) {
return $permissionsArray[$newPath][$user];
}
}
return false;
}
echo "Result: " . (userHasPermissions($array, 'supermoderator', 'backend/article/add') ? "true" : "false");
请注意,'backend / article'将为'supermoderator'返回false,因为'backend / article / *'与它不匹配。要更改此设置,只需将$i = substr_count($path, '/');
更改为$i = substr_count($path, '/')+1;
。