А это клавиатура, с помощью которой я творю...
http://kurepin.ru/php/utils/
Rambler's Top100
Пишем на PHP: Язык SQL и utils.class

Значится так. Мы уже умеем создавать таблицы, заносить в них данные и извлекать эти самые данные из этих самых таблиц.

Давайте разберем еще один мощный select, затем посмотрим методы удаления и на этом закончим наше отступление в сторону MySQL.

select date_format(book_date,'%d.%m.%Y') as date, book_name from books where book_name like "А.__%" && book_id<100 && book_date<"2002-01-01 00:00:00" order by book_date desc limit 0,2;


+------------+------------------------------------------------------+
| date       | book_name                                            |
+------------+------------------------------------------------------+
| 28.08.2001 | А.Толстой. 'Золотой ключик или приключения Буратино' |
| 00.00.0000 | А.Платонов. 'Котлован'                               |
+------------+------------------------------------------------------+
2 rows in set (0.00 sec)


Запрос, конечно, не самый сложный, но на такой ущербной базе данных особенно не разгуляешься. Ну, да ладно.

Перевожу строку запроса на русский язык.

Выбрать даты в формате "дд.мм.гггг" и называния книг из базы данных "книги", в тех записях, которые удовлетворяют условиям:
1. Название книги начинается на "А.", имеет еще минимум два символа после этого "__" и продолжается как угодно до конца"%".
2. Порядковый номер в базе не превышает цифры 100.
3. Дата меньше, чем 2002-й год.
Полученные данные отсортировать по дате, в обратном порядке: от большего к меньшему. Из полученных данных взять только две строки, начиная с первой же позиции (0 — первая запись).

Вот так расшифровывается наш запрос.

Интереснее поиграть с запросами сразу из нескольких таблиц, конечно. Будем надеяться, что наша задача предоставит нам такую возможность. Посмотрим. Все же по SQL написано много умных книг, и я пока не планировал писать учебника по нему. Эту главу и предыдущую я посвятил сему языку, чтобы вы могли нормально читать те несложные запросы, которые мы будем составлять по мере создания нашего проекта.

Теперь об удалении из базы данных.

Удалять из базы записи так же просто, как и выбирать их select-ом. Все то же самое, только вместо слова select используется слово delete. При этом не указываются названия полей (т.к. удаление производится по целым записям), и не используются сортировки и группировки.

Например:

delete from books where b_id>2 && book_name like "___"

"Удалить из таблицы books записи, id которых больше 2 и имя книги состоит из трех любых символов".

Надеюсь, других примеров удаление приводить не надо, и так должно быть все понятно.

Если возникли попутные вопросы — Добро пожаловать на форум.

* * *

Возвращаемся к нашей программе.

Если я ничего не напутал, то у нас на очереди наименее нудный класс, который мы назвали utils. Почему наименее нудный? А потому, что состоять он у нас будет из большого количества процедур, имеющих самое разное предназначение: обработка ошибок, система оповещения, контроль кеширования страниц, преобразование и приведение форматов дат и времени, и так далее.

В течение всего нашего "учебного курса" мы будем возвращаться к этому классу, чтобы добавить в его тело очередную нужную нам функцию.

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

Думаю, вы уже сами догадались, что надо создать файл utils.class и породить в нем новый класс class_utils от класса class_mysql. Эту процедуру мы неоднократно повторяли, не будем задерживаться, перейдем к "ошибкам".


    Позвольте дать вам один совет. Многие начинающие программисты, пишущие на C, perl или php часто совершают одну небольшую ошибку, приводящую порою к страшной нервотрепке. Это проблема открывающих и закрывающих элементов конструкций. Чаще всего это выражается в том, что открыв очередную конструкцию той же фигурной скобкой, они не закрывают ее сразу, а откладывают это дело на потом. Но в процессе написания функции накапливается столько открывающих и закрывающих скобок, что не сложно запутаться самому и запутать интерпретатор. Последний может запутаться так, что укажет вам место ошибки очень далеко от ее настоящего места, совсем в другом месте вашего листинга. Старайтесь всегда ставить скобки, теги, кавычки и прочих "парных тварей" сразу парами. Поставил пару кавычек, а уж потом вписывай между ними свой текст. Это сэкономит вам кучу времени, уверяю.


Мы еще не знаем, какие ошибки у нас будут возникать в процессе работы наших скриптов. Поэтому создадим саму процедуру с несколькими ошибками, а в процессе работы над проектом будем добавлять в нее новые данные.

Для наглядности будем использовать в качестве базы хранения ошибок обычный массив переменных. Для больших проектов это не самый разумный способ, но он очень нагляден и понятен. А место хранения описания ошибок мы всегда можем изменить, если того потребуют обстоятельства.

В общем, функция возврата текста ошибки по ее номеру — феноменально примитивна. Ее можно разделить на две составляющие: описание базы ошибок и собственно возврат описания ошибки по ее номеру. Смотрим.


Почти все понятно без объяснений.

Мы передаем номер ошибки нашей функции, которая хранит этот номер в переменной $num.

$err[2]="Ошибка авторизации."; — это мы занесли строку "Ошибка авторизации" в ячейку массива под номером 2. Т.е. 2 — это у нас уже зафиксированный номер ошибки, которые будет возбуждаться при нарушении правил авторизации: при неверной попытке доступа в защищенную часть сайта.

return($err[$num]); — собственно, возврат текста ошибки. То, ради чего создана эта функция.

И только одна строка требует более детальных пояснений:

