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

Что такое реляционная база данных

Реляционная база данных – это база данных основанная на реляционной модели (от англ. relationship — отношение, связь) выражаясь по другому, это некий набор данных с определёнными связями между ними. Обычно такие базы организованны в виде таблиц. В отдельных таблицах хранится сгруппированная по определённому смыслу информация о какой-либо сущности, например данные о покупателях (сущность — покупатель) или данные о товарах (сущность — товар) и т.д.  Каждый столбец таблицы отвечает за хранение одного свойства сущности, внутри ячейки хранится значение свойства сущности, например столбец — цена, значение — 1000.

Отношения между таблицами в БД


Преимущественно отдельные столбцы имеют строго определённый тип данных (числовой, логический, текстовый, дату и время и т.д.). Каждая стока таблицы это набор значений свойств относящихся к определённой сущности (напр. определённому пользователю может соответствовать строка где хранит его имя, фамилия, телефон, email, возраст и пол.). Каждая строка в таблице должна иметь уникальный идентификатор, а так же так называемый «первичный ключ» (часто первичный ключ = уникальный идентификатор). При помощи первичного ключа, несколько таблиц базы данных могут быть связаны, например в таблице users — хранятся пользователи, а в таблице orders — заказы пользователей сделанные в интернет-магазине. По первичному ключу user_id  (идентификатор пользователя) мы можем узнать что этот пользователь заказал, т.е. получить данные из таблицы orders.

Для работы с реляционными базами данных существует множество инструментов, они позволяют «вытаскивать» из БД различные наборы данных, даже более сложные чем в приведённом примере, при этом, структура таблиц не требует реорганизации.

СУБД MySQL

Что же такое MySQL? Это надежная. быстрая и универсальная система управления базами данных (СУБД), пожалуй  самая популярная в мире (в 2019 году 39% разработчиков использовали MySQL в своих проектах). Несмотря на более слабый функционал в сравнении с PostgreSQL, данная СУБД прекрасно масштабируется и отлично подходит для большинства проектов.

MySQL СУБД

MySQL — идеальный выбор для разработке веб-приложений. Данная СУБД входит в стандартный набор: Linux, Apache HTTP Server, MySQL и PHP (LAMP — набор программ с открытым исходным кодом). Так же не основе MySQL работает большинство популярных CMS ( Content Management System — система управление содержимым), таких как WordPress, OpenCart, 1С Битрикс и т.д.

К преимуществам этой СУБД можно отнести:

  • Простота: Mysql легко установить на любую платформу (Linux, Windows, MacOS), под эту СУБД написано множество настольных приложений позволяющих работать с базой в визуальном режиме (очень удобно особенно для новичков), к подобным системам относятся Workbench, Navicat, PHPMyAdmin и другие.
  • Много функций: MySQL поддерживает весь функционал реализованный на  языке SQL.
  • Безопасность: в СУБД MySQL встроено много функций безопасности, например Access Control Lists и поддержка SSH-зашифрованных соединений.
  • Масштабируемость: MySQL достаточно легко и не дорого масштабируется, что позволяет разрабатывать на ней довольно крупные и высоко-нагруженные проекты.

В большинстве языков программирования встроена поддержка СУБД MySQL, PHP так же не стал исключением.

PHP PDO

PHP PDO
 PDO — это специализированный класс реализующий интерфейс доступа к базе данных. Его отличает универсальность, т.к. вам без разницы какая база данных будет использована.


Подключение к БД

Для подключения к БД необходимо создать экземпляр класса PDO и передать в него параметры подключения:


/* Подключение к базе данных MySQL с помощью PDO */
$dsn = 'mysql:dbname=testdb;host=localhost';
$user = 'root';
$password = '123456';

//Чтобы перехватить ошибки подключения используем исключения try {...} catch () {...}
try {
    $dbh = new PDO($dsn, $user, $password);
} catch (PDOException $e) {
	//В случае ошибки выводим сообщения из перехваченного исключения
    echo 'Подключение к БД не удалось: ' . $e->getMessage();
}

Конструктор PDO так же поддерживает и четвёртый параметр options — это массив ключ=>значение специфичных для драйвера (например MySQL или PostgreSQL) настроек подключения. Например сразу после подключения можно выполнить MySQL запрос указав это в параметре options:

