Статья

📘 Глава 15. Создание Database-класса на PDO

Настало время структурировать код — мы вынесем работу с базой данных в отдельный Database-класс. Это важный шаг к чистому и масштабируемому коду.


🎯 Цель

Сделать класс Database, который:

  • подключается к MySQL с помощью PDO

  • предоставляет методы query(), execute(), fetchAll(), fetchOne()

  • обрабатывает ошибки


📁 Структура проекта

guestbook/
├── index.php
├── Database.php
└── .env (необязательно)

🧱 Database.php — базовый класс

<?php

class Database {
    private PDO $pdo;

    public function __construct(string $host, string $dbname, string $user, string $password) {
        $dsn = "mysql:host=$host;dbname=$dbname;charset=utf8mb4";
        try {
            $this->pdo = new PDO($dsn, $user, $password);
            $this->pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
        } catch (PDOException $e) {
            die("DB connection failed: " . $e->getMessage());
        }
    }

    public function query(string $sql, array $params = []): PDOStatement {
        $stmt = $this->pdo->prepare($sql);
        $stmt->execute($params);
        return $stmt;
    }

    public function fetchAll(string $sql, array $params = []): array {
        return $this->query($sql, $params)->fetchAll(PDO::FETCH_ASSOC);
    }

    public function fetchOne(string $sql, array $params = []): array|false {
        return $this->query($sql, $params)->fetch(PDO::FETCH_ASSOC);
    }

    public function execute(string $sql, array $params = []): bool {
        return $this->query($sql, $params)->rowCount() > 0;
    }
}

📄 index.php — использование класса

<?php
require_once 'Database.php';

$db = new Database("localhost", "guestbook", "root", "password");

if ($_SERVER["REQUEST_METHOD"] === "POST") {
    $author = trim($_POST["author"]);
    $text = trim($_POST["text"]);

    if ($author && $text) {
        $db->execute(
            "INSERT INTO messages (author, text) VALUES (?, ?)",
            [$author, $text]
        );
        header("Location: " . $_SERVER["PHP_SELF"]);
        exit;
    } else {
        echo "Please fill in both fields.";
    }
}
?>

<form method="post">
    <input type="text" name="author" placeholder="Your name">
    <br>
    <textarea name="text" placeholder="Your message"></textarea>
    <br>
    <button type="submit">Send</button>
</form>

<hr>

<?php
$messages = $db->fetchAll("SELECT * FROM messages ORDER BY created_at DESC");

foreach ($messages as $message) {
    echo "<p><strong>" . htmlspecialchars($message["author"]) . ":</strong> "
        . htmlspecialchars($message["text"]) . "</p>";
}
?>

✅ Что ты изучил

  • Инкапсуляция подключения в отдельном классе

  • Удобные обёртки для query, fetchAll, fetchOne, execute

  • Чистый и переиспользуемый код


В следующей главе мы создадим MVC-структуру на чистом PHP — отделим логику, представление и контроллер.

PHP
Для ответа вы можете авторизоваться