Version 5.0.0 beta 1

This commit is contained in:
Neo committed 2025-12-19 16:27:35 -08:00
1 parent 25ddeb65d6
commit 15c7beabc5
6736 files changed
+627902 -497943

No files matched your search

@@ -10,25 +10,28 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\Application\Module;
use IPS\core\api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\ActiveUsersType;
use IPS\Member;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* OurPicks query for GraphQL API
*/
class _ActiveUsers
class ActiveUsers
{
/*
* @brief Query description
*/
public static $description = "Returns active user information";
public static string $description = "Returns active user information";
/*
* Query arguments
@@ -41,20 +44,20 @@ class _ActiveUsers
/**
* Return the query return type
*/
public function type()
public function type() : ActiveUsersType
{
return \IPS\core\api\GraphQL\TypeRegistry::activeUsers();
return TypeRegistry::activeUsers();
}
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @return mixed
*/
public function resolve($val)
public function resolve( mixed $val ) : mixed
{
if ( !\IPS\Member::loggedIn()->canAccessModule( \IPS\Application\Module::get( 'core', 'online', 'front' ) ) )
if ( !Member::loggedIn()->canAccessModule( Module::get( 'core', 'online', 'front' ) ) )
{
return NULL;
}
+14 -12
View File
@@ -10,25 +10,27 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\ClubType;
use IPS\Member\Club as ClubClass;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Club query for GraphQL API
*/
class _Club
class Club
{
/*
* @brief Query description
*/
public static $description = "Returns a club";
public static string $description = "Returns a club";
/*
* Query arguments
@@ -42,7 +44,7 @@ class _Club
/**
* Return the query return type
*/
public function type()
public function type() : ClubType
{
return \IPS\core\api\GraphQL\TypeRegistry::club();
}
@@ -50,13 +52,13 @@ class _Club
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member\Club
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return ClubClass
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : ClubClass
{
return \IPS\Member\Club::loadAndCheckPerms( $args['id'] );
return ClubClass::loadAndCheckPerms( $args['id'] );
}
}
+22 -16
View File
@@ -10,20 +10,26 @@
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\ClubType;
use IPS\Db;
use IPS\Patterns\ActiveRecordIterator;
use function defined;
use function in_array;
use function is_int;
/* To prevent PHP errors (extending class does not exist) revealing path */
if( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER[ 'SERVER_PROTOCOL' ] ) ? $_SERVER[ 'SERVER_PROTOCOL' ] : 'HTTP/1.0' ).' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ).' 403 Forbidden' );
exit;
}
/**
* Club query for GraphQL API
*/
class _Clubs
class Clubs
{
/*
* @brief Query description
@@ -49,7 +55,7 @@ class _Clubs
'type' => TypeRegistry::eNum( [
'name' => 'clubs_order_by',
'description' => 'Fields on which topics can be sorted',
'values' => \IPS\core\api\GraphQL\Types\ClubType::getOrderByOptions()
'values' => ClubType::getOrderByOptions()
] ),
'defaultValue' => NULL // will use default sort option
],
@@ -70,7 +76,7 @@ class _Clubs
/**
* Return the query return type
*/
public function type(): \GraphQL\Type\Definition\ListOfType
public function type(): ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::club() );
}
@@ -78,19 +84,19 @@ class _Clubs
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Patterns\ActiveRecordIterator[\IPS\Member\Club]
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return ActiveRecordIterator[\IPS\Member\Club]
*/
public function resolve( mixed $val, array $args, array $context ): \IPS\Patterns\ActiveRecordIterator
public function resolve( mixed $val, array $args, array $context ): ActiveRecordIterator
{
$where = [];
$sortBy = ( isset( $args['orderBy'] ) and \in_array( $args['orderBy'], \IPS\core\api\GraphQL\Types\ClubType::getOrderByOptions() ) ) ? $args['orderBy'] : 'name';
$sortDir = ( isset( $args['orderDir'] ) and \in_array( mb_strtolower( $args['orderDir'] ), array( 'asc', 'desc' ) ) ) ? $args['orderDir'] : 'desc';
$limit =( isset( $args['orderDir'] ) and \is_int( $args['limit'] ) ) ? $args['limit'] : 25;
$sortBy = ( isset( $args['orderBy'] ) and in_array( $args['orderBy'], ClubType::getOrderByOptions() ) ) ? $args['orderBy'] : 'name';
$sortDir = ( isset( $args['orderDir'] ) and in_array( mb_strtolower( $args['orderDir'] ), array( 'asc', 'desc' ) ) ) ? $args['orderDir'] : 'desc';
$limit =( isset( $args['orderDir'] ) and is_int( $args['limit'] ) ) ? $args['limit'] : 25;
$query = \IPS\Db::i()->select( '*', 'core_clubs', $where, "{$sortBy} {$sortDir}", $limit );
return new \IPS\Patterns\ActiveRecordIterator( $query, '\IPS\Member\Club' );
$query = Db::i()->select( '*', 'core_clubs', $where, "{$sortBy} {$sortDir}", $limit );
return new ActiveRecordIterator( $query, '\IPS\Member\Club' );
}
}
@@ -10,26 +10,32 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use Exception;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\Application;
use IPS\Content as ContentClass;
use IPS\Content\Api\GraphQL\ContentType;
use IPS\Http\Url;
use IPS\Member;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Me query for GraphQL API
*/
class _Content
class Content
{
/*
* @brief Query description
*/
public static $description = "Return a generic piece of content";
public static string $description = "Return a generic piece of content";
/*
* Query arguments
@@ -44,7 +50,7 @@ class _Content
/**
* Return the query return type
*/
public function type()
public function type() : ContentType
{
return \IPS\Content\Api\GraphQL\TypeRegistry::content();
}
@@ -52,21 +58,20 @@ class _Content
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member|null
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @return ContentClass|null
*/
public function resolve($val, $args)
public function resolve( mixed $val, array $args ) : ?ContentClass
{
$url = \IPS\Http\Url::createFromString( $args['url'] );
$url = Url::createFromString( $args['url'] );
if ( !isset( $url->hiddenQueryString['app'] ) )
{
throw new Exception('Not a valid URL');
}
foreach ( \IPS\Application::load( $url->hiddenQueryString['app'] )->extensions( 'core', 'ContentRouter' ) as $ext )
foreach ( Application::load( $url->hiddenQueryString['app'] )->extensions( 'core', 'ContentRouter' ) as $ext )
{
foreach ( $ext->classes as $class )
{
@@ -85,7 +90,7 @@ class _Content
$object = $reviewClass::load( $url->queryString['review'] );
}
if ( !$object->canView( \IPS\Member::loggedIn() ) )
if ( !$object->canView( Member::loggedIn() ) )
{
// No permission
return NULL;
@@ -93,7 +98,7 @@ class _Content
return $object;
}
catch (\Exception $e)
catch (Exception $e)
{}
}
}
+18 -14
View File
@@ -10,26 +10,30 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\SafeException;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\GroupType;
use IPS\Member\Group as GroupClass;
use OutOfRangeException;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Group query for GraphQL API
*/
class _Group
class Group
{
/*
* @brief Query description
*/
public static $description = "Returns a member group";
public static string $description = "Returns a member group";
/*
* @brief Query arguments
@@ -44,7 +48,7 @@ class _Group
/**
* Return the query return type
*/
public function type()
public function type() : GroupType
{
return \IPS\core\api\GraphQL\TypeRegistry::group();
}
@@ -52,20 +56,20 @@ class _Group
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member\Group
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return GroupClass
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : GroupClass
{
try
{
return \IPS\Member\Group::load( $args['id'] );
return GroupClass::load( $args['id'] );
}
catch ( \OutOfRangeException $e )
catch ( OutOfRangeException $e )
{
throw new \IPS\Api\GraphQL\SafeException( 'INVALID_GROUP', '1invalid_group_graph', 400 );
throw new SafeException( 'INVALID_GROUP', '1invalid_group_graph', 400 );
}
}
}
@@ -10,26 +10,29 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\LanguageType;
use IPS\Lang;
use IPS\Member;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Me query for GraphQL API
*/
class _Language
class Language
{
/*
* @brief Query description
*/
public static $description = "Return language data";
public static string $description = "Return language data";
/*
* Query arguments
@@ -44,7 +47,7 @@ class _Language
/**
* Return the query return type
*/
public function type()
public function type() : LanguageType
{
return \IPS\core\api\GraphQL\TypeRegistry::language();
}
@@ -52,17 +55,16 @@ class _Language
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member|null
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @return Lang
*/
public function resolve($val, $args)
public function resolve( mixed $val, array $args ) : Lang
{
if( isset( $args['id'] ) ){
return \IPS\Lang::load( $args['id'] );
return Lang::load( $args['id'] );
}
return \IPS\Member::loggedIn()->language();
return Member::loggedIn()->language();
}
}
@@ -10,26 +10,29 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\LoginType;
use IPS\Login;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Login handler query for GraphQL API
*/
class _LoginHandlers
class LoginHandlers
{
/*
* @brief Query description
*/
public static $description = "Return login handler data";
public static string $description = "Return login handler data";
/*
* Query arguments
@@ -43,8 +46,10 @@ class _LoginHandlers
/**
* Return the query return type
*
* @return ListOfType<LoginType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::login() );
}
@@ -52,14 +57,13 @@ class _LoginHandlers
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member|null
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @return array
*/
public function resolve($val, $args)
public function resolve( mixed $val, array $args ) : array
{
$login = new \IPS\Login;
$login = new Login;
return $login->buttonMethods();
}
}
+16 -14
View File
@@ -10,26 +10,28 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\MemberType;
use IPS\Member;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Me query for GraphQL API
*/
class _Me
class Me
{
/*
* @brief Query description
*/
public static $description = "Return the logged-in member";
public static string $description = "Return the logged-in member";
/*
* Query arguments
@@ -42,21 +44,21 @@ class _Me
/**
* Return the query return type
*/
public function type()
public function type() : MemberType
{
return \IPS\core\api\GraphQL\TypeRegistry::member();
return TypeRegistry::member();
}
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member|null
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return Member
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : Member
{
return \IPS\Member::loggedIn();
return Member::loggedIn();
}
}
@@ -10,26 +10,28 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\MemberType;
use IPS\Member as MemberClass;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Member query for GraphQL API
*/
class _Member
class Member
{
/*
* @brief Query description
*/
public static $description = "Return a member";
public static string $description = "Return a member";
/*
* Query arguments
@@ -45,7 +47,7 @@ class _Member
/**
* Return the query return type
*/
public function type()
public function type() : MemberType
{
return \IPS\core\api\GraphQL\TypeRegistry::member();
}
@@ -53,17 +55,19 @@ class _Member
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Member|null
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return MemberClass|null
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : ?MemberClass
{
if( isset( $args['loggedIn'] ) ){
return \IPS\Member::loggedIn();
return MemberClass::loggedIn();
} elseif ( isset( $args['id'] ) ){
return \IPS\Member::load( $args['id'] );
return MemberClass::load( $args['id'] );
}
return null;
}
}
@@ -11,25 +11,31 @@
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\MemberType;
use IPS\Db;
use IPS\Patterns\ActiveRecordIterator;
use function defined;
use function in_array;
use function is_int;
/* To prevent PHP errors (extending class does not exist) revealing path */
if( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER[ 'SERVER_PROTOCOL' ] ) ? $_SERVER[ 'SERVER_PROTOCOL' ] : 'HTTP/1.0' ).' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ).' 403 Forbidden' );
exit;
}
/**
* Members query for GraphQL API
*/
class _Members
class Members
{
/*
* @brief Query description
*/
public static $description = 'Returns a list of members';
public static string $description = 'Returns a list of members';
/*
* Query arguments
@@ -50,7 +56,7 @@ class _Members
'type' => TypeRegistry::eNum( [
'name' => 'member_order_by',
'description' => 'Fields on which topics can be sorted',
'values' => \IPS\core\api\GraphQL\Types\MemberType::getOrderByOptions()
'values' => MemberType::getOrderByOptions()
] ),
'defaultValue' => NULL // will use default sort option
],
@@ -68,8 +74,10 @@ class _Members
/**
* Return the query return type
*
* @return ListOfType<MemberType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::member() );
}
@@ -77,19 +85,20 @@ class _Members
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return [\IPS\Members]
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @param array $info
* @return ActiveRecordIterator
*/
public function resolve( $val, $args, $context, $info )
public function resolve( mixed $val, array $args, array $context, array $info ) : ActiveRecordIterator
{
$where = [];
$sortBy = ( isset( $args['orderBy'] ) and \in_array( $args['orderBy'], \IPS\core\api\GraphQL\Types\MemberType::getOrderByOptions() ) ) ? $args['orderBy'] : 'member_id';
$sortDir = ( isset( $args['orderDir'] ) and \in_array( mb_strtolower( $args['orderDir'] ), array( 'asc', 'desc' ) ) ) ? $args['orderDir'] : 'desc';
$limit =( isset( $args['orderDir'] ) and \is_int( $args['limit'] ) ) ? $args['limit'] : 25;
$sortBy = ( isset( $args['orderBy'] ) and in_array( $args['orderBy'], MemberType::getOrderByOptions() ) ) ? $args['orderBy'] : 'member_id';
$sortDir = ( isset( $args['orderDir'] ) and in_array( mb_strtolower( $args['orderDir'] ), array( 'asc', 'desc' ) ) ) ? $args['orderDir'] : 'desc';
$limit =( isset( $args['orderDir'] ) and is_int( $args['limit'] ) ) ? $args['limit'] : 25;
$query = \IPS\Db::i()->select( '*', 'core_members', $where, "{$sortBy} {$sortDir}", $limit );
return new \IPS\Patterns\ActiveRecordIterator( $query, 'IPS\Member' );
$query = Db::i()->select( '*', 'core_members', $where, "{$sortBy} {$sortDir}", $limit );
return new ActiveRecordIterator( $query, 'IPS\Member' );
}
}
@@ -10,25 +10,29 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\SafeException;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\MessengerConversationType;
use IPS\core\Messenger\Conversation;
use OutOfRangeException;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Messenger conversation query for GraphQL API
*/
class _MessengerConversation
class MessengerConversation
{
/*
* @brief Query description
*/
public static $description = "Returns a messenger conversation";
public static string $description = "Returns a messenger conversation";
/*
* Query arguments
@@ -43,7 +47,7 @@ class _MessengerConversation
/**
* Return the query return type
*/
public function type()
public function type() : MessengerConversationType
{
return \IPS\core\api\GraphQL\TypeRegistry::messengerConversation();
}
@@ -51,20 +55,21 @@ class _MessengerConversation
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Messenger\Conversation
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @param array $info
* @return Conversation
*/
public function resolve($val, $args, $context, $info)
public function resolve( mixed $val, array $args, array $context, array $info ) : Conversation
{
try
{
$conversation = \IPS\core\Messenger\Conversation::loadAndCheckPerms( $args['id'] );
$conversation = Conversation::loadAndCheckPerms( $args['id'] );
}
catch ( \OutOfRangeException $e )
catch ( OutOfRangeException $e )
{
throw new \IPS\Api\GraphQL\SafeException( 'NO_MESSAGE', '1F294/2', 400 );
throw new SafeException( 'NO_MESSAGE', '1F294/2', 400 );
}
return $conversation;
@@ -10,25 +10,35 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\Content\Search\Mysql\Query;
use IPS\core\api\GraphQL\Types\MessengerConversationType;
use IPS\Db;
use IPS\Member;
use IPS\Patterns\ActiveRecordIterator;
use UnderflowException;
use function count;
use function defined;
use function in_array;
use function is_null;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Messenger conversations query for GraphQL API
*/
class _MessengerConversations
class MessengerConversations
{
/*
* @brief Query description
*/
public static $description = "Returns a list of messenger conversations";
public static string $description = "Returns a list of messenger conversations";
/*
* Query arguments
@@ -66,7 +76,7 @@ class _MessengerConversations
'type' => TypeRegistry::eNum([
'name' => 'core_messengerConversations_orderBy',
'description' => 'Fields on which conversations can be sorted',
'values' => \IPS\core\api\GraphQL\Types\MessengerConversationType::getOrderByOptions()
'values' => MessengerConversationType::getOrderByOptions()
]),
'defaultValue' => 'last_post_time'
],
@@ -83,8 +93,10 @@ class _MessengerConversations
/**
* Return the query return type
*
* @return ListOfType<MessengerConversationType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::messengerConversation() );
}
@@ -92,22 +104,23 @@ class _MessengerConversations
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Messenger\Conversation
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @param array $info
* @return ActiveRecordIterator|array
*/
public function resolve($val, $args, $context, $info)
public function resolve( mixed $val, array $args, array $context, array $info ) : ActiveRecordIterator|array
{
// Start to build the query to fetch messages
$where = array( array( 'core_message_topic_user_map.map_user_id=? AND core_message_topic_user_map.map_user_active=1', \IPS\Member::loggedIn()->member_id ) );
$where = array( array( 'core_message_topic_user_map.map_user_id=? AND core_message_topic_user_map.map_user_active=1', Member::loggedIn()->member_id ) );
$orderBy = 'mt_' . $args['orderBy'];
$offset = max( $args['offset'], 0 );
$limit = min( $args['limit'], 50 );
$iterator = NULL;
// Filters
if( !\is_null( $args['filter'] ) )
if( !is_null( $args['filter'] ) )
{
switch ($args['filter'] ) {
case "MINE":
@@ -126,7 +139,7 @@ class _MessengerConversations
}
// Folder
if ( !\is_null( $args['folder'] ) )
if ( !is_null( $args['folder'] ) )
{
$folderObj = \IPS\core\api\GraphQL\TypeRegistry::messengerFolder();
$folders = $folderObj->getMemberFolders();
@@ -138,33 +151,33 @@ class _MessengerConversations
}
// Search
if( !\is_null( $args['search'] ) )
if( !is_null( $args['search'] ) )
{
$subQuery = \IPS\Db::i()->select( 'map_topic_id', array( 'core_message_topic_user_map', 'core_message_topic_user_map' ), $where );
$subQuery = Db::i()->select( 'map_topic_id', array( 'core_message_topic_user_map', 'core_message_topic_user_map' ), $where );
$where = array( array( 'core_message_posts.msg_topic_id IN (?)', $subQuery ) );
$query = array();
$prefix = \IPS\Db::i()->prefix;
$prefix = Db::i()->prefix;
if ( !\is_null( $args['searchIn'] ) )
if ( !is_null( $args['searchIn'] ) )
{
if ( \in_array( 'TOPIC', $args['searchIn'] ) )
if ( in_array( 'TOPIC', $args['searchIn'] ) )
{
$query[] = \IPS\Content\Search\Mysql\Query::matchClause( "core_message_topics.mt_title", $args['search'], '+', FALSE );
$query[] = Query::matchClause( "core_message_topics.mt_title", $args['search'], '+', FALSE );
}
if ( \in_array( 'POST', $args['searchIn'] ) )
if ( in_array( 'POST', $args['searchIn'] ) )
{
$query[] = \IPS\Content\Search\Mysql\Query::matchClause( "core_message_posts.msg_post", $args['search'], '+', FALSE );
$query[] = Query::matchClause( "core_message_posts.msg_post", $args['search'], '+', FALSE );
}
if ( \in_array( 'RECIPIENT', $args['searchIn'] ) )
if ( in_array( 'RECIPIENT', $args['searchIn'] ) )
{
$query[] = "core_message_posts.msg_topic_id IN ( SELECT sender_map.map_topic_id FROM {$prefix}core_message_topic_user_map AS sender_map WHERE sender_map.map_is_starter=1 AND sender_map.map_user_id IN ( SELECT member_id FROM {$prefix}core_members AS sm WHERE name LIKE '" . \IPS\Db::i()->escape_string( $args['search'] ) . "%' ) )";
$query[] = "core_message_posts.msg_topic_id IN ( SELECT sender_map.map_topic_id FROM {$prefix}core_message_topic_user_map AS sender_map WHERE sender_map.map_is_starter=1 AND sender_map.map_user_id IN ( SELECT member_id FROM {$prefix}core_members AS sm WHERE name LIKE '" . Db::i()->escape_string( $args['search'] ) . "%' ) )";
}
if ( \in_array( 'SENDER', $args['searchIn'] ) )
if ( in_array( 'SENDER', $args['searchIn'] ) )
{
$query[] = "core_message_posts.msg_topic_id IN ( SELECT receiver_map.map_topic_id FROM {$prefix}core_message_topic_user_map AS receiver_map WHERE receiver_map.map_is_starter=0 AND receiver_map.map_user_id IN ( SELECT member_id FROM {$prefix}core_members AS rm WHERE name LIKE '" . \IPS\Db::i()->escape_string( $args['search'] ) . "%') )";
$query[] = "core_message_posts.msg_topic_id IN ( SELECT receiver_map.map_topic_id FROM {$prefix}core_message_topic_user_map AS receiver_map WHERE receiver_map.map_is_starter=0 AND receiver_map.map_user_id IN ( SELECT member_id FROM {$prefix}core_members AS rm WHERE name LIKE '" . Db::i()->escape_string( $args['search'] ) . "%') )";
}
if ( \count( $query ) )
if ( count( $query ) )
{
$where[] = array( '(' . implode( ' OR ', $query ) . ')' );
}
@@ -173,7 +186,7 @@ class _MessengerConversations
/* Get a count */
try
{
$count = \IPS\Db::i()->select( 'COUNT(*)', 'core_message_posts', $where, NULL, NULL, 'msg_topic_id' )
$count = Db::i()->select( 'COUNT(*)', 'core_message_posts', $where, NULL, NULL, 'msg_topic_id' )
->join(
'core_message_topics',
'core_message_posts.msg_topic_id=core_message_topics.mt_id'
@@ -184,7 +197,7 @@ class _MessengerConversations
)
->first();
}
catch( \UnderflowException $e )
catch( UnderflowException $e )
{
$count = 0;
}
@@ -193,7 +206,7 @@ class _MessengerConversations
if( $count )
{
/* Because of strict group by, we first need to select the ids, then grab those topics */
$iterator = \IPS\Db::i()->select(
$iterator = Db::i()->select(
'core_message_posts.msg_topic_id',
'core_message_posts',
$where,
@@ -209,7 +222,7 @@ class _MessengerConversations
);
/* Get iterator */
$iterator = \IPS\Db::i()->select(
$iterator = Db::i()->select(
'core_message_topic_user_map.*, core_message_topics.*',
'core_message_topic_user_map',
array( 'map_topic_id IN(' . implode( ',', iterator_to_array( $iterator ) ) . ')' ),
@@ -223,7 +236,7 @@ class _MessengerConversations
else
{
/* Get iterator */
$iterator = \IPS\Db::i()->select(
$iterator = Db::i()->select(
'core_message_topic_user_map.*, core_message_topics.*',
'core_message_topic_user_map',
$where,
@@ -237,7 +250,7 @@ class _MessengerConversations
if( $iterator )
{
return new \IPS\Patterns\ActiveRecordIterator( $iterator, 'IPS\core\Messenger\Conversation' );
return new ActiveRecordIterator( $iterator, 'IPS\core\Messenger\Conversation' );
}
return array();
@@ -10,25 +10,28 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\MessengerFolderType;
use IPS\Member;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Messenger folders query for GraphQL API
*/
class _MessengerFolders
class MessengerFolders
{
/*
* @brief Query description
*/
public static $description = "Returns the member's messenger folders";
public static string $description = "Returns the member's messenger folders";
/*
* Query arguments
@@ -42,8 +45,10 @@ class _MessengerFolders
/**
* Return the query return type
*
* @return ListOfType<MessengerFolderType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::messengerFolder() );
}
@@ -51,14 +56,15 @@ class _MessengerFolders
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Messenger\Conversation
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @param array $info
* @return array|null
*/
public function resolve($val, $args, $context, $info)
public function resolve( mixed $val, array $args, array $context, array $info ) : ?array
{
if( !\IPS\Member::loggedIn()->member_id || \IPS\Member::loggedIn()->members_disable_pm )
if( !Member::loggedIn()->member_id || Member::loggedIn()->members_disable_pm )
{
return NULL;
}
@@ -10,25 +10,31 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\Application;
use IPS\core\api\GraphQL\Types\NotificationTypeType;
use IPS\Member;
use IPS\Notification;
use function defined;
use function in_array;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* NotificationTypes query for GraphQL API
*/
class _NotificationTypes
class NotificationTypes
{
/*
* @brief Query description
*/
public static $description = "Returns available notification types";
public static string $description = "Returns available notification types";
/*
* Query arguments
@@ -40,8 +46,10 @@ class _NotificationTypes
/**
* Return the query return type
*
* @return ListOfType<NotificationTypeType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::notificationType() );
}
@@ -49,23 +57,23 @@ class _NotificationTypes
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return array
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : array
{
//$defaultConfiguration = \IPS\Notification::defaultConfiguration();
//$memberConfiguration = $member->notificationsConfiguration();
$notificationTypes = array();
$extensions = \IPS\Application::allExtensions( 'core', 'Notifications' );
$extensions = Application::allExtensions( 'core', 'Notifications' );
$availableOptions = array();
foreach( $extensions as $extensionKey => $extension )
{
$extensionOptions = \IPS\Notification::availableOptions( \IPS\Member::loggedIn(), $extension );
$extensionOptions = Notification::availableOptions( Member::loggedIn(), $extension );
foreach( $extensionOptions as $key => $option )
{
@@ -84,9 +92,9 @@ class _NotificationTypes
continue;
}
$methods[ $method ]['default'] = isset( $option['default'] ) && \in_array( $method, $option['default'] );
$methods[ $method ]['disabled'] = isset( $option['disabled'] ) && \in_array( $method, $option['disabled'] );
$methods[ $method ]['member'] = isset( $option['options'][ $method ] ) && $option['options'][ $method ]['value'] == TRUE;
$methods[ $method ]['default'] = isset( $option['default'] ) && in_array( $method, $option['default'] );
$methods[ $method ]['disabled'] = isset( $option['disabled'] ) && in_array( $method, $option['disabled'] );
$methods[ $method ]['member'] = ( $option['options'][ $method ]['value'] == TRUE );
}
$notificationTypes[] = array(
@@ -10,25 +10,30 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\PromotedItemType;
use IPS\core\Feature;
use function count;
use function defined;
use function is_int;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* OurPicks query for GraphQL API
*/
class _OurPicks
class OurPicks
{
/*
* @brief Query description
*/
public static $description = "Returns promoted items";
public static string $description = "Returns promoted items";
/*
* Query arguments
@@ -42,8 +47,10 @@ class _OurPicks
/**
* Return the query return type
*
* @return ListOfType<PromotedItemType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::promotedItem() );
}
@@ -51,21 +58,21 @@ class _OurPicks
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return array|null
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : ?array
{
$limit = 7;
if( isset( $args['count'] ) && \is_int( $args['count'] ) )
if( isset( $args['count'] ) && is_int( $args['count'] ) )
{
$limit = $args['count'];
}
$items = \IPS\core\Promote::internalStream( $limit );
if( !\count( $items ) )
$items = Feature::internalStream( $limit );
if( !count( $items ) )
{
return NULL;
}
@@ -10,25 +10,31 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use DateInterval;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\PopularContributorType;
use IPS\DateTime;
use IPS\Db;
use IPS\Member;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* PopularContributors query for GraphQL API
*/
class _PopularContributors
class PopularContributors
{
/*
* @brief Query description
*/
public static $description = "Returns popular contributors";
public static string $description = "Returns popular contributors";
/*
* Query arguments
@@ -52,8 +58,10 @@ class _PopularContributors
/**
* Return the query return type
*
* @return ListOfType<PopularContributorType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::popularContributor() );
}
@@ -61,12 +69,12 @@ class _PopularContributors
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return array
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : array
{
/* How many? */
$limit = min( $args['limit'], 25 );
@@ -79,29 +87,29 @@ class _PopularContributors
switch ( $args['period'] )
{
case 'WEEK':
$where[] = array( 'rep_date>' . \IPS\DateTime::create()->sub( new \DateInterval( 'P1W' ) )->getTimestamp() );
$where[] = array( 'rep_date>' . DateTime::create()->sub( new DateInterval( 'P1W' ) )->getTimestamp() );
break;
case 'MONTH':
$where[] = array( 'rep_date>' . \IPS\DateTime::create()->sub( new \DateInterval( 'P1M' ) )->getTimestamp() );
$where[] = array( 'rep_date>' . DateTime::create()->sub( new DateInterval( 'P1M' ) )->getTimestamp() );
break;
case 'YEAR':
$where[] = array( 'rep_date>' . \IPS\DateTime::create()->sub( new \DateInterval( 'P1Y' ) )->getTimestamp() );
$where[] = array( 'rep_date>' . DateTime::create()->sub( new DateInterval( 'P1Y' ) )->getTimestamp() );
break;
}
$innerQuery = \IPS\Db::i()->select( 'core_reputation_index.member_received as member, SUM(rep_rating) as rep', 'core_reputation_index', $where, NULL, NULL, 'member' );
$topContributors = iterator_to_array( \IPS\Db::i()->select( 'member, rep', array( $innerQuery, 'in' ), NULL, 'rep DESC', $limit )->setKeyField('member')->setValueField('rep') );
$innerQuery = Db::i()->select( 'core_reputation_index.member_received as member, SUM(rep_rating) as rep', 'core_reputation_index', $where, NULL, NULL, 'member' );
$topContributors = iterator_to_array( Db::i()->select( 'member, rep', array( $innerQuery, 'in' ), NULL, 'rep DESC', $limit )->setKeyField('member')->setValueField('rep') );
}
else
{
$topContributors = iterator_to_array( \IPS\Db::i()->select( 'member_id as member, pp_reputation_points as rep', 'core_members', array( 'pp_reputation_points > 0' ), 'rep DESC', $limit )->setKeyField('member')->setValueField('rep') );
$topContributors = iterator_to_array( Db::i()->select( 'member_id as member, pp_reputation_points as rep', 'core_members', array( 'pp_reputation_points > 0' ), 'rep DESC', $limit )->setKeyField('member')->setValueField('rep') );
}
/* Contruct their data */
/* The PopularContributorsType will call ::load on the member ID to get the object */
foreach ( \IPS\Db::i()->select( '*', 'core_members', \IPS\Db::i()->in( 'member_id', array_keys( $topContributors ) ) ) as $member )
foreach ( Db::i()->select( '*', 'core_members', Db::i()->in( 'member_id', array_keys( $topContributors ) ) ) as $member )
{
\IPS\Member::constructFromData( $member );
Member::constructFromData( $member );
}
$output = array();
@@ -10,25 +10,34 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\Application\Module;
use IPS\Content\Search\ContentFilter;
use IPS\Content\Search\Query;
use IPS\core\api\GraphQL\Types\SearchType;
use IPS\core\modules\front\search\search as searchController;
use IPS\Db;
use IPS\Member;
use IPS\Patterns\ActiveRecordIterator;
use function defined;
use function in_array;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Search query for GraphQL API
*/
class _Search
class Search
{
/*
* @brief Query description
*/
public static $description = "Returns search results";
public static string $description = "Returns search results";
/*
* Query arguments
@@ -41,7 +50,7 @@ class _Search
'type' => TypeRegistry::eNum([
'name' => 'core_search_types_input',
'description' => "The available search types",
'values' => array_merge( array('core_members'), array_keys( \IPS\core\modules\front\search\search::contentTypes() ) )
'values' => array_merge( array('core_members'), array_keys( searchController::contentTypes() ) )
]),
],
'offset' => [
@@ -73,7 +82,7 @@ class _Search
/**
* Return the query return type
*/
public function type()
public function type() : SearchType
{
return \IPS\core\api\GraphQL\TypeRegistry::search();
}
@@ -81,12 +90,12 @@ class _Search
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return array
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : array
{
$where = array();
$returnObject = array();
@@ -94,7 +103,7 @@ class _Search
$limit = min( $args['limit'], 50 );
// Member search
if ( isset( $args['type'] ) and $args['type'] === 'core_members' and \IPS\Member::loggedIn()->canAccessModule( \IPS\Application\Module::get( 'core', 'members', 'front' ) ) )
if ( isset( $args['type'] ) and $args['type'] === 'core_members' and Member::loggedIn()->canAccessModule( Module::get( 'core', 'members', 'front' ) ) )
{
if ( $args['term'] )
{
@@ -106,10 +115,10 @@ class _Search
}
// Ordering
$orderDir = isset( $args['orderDir'] ) ? $args['orderDir'] : 'DESC';
$orderDir = $args['orderDir'] ?? 'DESC';
$orderBy = 'name';
if( isset( $args['orderBy'] ) && \in_array( $args['orderBy'], array( 'joined', 'name', 'member_posts', 'pp_reputation_points' ) ) )
if( isset( $args['orderBy'] ) && in_array( $args['orderBy'], array( 'joined', 'name', 'member_posts', 'pp_reputation_points' ) ) )
{
$orderBy = $args['orderBy'];
}
@@ -117,26 +126,26 @@ class _Search
$order = $orderBy . ' ' . $orderDir;
// Get results
$select = \IPS\Db::i()->select( 'COUNT(*)', 'core_members', $where );
$select = Db::i()->select( 'COUNT(*)', 'core_members', $where );
$select->join( 'core_pfields_content', 'core_pfields_content.member_id=core_members.member_id' );
$returnObject['count'] = $select->first();
$select = \IPS\Db::i()->select( 'core_members.*', 'core_members', $where, $order, array( $offset, $limit ) );
$select = Db::i()->select( 'core_members.*', 'core_members', $where, $order, array( $offset, $limit ) );
$select->join( 'core_pfields_content', 'core_pfields_content.member_id=core_members.member_id' );
$returnObject['results'] = new \IPS\Patterns\ActiveRecordIterator( $select, 'IPS\Member' );
$returnObject['results'] = new ActiveRecordIterator( $select, 'IPS\Member' );
return $returnObject;
}
// Content search
$query = \IPS\Content\Search\Query::init();
$types = \IPS\core\modules\front\search\search::contentTypes();
$query = Query::init();
$types = searchController::contentTypes();
if( isset( $args['type'] ) && !empty( $args['type'] ) )
if( !empty( $args['type'] ) )
{
$class = $types[ $args['type'] ];
$filter = \IPS\Content\Search\ContentFilter::init( $class );
$filter = ContentFilter::init( $class );
$query->filterByContent( array( $filter ) );
}
@@ -148,10 +157,10 @@ class _Search
switch( $args['orderBy'] )
{
case 'newest':
$query->setOrder( \IPS\Content\Search\Query::ORDER_NEWEST_CREATED );
$query->setOrder( Query::ORDER_NEWEST_CREATED );
break;
case 'relevancy':
$query->setOrder( \IPS\Content\Search\Query::ORDER_RELEVANCY );
$query->setOrder( Query::ORDER_RELEVANCY );
break;
default:
$query->setOrder( $orderBy );
@@ -179,7 +188,7 @@ class _Search
$returnObject['results'] = $query->search(
isset( $args['term'] ) ? ( $args['term'] ) : NULL,
NULL,
\IPS\Content\Search\Query::TERM_AND_TAGS + \IPS\Content\Search\Query::TAGS_MATCH_ITEMS_ONLY,
Query::TERM_AND_TAGS + Query::TAGS_MATCH_ITEMS_ONLY,
NULL
);
$returnObject['count'] = $returnObject['results']->count( TRUE );
@@ -10,26 +10,28 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\SettingsType;
use IPS\Settings as SettingsClass;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Settings query for GraphQL API
*/
class _Settings
class Settings
{
/*
* @brief Query description
*/
public static $description = "Returns values of system settings (subject to the setting being exposed by the API)";
public static string $description = "Returns values of system settings (subject to the setting being exposed by the API)";
/*
* Query arguments
@@ -42,21 +44,21 @@ class _Settings
/**
* Return the query return type
*/
public function type()
public function type() : SettingsType
{
return \IPS\core\api\GraphQL\TypeRegistry::settings();
return TypeRegistry::settings();
}
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\Settings
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return SettingsClass
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : SettingsClass
{
return \IPS\Settings::i();
return SettingsClass::i();
}
}
+14 -13
View File
@@ -10,25 +10,26 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\StatsType;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Stats query for GraphQL API
*/
class _Stats
class Stats
{
/*
* @brief Query description
*/
public static $description = "Returns community stats";
public static string $description = "Returns community stats";
/*
* Query arguments
@@ -41,20 +42,20 @@ class _Stats
/**
* Return the query return type
*/
public function type()
public function type() : StatsType
{
return \IPS\core\api\GraphQL\TypeRegistry::stats();
return TypeRegistry::stats();
}
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return mixed
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : mixed
{
return $val;
}
@@ -10,25 +10,31 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use IPS\Api\GraphQL\SafeException;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\StreamType;
use IPS\core\Stream as StreamClass;
use IPS\Member;
use OutOfRangeException;
use function defined;
use function intval;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Stream query for GraphQL API
*/
class _Stream
class Stream
{
/*
* @brief Query description
*/
public static $description = "Returns an activity stream";
public static string $description = "Returns an activity stream";
/*
* Query arguments
@@ -43,7 +49,7 @@ class _Stream
/**
* Return the query return type
*/
public function type()
public function type() : StreamType
{
return \IPS\core\api\GraphQL\TypeRegistry::stream();
}
@@ -51,34 +57,34 @@ class _Stream
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @return \IPS\core\Stream
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return StreamClass|null
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : ?StreamClass
{
if( isset( $args['id'] ) && \intval( $args['id'] ) )
if( isset( $args['id'] ) && intval( $args['id'] ) )
{
try
{
$stream = \IPS\core\Stream::load( $args['id'] );
$stream = StreamClass::load( $args['id'] );
}
catch ( \OutOfRangeException $e )
catch ( OutOfRangeException $e )
{
return NULL;
}
/* Suitable for guests? */
if ( !\IPS\Member::loggedIn()->member_id and !( ( $stream->ownership == 'all' or $stream->ownership == 'custom' ) and $stream->read == 'all' and $stream->follow == 'all' and $stream->date_type != 'last_visit' ) )
if ( !Member::loggedIn()->member_id and !( ( $stream->ownership == 'all' or $stream->ownership == 'custom' ) and $stream->read == 'all' and $stream->follow == 'all' and $stream->date_type != 'last_visit' ) )
{
throw new \IPS\Api\GraphQL\SafeException( 'INVALID_STREAM', 'GQL/0003/1', 403 );
throw new SafeException( 'INVALID_STREAM', 'GQL/0003/1', 403 );
}
}
else
{
/* Start with a blank stream */
$stream = \IPS\core\Stream::allActivityStream();
$stream = StreamClass::allActivityStream();
}
return $stream;
@@ -10,26 +10,31 @@
*/
namespace IPS\core\api\GraphQL\Queries;
use GraphQL\Type\Definition\ObjectType;
use GraphQL\Type\Definition\ListOfType;
use IPS\Api\GraphQL\TypeRegistry;
use IPS\core\api\GraphQL\Types\StreamType;
use IPS\Db;
use IPS\Member;
use IPS\Patterns\ActiveRecordIterator;
use function defined;
/* To prevent PHP errors (extending class does not exist) revealing path */
if ( !\defined( '\IPS\SUITE_UNIQUE_KEY' ) )
if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )
{
header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );
header( ( $_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.0' ) . ' 403 Forbidden' );
exit;
}
/**
* Streams query for GraphQL API
*/
class _Streams
class Streams
{
/*
* @brief Query description
*/
public static $description = "Returns a list of user's activity streams";
public static string $description = "Returns a list of user's activity streams";
/*
* @brief Query arguments
@@ -41,8 +46,10 @@ class _Streams
/**
* Return the query return type
*
* @return ListOfType<StreamType>
*/
public function type()
public function type() : ListOfType
{
return TypeRegistry::listOf( \IPS\core\api\GraphQL\TypeRegistry::stream() );
}
@@ -50,26 +57,26 @@ class _Streams
/**
* Resolves this query
*
* @param mixed Value passed into this resolver
* @param array Arguments
* @param array Context values
* @param mixed $val Value passed into this resolver
* @param array $args Arguments
* @param array $context Context values
* @return array
*/
public function resolve($val, $args, $context)
public function resolve( mixed $val, array $args, array $context ) : array
{
$streams = array();
foreach ( new \IPS\Patterns\ActiveRecordIterator( \IPS\Db::i()->select( '*', 'core_streams', '`member` IS NULL', 'position ASC' ), 'IPS\core\Stream' ) as $stream )
foreach ( new ActiveRecordIterator( Db::i()->select( '*', 'core_streams', '`member` IS NULL', 'position ASC' ), 'IPS\core\Stream' ) as $stream )
{
if( \IPS\Member::loggedIn()->member_id || ( !\IPS\Member::loggedIn()->member_id && ( $stream->ownership == 'all' and $stream->read == 'all' and $stream->follow == 'all' and $stream->date_type != 'last_visit' ) ) )
if( Member::loggedIn()->member_id || ( !Member::loggedIn()->member_id && ( $stream->ownership == 'all' and $stream->read == 'all' and $stream->follow == 'all' and $stream->date_type != 'last_visit' ) ) )
{
$streams[ $stream->id ] = $stream;
}
}
if ( \IPS\Member::loggedIn()->member_id )
if ( Member::loggedIn()->member_id )
{
foreach ( new \IPS\Patterns\ActiveRecordIterator( \IPS\Db::i()->select( '*', 'core_streams', array( '`member`=?', \IPS\Member::loggedIn()->member_id ), 'position ASC' ), 'IPS\core\Stream' ) as $stream )
foreach ( new ActiveRecordIterator( Db::i()->select( '*', 'core_streams', array( '`member`=?', Member::loggedIn()->member_id ), 'position ASC' ), 'IPS\core\Stream' ) as $stream )
{
$streams[ $stream->id ] = $stream;
}