//Чтобы перехватить ошибки подключения используем исключения try {...} catch () {...}
try {
    $dbh = new PDO(
		$dsn, 
		$user, 
		$password, 
		[PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES 'utf8'"] //Команда которую необходимо выполнить сразу после подключения к серверу
	);
} catch (PDOException $e) {
	//В случае ошибки выводим сообщения из перехваченного исключения
    echo 'Подключение к БД не удалось: ' . $e->getMessage();
}

Полный перечень параметров доступных в options вы найдёте в документации.

Базовый набор операций (CRUD)

Большинство веб-приложений работающих с базой данных, так или иначе реализуют базовый набор операций, а именно Create — создание, Read — чтение, Update — обновление и Delete — удаление (CRUD). Давайте рассмотрим как этот набор операций сделать в PDO.

Создание

Для теста, давайте создадим таблицу с пользователями сайта и заполним её данными. Таблица будет называться просто users и иметь 4 поля:

  1. id — автоинкрементный идентификатор записи
  2. name — имя пользователя
  3. email — адрес электронной почты
  4. phone — контактный телефон

try {
    //Соединяемся с базой данных
    $dbh = new PDO('mysql:dbname=test_db;host=localhost', $user, $password);

    //запрос на создание таблицы
    $sqlCreateTable = 'CREATE TABLE `users` ( `id` INT(11) NOT NULL AUTO_INCREMENT, `name` VARCHAR(255) NOT NULL, `email` VARCHAR(255) NOT NULL, `phone` VARCHAR(255) NOT NULL, PRIMARY KEY (`id`)) ';
    $dbh->exec($sqlCreateTable);
    echo 'Создана таблица <b>users</b>';

} catch(PDOException $e) {
    echo 'Ошибка: ' . $e->getMessage();
}

Здесь мы используем метод exec() он запускает запрос на выполнение возвращая количество затронутых строк. Метод не предназначен для выборки данных из таблицы. Если всё сделано верно у вас будет создана таблица пользователей. Давайте заполним её данными.

/*Данные пользователей, в реальном проектк они могут
 быть получены из JSON, файла импорта или из формы регистрации */
$usersData = [
    [
        'name'=>'Иван Иванов',
        'email'=>'ivan@mail.ru',
        'phone'=>'+79001234567'],
    [
        'name'=>'Пётр Петров',
        'email'=>'petrov@yandex.ru',
        'phone'=>'+79281534874'],
    [
        'name'=>'Олег Сидоров',
        'email'=>'sidor@gmail.com',
        'phone'=>'+79508975248'
    ],
];

try {
    //Соединяемся с базой данных
    $dbh = new PDO('mysql:dbname=test_db;host=localhost', $user, $password);
    $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    //Подготовка запроса, обратите внимание что ключи в запросе совпадают с ключами массив отдельного пользователя
    $data = $dbh->prepare('INSERT INTO users (name, email, phone) VALUES(:name, :email, :phone)');

    //Перебираем массив пользователей
    foreach ($usersData as $user) {
        //Подставляем данные пользователей в запрос
        $data->execute($user);
    }

} catch(PDOException $e) {
    echo 'Ошибка: ' . $e->getMessage();
}




Если всё сделано верно, вы получите заполненную таблицу users:
Заполненная таблица users

Чтение

Прочитать записи в таблице БД можно несколькими способами, при помощи метода query и execute , давайте разберём оба:

Чтение таблицы при помощи метода query


$user = 'root';
$password = 'Ваш пароль';

//Чтобы перехватить ошибки подключения используем исключения try {...} catch () {...}
try {
    $dbh = new PDO('mysql:dbname=test_db;host=localhost', $user, $password);
    $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    //Выборка всех записей
    $users = $dbh->query('SELECT * FROM `users`');

    echo '<ul>';
    foreach ($users as $user){
        echo '<li>id: ' . $user['id'] . ' - name: ' . $user['name'] . ' - phone: ' . $user['phone'] . ' - email: <a href="'. $user['email'] . '">'. $user['email'] .'</a></li>';
    }
    echo '</ul>';

} catch (PDOException $e) {
    //В случае ошибки выводим сообщения из перехваченного исключения
    echo 'Ошибка: ' . $e->getMessage();
}

В результате на экране вы увидите такую картину:
Результат чтения таблицы users
Обратите внимание на следующее:

$dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

Данные параметры устанавливают расширенный режим вывода ошибок и исключение PDO.

Чтение таблицы при помощи метода execute

Давайте выберем из БД одного пользователя по конкретному email адресу.


try {
    $dbh = new PDO('mysql:dbname=test_db;host=localhost', $user, $password);
    $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    //Вывод пользователя с email адресом ivan@mail.ru

    //Подготовка запроса
    $data = $dbh->prepare('SELECT * FROM `users` WHERE `email` = :user_email');
    // Выполнение с подстановкой параметра в запрос
    $data->execute(['user_email'=>'ivan@mail.ru']);

    //Получаем результат
    $users = $data->fetchAll();

    echo '<ul>';
    foreach ($users as $user){
        echo '<li>id: ' . $user['id'] . ' - name: ' . $user['name'] . ' - phone: ' . $user['phone'] . ' - email: <a href="'. $user['email'] . '">'. $user['email'] .'</a></li>';
    }
    echo '</ul>';

} catch (PDOException $e) {
    //В случае ошибки выводим сообщения из перехваченного исключения
    echo 'Ошибка: ' . $e->getMessage();
}

В данном примере используется метод prepare т.е. подготовка запроса. Это позволят почти с 100% гарантией избежать SQL инъекций т.к. подставляемый параметры email не встраивается в зарос напрямую, в запросе есть лишь метка :email куда через метод execute будет подставлена переданная через ассоциативный массив переменная.

В результате выполнения запроса, получаем одну запись из таблицы users:

Чтение таблицы методом execute

Редактирование

Давайте теперь изменим контактный телефон для пользователя с id равным 2 и сразу посмотрим на результат (выведем на экран список всех пользователей).


try {
    //Соединяемся с базой данных
    $dbh = new PDO('mysql:dbname=test_db;host=localhost', $user, $password);
    $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    //Подготовка запроса
    $data = $dbh->prepare('UPDATE  users SET phone = :phone WHERE id = :id');

    //Подстановка параметров
    $data->execute([
        'phone'=>'+7 900 000 00 00',
        'id' => 2
    ]);

    //Выведем на экран сколько строк затронул наш запрос
    echo 'Обновлено строк таблицы: ' . $data->rowCount();

    //И сразу посмотрим на результат, выведем всех пользователей
    $users = $dbh->query('SELECT * FROM `users`');

    echo '<ul>';
    foreach ($users as $user){
        echo '<li>id: ' . $user['id'] . ' - name: ' . $user['name'] . ' - phone: ' . $user['phone'] . ' - email: <a href="'. $user['email'] . '">'. $user['email'] .'</a></li>';
    }
    echo '</ul>';


} catch(PDOException $e) {
    echo 'Ошибка: ' . $e->getMessage();
}

Как видите, запись обновилась:
Обновление записи в БД


Отлично, осталось понять как удалять запись. Давайте удалим того же пользователя, этот Пётр Петров мне надоел =)

