OpenXE/classes/Modules/SuperSearch/SearchIndex/Provider/AbstractBulkIndexDatabaseProvider.php

189 lines
4.9 KiB
PHP
Raw Normal View History

2021-05-21 08:49:41 +02:00
<?php
namespace Xentral\Modules\SuperSearch\SearchIndex\Provider;
use Closure;
use DateTimeInterface;
use Exception;
use Xentral\Components\Database\Database;
use Xentral\Components\Database\SqlQuery\SelectQuery;
use Xentral\Modules\SuperSearch\Exception\FormatterFailureException;
use Xentral\Modules\SuperSearch\Exception\InvalidReturnTypeException;
use Xentral\Modules\SuperSearch\Exception\SuperSearchExceptionInterface;
use Xentral\Modules\SuperSearch\SearchIndex\Collection\ItemFormatterCollection;
use Xentral\Modules\SuperSearch\SearchIndex\Data\IndexIdentifier;
use Xentral\Modules\SuperSearch\SearchIndex\Data\IndexItem;
abstract class AbstractBulkIndexDatabaseProvider implements
SearchIndexProviderInterface,
BulkIndexProviderInterface,
ItemIndexProviderInterface,
DiffIndexProviderInterface
{
/** @var Database $db */
protected $db;
/**
* @param Database $database
*/
public function __construct(Database $database)
{
$this->db = $database;
}
/**
* @param SelectQuery $query
*
* @return void
*/
abstract protected function configureBaseQuery(SelectQuery $query);
/**
* @param SelectQuery $baseQuery
* @param int|string $indexId
*
* @return void
*/
abstract protected function configureItemQuery(SelectQuery $baseQuery, $indexId);
/**
* @param SelectQuery $baseQuery
* @param DateTimeInterface $since
*
* @return void
*/
abstract protected function configureSinceQuery(SelectQuery $baseQuery, DateTimeInterface $since);
/**
* @param SelectQuery $baseQuery
*
* @return void
*/
abstract protected function configureCountQuery(SelectQuery $baseQuery);
/**
* @return Closure
*/
abstract protected function getRowFormatter();
/**
* @return int Anzahl der IndexItems die in einem Durchlauf geschrieben werden
*/
public function getBulkSize()
{
return 20000;
}
/**
* @param IndexIdentifier $identifier
*
* @throws InvalidReturnTypeException
*
* @return IndexItem|null
*/
public function getItem(IndexIdentifier $identifier)
{
$select = $this->db->select();
$this->configureBaseQuery($select);
$this->configureItemQuery($select, $identifier->getId());
$row = $this->db->fetchRow(
$select->getStatement(),
$select->getBindValues()
);
if (empty($row)) {
return null;
}
try {
// Formatter aufrufen
$formatter = $this->getRowFormatter();
$item = $formatter($row);
} catch (SuperSearchExceptionInterface $exception) {
throw new FormatterFailureException(
sprintf('Formatter failed. Row data: %s', var_export($row, true)),
$exception->getCode(),
$exception
);
}
// Prüfen ob Formatter den richtigen Typ zurückliefert
if (!$item instanceof IndexItem) {
$itemType = gettype($item);
if ($itemType === 'object') {
$itemType = get_class($item);
}
throw new InvalidReturnTypeException(sprintf(
'"%s::getRowFormatter()" returned invalid type. Required type "%s". Returned type "%s".',
get_class($this),
IndexItem::class,
$itemType
));
}
return $item;
}
/**
* @inheritDoc
* @throws Exception
*/
public function getItemsSince(DateTimeInterface $since)
{
$select = $this->db->select();
$this->configureBaseQuery($select);
$this->configureSinceQuery($select, $since);
$callback = $this->getRowFormatter();
$data = $this->db->fetchAll(
$select->getStatement(),
$select->getBindValues()
);
return new ItemFormatterCollection($data, $callback);
}
/**
* @inheritDoc
*/
public function getTotalCount()
{
$select = $this->db->select();
$this->configureBaseQuery($select);
$select->resetCols();
$this->configureCountQuery($select);
return (int)$this->db->fetchValue(
$select->getStatement(),
$select->getBindValues()
);
}
/**
* @param int $offset
* @param int $count
*
* @throws InvalidReturnTypeException
* @throws Exception
*
* @return ItemFormatterCollection
*/
public function getBulkItems($offset, $count)
{
$select = $this->db->select();
$this->configureBaseQuery($select);
$select->offset($offset);
$select->limit($count);
$callback = $this->getRowFormatter();
$data = $this->db->fetchAll(
$select->getStatement(),
$select->getBindValues()
);
return new ItemFormatterCollection($data, $callback);
}
}