Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fixing some bugs in Emby Server and general code improvements #4

Merged
merged 7 commits into from
Feb 11, 2022
8 changes: 5 additions & 3 deletions config/config.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,11 @@
return (function () {
$config = [
'name' => 'WatchState',
'version' => 'v0.0.1-alpha',
'version' => 'v0.0.2',
'tz' => null,
'path' => fixPath(env('WS_DATA_PATH', fn() => realpath(__DIR__ . DS . '..' . DS . 'var'))),
'path' => fixPath(
env('WS_DATA_PATH', fn() => env('IN_DOCKER') ? '/config' : realpath(__DIR__ . DS . '..' . DS . 'var'))
),
];

$config['storage'] = [
Expand Down Expand Up @@ -105,8 +107,8 @@

$config['supported'] = [
'plex' => PlexServer::class,
'emby' => EmbyServer::class,
'jellyfin' => JellyfinServer::class,
'emby' => EmbyServer::class
];

$config['servers'] = [];
Expand Down
2 changes: 1 addition & 1 deletion console
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ if (!defined('DS')) {
}

if (!defined('ROOT_PATH')) {
define('ROOT_PATH', __DIR__);
define('ROOT_PATH', realpath(__DIR__));
}

set_error_handler(function (int $number, mixed $error, mixed $file, int $line) {
Expand Down
5 changes: 3 additions & 2 deletions public/index.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,8 @@
use Psr\Log\LoggerInterface;

error_reporting(E_ALL);
ini_set('display_errors', 'On');
ini_set('error_reporting', 'On');
ini_set('display_errors', 'Off');

if (!defined('BASE_MEMORY')) {
define('BASE_MEMORY', memory_get_usage());
Expand All @@ -29,7 +30,7 @@
}

if (!defined('ROOT_PATH')) {
define('ROOT_PATH', __DIR__ . '..' . DS);
define('ROOT_PATH', realpath(__DIR__ . '..' . DS));
}

set_error_handler(function (int $number, mixed $error, mixed $file, int $line) {
Expand Down
12 changes: 3 additions & 9 deletions src/Commands/Config/DumpCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,19 +22,13 @@ class DumpCommand extends Command
protected function configure(): void
{
$this->setName('config:dump')
->setDescription('Dump configs to customize.')
->addOption(
'location',
'l',
InputOption::VALUE_OPTIONAL,
'Path to config dir.',
Config::get('path'),
)
->setDescription('Create config files.')
->addOption('location', 'l', InputOption::VALUE_OPTIONAL, 'Path to config dir.', Config::get('path'))
->addOption('override', 'w', InputOption::VALUE_NONE, 'Override existing file.')
->addArgument(
'type',
InputArgument::REQUIRED,
sprintf('Config to dump. Can be one of ( %s )', implode(' or ', array_keys(self::$configs)))
sprintf('Config type to create. Can be one of ( %s )', implode(' or ', array_keys(self::$configs)))
);
}

Expand Down
12 changes: 2 additions & 10 deletions src/Commands/Config/GenerateCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ protected function configure(): void
{
$this->setName('config:generate')
->setDescription('Generate API key for webhook.')
->addOption('regenerate', 'w', InputOption::VALUE_NONE, 'Regenerate the API key');
->addOption('regenerate', 'w', InputOption::VALUE_NONE, 'Regenerate the API key.');
}

/**
Expand All @@ -37,20 +37,12 @@ protected function runCommand(InputInterface $input, OutputInterface $output): i
}
}

$randomKey = $this->generateHash();
$randomKey = bin2hex(random_bytes(16));

$output->writeln(sprintf('<info>Your Webhook API key is: %s</info>', $randomKey));

file_put_contents($config, Yaml::dump(ag_set($yaml, 'webhook.apikey', $randomKey), 8, 2));

return self::SUCCESS;
}

/**
* @throws Exception
*/
private function generateHash(): string
{
return bin2hex(random_bytes(16));
}
}
6 changes: 3 additions & 3 deletions src/Commands/Config/PHPCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,11 @@ final class PHPCommand extends Command
protected function configure(): void
{
$this->setName('config:php')
->setDescription('Generate PHP Config')
->addOption('fpm', null, InputOption::VALUE_NONE, 'Generate FPM Config.');
->setDescription('Generate php config.')
->addOption('fpm', null, InputOption::VALUE_NONE, 'Generate php-fpm config.');
}

protected function execute(InputInterface $input, OutputInterface $output): int
protected function runCommand(InputInterface $input, OutputInterface $output): int
{
return $input->getOption('fpm') ? $this->makeFPM($output) : $this->makeConfig($output);
}
Expand Down
17 changes: 4 additions & 13 deletions src/Commands/State/ExportCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,6 @@
use Symfony\Component\Yaml\Yaml;
use Throwable;

use function ag;
use function makeDate;

class ExportCommand extends Command
{
public function __construct(private ExportInterface $mapper, private Request $http, private LoggerInterface $logger)
Expand All @@ -42,21 +39,15 @@ protected function configure(): void
{
$this->setName('state:export')
->setDescription('Export watch state to servers.')
->addOption(
'read-mapper',
null,
InputOption::VALUE_OPTIONAL,
'Shows what kind of mapper configured.',
$this->mapper::class
)
->addOption('redirect-logger', 'r', InputOption::VALUE_NONE, 'Redirect logger to stderr.')
->addOption('memory-usage', 'm', InputOption::VALUE_NONE, 'Display memory usage.')
->addOption('read-mapper', null, InputOption::VALUE_OPTIONAL, 'Configured mapper.', $this->mapper::class)
->addOption('redirect-logger', 'r', InputOption::VALUE_NONE, 'Redirect logger to stdout.')
->addOption('memory-usage', 'm', InputOption::VALUE_NONE, 'Show memory usage.')
->addOption('force-full', 'f', InputOption::VALUE_NONE, 'Force full export.')
->addOption(
'concurrency',
null,
InputOption::VALUE_OPTIONAL,
'How many Requests to send.',
'How many parallel requests to send.',
(int)Config::get('request.export.concurrency')
)
->addOption(
Expand Down
17 changes: 5 additions & 12 deletions src/Commands/State/ImportCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,6 @@
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Yaml\Yaml;

use function ag;
use function makeDate;

class ImportCommand extends Command
{
public function __construct(private ImportInterface $mapper, private LoggerInterface $logger)
Expand All @@ -38,15 +35,9 @@ protected function configure(): void
{
$this->setName('state:import')
->setDescription('Import watch state from servers.')
->addOption(
'read-mapper',
null,
InputOption::VALUE_OPTIONAL,
'Shows what kind of mapper configured.',
$this->mapper::class
)
->addOption('redirect-logger', 'r', InputOption::VALUE_NONE, 'Redirect logger to stderr.')
->addOption('memory-usage', 'm', InputOption::VALUE_NONE, 'Display memory usage.')
->addOption('read-mapper', null, InputOption::VALUE_OPTIONAL, 'Configured Mapper.', $this->mapper::class)
->addOption('redirect-logger', 'r', InputOption::VALUE_NONE, 'Redirect logger to stdout.')
->addOption('memory-usage', 'm', InputOption::VALUE_NONE, 'Show memory usage.')
->addOption('force-full', 'f', InputOption::VALUE_NONE, 'Force full import.')
->addOption(
'servers-filter',
Expand Down Expand Up @@ -181,7 +172,9 @@ protected function runCommand(InputInterface $input, OutputInterface $output): i
Utils::settle($promises)->wait();
$this->logger->notice(sprintf('Finished waiting on (%d) HTTP Requests.', count($promises)));

$this->logger->notice(sprintf('Committing (%d) Changes.', count($this->mapper)));
$operations = $this->mapper->commit();
$this->logger->notice('Finished Committing the changes.');

if ($input->getOption('stats-show')) {
Data::add('operations', 'stats', $operations);
Expand Down
2 changes: 1 addition & 1 deletion src/Commands/Storage/MaintenanceCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ protected function configure(): void
->setDescription('Run maintenance tasks on storage backend.');
}

protected function execute(InputInterface $input, OutputInterface $output): int
protected function runCommand(InputInterface $input, OutputInterface $output): int
{
$this->storage->maintenance($input, $output);

Expand Down
2 changes: 1 addition & 1 deletion src/Commands/Storage/MakeCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ protected function configure(): void
$this->setName('storage:make')
->setDescription('Create Storage backend migration.')
->addOption('extra', null, InputOption::VALUE_OPTIONAL, 'Extra options.', null)
->addArgument('name', InputArgument::REQUIRED, 'Migration name');
->addArgument('name', InputArgument::REQUIRED, 'Migration name.');
}

protected function runCommand(InputInterface $input, OutputInterface $output): int
Expand Down
4 changes: 2 additions & 2 deletions src/Commands/Storage/MigrationsCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@ protected function configure(): void
{
$this->setName('storage:migrations')
->setDescription('Update storage backend schema.')
->addOption('extra', null, InputOption::VALUE_OPTIONAL, 'Extra options', null)
->addOption('fresh', 'f', InputOption::VALUE_NONE, 'Start migrations from start')
->addOption('extra', null, InputOption::VALUE_OPTIONAL, 'Extra options.', null)
->addOption('fresh', 'f', InputOption::VALUE_NONE, 'Start migrations from start.')
->addArgument('direction', InputArgument::OPTIONAL, 'Migrations path (up/down).', 'up');
}

Expand Down
4 changes: 2 additions & 2 deletions src/Libs/KernelConsole.php
Original file line number Diff line number Diff line change
Expand Up @@ -131,9 +131,9 @@ public function runConsole(): void
public function runHttp(
Closure $fn,
ServerRequestInterface|null $request = null,
EmitterInterface|null $emit = null
EmitterInterface|null $emitter = null
): void {
$emitter = $emit ?? new SapiEmitter();
$emitter = $emitter ?? new SapiEmitter();
$request = $request ?? ServerRequestFactory::fromGlobals();

try {
Expand Down
7 changes: 6 additions & 1 deletion src/Libs/Mappers/Import/DirectMapper.php
Original file line number Diff line number Diff line change
Expand Up @@ -104,11 +104,16 @@ public function has(StateEntity $entity): bool

public function remove(StateEntity $entity): bool
{
return null !== $this->storage->get($entity);
return $this->storage->remove($entity);
}

public function reset(): self
{
return $this;
}

public function count(): int
{
return 0;
}
}
5 changes: 5 additions & 0 deletions src/Libs/Mappers/Import/MemoryMapper.php
Original file line number Diff line number Diff line change
Expand Up @@ -234,4 +234,9 @@ public function reset(): self

return $this;
}

public function count(): int
{
return count($this->changed);
}
}
2 changes: 1 addition & 1 deletion src/Libs/Mappers/ImportInterface.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
use DateTimeImmutable;
use Psr\Log\LoggerInterface;

interface ImportInterface
interface ImportInterface extends \Countable
{
/**
* Initiate Mapper.
Expand Down
7 changes: 3 additions & 4 deletions src/Libs/Servers/EmbyServer.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ public static function parseWebhook(ServerRequestInterface $request): StateEntit
$type = ag($json, 'Item.Type', 'not_found');

if (true === Config::get('webhook.debug')) {
saveWebhookPayload($request, "jellyfin.{$via}.{$event}", $json);
saveWebhookPayload($request, "emby.{$via}.{$event}", $json);
}

if (null === $type || !in_array($type, self::WEBHOOK_ALLOWED_TYPES)) {
Expand Down Expand Up @@ -93,9 +93,9 @@ public static function parseWebhook(ServerRequestInterface $request): StateEntit
];
}

if ('markplayed' === $event || 'playback.scrobble' === $event) {
if ('item.markplayed' === $event || 'playback.scrobble' === $event) {
$isWatched = 1;
} elseif ('markunplayed' === $event) {
} elseif ('item.markunplayed' === $event) {
$isWatched = 0;
} else {
$isWatched = (int)(bool)ag($json, 'Item.Played', ag($json, 'Item.PlayedToCompletion', 0));
Expand All @@ -111,5 +111,4 @@ public static function parseWebhook(ServerRequestInterface $request): StateEntit

return new StateEntity($row);
}

}
27 changes: 18 additions & 9 deletions src/Libs/Storage/PDO/PDOMigrations.php
Original file line number Diff line number Diff line change
Expand Up @@ -17,15 +17,13 @@ final class PDOMigrations
{
private string $path;
private string $versionFile;
private string $driver;

public function __construct(private PDO $pdo)
{
$this->path = __DIR__ . DS . 'Migrations';
$this->versionFile = Config::get('path') . DS . 'db' . DS . 'pdo_migrations_version';

if (!file_exists($this->versionFile)) {
$this->setVersion(0);
}
$this->driver = $this->getDriver();
}

public function up(InputInterface $input, OutputInterface $output): int
Expand Down Expand Up @@ -104,7 +102,7 @@ public function make(string $name, OutputInterface $output): string
{
$name = str_replace(chr(040), '_', $name);

$fileName = sprintf('%s_%d_%s.sql', $this->getDriver(), time(), $name);
$fileName = sprintf('%s_%d_%s.sql', $this->driver, time(), $name);

$file = $this->path . DS . $fileName;

Expand Down Expand Up @@ -138,12 +136,24 @@ public function runMaintenance(): int|bool

private function getVersion(): int
{
return (int)file_get_contents($this->versionFile);
if ('sqlite' === $this->driver) {
return (int)$this->pdo->query('PRAGMA user_version')->fetchColumn();
}

if (file_exists($this->versionFile)) {
return (int)file_get_contents($this->versionFile);
}

return 0;
}

private function setVersion(int $version): void
{
file_put_contents($this->versionFile, $version);
if ('sqlite' === $this->driver) {
$this->pdo->exec('PRAGMA user_version = ' . $version);
} else {
file_put_contents($this->versionFile, $version);
}
}

private function getDriver(): string
Expand All @@ -160,7 +170,6 @@ private function getDriver(): string
private function parseFiles(): array
{
$migrations = [];
$driver = $this->getDriver();

foreach ((array)glob($this->path . DS . '*.sql') as $file) {
if (!is_string($file) || false === ($f = realpath($file))) {
Expand All @@ -174,7 +183,7 @@ private function parseFiles(): array
PREG_SPLIT_NO_EMPTY | PREG_SPLIT_DELIM_CAPTURE
);

if ($type !== $driver) {
if ($type !== $this->driver) {
continue;
}

Expand Down