if($this->DEBUG_LEVEL>=$num) $this->mail_to_noc($err[$num]);

Дело в том, что есть ошибки, о появлении которых необходимо знать администратору сайта: ошибки базы данных, попытки взлома, попытки подбора паролей и тому подобное. А есть такие, которые будут возникать в больших количествах для посетителей страниц, но не являющиеся при этом нарушениями работы системы: "вы забыли ввести ваше имя", "по этому материалу нет комментариев", "по вашему запросу ничего не найдено" и прочее.

Вот, чтобы администратор получал только те ошибки, которые ему интересны, мы вводим в наш первый класс class_vars еще одну переменную, определяющую текущий уровень отладки скриптов (добавьте в файл vars.class):


// уровень отладки
 var $DEBUG_LEVEL=100;

Как это работает.

Вы обратили внимание, что я разделил все наши ошибки на несколько групп? И не просто так, а с некоторой особенностью. Чем серьезнее и фатальнее ошибка, тем ниже ее порядковый номер. "Страшные" ошибки нумеруются 1, 2, 3..., ошибки попроще (вроде MySQL) нумеруются с номера 11. А совсем неинтересные администратору сообщения — начинают нумероваться с числа 101.

Это сделано для того, чтобы удобно нам было выставлять уровень отладки.

Смотрим еще раз на строку:

if($this->DEBUG_LEVEL>=$num) $this->mail_to_noc($err[$num]);

Из нее не сложно понять, что мы вызываем некую функцию mail_to_noc() (она отсылает администратору сообщение об ошибке по почте), но только в том случае, если номер активной ошибки меньше или равен той, что мы указали в нашей переменной $DEBUG_LEVEL.

Сейчас мы установили DEBUG_LEVEL в состояние 100. Это значит, что администратор получит сообщение об ошибке по почте только в том случае, когда эта ошибка не имеет отношения к сообщениям для web-серфера.

При отладке наших скриптов мы можем поднять уровень отладки до любой большой цифры, чтобы получать полную информацию о том, что творится на сайте, но после отладки этот уровень вполне можно уменьшить обратно до 100 и спасть спокойно.


    Очень подробно я разжевал эту простейшую функцию только для того, чтобы вы поняли важность "ошибки" для программы. Если мы построим грамотную систему самоанализа программы, то никогда не будем иметь проблем со взломами, добавлением ошибочных данных и другими неприятностями, которые не только могут подпортить нам нервы, но и подпортить результат многолетнего труда.

    Кстати, по уровню отношения к ошибкам и самоанализу системы можно судить о серьезности программиста. Научиться кодировать для web — совсем не сложно. Гораздо сложнее сделать это так, чтобы система могла за себя постоять, чтобы пользователь знал — что он сделал не так, чтобы администратор сайта знал, что на нем творится, чтобы другие программисты могли после тебя разобраться в том, что ты написал. Хотя последнее — не обязательно. У каждого программиста своя манера, как у художника. Поэтому, не всегда удается дописать талантливый фрагмент к чужому творению. Художникам это и не надо, а вот программистам — наоборот.



Нам осталось разобрать еще две функции.

Совсем коротенькая функция получения html-версии ошибки:


Тут даже пояснять нечего. Мы вызываем написанную нами err_to_str с номером ошибки, чтобы получить ее текст. А затем оформляем все это html-тэгами и просьбой прислать описание ситуации, при которой произошла данная ошибка. Все просто, даже языком тут почесать не обо что.

Лучше освоим новую для нас функцию обращения с почтовыми сообщениями.

В PHP известно два способа отправлять почтовые сообщения: при помощи стандартной почтовой службы сервера и отправка сообщения без посторонней помощи через socket. Мы остановимся на первом варианте. В 99.9% случаев его оказывается достаточно. Кроме того, у меня просто не хватит преподавательской квалификации, чтобы разжевать вам второй способ.

Давайте напишем сразу две функции. Первая будет у нас заниматься отправкой почты как таковой, а вторая будет вызывать первую, чтобы отправить именно письмо с ошибкой.

Первую функцию назовем mailer. Вот так она выглядит.


В качестве аргументов этой функции мы передаем параметры:
$from — от кого
$to — кому
$subj — тема сообщения
$body — само сообщение (тело сообщения — так правильно это называется)

Далее мы производим магические пассы над нашими аргументами. Я не буду объяснять, что означают эти странные добавления, вроде "nContent-Type: text/plain; charset=\"koi8-r\"\nContent-Transfer-Encoding: 8bit", вам это знать не так уж обязательно. Скажу только, что это служебная информация для вашего outlook или TheBat, уж не знаю, чем вы там пользуетесь для чтения почты. Если этой информации в заголовке письма не будет, то письмо вы увидите в жутком формате, русский язык в виде всяких "зюков" и так далее.

А функция convert_cyr_string() просто преобразует текст из формата win-1251 в формат KOI-8, который является стандартом для почтовых сообщений в русскоязычном Интернете (к сожалению, далеко не все это знают).

Опустив все эти "пассы", мы подходим к функции PHP mail(), которая и отправит наше письмо при помощи почтовой службы сервера. Ей мы и предаем подготовленные нами параметры: отправителя, получателя, тему и сообщение.

Ну вот. А теперь можно и послать администратору сообщение об ошибке.


Круто?! Ничего не поняли? Это хорошо. Попробуйте разобрать эту фигню, а завтра сравните ваши предположения с тем, что это есть на самом деле.

До завтра!

[шаг назад] [печатать] [в начало сайта]



copyright ©2000-2017 Ruslan Kurepin