Профессиональная разработка Web-приложений.  
Боишься нашего дизайна?
Новости
PDF журнал
Участники проектa
Сотрудничество
Ссылки
Карта сайта
Комментарии
Комментарии к статье
Добавить комментарий
Обсудить на форуме
Информация об авторе
Оценка статьи

Использование PEAR для доступа к базе данных

Мы все привыкли к MySQL. Мы любим его за простоту, легкость освоения и множество программ для облегчения работы (phpMyAdmin). Мы делаем скрипты и задумываемся, а вдруг у заказчика стоит другая SQL-база? И вот тут мы начинаем выдумывать или скачивать классы для работы с различными базами. А не проще ли использовать готовое, да ещё к тому же включенное по умолчанию в дистрибутив php?

Мы все привыкли к MySQL. Мы любим его за простоту, легкость освоения и множество программ для облегчения работы (phpMyAdmin). Мы делаем скрипты и задумываемся, а вдруг у заказчика стоит другая SQL-база? Как сделать универсальность, когда наши скрипты не зависят от базы данных?

И вот тут мы начинаем выдумывать или скачивать классы для работы с различными базами. А зачем морочить голову и думать, как проверить, работает ли на остальных SQL базах то, что мы написали? А не проще ли использовать готовое, да ещё к тому же включенное по умолчанию в дистрибутив php? Это прекрасное дополнение к php, о котором вы больше сможете узнать посетив их сайт.

Сегодня попробуем разобраться с их классом DB, отвечающим за доступ к различным базам данных (MySQL, PostgreSQL, Oracle 7/8/8i, Microsoft SQL, InterBase, MiniSQL, SyBase, Informix, FrontBase и универсальный ODBC).

Как ни стандартно, при разработке проектов мы сделаем один файл connect.php, который будет подключатся к нашей базе в каждом скрипте, где это необходимо:

------------- connect.php ------------
<?PHP
require_once("DB.php");
#подключаем класс DB PEAR

$TypeSQL= "mysql";
$Host="localhost";
$User="YourPasswordSQL"
$Name="YourNameSQL";
$Dbase="MyDBase";
//Все так же, как и делали раньше, только добавилась переменная $TypeSQL, в которой мы 
//и указываем, какая у нас База Данных.

#  прописываем источник DSN http://pear.sourceforge.net/manual/core.db.tut_dsn.php
$dsn="$TypeSQL://$User:$Password@Host/$Dbase"
$db= DB::connect($dsn, true);
#Что соответствует знакомому по MySQL: mysql_db_connect() и mysql_db_select
$db->setFetchMode(DB_FETCHMODE_ASSOC);
//выбор формата выбираемых строк. В нашем случае мы используем
// fetchRow().А вообще, кому что нравится 
//http://pear.sourceforge.net/manual/core.db.setfetchmode.php.

?>

Вот, в принципе, и весь наш connect. И если мы захотим использовать другую базу данных, нам в этом скрипте необходимо заменить значение переменной $TypeSQL, к примеру, на "pgsql" (PostgreSQL).

Теперь приступим, собственно, к созданию запросов и работой с нашей базой данных.

<?PHP
require_once("connect.php");
#Подключаемся к Базе Данных.

$sql= "SELECT * FROM MyTable";
$res= $db->query($sql);
#Выполняем наш запрос (аналогия mysql_query() )
$num= $res->numRows();
#Определяем количество строк (аналогия mysql_num_rows() )
while($row= $res->fetchRow())  
{
$id= $row["id"];
$name= $row["name"];
}
#Получаем необходимые нам данные (аналогия mysql_fetch_array() )
#Или другим удобным для Вас методом подробнее http://pear.sourceforge.net/manual/

$res->free();
#освобождаем память (аналогия mysql_free_result() )
?>

Ничего сложного нет. Если вы работали с другими базами кроме MySQL то вы возмутитесь, сказав, что у MySQL есть такой замечательный метод, как auto_increment, а в других базах это реализовано по другому. Попытаюсь объяснить, как НЕ ИСПОЛЬЗОВАТЬ сразу auto_increment с MySQL и потом не иметь головной боли при переходе на другую базу данных.

В PEAR есть замечательная штука Sequence, которая создает новую последовательность с помощью createSequence()

