Таблицы и записи
ORM — часть фреймворка, которая позволяет работать с базой данных через объекты PHP вместо запросов SQL. В CakePHP у каждой таблицы два класса: класс таблицы выполняет запросы и сохраняет данные, класс записи представляет одну строку таблицы.
Где лежат
| Класс | Файл | За что отвечает |
|---|---|---|
ArticlesTable | src/Model/Table/ArticlesTable.php | Поиск, сохранение, удаление |
Article | src/Model/Entity/Article.php | Одна статья и её поля |
Создание
bin/cake bake model ArticlesКоманда читает столбцы таблицы articles из базы и создаёт оба файла. Таблица должна уже существовать — её создала миграция.
Класс таблицы
// src/Model/Table/ArticlesTable.php
namespace App\Model\Table;
use Cake\ORM\Table;
class ArticlesTable extends Table
{
public function initialize(array $config): void
{
parent::initialize($config);
$this->addBehavior('Timestamp');
}
}Столбцы перечислять не нужно — ORM узнаёт их из базы. Строка addBehavior('Timestamp') поручает фреймворку заполнять created и modified. Генератор добавит в файл ещё и правила проверки — о них отдельный урок.
Класс записи
// src/Model/Entity/Article.php
namespace App\Model\Entity;
use Cake\ORM\Entity;
class Article extends Entity
{
protected array $_accessible = [
'title' => true,
'body' => true,
'published' => true,
];
}$_accessible перечисляет поля, которые разрешено заполнять данными формы. Столбцы доступны как свойства: $article->title.
Использование в контроллере
В ArticlesController таблица доступна как $this->Articles — фреймворк находит её по имени контроллера:
// src/Controller/ArticlesController.php
public function index(): void
{
$articles = $this->Articles->find()->all();
$this->set(compact('articles'));
}<ul>
<?php foreach ($articles as $article): ?>
<li><?= h($article->title) ?></li>
<?php endforeach; ?>
</ul>Откройте /articles — появятся заголовки статей, добавленных сидом. Каждый элемент списка — объект класса Article.
Таблица в другом месте
В чужом контроллере или в команде таблицу получают по имени:
$articles = $this->fetchTable('Articles');Вычисляемое поле
В классе записи можно описать поле, которого нет в таблице:
// src/Model/Entity/Article.php
protected function _getExcerpt(): string
{
return mb_substr($this->body, 0, 100) . '…';
}Метод с приставкой _get превращается в свойство: $article->excerpt вернёт первые сто символов текста.
Частая ошибка
Сохраняет и удаляет таблица, а не запись: метода $article->save() не существует. Правильный вызов — $this->Articles->save($article). Запись хранит данные, таблица работает с базой.