Version 5.1 - All the GraphQL #32

Closed
timw4mail wants to merge 1160 commits from develop into master
17 changed files with 498 additions and 332 deletions
Showing only changes of commit 789af166ae - Show all commits

View File

@ -118,9 +118,9 @@ final class Model
{
$createData = $data['data'];
$mediaId = $this->getMediaIdFromMalId($data['mal_id']);
$createData['id'] = $mediaId;
return $this->listItem->createFull($createData);
}
@ -192,22 +192,22 @@ final class Model
$mediaId = $this->getMediaIdFromMalId($malId, $type);
return $this->getListIdFromMediaId($mediaId);
}
/**
* Get the Anilist media id from its MAL id
* this way is more accurate than getting the list item id
* directly from the MAL id
*/
private function getListIdFromMediaId(string $mediaId)
private function getListIdFromMediaId(string $mediaId): string
{
$config = $this->container->get('config');
$anilistUser = $config->get(['anilist', 'username']);
$info = $this->runQuery('ListItemIdByMediaId', [
'id' => $mediaId,
'userName' => $anilistUser,
]);
/* dump([
'media_id' => $mediaId,
'userName' => $anilistUser,
@ -231,7 +231,7 @@ final class Model
'id' => $malId,
'type' => mb_strtoupper($type),
]);
/* dump([
'mal_id' => $malId,
'response' => $info,

File diff suppressed because it is too large Load Diff

View File

@ -70,17 +70,9 @@ final class Auth {
public function authenticate(string $password): bool
{
$config = $this->container->get('config');
$username = $config->get(['kitsu_username']);
// try
{
$auth = $this->model->authenticate($username, $password);
}
/* catch (Exception $e)
{
return FALSE;
}*/
$username = $config->get('kitsu_username');
$auth = $this->model->authenticate($username, $password);
if (FALSE !== $auth)
{
@ -104,6 +96,7 @@ final class Auth {
$this->segment->set('auth_token', $auth['access_token']);
$this->segment->set('auth_token_expires', $expire_time);
$this->segment->set('refresh_token', $auth['refresh_token']);
return TRUE;
}
@ -119,14 +112,7 @@ final class Auth {
*/
public function reAuthenticate(string $token): bool
{
try
{
$auth = $this->model->reAuthenticate($token);
}
catch (Exception $e)
{
return FALSE;
}
$auth = $this->model->reAuthenticate($token);
if (FALSE !== $auth)
{
@ -186,7 +172,7 @@ final class Auth {
{
$token = $this->segment->get('auth_token', FALSE);
$refreshToken = $this->segment->get('refresh_token', FALSE);
$isExpired = time() > $this->segment->get('auth_token_expires', 0);
$isExpired = time() >= $this->segment->get('auth_token_expires', 0);
// Attempt to re-authenticate with refresh token
if ($isExpired && $refreshToken)

View File

@ -121,11 +121,6 @@ final class Model {
]);
$data = Json::decode(wait($response->getBody()));
if (array_key_exists('access_token', $data))
{
return $data;
}
if (array_key_exists('error', $data))
{
dump($data['error']);
@ -133,6 +128,11 @@ final class Model {
die();
}
if (array_key_exists('access_token', $data))
{
return $data;
}
return FALSE;
}
@ -376,9 +376,7 @@ final class Model {
// Bail out on no data
if (empty($data))
{
$cacheItem->set([]);
$cacheItem->save();
return $cacheItem->get();
return [];
}
$included = JsonAPI::organizeIncludes($data['included']);
@ -638,9 +636,7 @@ final class Model {
// Bail out on no data
if (empty($data) || ( ! array_key_exists('included', $data)))
{
$cacheItem->set([]);
$cacheItem->save();
return $cacheItem->get();
return [];
}
$included = JsonAPI::organizeIncludes($data['included']);

View File

@ -79,7 +79,7 @@ final class Index extends BaseController {
{
$redirectUrl = 'https://anilist.co/api/v2/oauth/authorize?' .
http_build_query([
'client_id' => 271,
'client_id' => $this->config->get(['anilist', 'client_id']),
'response_type' => 'code',
]);
@ -109,6 +109,7 @@ final class Index extends BaseController {
{
$auth = $this->container->get('auth');
$post = $this->request->getParsedBody();
if ($auth->authenticate($post['password']))
{
$this->sessionRedirect();

View File

@ -18,7 +18,7 @@ namespace Aviat\AnimeClient;
use function Aviat\Ion\_dir;
use Aura\Router\Matcher;
use Aura\Router\{Matcher, Rule};
use Aviat\AnimeClient\API\FailedResponseException;
use Aviat\Ion\Di\ContainerInterface;
@ -314,7 +314,7 @@ final class Dispatcher extends RoutingBase {
$params = [];
switch($failure->failedRule) {
case 'Aura\Router\Rule\Allows':
case Rule\Allows::class:
$params = [
'http_code' => 405,
'title' => '405 Method Not Allowed',
@ -322,7 +322,7 @@ final class Dispatcher extends RoutingBase {
];
break;
case 'Aura\Router\Rule\Accepts':
case Rule\Accepts::class:
$params = [
'http_code' => 406,
'title' => '406 Not Acceptable',

View File

@ -42,15 +42,15 @@ class Collection extends DB {
try
{
$this->db = \Query($this->dbConfig['collection']);
$this->db = \Query($this->dbConfig);
}
catch (PDOException $e) {}
// Is database valid? If not, set a flag so the
// app can be run without a valid database
if ($this->dbConfig['collection']['type'] === 'sqlite')
if ($this->dbConfig['type'] === 'sqlite')
{
$dbFileName = $this->dbConfig['collection']['file'];
$dbFileName = $this->dbConfig['file'];
if ($dbFileName !== ':memory:' && file_exists($dbFileName))
{

View File

@ -44,12 +44,6 @@ class RoutingBase {
*/
protected $routes;
/**
* Route configuration options
* @var array
*/
protected $routeConfig;
/**
* Constructor
*
@ -63,20 +57,19 @@ class RoutingBase {
$this->container = $container;
$this->config = $container->get('config');
$this->routes = $this->config->get('routes');
$this->routeConfig = $this->config->get('route_config');
}
/**
* Retrieve the appropriate value for the routing key
*
* @param string $key
* @param string|int|array $key
* @return mixed
*/
public function __get($key)
{
if (array_key_exists($key, $this->routeConfig))
if ($this->config->has($key))
{
return $this->routeConfig[$key];
return $this->config->get($key);
}
}

View File

@ -17,11 +17,10 @@
namespace Aviat\AnimeClient\Types;
use ArrayAccess;
use LogicException;
abstract class AbstractType implements ArrayAccess {
/**
* Populate values for unserializing data
* Populate values for un-serializing data
*
* @param $properties
* @return mixed
@ -87,7 +86,7 @@ abstract class AbstractType implements ArrayAccess {
{
$existing = json_encode($this);
throw new LogicException("Trying to set non-existent property: '$name'. Existing properties: $existing");
throw new UndefinedPropertyException("Trying to set undefined property: '$name'. Existing properties: $existing");
}
$this->$name = $value;
@ -106,7 +105,7 @@ abstract class AbstractType implements ArrayAccess {
return $this->$name;
}
throw new LogicException("Trying to get non-existent property: '$name'");
throw new UndefinedPropertyException("Trying to get undefined property: '$name'");
}
/**

View File

@ -21,9 +21,13 @@ class Config extends AbstractType {
public $anilist;
public $cache;
public $database;
public $route_config;
// Settings in config.toml
public $asset_path; // Path to public folder for urls
public $default_anime_list_path;
public $default_list;
public $default_manga_list_path;
public $default_view_type;
public $kitsu_username;
public $show_anime_collection;
public $show_manga_collection;
@ -34,7 +38,7 @@ class Config extends AbstractType {
public $routes;
// Generated config values
public $asset_dir;
public $asset_dir; // Path to public folder for local files
public $base_config_dir;
public $config_dir;
public $data_cache_path;
@ -43,57 +47,16 @@ class Config extends AbstractType {
public function setAnilist ($data): void
{
$this->anilist = new class($data) extends AbstractType {
public $enabled;
public $client_id;
public $client_secret;
public $redirect_uri;
public $access_token;
public $refresh_token;
public $user_id;
public $username;
};
$this->anilist = new Config\Anilist($data);
}
public function setCache ($data): void
{
$this->cache = new class($data) extends AbstractType {
public $driver;
public $connection;
public $options;
};
$this->cache = new Config\Cache($data);
}
public function setDatabase ($data): void
{
$this->database = new class($data) extends AbstractType {
public $collection;
public function setCollection ($data): void
{
$this->collection = new class($data) extends AbstractType {
public $type;
public $host;
public $user;
public $pass;
public $port;
public $database;
public $file;
};
}
};
}
public function setRoute_config ($data): void
{
$this->route_config = new class($data) extends AbstractType {
public $asset_path;
public $default_list;
public $default_anime_list_path;
public $default_manga_list_path;
};
$this->database = new Config\Database($data);
}
}

View File

@ -0,0 +1,33 @@
<?php declare(strict_types=1);
/**
* Hummingbird Anime List Client
*
* An API client for Kitsu to manage anime and manga watch lists
*
* PHP version 7.1
*
* @package HummingbirdAnimeClient
* @author Timothy J. Warren <tim@timshomepage.net>
* @copyright 2015 - 2018 Timothy J. Warren
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @version 4.1
* @link https://git.timshomepage.net/timw4mail/HummingBirdAnimeClient
*/
namespace Aviat\AnimeClient\Types\Config;
use Aviat\AnimeClient\Types\AbstractType;
class Anilist extends AbstractType {
public $enabled = FALSE;
public $client_id;
public $client_secret;
public $redirect_uri;
public $access_token;
public $refresh_token;
public $user_id;
public $username;
}

View File

@ -0,0 +1,32 @@
<?php declare(strict_types=1);
/**
* Hummingbird Anime List Client
*
* An API client for Kitsu to manage anime and manga watch lists
*
* PHP version 7.1
*
* @package HummingbirdAnimeClient
* @author Timothy J. Warren <tim@timshomepage.net>
* @copyright 2015 - 2018 Timothy J. Warren
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @version 4.1
* @link https://git.timshomepage.net/timw4mail/HummingBirdAnimeClient
*/
namespace Aviat\AnimeClient\Types\Config;
use Aviat\AnimeClient\Types\AbstractType;
class Cache extends AbstractType {
public $driver;
public $connection = [];
public $options = [];
/* public function setConnection($data): void
{
$this->connection = new class($data) extends AbstractType {
};
} */
}

View File

@ -0,0 +1,29 @@
<?php declare(strict_types=1);
/**
* Hummingbird Anime List Client
*
* An API client for Kitsu to manage anime and manga watch lists
*
* PHP version 7.1
*
* @package HummingbirdAnimeClient
* @author Timothy J. Warren <tim@timshomepage.net>
* @copyright 2015 - 2018 Timothy J. Warren
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @version 4.1
* @link https://git.timshomepage.net/timw4mail/HummingBirdAnimeClient
*/
namespace Aviat\AnimeClient\Types\Config;
use Aviat\AnimeClient\Types\AbstractType;
class Database extends AbstractType {
public $type;
public $host;
public $user;
public $pass;
public $port;
public $database;
public $file;
}

View File

@ -0,0 +1,21 @@
<?php declare(strict_types=1);
/**
* Hummingbird Anime List Client
*
* An API client for Kitsu to manage anime and manga watch lists
*
* PHP version 7.1
*
* @package HummingbirdAnimeClient
* @author Timothy J. Warren <tim@timshomepage.net>
* @copyright 2015 - 2018 Timothy J. Warren
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @version 4.1
* @link https://git.timshomepage.net/timw4mail/HummingBirdAnimeClient
*/
namespace Aviat\AnimeClient\Types;
use LogicException;
class UndefinedPropertyException extends LogicException {}

View File

@ -70,7 +70,7 @@ class AnimeClientTestCase extends TestCase {
$APP_DIR = _dir($ROOT_DIR, 'app');
$config_array = [
'asset_path' => '//localhost/assets/',
'asset_path' => '/assets',
'img_cache_path' => _dir(ROOT_DIR, 'public/images'),
'data_cache_path' => _dir(TEST_DATA_DIR, 'cache'),
'cache' => [
@ -99,16 +99,9 @@ class AnimeClientTestCase extends TestCase {
'file' => ':memory:',
]
],
'route_config' => [
'asset_path' => '/assets'
],
'routes' => [
],
'mal' => [
'username' => 'foo',
'password' => 'bar'
]
];
// Set up DI container

View File

@ -51,7 +51,7 @@ class ControllerTest extends AnimeClientTestCase {
public function testControllersSanity()
{
$config = $this->container->get('config');
$config->set(['database', 'collection'], [
$config->set('database', [
'type' => 'sqlite',
'database' => '',
'file' => ":memory:"

View File

@ -98,7 +98,7 @@ class DispatcherTest extends AnimeClientTestCase {
]
],
],
'route_config' => [
'config' => [
'anime_path' => 'anime',
'manga_path' => 'manga',
'default_list' => 'anime'
@ -132,8 +132,8 @@ class DispatcherTest extends AnimeClientTestCase {
]
];
$data['manga_default_routing_anime']['config']['route_config']['default_list'] = 'manga';
$data['manga_default_routing_manga']['config']['route_config']['default_list'] = 'manga';
$data['manga_default_routing_anime']['config']['default_list'] = 'manga';
$data['manga_default_routing_manga']['config']['default_list'] = 'manga';
return $data;
}
@ -167,7 +167,7 @@ class DispatcherTest extends AnimeClientTestCase {
public function testDefaultRoute()
{
$config = [
'route_config' => [
'config' => [
'anime_path' => 'anime',
'manga_path' => 'manga',
'default_anime_list_path' => "watching",
@ -192,11 +192,12 @@ class DispatcherTest extends AnimeClientTestCase {
]
];
$this->expectException(\InvalidArgumentException::class);
$this->doSetUp($config, "/", "localhost");
$this->assertEquals('//localhost/manga/all', $this->urlGenerator->defaultUrl('manga'), "Incorrect default url");
$this->assertEquals('//localhost/anime/watching', $this->urlGenerator->defaultUrl('anime'), "Incorrect default url");
$this->expectException(\InvalidArgumentException::class);
$this->urlGenerator->defaultUrl('foo');
}
@ -205,16 +206,12 @@ class DispatcherTest extends AnimeClientTestCase {
return [
'controller_list_sanity_check' => [
'config' => [
'routes' => [
],
'route_config' => [
'anime_path' => 'anime',
'manga_path' => 'manga',
'default_anime_list_path' => "watching",
'default_manga_list_path' => 'all',
'default_list' => 'manga'
],
'anime_path' => 'anime',
'manga_path' => 'manga',
'default_anime_list_path' => "watching",
'default_manga_list_path' => 'all',
'default_list' => 'manga',
'routes' => [],
],
'expected' => [
'anime' => 'Aviat\AnimeClient\Controller\Anime',
@ -230,13 +227,11 @@ class DispatcherTest extends AnimeClientTestCase {
'routes' => [
],
'route_config' => [
'anime_path' => 'anime',
'manga_path' => 'manga',
'default_anime_path' => "/anime/watching",
'default_manga_path' => '/manga/all',
'default_list' => 'manga'
],
'anime_path' => 'anime',
'manga_path' => 'manga',
'default_anime_path' => "/anime/watching",
'default_manga_path' => '/manga/all',
'default_list' => 'manga'
],
'expected' => [
'anime' => 'Aviat\AnimeClient\Controller\Anime',