Строим свою CMS на PHP и MySQL. Часть 7
В предыдущем уроке серии мы начали процесс добавления функционала категорий в нашу простую CMS. Рассмотрим, что нужно поменять в коде классов для реализации задуманных изменений.
Создание класса Category
Также как ранее мы создавали класс Article для управления хранением и выводом статей, нам нужно построить класс Category для решения таких же задач с категориями.
В папке cms имеется каталог classes. В каталоге classes создаем новый файл Category.php и копируем в него следующий код:
<?php
/**
* Класс для обработки категорий статей
*/
class Category
{
// Свойства
/**
* @var int ID категории из базы данных
*/
public $id = null;
/**
* @var string Название категории
*/
public $name = null;
/**
* @var string Короткое описание категории
*/
public $description = null;
/**
* Устанавливаем свойства объекта с использованием значений в передаваемом массиве
*
* @param assoc Значения свойств
*/
public function __construct( $data=array() ) {
if ( isset( $data['id'] ) ) $this->id = (int) $data['id'];
if ( isset( $data['name'] ) ) $this->name = preg_replace ( "/[^\.\,\-\_\'\"\@\?\!\:\$ a-zA-Z0-9()]/", "", $data['name'] );
if ( isset( $data['description'] ) ) $this->description = preg_replace ( "/[^\.\,\-\_\'\"\@\?\!\:\$ a-zA-Z0-9()]/", "", $data['description'] );
}
/**
* Устанавливаем свойства объекта с использованием значений из формы редактирования
*
* @param assoc Значения из формы редактирования
*/
public function storeFormValues ( $params ) {
// Store all the parameters
$this->__construct( $params );
}
/**
* Возвращаем объект Category, соответствующий заданному ID
*
* @param int ID категории
* @return Category|false Объект Category object или false, если запись не была найдена или в случае другой ошибки
*/
public static function getById( $id ) {
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "SELECT * FROM categories WHERE id = :id";
$st = $conn->prepare( $sql );
$st->bindValue( ":id", $id, PDO::PARAM_INT );
$st->execute();
$row = $st->fetch();
$conn = null;
if ( $row ) return new Category( $row );
}
/**
* Возвращаем все (или диапазон) объектов Category из базы данных
*
* @param int Optional Количество возвращаемых строк (по умолчаниюt = all)
* @param string Optional Столбец, по которому сортируются категории(по умолчанию = "name ASC")
* @return Array|false Двух элементный массив: results => массив с объектами Category; totalRows => общее количество категорий
*/
public static function getList( $numRows=1000000, $order="name ASC" ) {
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "SELECT SQL_CALC_FOUND_ROWS * FROM categories
ORDER BY " . mysql_escape_string($order) . " LIMIT :numRows";
$st = $conn->prepare( $sql );
$st->bindValue( ":numRows", $numRows, PDO::PARAM_INT );
$st->execute();
$list = array();
while ( $row = $st->fetch() ) {
$category = new Category( $row );
$list[] = $category;
}
// Получаем общее количество категорий, которые соответствуют критериям
$sql = "SELECT FOUND_ROWS() AS totalRows";
$totalRows = $conn->query( $sql )->fetch();
$conn = null;
return ( array ( "results" => $list, "totalRows" => $totalRows[0] ) );
}
/**
* Вставляем текущий объект Category в базу данных и устанавливаем его свойство ID.
*/
public function insert() {
// У объекта Category уже есть ID?
if ( !is_null( $this->id ) ) trigger_error ( "Category::insert(): Attempt to insert a Category object that already has its ID property set (to $this->id).", E_USER_ERROR );
// Вставляем категорию
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "INSERT INTO categories ( name, description ) VALUES ( :name, :description )";
$st = $conn->prepare ( $sql );
$st->bindValue( ":name", $this->name, PDO::PARAM_STR );
$st->bindValue( ":description", $this->description, PDO::PARAM_STR );
$st->execute();
$this->id = $conn->lastInsertId();
$conn = null;
}
/**
* Обновляем текущий объект Category в базе данных.
*/
public function update() {
// У объекта Category есть ID?
if ( is_null( $this->id ) ) trigger_error ( "Category::update(): Attempt to update a Category object that does not have its ID property set.", E_USER_ERROR );
// Обновляем категорию
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "UPDATE categories SET name=:name, description=:description WHERE id = :id";
$st = $conn->prepare ( $sql );
$st->bindValue( ":name", $this->name, PDO::PARAM_STR );
$st->bindValue( ":description", $this->description, PDO::PARAM_STR );
$st->bindValue( ":id", $this->id, PDO::PARAM_INT );
$st->execute();
$conn = null;
}
/**
* Удаляем текущий объект Category из базы данных.
*/
public function delete() {
// У объекта Category есть ID?
if ( is_null( $this->id ) ) trigger_error ( "Category::delete(): Attempt to delete a Category object that does not have its ID property set.", E_USER_ERROR );
// Удаляем категорию
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$st = $conn->prepare ( "DELETE FROM categories WHERE id = :id LIMIT 1" );
$st->bindValue( ":id", $this->id, PDO::PARAM_INT );
$st->execute();
$conn = null;
}
}
?>
Данный класс очень похож на класс Article и немного проще. Он содержит три свойства, которые соответствуют полям в таблице categories — id, name и description, конструктор __construct(), который создает новый объект Category. Также класс имеет метод storeFormValues() для сохранения данных из формы редактирования, методы для получения одной категории по ID и списка категорий, а также методов для вставки, обновления и удаления категории в базе данных.
Нам нужно включить новый класс Category в наши файлы кода, чтобы CMS могла получить доступ к нему. Поэтому включаем файл с классом в файл config.phpв папке cms, также как мы включали Article.php:
<?php
ini_set( "display_errors", true );
date_default_timezone_set( "Australia/Sydney" ); // http://www.php.net/manual/en/timezones.php
define( "DB_DSN", "mysql:host=localhost;dbname=cms" );
define( "DB_USERNAME", "username" );
define( "DB_PASSWORD", "password" );
define( "CLASS_PATH", "classes" );
define( "TEMPLATE_PATH", "templates" );
define( "HOMEPAGE_NUM_ARTICLES", 5 );
define( "ADMIN_USERNAME", "admin" );
define( "ADMIN_PASSWORD", "mypass" );
require( CLASS_PATH . "/Article.php" );
require( CLASS_PATH . "/Category.php" );
function handleException( $exception ) {
echo "Sorry, a problem occurred. Please try later.";
error_log( $exception->getMessage() );
}
set_exception_handler( 'handleException' );
?>
Модифицируем Article
Кроме создания нового класса Category нужно также модифицировать класс Article для работы с категориями. Ниже приводится код файла Article.php:
<?php
/**
* Класс для управления статьями
*/
class Article
{
// Свойства
/**
* @var int ID статьи из базы данных
*/
public $id = null;
/**
* @var int Дата публикации статьи
*/
public $publicationDate = null;
/**
* @var int ID категории статьи
*/
public $categoryId = null;
/**
* @var string Полное название статьи
*/
public $title = null;
/**
* @var string Резюме статьи
*/
public $summary = null;
/**
* @var string Содержание HTML статьи
*/
public $content = null;
/**
* Устанавливаем свойства объекта с использованием значений из массива
*
* @param assoc Значения свойств
*/
public function __construct( $data=array() ) {
if ( isset( $data['id'] ) ) $this->id = (int) $data['id'];
if ( isset( $data['publicationDate'] ) ) $this->publicationDate = (int) $data['publicationDate'];
if ( isset( $data['categoryId'] ) ) $this->categoryId = (int) $data['categoryId'];
if ( isset( $data['title'] ) ) $this->title = preg_replace ( "/[^\.\,\-\_\'\"\@\?\!\:\$ a-zA-Z0-9()]/", "", $data['title'] );
if ( isset( $data['summary'] ) ) $this->summary = preg_replace ( "/[^\.\,\-\_\'\"\@\?\!\:\$ a-zA-Z0-9()]/", "", $data['summary'] );
if ( isset( $data['content'] ) ) $this->content = $data['content'];
}
/**
* Устанавливаем свойства объекта с использованием значений из формы
*
* @param assoc Значения из формы
*/
public function storeFormValues ( $params ) {
// Сохраняем все параметры
$this->__construct( $params );
// Разбираем и сохраняем дату публикации
if ( isset($params['publicationDate']) ) {
$publicationDate = explode ( '-', $params['publicationDate'] );
if ( count($publicationDate) == 3 ) {
list ( $y, $m, $d ) = $publicationDate;
$this->publicationDate = mktime ( 0, 0, 0, $m, $d, $y );
}
}
}
/**
* Возвращаем объект Article соответствующий заданному ID
*
* @param int ID статьи
* @return Article|false Объект Article или false, если запись не найдена или в случае другой ошибки
*/
public static function getById( $id ) {
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "SELECT *, UNIX_TIMESTAMP(publicationDate) AS publicationDate FROM articles WHERE id = :id";
$st = $conn->prepare( $sql );
$st->bindValue( ":id", $id, PDO::PARAM_INT );
$st->execute();
$row = $st->fetch();
$conn = null;
if ( $row ) return new Article( $row );
}
/**
* Возвращает все (или диапазон) объекты Article из базы данных
*
* @param int Optional Количество возвращаемых строк (по умолчанию = all)
* @param int Optional Вернуть статьи только из категории с указанным ID
* @param string Optional Столбц, по которому выполняется сортировка статей (по умолчанию = "publicationDate DESC")
* @return Array|false Двух элементный массив: results => массив объектов Article; totalRows => общее количество строк
*/
public static function getList( $numRows=1000000, $categoryId=null, $order="publicationDate DESC" ) {
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$categoryClause = $categoryId ? "WHERE categoryId = :categoryId" : "";
$sql = "SELECT SQL_CALC_FOUND_ROWS *, UNIX_TIMESTAMP(publicationDate) AS publicationDate
FROM articles $categoryClause
ORDER BY " . mysql_escape_string($order) . " LIMIT :numRows";
$st = $conn->prepare( $sql );
$st->bindValue( ":numRows", $numRows, PDO::PARAM_INT );
if ( $categoryId ) $st->bindValue( ":categoryId", $categoryId, PDO::PARAM_INT );
$st->execute();
$list = array();
while ( $row = $st->fetch() ) {
$article = new Article( $row );
$list[] = $article;
}
// Получаем общее количество статей, которые соответствуют критерию
$sql = "SELECT FOUND_ROWS() AS totalRows";
$totalRows = $conn->query( $sql )->fetch();
$conn = null;
return ( array ( "results" => $list, "totalRows" => $totalRows[0] ) );
}
/**
* Вставляем текущий объек Article в базу данных, устанавливаем его ID.
*/
public function insert() {
// Есть уже у объекта Article ID?
if ( !is_null( $this->id ) ) trigger_error ( "Article::insert(): Attempt to insert an Article object that already has its ID property set (to $this->id).", E_USER_ERROR );
// Вставляем статью
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "INSERT INTO articles ( publicationDate, categoryId, title, summary, content ) VALUES ( FROM_UNIXTIME(:publicationDate), :categoryId, :title, :summary, :content )";
$st = $conn->prepare ( $sql );
$st->bindValue( ":publicationDate", $this->publicationDate, PDO::PARAM_INT );
$st->bindValue( ":categoryId", $this->categoryId, PDO::PARAM_INT );
$st->bindValue( ":title", $this->title, PDO::PARAM_STR );
$st->bindValue( ":summary", $this->summary, PDO::PARAM_STR );
$st->bindValue( ":content", $this->content, PDO::PARAM_STR );
$st->execute();
$this->id = $conn->lastInsertId();
$conn = null;
}
/**
* Обновляем текущий объект Article в базе данных.
*/
public function update() {
// У объекта Article есть ID?
if ( is_null( $this->id ) ) trigger_error ( "Article::update(): Attempt to update an Article object that does not have its ID property set.", E_USER_ERROR );
// Обновляем статью
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "UPDATE articles SET publicationDate=FROM_UNIXTIME(:publicationDate), categoryId=:categoryId, title=:title, summary=:summary, content=:content WHERE id = :id";
$st = $conn->prepare ( $sql );
$st->bindValue( ":publicationDate", $this->publicationDate, PDO::PARAM_INT );
$st->bindValue( ":categoryId", $this->categoryId, PDO::PARAM_INT );
$st->bindValue( ":title", $this->title, PDO::PARAM_STR );
$st->bindValue( ":summary", $this->summary, PDO::PARAM_STR );
$st->bindValue( ":content", $this->content, PDO::PARAM_STR );
$st->bindValue( ":id", $this->id, PDO::PARAM_INT );
$st->execute();
$conn = null;
}
/**
* Удаляем текущий объект Article из базы данных
*/
public function delete() {
// У объекта Article есть ID?
if ( is_null( $this->id ) ) trigger_error ( "Article::delete(): Attempt to delete an Article object that does not have its ID property set.", E_USER_ERROR );
// Удаляем объект Article
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$st = $conn->prepare ( "DELETE FROM articles WHERE id = :id LIMIT 1" );
$st->bindValue( ":id", $this->id, PDO::PARAM_INT );
$st->execute();
$conn = null;
}
}
?>
Рассмотрим изменения в классе Article подробно:
- Новое свойство
categoryIdЧтобы установить соответствие статьи и категории мы добавили свойство
categoryIdдля хранения ID категории, которой принадлежит статья. Также мы модифицировали конструктор__construct()для сохранения нового свойстваcategoryIdв только что созданных объектахArticle. - Изменение метода
getList()Первоначальный вариант метода
getList()возвращал все статьи в базе данных (или заданное количество записей). Так как нам нужно, чтобы CMS выводила список статей в определенной категории, модифицируем методgetList()для принятия опционального аргумента$categoryId. Если он задан, то возвращаются статьи только из указанной категории.Если задан
$categoryId, создаем строку$categoryClauseдля выраженияWHERE, чтобы вернуть только те статьи, в которых значение поляcategoryIdсоответствует значениюcategoryId. Затем модифицируем выражения SQLSELECTдля включения переменной$categoryClause. Также добавляем новый вызов к$st->bindValue()для привязки заданного$categoryId. - Изменяем методы
insert()иupdate()Также мы модифицировали методы класса
Articleinsert()иupdate()для работы с новым полемcategoryId. Изменили запросы SQLINSERTиUPDATEв каждом методе, и добавили новые вызовы кbindValue()для передачи свойства$categoryIdв выражения SQL.
В следующем уроке серии мы изменим шаблоны клиентской и серверной частей для работы с категориями.
Источник: http://feedproxy.google.com/~r/ruseller/CdHX/~3/m51GqK2z6a0/lessons.php
|
В предыдущем уроке серии мы начали процесс добавления функционала категорий в нашу простую CMS. Рассмотрим, что нужно поменять в коде классов для реализации задуманных изменений.Создание класса |
РэдЛайн, создание сайта, заказать сайт, разработка сайтов, реклама в Интернете, продвижение, маркетинговые исследования, дизайн студия, веб дизайн, раскрутка сайта, создать сайт компании, сделать сайт, создание сайтов, изготовление сайта, обслуживание сайтов, изготовление сайтов, заказать интернет сайт, создать сайт, изготовить сайт, разработка сайта, web студия, создание веб сайта, поддержка сайта, сайт на заказ, сопровождение сайта, дизайн сайта, сайт под ключ, заказ сайта, реклама сайта, хостинг, регистрация доменов, хабаровск, краснодар, москва, комсомольск |
Дайджест новых статей по интернет-маркетингу на ваш email
Новые статьи и публикации
- 2025-12-23 » API Яндекс Бизнеса: как подключить карточки компании к вашей CRM или ERP-системе
- 2025-12-23 » Как управлять всеми филиалами в Яндекс Картах из одной панели
- 2025-12-23 » От отзыва к продаже: система быстрого ответа и управления репутацией через интеграцию
- 2025-12-23 » Оформление карточки организации в Яндекс Бизнес = Продающее оформление вашей компании на Яндекс Картах
- 2025-12-23 » Из чего складывается стоимость логотипа: разбираем по полочкам
- 2025-12-23 » Как провести ребрендинг логотипа, не потеряв старых клиентов
- 2025-12-23 » Логотип vs. Иконка: Что на самом деле нужно вашему бизнесу?
- 2025-12-23 » Трейд-маркетинг: как продвигать товары в точках продаж
- 2025-12-23 » Подписная модель: стратегия, риски и эффективность
- 2025-12-23 » Чёрный список почтовых серверов: как защитить рассылки от блокировки
- 2025-12-23 » Закон о рекомендательных технологиях: как использовать их легально
- 2025-12-23 » Как управлять жизненным циклом продукта: от запуска до спада
- 2025-12-17 » Почему медленный госсайт — это провал и как это исправить
- 2025-12-17 » Как соответствовать требованиям 152-ФЗ и 210-ФЗ при разработке государственных сайтов
- 2025-12-17 » Интеграция госсайта с внешними системами: от визитки к цифровому сервису
- 2025-12-17 » Введение: Ненужные страницы в индексе — это тихий слив бюджета и позиций
- 2025-12-17 » Продвинутая работа с анкорным профилем: баланс, многоуровневая стратегия и защита от спама
- 2025-12-17 » >Как удержать и повысить продажи после праздников
- 2025-12-17 » Почему сегодня офлайн-данные и SEO — это единая система
- 2025-12-17 » Надёжная доставка кодов входа: каскадная логика, которая защищает конверсию
- 2025-12-11 » Будущее SEO в эпоху ИИ: тренды 2024-2025 и стратегии адаптации
- 2025-12-11 » Техническое SEO 2025: Фундаментальное руководство по созданию безупречного цифрового актива
- 2025-12-11 » 10 устаревших SEO-ошибок, которые мешают росту в 2026 году + чек-лист для срочной проверки сайта
- 2025-12-11 » Навигация типа «хлебные крошки»: современный подход к удобству сайта
- 2025-12-11 » Оптимизация сайтов: как микроразметка Schema.org влияет на видимость и привлечение клиентов
- 2025-12-11 » Вирусы на сайте: как обнаружить, обезвредить и предотвратить угрозу
- 2025-12-11 » Generative Engine Optimization (GEO): как работать с новым типом поиска
- 2025-12-02 » Когда ошибка молчит: как бессмысленные сообщения ломают пользовательский опыт
- 2025-12-02 » 9 лучших бесплатных фотостоков
- 2025-12-02 » UTM-метки: ключевой инструмент аналитики для маркетолога
«Web делает доступным все, для всех, везде и всегда. Если знания - это сила, то сила сейчас находится практически везде». К. Нордстрем, Й. Ридерстрале |
Мы создаем сайты, которые работают! Профессионально обслуживаем и продвигаем их , а также по всей России и ближнему зарубежью с 2006 года!
Как мы работаем
Заявка
Позвоните или оставьте заявку на сайте.
Консультация
Обсуждаем что именно Вам нужно и помогаем определить как это лучше сделать!
Договор
Заключаем договор на оказание услуг, в котором прописаны условия и обязанности обеих сторон.
Выполнение работ
Непосредственно оказание требующихся услуг и работ по вашему заданию.
Поддержка
Сдача выполненых работ, последующие корректировки и поддержка при необходимости.


Мы создаем практически любые сайты от продающих страниц до сложных, высоконагруженных и нестандартных веб приложений! Наши сайты это надежные маркетинговые инструменты для успеха Вашего бизнеса и увеличения вашей прибыли! Мы делаем красивые и максимально эффектные сайты по доступным ценам уже много лет!
Комплексный подход это не просто продвижение сайта, это целый комплекс мероприятий, который определяется целями и задачами поставленными перед сайтом и организацией, которая за этим стоит. Время однобоких методов в продвижении сайтов уже прошло, конкуренция слишком высока, чтобы была возможность расслабиться и получать \ удерживать клиентов из Интернета, просто сделав сайт и не занимаясь им...
Мы оказываем полный комплекс услуг по сопровождению сайта: информационному и техническому обслуживанию и развитию Интернет сайтов.
Контекстная реклама - это эффективный инструмент в интернет маркетинге, целью которого является увеличение продаж. Главный плюс контекстной рекламы заключается в том, что она работает избирательно.