Представлен Вашему вниманию класс на PHP для формирования у себя на сайте каталога — будь то продукция, фирмы, сайты или просто сборник ваших файлов.
Для работы необходима таблица MySQL с произвольным именем (в нашем проекте название такблицы «structure«).
Особенности скрипта:
— неограниченная вложенность
— неограниченное количество записей и разделов
— возможность существования записей и разделов с одинаковыми именами по одному пути
— записи и папки поддерживают все символы UTF-8 неограниченной длины.
class Products{ var $db = false; var $tablename = ''; // конструктор public function Products($db, $tablename){ $this->db = $db; $this->tablename = $tablename; } public function search($str){ // релевантный поиск $points = $where = $output = array(); $fields = array('name', '`desc`'); // в каких полях будем искать фразу $str = mysql_real_escape_string($str); $words = explode(' ', str_replace(",", "", trim($str))); // максимальное количество баллов за точное вхождение фразы $max_points = count($words) * 1; foreach ($fields as $field) { if (count($words) > 1) { $points[] = "IF ({$field} LIKE '%{$str}%', {$max_points}, 0)"; } foreach ($words as $w) { if (!$w) continue; $where[] = "{$field} LIKE '%{$w}%'"; $points[] = "IF ({$field} LIKE '%{$w}%', 1, 0)"; } } $where = "(" . implode(' OR ', $where) . ")"; $points = implode(' + ', $points); $result = $this->db->sql_query('SELECT *, (' . $points . ') AS `points` FROM `' . $this->tablename . '` ORDER BY `points` DESC LIMIT 50'); while($row = $this->db->sql_fetchassoc($result)){ $output[] = $row; // это наш массив в котором будут результаты поиска } return $output; } // путь - где находимся? public function where($id){ // по ID $out = array(); do{ if(!$row = $this->db->sql_fetchassoc($this->db->sql_query("SELECT * FROM `{$this->tablename}` WHERE `id`='{$id}'"))){ break; } if(is_array($row))$out[] = $row; $id = @$row['parent']; }while(1); return array_reverse($out); // реверс массива } // метод "что это?" -- отдаём массив со значениями полей записи по его id public function whatis($id){ return $this->db->sql_fetchassoc($this->db->sql_query("SELECT * FROM `{$this->tablename}` WHERE `id`='{$id}'")); } // читаем директорию public function readdir($parent){ $dirs = array(); $files = array(); $result = $this->db->sql_query("SELECT * FROM `{$this->tablename}` WHERE `parent`='{$parent}' ORDER BY `name`"); while($row = $this->db->sql_fetchassoc($result)){ if($row['type'] == _DIR) $dirs[$row['id']] = $row['name']; if($row['type'] == _FILE) $files[$row['id']] = $row["name"]; } return array("dirs" => $dirs, "files" => $files); } // метод создания записи в структуре public function mkitem($data){ // $data - массив данных о создаваемой записи $keys = array(); $values = array(); foreach((array)$data as $k => $v){ $keys[] = "`{$k}`"; $values[] = "'{$v}'"; } return $this->db->sql_query("INSERT INTO `{$this->tablename}` (" . implode(",", $keys) . ") VALUES (" . implode(",", $values) . ")") ? $this->db->sql_nextid() : false; // вернёт id созданной записи } // метод редактирования записи в структуре public function edititem($data){ // $data - массив данных о редактируемой записи $id = $data['id']; unset($data['id']); $array = array(); foreach((array)$data as $k => $v){ $array[] = "`{$k}`='{$v}'"; } return $this->db->sql_query("UPDATE `{$this->tablename}` SET " . implode(",", $array) . " WHERE `id`='{$id}'"); } public function delitem($id){ // удаляется ОДНА запись (возврат родительского ID) if(file_exists("uploads/{$id}.jpg"))unlink("uploads/{$id}.jpg"); list($parent) = $this->db->sql_fetchrow($this->db->sql_query("SELECT `parent` FROM `{$this->tablename}` WHERE `id`='{$id}'")); return $this->db->sql_query("DELETE FROM `{$this->tablename}` WHERE `id`='{$id}'") ? $parent : false; // возвращаем id родителя для перехода на уровень вверх } public function delitems($id){ // удаляются ВСЕ дочерние записи этого элемента(рекурсивом) $return = list($parent) = $this->db->sql_fetchrow($this->db->sql_query("SELECT `parent` FROM `{$this->tablename}` WHERE `id`='{$id}'")); $ids = array(); foreach((array)explode(" ", $this->child_ids($id)) as $v){ // бъём строку по пробелам на массив и удаляем пустые ячейки массива if(!empty($v)){ if(file_exists("uploads/{$v}.jpg"))unlink("uploads/{$v}.jpg"); // удалим фоточки если есть $ids[] = $v; } } $this->db->sql_query("DELETE FROM `{$this->tablename}` WHERE `id` IN (" . implode(", ", $ids) . ")"); return $this->delitem($id); // возвращаем id родителя для перехода на уровень вверх } private function child_ids($id){ $ids = ""; $struct = $this->readdir($id); foreach($struct as $type => $arr){ foreach($arr as $k => $v){ $ids .= $k . " "; if($type == 'dirs') $ids .= $this->child_ids($k) . " "; // потом по пробелу будем бить строку } } return $ids; } }
В классе собрано всё для полноценного функционирования простейшего каталога: создание, редактирование, удаление и поиск по элементам каталога. Также присутствует и главный метод (where) — положение в текущий момент в каталоге (отдаётся массив с директориями и элементами списка).
Структура базы данных для класса:
create table `structure` ( `id` int , `name` varchar (50), `type` int , `desc` blob , `parent` int );
Ниже представлен данный класс в наборе с простейшей CMS , позволяющий запустить и протестировать у себя на сервере данную структуру каталога. Скачать класс с «обёрткой» : STRUCTURE. Example-база данныx для «обёртки»: database