Эта тема на forum.dklab.ru


Punisher: Проблема с обработкой многомерного массива
Уже несколько дней глухо застопорился на этой проблеме и никак не могу найти проблему. Есть многомерный массив, который представляет собой список прав пользователей для выполнения определённых действий определённых ресурсов системы. Этот массив формируется путем сбора информации о правах из группы, к которой принадлежит пользователь, а также из профайла самого пользователя. В итоге, получается массив, в котором могут находиться одинаковые записи или записи, где ресурс и действие совпадают, а право отличается. В таком случае, необходимо переписать права.

Т.е., к примеру, из группы мы получаем такую запись:

Просмотр директории politics/ru/ модуля news запрещён:


array (
'permission_type' => '0',
'operation' => 'view',
'resource' => 'politics/ru/',
'module' => 'news',
)


А у самого пользователя есть вот такая запись:

Просмотр директории politics/ru/ модуля news разрешён:


array (
'permission_type' => '1',
'operation' => 'view',
'resource' => 'politics/ru/',
'module' => 'news',
)


В итоге, право группы должно быть перекрыто правом пользователя.

Вот, для примера, тестовый массив:


$prefences = array(
0 =>
array (
'permission_type' => '0',
'operation' => 'add',
'resource' => 'contacts',
'module' => 'mail',
),
1 =>
array (
'permission_type' => '1',
'operation' => 'view',
'resource' => '/',
'module' => 'files',
),
2 =>
array (
'permission_type' => '2',
'operation' => 'add',
'resource' => '/',
'module' => 'files',
),
3 =>
array (
'permission_type' => '0',
'operation' => 'view',
'resource' => 'politics/ru/',
'module' => 'news',
),
4 =>
array (
'permission_type' => '0',
'operation' => 'add',
'resource' => 'politics/ru/',
'module' => 'news',
),
5 =>
array (
'permission_type' => '0',
'operation' => 'edit',
'resource' => 'contacts',
'module' => 'mail',
),
6 =>
array (
'permission_type' => '0',
'operation' => 'edit',
'resource' => 'contacts',
'module' => 'mail',
),
7 =>
array (
'permission_type' => '0',
'operation' => 'add',
'resource' => 'politics/ru/',
'module' => 'news',
),
8 =>
array (
'permission_type' => '1',
'operation' => 'edit',
'resource' => 'politics/ru/',
'module' => 'news',
),
9 =>
array (
'permission_type' => '0',
'operation' => 'edit',
'resource' => 'contacts',
'module' => 'mail',
),
10 =>
array (
'permission_type' => '0',
'operation' => 'add',
'resource' => '/',
'module' => 'files',
),
11 =>
array (
'permission_type' => '1',
'operation' => 'edit',
'resource' => 'politics/ru/',
'module' => 'news',
),
12 =>
array (
'permission_type' => '1',
'operation' => 'add',
'resource' => 'politics/ru/',
'module' => 'news',
),
);


Массив устроен так, что сначала в него был записан список прав из группы, а потом добавлен список прав пользователя. Массив я пытался обработать вот такой функцией:


function handle_prefences($prefences)
{
$diff_permission = array();
for ($i = 0; $i < count($prefences); $i++)
{
if (count($diff_permission) == 0)
{
$diff_permission[] = $prefences[$i];
}
else
{
for($j = 0; $j < count($diff_permission); $j++)
{
if ($diff_permission[$j]["module"] == $prefences[$i]["module"] && $diff_permission[$j]["resource"] == $prefences[$i]["resource"] && $diff_permission[$j]["operation"] == $prefences[$i]["operation"])
{
$diff_permission[$j]["permission_type"] = $prefences[$i]["permission_type"];
}
else if (!in_array($prefences[$i], $diff_permission))
{
$diff_permission[] = $prefences[$i];
}
}
}
}
return $diff_permission;
}

Проверка работы и распечатка результатов:


$prefences = handle_prefences($prefences);
for($i = 0; $i < count($prefences); $i++)
{
echo $prefences[$i]["module"]." <font color=#0000FF>||</font> ".$prefences[$i]["resource"]." <font color=#0000FF>||</font> ".$prefences[$i]["operation"].":".$prefences[$i]["permission_type"]."<br>";
}


Не знаю где утечка, но результаты работы неверные – происходит дублирование некоторых записей. Обработка этой функцией выдаёт такой результат:


mail || contacts || add:0
files || / || view:1
files || / || add:0
news || politics/ru/ || view:0
news || politics/ru/ || add:1
mail || contacts || edit:0
news || politics/ru/ || edit:1
files || / || add:0
news || politics/ru/ || add:1


хотя, должен быть такой:


mail || contacts || add:0
files || / || view:1
files || / || add:0
news || politics/ru/ || view:0
news || politics/ru/ || add:1
mail || contacts || edit:0
news || politics/ru/ || edit:1

Дмитрий Котеров:
Слишком сложно - долго вникать. Общий совет - попробуйте поотлаживать код.
http://phpfaq.ru/debug
Punisher:
Дмитрий Котеров
Дело в том, что код я отлаживал. В NuSphere phpED прошёл каждую строчку и проблема в том, что функция in_array() почему-то не находит в массиве уже имеющееся там значение.

Я просто детельно и подробно всё описал, чтобы было проще понять. Если соединить куски РНР-кода: тестовый массив, функцию и её вызов с выводом результатов, то получится вполне рабочий кусок. А вся проблема заключается в условиях функции обработки массива. Но как я только не пробовал, проблема остаётся... Я уже крышей немного двинул на этом куске кода...
Дмитрий Котеров:
функция in_array() почему-то не находит в массиве уже имеющееся там значение.
1. Проверьте совпадение регистра символов.
2. Проверьте пробелы.

Функция должна работать, ищите ошибку в коде.
Punisher:
Дмитрий Котеров
Вот это самое удивительное. Конечно, я не 100% в этом уверен, но подозрение вызывает именно эта функция.

На самом деле, вопрос больше в том, как правильно обработать многомерный массив, в котором нужно переписать значение 'permission_type' у подмассива, если все остальные значения в подмассиве совпадают со значениями предшествующих подмассивов в нём. В первом посте как раз пример есть.
Anonymous:
Вопрос решен, тему можно закрыть.

Эта тема на forum.dklab.ru