Что бы понять, я объясню проще: в базе данных создается таблица с одним полем, в котором и будет находиться увеличивающееся значение счетчика записей. Сразу скажу, что если вы удалите в середине запись, то последовательность не уменьшится! Т.е. если было 1,2,3,4,5 и вы удалите запись 3 то будет 1,2,4,5.., и следующая последовательность будет 6, а не 3! Последовательность нам необходима, когда мы делаем вставку в базу данных, т.е. INSERT

<?PHP
require_once("connect.php");
$id= $db->nextID(w_, MyTable);
# Эта функция возвращает следующее число, находящееся в таблице последовательности.
# Если таблица последовательности еще не была создана, то она создается.
# В скобках пишется имя таблицы последовательности.
# для удобства используется имя таблицы данных и приставка w_ для того, что бы все  
# таблицы последовательностей находились внизу при просмотре всей базы.
# Не забудь! При создании таблицы НЕ УКАЗЫВАТЬ auto_increment в MySQL или другие
# увеличения в других базах. PEAR сделает все сам.

$sql= "INSERT INTO MyTable VALUES('$id', '$name')";
$res= $db->query($sql);
$res->free();
?>

Внимательный читатель сделает замечание: "А обработка ошибок?!" И будет прав. Мы здесь её нигде не делали. Для обработки ошибок будем использовать PEAR. Подробнее можно почитать здесь.

Мы же здесь используем обработчик ошибок (режим PEAR_ERROR_CALLBACK) на основании нашей функции, который будет вызываться и останавливать работу в любом месте программы, где вызвана ошибка, с подробным описанием. Для этого используем наш файл connect.php

<?PHP

define(DEBUG_ENV, true);
#Устанавливаем именованную константу. И когда наш сайт готов и мы можем его
#использовать, устанавливаем в FALSE, что бы нашим пользователем не выдавался код и
#сообщение, а просто стандартное сообщение на ошибку.

