|
 1.1 Кб |
|
| В базе - четыре таблицы - модули, разрешения, группы пользователей и операции, которые следует реализовать над модулями. Все операции одинаковые. Структуру таблиц прикрепила.
На странице все это будет выглядеть вот так:
_________________________________________
Модуль1 |public | auth | admin
view | | |
edit | V
delete |
_________________________________________
Модуль2 | | |
view |
edit |
delete |
_________________________________________
Например, модуль1 можно редактировать только админу(я поставила там галочку - на самом деле там будет чекбокс).
Вопрос 1. В таблице permission какой лучше ключ сделать? в смысле, какое поле?
Вопрос 2. Что передавать в value чекбокса ,чтобы узнать, что чекбокс отмечен? | |
|
|
|
|
|
|
|
для: Лена
(23.09.2009 в 22:12)
| |
CREATE TABLE `groups` (
`id_group` int(11) NOT NULL auto_increment,
`type_group` tinytext NOT NULL,
`descr` text,
PRIMARY KEY (`id_group`)
) ENGINE=MyISAM AUTO_INCREMENT=25 DEFAULT CHARSET=utf8
PACK_KEYS=0
COMMENT='таблица определяет группы польз?'
AUTO_INCREMENT=25 ;
CREATE TABLE `modules` (
`mod_id` int(32) NOT NULL auto_increment,
`mod_pid` tinyint(4) default '0',
`block_id` int(11) default '0',
`mod_name` mediumtext,
`mod_path` varchar(255) default NULL,
`descr` mediumtext,
`visib` tinyint(5) NOT NULL default '0',
`show_sitemap` enum('yes','no') NOT NULL default 'yes',
PRIMARY KEY (`mod_id`),
FULLTEXT KEY `mod_name` (`mod_name`)
) ENGINE=MyISAM AUTO_INCREMENT=4 DEFAULT CHARSET=utf8 PACK_KEYS=0 AUTO_INCREMENT=4 ;
CREATE TABLE `operations` (
`op_id` int(11) NOT NULL,
`op_name` text NOT NULL,
PRIMARY KEY (`op_id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
CREATE TABLE `permission` (
`id_group` int(11) default NULL,
`mod_id` int(11) default NULL,
`op_id` int(11) NOT NULL
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
|
| |
|
|
|
|
|
|
|
для: Trianon
(23.09.2009 в 22:14)
| | 1. Составной. Возможно, не один.
2. Важнее, какое name. Тоже составное. К примеру, name="act[$mod-$grp-$op]"
А можно name="act[$mod-$grp][]" value=$op попробовать. Хотя не уверен, что с ним будет проще. | |
|
|
|
|
|
|
|
для: Trianon
(23.09.2009 в 22:19)
| | Ключ сделала таким - PRIMARY KEY (`id_group`,`mod_id`,`op_id`)
Сейчас не получается обозначить отмеченный чекбокс. То, что пока не нужно, выбросила:
permission.php - обработчик формы
<?php
if(isset($_POST['Perm'])){
print '<pre>';
print_r($_POST['act']);
print '</pre>';
}
if(!isset($_POST['Perm'])){
include("permission_form.php");
}
?>
|
permission_form.php
<?php
//готовим переменные для шаблона $groups,$mod,$op(это выбросила)
$q = "SELECT * FROM permission";
$result = mysql_query($q);
if(!$result) exit("Error in $q: ". mysql_error());
while($row = mysql_fetch_assoc($result)){
$all = $row['id_group'] . "-" . $row['mod_id'] . "-" . $row['op_id'];
foreach($_POST['act'] as $key=>$value){
if($key == $all){
$check = 'checked';
}else{
$check = ''; }
}
}
//отправляем переменные в шаблон
$smarty->assign('checked',$check);
$nbsp = str_repeat(" ", 20);
$smarty->assign('nbsp',$nbsp);
$smarty->assign('groups',$groups);
$smarty->assign('mod',$mod);
$smarty->assign('op',$op);
$smarty->display('permission.tpl');
?>
|
шаблон - 'permission.tpl'
<table width=100% border='1px'>
<tr>
<td>№</td>
<td>Название модуля</td>
{* названия групп пользователей *}
{foreach from = $groups item = gr}
<td>{$gr.type_group}</td>
{/foreach}
</tr>
<form action='permission.php' method='post'>
{* названия модулей *}
{foreach from=$mod item=one key=keys}
<tr>
<td>{$keys}</td>
<td colspan = 4>{$one.mod_name}</td>
</tr>
{* название операций *}
{foreach from=$op item=p}
<tr>
<td></td>
<td>{$nbsp}{$p.op_name}</td>
{* группы *}
{foreach from = $groups item = gr}
{*название чекбокса - группа+модуль+операция *}
<td><input type="checkbox" name="act[{$gr.id_group}-{$one.mod_id}-{$p.op_id}]"
value="1" {$checked}></td>
{/foreach}
</tr>
{/foreach}
{/foreach}
<tr>
<td colspan=5><input type='submit' value='Установить разрешения' name = 'Perm'></td>
</tr>
</form>
</table>
|
Не пойму, почему отмеченные чекбоксы после нажатия кнопки становятся неотмеченными. | |
|
|
|
|
|
|
|
для: Лена
(24.09.2009 в 22:19)
| | //отправляем переменные в шаблон
Вот на этом месте можно сделать var_dump($check); и всё станет ясно. | |
|
|
|
|
|
|
|
для: Trianon
(24.09.2009 в 22:24)
| | Не выходит.
обработчик(кусок, что поменяла):
<?php
$sql = "SELECT g.type_group gt, g.id_group gi, m.mod_name mn, m.mod_id mi, o.op_name opn, o.op_id oi, (l.op_id IS
NOT NULL) chk
FROM (
modules m
JOIN groups g
JOIN operations o)
LEFT JOIN permission l ON l.mod_id = m.mod_id
AND l.id_group = g.id_group
AND l.op_id = o.op_id
LIMIT 0 , 30";
$result = mysql_query($sql);
if(!$result) exit("Error in $sql: ". mysql_error());
for($i=0;$row = mysql_fetch_assoc($result);$i++){
if($i!=$row['mi']){
$i =$row['mi'];
$mod[$i] = $row['mn'];
}
if($i!=$row['gi']){
$i =$row['gi'];
$groups[$i] = $row['gt'];
}
if($i!=$row['oi']){
$i =$row['oi'];
$op[$i] = $row['opn'];
}
foreach($_POST['cat'] as $cat){
if($cat == 1 && $cat == $row['chk'][$i]) $checked = 'cheked';
else $checked = '';
}
}
?>
|
Шаблон:
<table width=100% border='1px'>
<tr>
<td>№</td>
<td>Название модуля</td>
{* названия групп пользователей *}
{foreach from = $groups item = gr}
<td>{$gr}</td>
{/foreach}
</tr>
<form action='permission.php' method='post'>
{* названия модулей *}
{foreach from=$mod item=one key=keys}
<tr>
<td>{$keys}</td>
<td colspan = 4>{$one}</td>
</tr>
{* название операций *}
{foreach from=$op item=p key = opk}
<tr>
<td></td>
<td>{$nbsp}{$p}</td>
{* группы *}
{foreach from = $groups item = gr key = grkey}
{*название чекбокса - группа+модуль+операция *}
<td><input type="checkbox" name="act[{$grkey}-{$keys}-{$opk}]" value="1" {$checked}></td>
{/foreach}
</tr>
{/foreach}
{/foreach}
<tr>
<td colspan=5><input type='submit' value='Установить разрешения' name = 'Perm'></td>
</tr>
</form>
</table>
|
var_dump($checked); дает NULL | |
|
|
|
|
|
|
|
для: Лена
(25.09.2009 в 13:29)
| | если Вы хотите структурировать элементы в порядок
модули(операции(группы(элементы)))
то нужно соответствующим образом
а) задать сортировку в запросе, которая бы сгруппировала (не в смысле gropup by , а в смысле - разместила бы рядом) строки согласно структуре.
б) определить php-код, который результат этого запрос расхлебает.
Первый, очевидно, будет ORDER BY модуль, группа, операция
Что до второго, то тут надо определиться, в массиве какого вида смарти ожидает данные. | |
|
|
|
|
|
|
|
для: Trianon
(25.09.2009 в 16:36)
| | Сделала, ошибки поняла, осталось обработчик формы сделать.
Я так понимаю, если чекбокс отмечен - в таблицу связки permission вставляем строку, если убрали чекбокс - удалили строку.
Вот что получилось:
<?php
//запрос к базе уже был выше
//вывод результата запроса
while($row = mysql_fetch_assoc($result)){
$mod = $row['mn'];
$gt = $row['gt'];
$opn = $row['opn'];
$arr[$mod][$gt][$opn] = $row['chk'];
}
$nbsp = str_repeat(" ", 20);
$smarty->assign('nbsp',$nbsp);
$smarty->assign('arr',$arr);
$smarty->display('permission.tpl');
?>
|
шаблон:
<table width=100% border='1px'>
{foreach from = $arr item = ar key = keys first = true name = mod}
{* шапка таблицы - только для первого цикла*}
{if $smarty.foreach.mod.first}
<tr>
<td>№</td>
<td>Название модуля</td>
{* названия групп пользователей *}
{foreach from = $ar item = gr key = kgr}
<td>{$kgr}</td>
{/foreach}
</tr>
{/if}
<form action='permission.php' method='post'>
{* названия модулей *}
<tr>
<td>{$number}</td>
<td colspan = 4>{$keys}</td>
</tr>
{* название операций *}
{foreach from= $gr item=op key = opk}
<tr>
<td></td>
<td>{$nbsp}{$opk}</td>
{* название группы *}
{foreach from = $ar item = gr key = kgr}
{*чекбокс*}
<td><input type="checkbox" name="act[{$keys}-{$kgr}-{$opk}]" value="1" {if $op == 1}checked{/if}></td>
{/foreach}
</tr>
{/foreach}
{/foreach}
<tr>
<td colspan=5><input type='submit' value='Установить разрешения' name = 'Perm'></td>
</tr>
</form>
</table>
|
| |
|
|
|
|
|
|
|
для: Лена
(25.09.2009 в 22:22)
| | >осталось обработчик формы сделать.
... который обходился бы возможно меньшим числом запросов...
Тоже задачка не самая примитивная. | |
|
|
|
|
|
|
|
для: Trianon
(26.09.2009 в 12:40)
| | Cделала две страницы - на одной модули+доступ к ним разных групп. На другой - операции с модулями, предполагается, что доступ к этой странице только у админов и т.д.
Изменила массив, в результате получился такой -
$arr[$mod][$id_mod][$gt][$id_gt] = $c[$i];
модуль-id модуля-группа-id группы = столбец, который показывает, выбран ли чекбокс.
В шаблоне чекбоксы выглядят так:
<td><input type="checkbox" name="act[{$kgr}-{$kgrmr}]" value="1" {if $grmr == 1}checked{/if}></td>
в названии - id модуля+id группы и здесь $grmr это $c[$i]
Все в одном массиве, все раскладывается, только циклов много.
В обрабочике, когда приходят post-параметры(после защиты от иньекции):
<?php
//очистить таблицу
$sql2 = "TRUNCATE TABLE permission";
$result2 = mysql_query($sql2);
if(!$result2) exit("Error in $sql2: ". mysql_error());
foreach($_POST['act'] as $k=>$v){
$chunk = explode("-",$k);
//присвоить значения выбранных чекбоксов
$q = "INSERT INTO permission(id_group,mod_id) VALUES('$chunk[1]','$chunk[0]')";
$res2 = mysql_query($q);
if(!$res2) exit("Error in $q: ". mysql_error());
}
?>
|
Спасибо. | |
|
|
|
|
|
|
|
для: Лена
(27.09.2009 в 14:04)
| | Дорого и сердито.
сердито стирать всю таблицу... а если кто-то обратится между запросами?
дорого заносить элементы по одной строке на запрос.
Может есть смысл переделать таблицу, добавив поле активен/неактивен? Ну и суррогатный ключ докучи... | |
|
|
|
|
|
|
|
для: Trianon
(27.09.2009 в 16:21)
| | То есть, вы предлагаете такую структуру?
CREATE TABLE `permission` (
`id_group` int(11) NOT NULL default '0',
`mod_id` int(11) NOT NULL default '0',
`my_check` int(11) NOT NULL,
`choos` int(11) NOT NULL auto_increment,
PRIMARY KEY (`choos`),
UNIQUE KEY `id_group` (`id_group`,`mod_id`)
) ENGINE=MyISAM AUTO_INCREMENT=4 DEFAULT CHARSET=utf8 AUTO_INCREMENT=4 ;
|
суррогатный ключ здесь choos, поле для отмеченного чекбокса - my_check. Тогда в названии чекбокса надо передавать значение суррогатного ключа. | |
|
|
|
|
|
|
|
для: Лена
(27.09.2009 в 18:25)
| | да , как-то так.
Запрос , формирующий чекбоксы , тоже несколько упрощается при этом. Поскольку отсутствие записей ловить не нужно.
пропустил момент, когда число связываемых факторов сократилось с трех до двух, но не суть важно. | |
|
|
|
|
|
|
|
для: Trianon
(27.09.2009 в 19:13)
| | Пробовала вчера делать, чтобы ввести еще одно поле, которое покажет выбранный чекбокс, что-то с ним не получается, где-то я ошибку пропускаю, поэтому отказалась.
Решила пойти путем более простым.
Цикл в обработчике немного поменяла, чтобы использовать многострочный INSERT
<?php
foreach($_POST['act'] as $k=>$v){
$chunk = explode("-",$k);
$id_group[]= "(" . $chunk[1] . ',' . $chunk[0] . ")";
}
$id = implode(",", $id_group);
//присвоить значения выбранных чекбоксов
$q = "INSERT INTO permission(id_group,mod_id) VALUES" . $id;
$res2 = mysql_query($q);
if(!$res2) exit("Error in $q: ". mysql_error());
?>
|
А вот от TRUNCATE я уже никак избавиться не могу, потому как у меня два поля с id'ами - составной уникальный ключ, обновить до нуля я их не могу, вот и приходится все вырезать. | |
|
|
|