Удаление

И так, мы знаем что у пользователя Пётр Петров id равен 2, приступим:


try {

    //id пользователя Пётр Петров
    $id = 2;

    //Соединяемся с базой данных
    $dbh = new PDO('mysql:dbname=test_db;host=localhost', $user, $password);
    $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    //Подготовка запроса
    $data = $dbh->prepare('DELETE FROM users WHERE id = :id');
    $data->bindParam('id', $id);
    $data->execute();

    echo 'Удалено записей: ' . $data->rowCount();

} catch(PDOException $e) {
    echo 'Ошибка: ' . $e->getMessage();
}

Как видите, здесь для подстановки параметра в запрос мы использовали метод bindParam() им удобно пользоваться когда нам нужно подставить единичную переменную в запрос. Обратите внимание, что второй аргумент не может быть передан напрямую в виде значение (нельзя написать просто 2), мы должны передать именно переменную (которую по идеи нужно предварительно проверить и всё такое).

Как видите работать с PDO да и в целом с базами данных в PHP не так уж и сложно. Надеюсь статья была вам полезна. Желаю удачи!

Полезная статья?
(Голосов: 3, Рейтинг: 3.56)
Вам также могут понравиться
Английский для программистов

Английский для программистов

Почему IT-специалисту необходимо освоить английский язык? Разбираем в статье.

Как подключить CSS и JS файлы к шаблону 1С Битрикс

Как подключить CSS и JS файлы к шаблону 1С Битрикс

Как правильно подключать стили и скрипты к шаблону 1С Битрикс.

Генерация оглавления статьи

Генерация оглавления статьи

В статье рассмотрен пример функции для генерации оглавления статьи блога или новости


Комментарии
Защита от автоматических сообщений
CAPTCHA
Введите слово на картинке