121 lines
5.3 KiB
PHP
121 lines
5.3 KiB
PHP
<?php
|
||
|
||
/**
|
||
* @noinspection SqlNoDataSourceInspection
|
||
*/
|
||
|
||
namespace goodboyalex\php_db_components_pack\traits\Database;
|
||
|
||
use Exception;
|
||
use goodboyalex\php_db_components_pack\classes\ConditionBuilder;
|
||
use PDO;
|
||
|
||
/**
|
||
* Трейт для работы с получением данных из базы данных.
|
||
*
|
||
* @author Александр Бабаев
|
||
* @package php_components_pack
|
||
* @version 1.0
|
||
* @since 1.0
|
||
* @see PDO
|
||
*/
|
||
trait DatabaseGet
|
||
{
|
||
/**
|
||
* Получает первую строку в массиве данных, удовлетворяющую выборке
|
||
*
|
||
* @param string $table Имя таблицы
|
||
* @param array $columns Колонки, которые нужно включить в запрос
|
||
* @param ConditionBuilder $where Параметры выборки
|
||
*
|
||
* @return false|array Строка в формате массива или false в случае ошибки
|
||
*
|
||
* @see Query
|
||
* @see QueryFirst
|
||
* @see QueryLast
|
||
* @see QueryScalar
|
||
* @see GetRows
|
||
*/
|
||
public function GetRowColumns (string $table, array $columns, ConditionBuilder $where): false|array
|
||
{
|
||
// Задаю массив параметров
|
||
$params = [];
|
||
|
||
// Получаю SQL запрос
|
||
$sql = $this->PrepareSQLForRowsQuery($table, $columns, $where, $params);
|
||
|
||
// Получаю строку на основании запроса
|
||
return $this->QueryScalar($sql, $params);
|
||
}
|
||
|
||
/**
|
||
* Извлекает одну запись из базы данных и создает соответствующий объект класса
|
||
*
|
||
* @param string $table Название таблицы
|
||
* @param ConditionBuilder $condition Условия выборки
|
||
* @param string $className Полное имя класса, реализуемого интерфейсом IDBItem
|
||
*
|
||
* @return object Заполненный объект класса
|
||
*/
|
||
public function GetRow (string $table, ConditionBuilder $condition, string $className): object
|
||
{
|
||
try {
|
||
// Строим условие WHERE для SQL-запроса
|
||
$whereClause = $condition->Build();
|
||
|
||
// Формируем SQL-запрос
|
||
$sql = "SELECT * FROM $table WHERE $whereClause LIMIT 1;";
|
||
|
||
// Подготовленное выражение
|
||
$stmt = $this->pdo->prepare($sql);
|
||
|
||
// Присваивание параметров
|
||
foreach ($params as $col => $val) {
|
||
$stmt->bindParam(":$col", $val);
|
||
}
|
||
|
||
// Выполнение запроса
|
||
$stmt->execute();
|
||
|
||
// Получаем первую строку результатов
|
||
$row = $stmt->fetch(PDO::FETCH_ASSOC);
|
||
|
||
if (!$row) {
|
||
throw new Exception("No data found with the given conditions.");
|
||
}
|
||
|
||
// Создание объекта желаемого класса
|
||
$obj = new $className();
|
||
|
||
// Заполняем поля объекта соответствующими значениями из БД
|
||
foreach ($row as $column => $value) {
|
||
// Анализируем свойства класса и находим соответствующее свойство
|
||
$properties = (new ReflectionClass($obj))->getProperties(ReflectionProperty::IS_PUBLIC);
|
||
foreach ($properties as $prop) {
|
||
// Проверяем, соответствует ли данное свойство указанному полю
|
||
$attributes = $prop->getAttributes(FieldName::class);
|
||
if ($attributes && $attributes[0]->getArguments()['name'] === $column) {
|
||
// Применяем процедуру конвертации (если указана)
|
||
$convertAttrs = $prop->getAttributes(ConvertToDB::class);
|
||
if ($convertAttrs) {
|
||
$converter = $convertAttrs[0]->getArguments()['fromDb'];
|
||
if ($converter !== null) {
|
||
$value = call_user_func($converter, $value);
|
||
}
|
||
}
|
||
|
||
// Устанавливаем значение свойства
|
||
$obj->{$prop->getName()} = $value;
|
||
break;
|
||
}
|
||
}
|
||
}
|
||
|
||
return $obj;
|
||
}
|
||
catch (\PDOException|\Exception $e) {
|
||
error_log("Error fetching data: " . $e->getMessage());
|
||
return null;
|
||
}
|
||
}
|
||
} |