Коли PHP-скрипт має зберігати дані (коментарі, замовлення, користувачів), без бази даних не обійтись, а найзручніший і найбезпечніший спосіб поговорити з MySQL у PHP – розширення PDO. Воно вбудоване в PHP, працює з різними базами й одразу привчає до правильних звичок. Покажу, як підключитись до MySQL, які параметри обов'язково задати й як не вилити пароль від бази на екран при першій же помилці.

Що таке PDO

PDO (PHP Data Objects) – універсальний шар доступу до баз даних. Код для MySQL, PostgreSQL чи SQLite виглядає майже однаково: змінюється лише рядок підключення. Головні переваги над старими mysql_* і частково mysqli:

  • підготовлені запити, які захищають від SQL-ін'єкцій (їм присвячу окрему статтю);
  • зручна обробка помилок через винятки;
  • однаковий інтерфейс для різних баз.

Що потрібно перед стартом

  1. Працюючий PHP із увімкненим розширенням pdo_mysql. Перевірити можна через phpinfo() або командою php -m.
  2. Сервер MySQL чи MariaDB. Якщо ще не маєш локального сервера, подивись статті про локальний сервер на Windows, Laragon або LAMP у Linux Mint та Ubuntu.
  3. База й користувач. Створити їх зручно в phpMyAdmin. Для сайту завжди роби окремого користувача лише з правами на його базу, а не працюй під root.

Мінімальне підключення

<?php
$dsn = 'mysql:host=localhost;dbname=mysite;charset=utf8mb4';
$user = 'mysite_user';
$pass = 'надійний_пароль';

$pdo = new PDO($dsn, $user, $pass);

Розберімо рядок підключення (DSN):

  • mysql: – драйвер;
  • host=localhost – адреса сервера бази (на хостингах буває іншою, її підкаже панель);
  • dbname=mysite – ім'я бази;
  • charset=utf8mb4 – кодування; без нього кирилиця й емодзі можуть перетворитись на «???» або крякозябри. Саме utf8mb4, а не utf8: перший повноцінно підтримує всі символи Unicode.

Правильне підключення з параметрами

Мінімальний варіант працює, але в реальних проєктах додають налаштування:

<?php
$dsn = 'mysql:host=localhost;dbname=mysite;charset=utf8mb4';

$options = [
    PDO::ATTR_ERRMODE            => PDO::ERRMODE_EXCEPTION,
    PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
    PDO::ATTR_EMULATE_PREPARES   => false,
];

$pdo = new PDO($dsn, 'mysite_user', 'надійний_пароль', $options);

Що тут важливо:

  • ERRMODE_EXCEPTION змушує PDO кидати виняток при помилці. Без цього помилки запитів можуть пройти непоміченими, а в журналі нічого не буде. Про те, як зробити помилки видимими, я розписував у статті про показ помилок у PHP.
  • FETCH_ASSOC задає, що результат запиту повертається масивом з іменами стовпців, а не подвійним масивом (за іменами й за номерами), як за замовчуванням.
  • EMULATE_PREPARES => false вимикає емуляцію підготовлених запитів, і MySQL готує їх справді. Це надійніше й коректно працює з типами даних.

Обробка помилки підключення

Якщо база недоступна чи пароль хибний, PDO кине виняток, і якщо показ помилок увімкнено, у трасуванні помилки може опинитись пароль від бази. Тому підключення обгортають у try/catch і не показують відвідувачам подробиць:

<?php
try {
    $pdo = new PDO($dsn, $user, $pass, $options);
} catch (PDOException $e) {
    error_log('DB connection failed: ' . $e->getMessage());
    http_response_code(500);
    exit('Сайт тимчасово недоступний.');
}

Деталі потрапляють у журнал помилок, а користувач бачить нейтральне повідомлення.

Де зберігати дані для підключення

  • Не пиши пароль прямо у файлі, який лежить у відкритій папці сайту і який потрапляє в репозиторій. Виніси налаштування в окремий файл конфігурації (поза кореневою папкою сайту, якщо хостинг це дозволяє) або у змінні середовища.
  • Додай цей файл у .gitignore, щоб випадково не опублікувати його в репозиторії.
  • Для різних середовищ (локального й бойового) тримай різні паролі.
<?php
// config.php (поза відкритою папкою)
return [
    'host' => 'localhost',
    'name' => 'mysite',
    'user' => 'mysite_user',
    'pass' => 'надійний_пароль',
];
<?php
$config = require __DIR__ . '/config.php';
$dsn = "mysql:host={$config['host']};dbname={$config['name']};charset=utf8mb4";
$pdo = new PDO($dsn, $config['user'], $config['pass'], $options);

Перший запит

Щоб переконатись, що все працює, виконай простий запит:

<?php
$version = $pdo->query('SELECT VERSION()')->fetchColumn();
echo 'Підключено, версія MySQL: ' . $version;

Якщо побачив версію сервера, з'єднання працює. Далі робота з даними: вибірка рядків, вставка й оновлення. Усе це робиться через підготовлені запити (prepare та execute), про них я напишу окремо. Не склеюй SQL із даних, які прийшли від користувача: саме так виникають SQL-ін'єкції.

Типові помилки підключення

  • Access denied for user – хибний логін чи пароль, або в користувача немає прав на цю базу.
  • Unknown database – такої бази немає: перевір назву в phpMyAdmin.
  • could not find driver – не ввімкнено розширення pdo_mysql у php.ini.
  • Connection refused – сервер MySQL не запущений або вказано хибну адресу чи порт.

Що далі

Далі логічно навчитись безпечно виконувати запити. А поки що, якщо працюєш із WordPress, зазирни в розбір об'єкта wpdb: він надає схожий інтерфейс до тієї самої бази, але вже у звичному середовищі. Керувати базою зручно через phpMyAdmin, а для налагодження зазирни в статтю про показ помилок у PHP. Локальний сервер для практики підніме Laragon.

Більше про це – за позначками MySQL, PHP та Веб-розробка.

А ти досі користуєшся mysqli чи вже перейшов/ла на PDO? Розкажи в коментарях 🙂