function handle_pear_error($error_obj)
{
    if(DEBUG_ENV)
    {
    die($error_obj->getMessage()."
".$error_obj->getDebugInfo()); } else { die("Ваш запрос не выполнен. Повторите попытку позже."); } } # функция обработки ошибок PEAR::setErrorHandling(PEAR_ERROR_CALLBACK, 'handle_pear_error'); #Устанавливаем, что при возникновении ошибки использовать нашу функцию. ?>

Вот, собственно, и всё. Более подробную информацию о PEAR, где есть и шаблоны, и работа с почтой, и многое другое, вы можете узнать, посетив официальную страничку PEAR или русскоязычную документацию.

Цель данной статьи - не конкуренция мануалу, а возможность дать понять, что иногда не стоит изобретать велосипед, а "стоит посмотреть под ноги" и увидеть, что многое есть уже готовое, да к тому же официально включено в PHP по умолчанию. А это много значит.

Источники информации

  • Официальный сайт PEAR
  • Русскоязычный мануал PEAR


  • For comment register here
       2002-11-01 13:01
    http://www.php4you.kiev.ua/
    на этом сайте есть полезные статьи о том как начать работать с PEAR...

       2002-11-02 14:44
    А как быть и особенностями SQL языков? Ведь в разных базах он разный.

       2002-11-02 22:58
    Не каждый же день на сайте меняют базу данных. Число используемых баз ограниченно. Так что переписать запросы вручную - не проблема. Не будете же вы писать универсальный класс для построения сложных запросов под конкретные базы. =)

       2002-11-04 02:34
    Привет.
    Приятно знать, что кто-то использует доки, которые мы переводили. Спасибо за ссылки.
    Хочу попросить добавить ссылку на более чайниковскую доку по PEAR::DB и не только..
    Писалась она еще до возникновения официальной документации на pear.php.net.
    Вот ссылка: http://pear.sourceforge.net/manual_old/

    Она конечно - очень uotdated, но для новичков в PEAR, ИМХО - самое то.

    Удачи всем.

    --
    kVn
    http://php4you.kiev.ua/

       2002-11-04 11:46
    http://cvs.php.net/cvs.php/pear?login=2
    Вот тут лежит самая последняя "Груша"... То, что пока не включено в дистрибутив можно найти там.
    Есть ещё очень интересное направление, окромя БД - это SOAP.

       2002-11-15 13:21
    Попробовал использовать PEAR::DB. Не думал, что начать так проблемно. Оказалось, просто так положить файлы в нужную директорию и вызвать через include. Либо клади в корень сайта (что не представляет угрозы безопасности - скрипты с паролями, запускающие соединение, лежат в закрытом месте, - но некрасиво), либо много думай. Решил проблему так: кладу файлы в специальную директорию. Перед подключением DB.php делаю

    ini_set("include_path", "include/");

    // вызываю скрипты, устанавливаю соединение с базой

    ini_restore("include_path");

       2002-11-18 19:48
    Для того, чтобы начать работать:

    Прописать include_path туда где лежит PEAR, обычно по умолчанию, - это /usr/local/lib/php (Unix), и C:php4pear (?)(Windows). Но можно и просто положить его в любое место, главное, чтобы include_path включал в себя путь к стартовой дирректории PEAR.

    Стартовая директория - это та, в которой ледит PEAR.php и DB.php..и еще куча всего + не забудьте папочки /DB/* /PEAR/* вложенные в корневую диру.

    Сейчас просто процесс становления инсталляционного процесса для установки самого PEAR, и packages для работы.

    Может чепрез днльта т, намокаю статейку типа: как начать работать с PEAR.

    П.С. А зачем делать ini_restore ?
    просто:
    ini_set('include_path',ini_get('include_path').':/path/to/pear');
    т.е. просто добавить к твоему инклуд пути еще и путь к папке PEAR.

    Удачи всем.

       2002-11-19 10:55
    Не знаю, имеет ли смысл делать целую статью про то, как надо разложить файлы и прописать include.

    ini_restore делается потому что после подключения главных скриптов PEAR и установления связи с БД (а это тоже подключение соответствующего класса DB::mysql) мне нужно вызывать другие скрипты.

       2002-11-19 17:51
    > Не знаю, имеет ли смысл делать целую статью про то, как надо разложить файлы и прописать include.

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

    > мне нужно вызывать другие скрипты
    это имеет смысл, если _твои_ скрипты имеют такое же название файлов как и PEAR-овские.

    Удачи.

       2002-11-19 18:40
    > это имеет смысл, если _твои_ скрипты имеют
    > такое же название файлов как и PEAR-овские

    Тут ты меня неправильно понял. Имена файлов разные и пути тоже разные. Только мне на сайте нужен пустой include_path, иначе начинаются сложности. PEAR лежит в отдельной директории. К тому же PEAR прикручен уже после того, как скрипты всего сайта были сделаны, поэтому нужно было либо менять парамерт ini, либо переписывать все пути.

       2002-11-21 11:04
    > Только мне на сайте нужен пустой include_path, иначе начинаются сложности.
    Вот здесь хотелось бы подробнее?
    Чем может мешать include_path, и какие сложности могут при этом возникнуть.

    Не подумай, я не придираюсь, просто сейчас в pear-dev как раз очень обильно лбсуждалась проблема с include_path, и инсталляцией PEAR в свою диру.
    т.е. там как раз проблема, что путь смотрит и туда и туда (/usr/local/lib/php и /home/vasya/PEAR) , а названия фалов одинаковые..

       2002-11-21 20:35
    Не думаю, что это относится к пробелмам PEAR. Просто у меня все скрипты на сайте работали из корня сайта. В поддиректориях ни один скрипт не запускался, разве что inc-файлы вызывались скриптами из корня сайта. Во всех скриптах пути для include указывались от корня - например include/file.inc (Не было возможности положить их в директорию, не доступную с веба, поэтому положил так и закрыл доступ в .htaccess). Достаточно удобно.

    Затем я добавил PEAR. Чтобы он не путался с другими скриптами, положил его в include/PEAR/. Но в самом PEAR все скрипты вызываются по путям относительно директории PEAR:

    include_once("DB/$.php");

    А без изменения include_path пришлось бы исправлять этот код на

    include_once("include/PEAR/DB/$.php");

    Поэтому, чтобы не переписывать свои собственные скрипты и не трогать код в PEAR, я поменял на время подключения библиотек include_path. ini_restore надо было делать потому что пути во всех моих скриптах написаны относительно корня сайта.

       2002-12-06 20:09
    Статья действительно интересная и даже более того.

    Сам попробовал PEAR. Но что то не удается осуществить подключение к базе данных через ODBC при помощи PEAR... Вроде все правильно делаю. Взял за основу пример из документации. Но ни как. Не подключается не к базе VisualFoxPro не к Mikrosoft Access. А к MySql подключается.
    При этом, при помощи стандартных функций РНР все подключения к тем же базам происходят нормально!!
    Не представляю в чем проблема.
    Может есть какието нюансы по поводу работы с c ODBC, или что то в PEAR в этом плане не доделано?

       2002-12-09 16:29
    Может я чего-то не понимаю:
    рассмотрим на примере (что просходит, при вызове include_*)

    1. ini_set("include_path", "/home/1:/home/2:/PEAR");
    2. include_once "include/file.inc";
    что происходит:
    PHP смотрит в /home/1/include/file.inc - есть? инклудим - дальше не сморим.
    нет? сморим в /home/2/include/file.inc - есть?
    инклудим - дальше не сморим.
    нет? сморим в /PEAR/include/file.inc - есть?
    инклудим - дальше не сморим.
    нет? Выводим сообщение об ошибке.

    соответственно
    include "DB.php"
    посмотрит его в /home/1/DB.php, /home/2/DB.php, /PEAR/DB.php и заинклудит из последнего, как и остальные скрипты PEAR.

    Или я чего-то не понимаю, или мы говорим о разных вещах. Потому как если _добавить_, а не заменить в инклуд_патх строку типа :
    было:
    php_value include_path '.:/home/vasya/htdocs/include'

    стало:
    php_value include_path '.:/home/vasya/htdocs/include:/home/vasya/htdocs/include/PEAR'

    то _ничего_ не должно измениться в _работающих_ скриптах. Эта проблема может возникнуть только если у тебя в обейх дирах есть файлы с одинаковым названием. Но что касается скриптов в данной статье - то, ИМХО, - ini_restore(), а так же страхи по поводу него - это лишнее.

    Буду благодарен за критику.
    --
    kVn

       2002-12-09 19:11
    А, сорри. Ты всё прекрасно понял. Просто я забыл, что в include_path можно указывать несколько путей и менял любое содержимое установки на путь/PEAR. Поэтому старые скрипты становились недоступны. Вопрос исчерпан. =)

       2002-12-18 14:32
    Код у Вас неправильный, батенька.
    Первый кусок должен быть таким (остальные еще не смотрел):

    <?PHP
    require_once("DB.php");
    #подключаем класс DB PEAR

    $TypeSQL= "mysql"; // Тип используемой БД
    $Host="localhost"; // Хост
    $User="YourUser"; // Логин для подключения к БД
    $Password="YourPassword"; // Пароль для подключения к БД
    $Dbase="MyDBase"; // Имя БД
    #Все так же, как и делали раньше, только добавилась переменная $TypeSQL, в которой мы и указываем, какая у нас База Данных.

    # прописываем источник DSN http://pear.sourceforge.net/manual/core.db.tut_dsn.php
    $dsn="$TypeSQL://$User:$Password@$Host/$Dbase"
    $db= DB::connect($dsn, true);
    #Что соответствует знакомому по MySQL: mysql_db_connect() и mysql_db_select
    $db->setFetchMode(DB_FETCHMODE_ASSOC);
    # выбор формата выбираемых строк. В нашем случае мы используем
    # fetchRow().А вообще, кому что нравится http://pear.sourceforge.net/manual/core.db.setfetchmode.php.

    ?>

       2002-12-18 14:35
    Да! Вот и сам ошибся. Там еще в строке
    $dsn="$TypeSQL://$User:$Password@Host/$Dbase"
    кроме знака "$" перед словом "Host" нужно в конце точку с запятой поставить.

       2003-08-01 13:23
    a для чего AdoDB тогда?? Вот ее и пользуйте для таких случаев!

       2005-01-30 04:13
    Хорошее сравнение PEAR::DB с ADODB (понятно что заангажированное, но факты объективные): http://phplens.com/phpeverywhere/node/view/39
    Почитайте раздел 2: Features Missing from PEAR DB и подумайте насколько реально вы сможете прикрутить PEAR::DB к своему проекту, ведь даже 1 запрос который работает с типом поля "Дата/время" способен поломать всю кросс-платформенность PEAR::DB

    Мы все привыкли к MySQL. Мы любим его за простоту, легкость освоения и множество программ для облегчения работы (phpMyAdmin). Мы делаем скрипты и задумываемся, а вдруг у заказчика стоит другая SQL-база? И вот тут мы начинаем выдумывать или скачивать класс

     
     
     
        © 1997-2008 PHPClubTeam
    []