Files
Cloud-CMS/lib/Factory/ConnectorFactory.php

263 lines
8.3 KiB
PHP
Raw Permalink Normal View History

2025-12-02 10:32:59 -05:00
<?php
/*
* Copyright (C) 2024 Xibo Signage Ltd
*
* Xibo - Digital Signage - https://xibosignage.com
*
* This file is part of Xibo.
*
* Xibo is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* Xibo is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with Xibo. If not, see <http://www.gnu.org/licenses/>.
*/
namespace Xibo\Factory;
use Illuminate\Support\Str;
use Psr\Container\ContainerInterface;
use Stash\Interfaces\PoolInterface;
use Xibo\Connector\ConnectorInterface;
use Xibo\Entity\Connector;
use Xibo\Service\ConfigServiceInterface;
use Xibo\Service\JwtServiceInterface;
use Xibo\Service\PlayerActionServiceInterface;
use Xibo\Support\Exception\GeneralException;
use Xibo\Support\Exception\NotFoundException;
/**
* Connector Factory
*/
class ConnectorFactory extends BaseFactory
{
/** @var \Stash\Interfaces\PoolInterface */
private $pool;
/** @var \Xibo\Service\ConfigServiceInterface */
private $config;
/** @var \Xibo\Service\JwtServiceInterface */
private $jwtService;
/** @var \Psr\Container\ContainerInterface */
private $container;
/** @var \Xibo\Service\PlayerActionServiceInterface */
private $playerActionService;
/**
* @param \Stash\Interfaces\PoolInterface $pool
* @param \Xibo\Service\ConfigServiceInterface $config
* @param \Xibo\Service\JwtServiceInterface $jwtService
* @param \Psr\Container\ContainerInterface $container
* @param \Xibo\Service\PlayerActionServiceInterface $playerActionService
*/
public function __construct(
PoolInterface $pool,
ConfigServiceInterface $config,
JwtServiceInterface $jwtService,
PlayerActionServiceInterface $playerActionService,
ContainerInterface $container
) {
$this->pool = $pool;
$this->config = $config;
$this->jwtService = $jwtService;
$this->playerActionService = $playerActionService;
$this->container = $container;
}
/**
* @param Connector $connector
* @return ConnectorInterface
* @throws \Xibo\Support\Exception\NotFoundException|\Xibo\Support\Exception\GeneralException
*/
public function create(Connector $connector): ConnectorInterface
{
// Check to see if this connector class exists
if (!\class_exists($connector->className)) {
throw new NotFoundException(sprintf(__('Class %s does not exist'), $connector->className));
}
// Instantiate it.
$out = new $connector->className();
if (!$out instanceof ConnectorInterface) {
throw new GeneralException('Connector ' . $connector->className . ' must implement ConnectorInterface');
}
return $out
->setFactories($this->container)
->useLogger($this->getLog()->getLoggerInterface())
->useSettings($connector->settings)
->useSettings($this->config->getConnectorSettings($out->getSourceName()), true)
->useHttpOptions($this->config->getGuzzleProxy())
->useJwtService($this->jwtService)
->usePlayerActionService($this->playerActionService)
->usePool($this->pool);
}
/**
* @param int $connectorId
* @return ConnectorInterface
* @throws \Xibo\Support\Exception\NotFoundException|\Xibo\Support\Exception\GeneralException
*/
public function createById(int $connectorId): ConnectorInterface
{
return $this->create($this->getById($connectorId));
}
/**
* @param $connectorId
* @return \Xibo\Entity\Connector
* @throws \Xibo\Support\Exception\NotFoundException
*/
public function getById($connectorId): Connector
{
$connectors = $this->query(['connectorId' => $connectorId]);
if (count($connectors) !== 1) {
throw new NotFoundException(__('Connector not found'));
}
return $connectors[0];
}
/**
* @param $className
* @return \Xibo\Entity\Connector[]
*/
public function getByClassName($className): array
{
return $this->query(['className' => $className]);
}
/**
* @return Connector[]
*/
public function query($filterBy): array
{
$sanitizedFilter = $this->getSanitizer($filterBy);
$entries = [];
$params = [];
$sql = 'SELECT `connectorId`, `className`, `settings`, `isEnabled`, `isVisible` FROM `connectors` WHERE 1 = 1 ';
if ($sanitizedFilter->hasParam('connectorId')) {
$sql .= ' AND connectorId = :connectorId ';
$params['connectorId'] = $sanitizedFilter->getInt('connectorId');
}
if ($sanitizedFilter->hasParam('isEnabled')) {
$sql .= ' AND isEnabled = :isEnabled ';
$params['isEnabled'] = $sanitizedFilter->getCheckbox('isEnabled');
}
if ($sanitizedFilter->hasParam('isVisible')) {
$sql .= ' AND isVisible = :isVisible ';
$params['isVisible'] = $sanitizedFilter->getCheckbox('isVisible');
}
if ($sanitizedFilter->hasParam('className')) {
$sql .= ' AND `className` = :className ';
$params['className'] = $sanitizedFilter->getString('className');
}
foreach ($this->getStore()->select($sql, $params) as $row) {
// Construct the class
$entries[] = $this->hydrate($row);
}
// No paging
$this->_countLast = count($entries);
return $entries;
}
/**
* @param $row
* @return \Xibo\Entity\Connector
*/
private function hydrate($row): Connector
{
$connector = new Connector($this->getStore(), $this->getLog(), $this->getDispatcher());
$connector->hydrate($row, [
'intProperties' => ['isEnabled', 'isVisible']
]);
if (empty($row['settings'])) {
$connector->settings = [];
} else {
$connector->settings = json_decode($row['settings'], true);
}
$connector->isSystem = !Str::contains(strtolower($connector->className), '\\custom\\');
return $connector;
}
/**
* @return Connector[]
*/
public function getUninstalled(): array
{
$connectors = [];
// Any system connectors are installed by default, so we're only concerned here with custom connectors
// which we would expect to me in the custom folder.
foreach (glob(PROJECT_ROOT . '/custom/*.connector') as $file) {
$config = json_decode(file_get_contents($file), true);
if (!is_array($config)) {
$this->getLog()->error('Problem with connector config: '
. json_last_error_msg() . ' ' . var_export($config, true));
continue;
}
$connector = $this->hydrate($config);
// Is this connector already installed?
if (count($this->getByClassName($connector->className)) > 0) {
continue;
}
$connector->connectorId = str_replace([' ', '.'], '-', basename($file));
$connector->isInstalled = false;
$connector->isVisible = 1;
$connector->isEnabled = 0;
if (empty($connector->settings)) {
$connector->settings = [];
}
$connectors[] = $connector;
}
return $connectors;
}
/**
* @param string $id
* @return \Xibo\Entity\Connector
* @throws \Xibo\Support\Exception\NotFoundException
*/
public function getUninstalledById(string $id): Connector
{
$connector = null;
foreach ($this->getUninstalled() as $item) {
if ($item->connectorId === $id) {
$connector = $item;
break;
}
}
if ($connector === null) {
throw new NotFoundException(__('Connector not found'), 'id');
}
return $connector;
}
}