2023-09-01 23:56:59 +02:00
< ? php
/**
* @ copyright Copyright ( C ) 2010 - 2023 , the Friendica project
*
* @ license GNU AGPL version 3 or any later version
*
* This program 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 ( at your option ) any later version .
*
* This program 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 this program . If not , see < https :// www . gnu . org / licenses />.
2023-09-02 21:37:20 +02:00
*
2023-09-01 23:56:59 +02:00
*/
namespace Friendica\Module\Conversation ;
2023-09-02 23:37:02 +02:00
use Friendica\App ;
use Friendica\App\Mode ;
2023-09-01 23:56:59 +02:00
use Friendica\BaseModule ;
use Friendica\Content\BoundariesPager ;
use Friendica\Content\Conversation ;
use Friendica\Content\Feature ;
use Friendica\Content\Nav ;
use Friendica\Content\Text\HTML ;
use Friendica\Content\Widget ;
use Friendica\Content\Widget\TrendingTags ;
2023-09-02 23:37:02 +02:00
use Friendica\Core\Cache\Capability\ICanCache ;
2023-09-02 14:47:48 +02:00
use Friendica\Core\Cache\Enum\Duration ;
2023-09-02 23:37:02 +02:00
use Friendica\Core\Config\Capability\IManageConfigValues ;
use Friendica\Core\L10n ;
use Friendica\Core\PConfig\Capability\IManagePersonalConfigValues ;
2023-09-01 23:56:59 +02:00
use Friendica\Core\Renderer ;
2023-09-02 23:37:02 +02:00
use Friendica\Core\Session\Capability\IHandleUserSessions ;
2023-09-01 23:56:59 +02:00
use Friendica\Model\Contact ;
use Friendica\Model\Post ;
use Friendica\Model\User ;
use Friendica\Module\Security\Login ;
use Friendica\Network\HTTPException ;
2023-09-02 23:37:02 +02:00
use Friendica\Core\Session\Model\UserSession ;
2023-09-02 23:48:55 +02:00
use Friendica\Database\Database ;
2023-09-03 14:54:25 +02:00
use Friendica\Model\Item ;
2023-09-02 23:37:02 +02:00
use Friendica\Module\Response ;
2023-09-03 07:23:49 +02:00
use Friendica\Navigation\SystemMessages ;
2023-09-02 23:37:02 +02:00
use Friendica\Util\Profiler ;
use Psr\Log\LoggerInterface ;
2023-09-01 23:56:59 +02:00
class Channel extends BaseModule
{
const WHATSHOT = 'whatshot' ;
const FORYOU = 'foryou' ;
const FOLLOWERS = 'followers' ;
2023-09-02 17:52:53 +02:00
const IMAGE = 'image' ;
const VIDEO = 'video' ;
const AUDIO = 'audio' ;
2023-09-03 07:23:49 +02:00
const LANGUAGE = 'language' ;
2023-09-01 23:56:59 +02:00
protected static $content ;
protected static $accountTypeString ;
protected static $accountType ;
protected static $itemsPerPage ;
protected static $min_id ;
protected static $max_id ;
protected static $item_id ;
2023-09-02 23:37:02 +02:00
/** @var UserSession */
2023-09-03 05:35:10 +02:00
protected $session ;
2023-09-02 23:37:02 +02:00
/** @var ICanCache */
2023-09-03 05:35:10 +02:00
protected $cache ;
2023-09-02 23:37:02 +02:00
/** @var IManageConfigValues The config */
2023-09-03 05:35:10 +02:00
protected $config ;
2023-09-02 23:37:02 +02:00
/** @var SystemMessages */
2023-09-03 05:35:10 +02:00
protected $systemMessages ;
2023-09-02 23:37:02 +02:00
/** @var App\Page */
2023-09-03 05:35:10 +02:00
protected $page ;
2023-09-02 23:37:02 +02:00
/** @var Conversation */
2023-09-03 05:35:10 +02:00
protected $conversation ;
2023-09-02 23:37:02 +02:00
/** @var App\Mode $mode */
2023-09-03 05:35:10 +02:00
protected $mode ;
2023-09-02 23:37:02 +02:00
/** @var IManagePersonalConfigValues */
2023-09-03 05:35:10 +02:00
protected $pConfig ;
2023-09-02 23:48:55 +02:00
/** @var Database */
2023-09-03 05:35:10 +02:00
protected $database ;
2023-09-02 23:37:02 +02:00
2023-09-02 23:48:55 +02:00
2023-09-03 07:23:49 +02:00
public function __construct ( SystemMessages $systemMessages , Database $database , IManagePersonalConfigValues $pConfig , Mode $mode , Conversation $conversation , App\Page $page , IManageConfigValues $config , ICanCache $cache , IHandleUserSessions $session , L10n $l10n , App\BaseURL $baseUrl , App\Arguments $args , LoggerInterface $logger , Profiler $profiler , Response $response , array $server , array $parameters = [])
2023-09-02 23:37:02 +02:00
{
parent :: __construct ( $l10n , $baseUrl , $args , $logger , $profiler , $response , $server , $parameters );
2023-09-03 07:23:49 +02:00
$this -> systemMessages = $systemMessages ;
$this -> database = $database ;
$this -> pConfig = $pConfig ;
$this -> mode = $mode ;
$this -> conversation = $conversation ;
$this -> page = $page ;
$this -> config = $config ;
$this -> cache = $cache ;
$this -> session = $session ;
2023-09-02 23:37:02 +02:00
}
2023-09-01 23:56:59 +02:00
protected function content ( array $request = []) : string
{
2023-09-02 23:37:02 +02:00
if ( ! $this -> session -> getLocalUserId ()) {
2023-09-01 23:56:59 +02:00
return Login :: form ();
}
2023-09-02 21:16:48 +02:00
$this -> parseRequest ( $request );
2023-09-01 23:56:59 +02:00
$t = Renderer :: getMarkupTemplate ( " community.tpl " );
$o = Renderer :: replaceMacros ( $t , [
'$content' => '' ,
2023-09-02 00:36:47 +02:00
'$header' => '' ,
2023-09-01 23:56:59 +02:00
]);
2023-09-02 23:37:02 +02:00
if ( $this -> pConfig -> get ( $this -> session -> getLocalUserId (), 'system' , 'infinite_scroll' )) {
2023-09-01 23:56:59 +02:00
$tpl = Renderer :: getMarkupTemplate ( 'infinite_scroll_head.tpl' );
2023-09-02 23:37:02 +02:00
$o .= Renderer :: replaceMacros ( $tpl , [ '$reload_uri' => $this -> args -> getQueryString ()]);
2023-09-01 23:56:59 +02:00
}
2023-09-02 21:16:48 +02:00
if ( empty ( $request [ 'mode' ]) || ( $request [ 'mode' ] != 'raw' )) {
2023-09-01 23:56:59 +02:00
$tabs = [];
$tabs [] = [
2023-09-02 23:37:02 +02:00
'label' => $this -> l10n -> t ( 'For you' ),
2023-09-02 00:36:47 +02:00
'url' => 'channel/' . self :: FORYOU ,
'sel' => self :: $content == self :: FORYOU ? 'active' : '' ,
2023-09-02 23:37:02 +02:00
'title' => $this -> l10n -> t ( 'Posts from contacts you interact with and who interact with you' ),
2023-09-02 00:36:47 +02:00
'id' => 'channel-foryou-tab' ,
2023-09-01 23:56:59 +02:00
'accesskey' => 'y'
];
$tabs [] = [
2023-09-02 23:37:02 +02:00
'label' => $this -> l10n -> t ( 'Followers' ),
2023-09-02 00:36:47 +02:00
'url' => 'channel/' . self :: FOLLOWERS ,
'sel' => self :: $content == self :: FOLLOWERS ? 'active' : '' ,
2023-09-02 23:37:02 +02:00
'title' => $this -> l10n -> t ( 'Posts from your followers that you don\'t follow' ),
2023-09-02 00:36:47 +02:00
'id' => 'channel-followers-tab' ,
2023-09-01 23:56:59 +02:00
'accesskey' => 'f'
];
2023-09-02 07:36:32 +02:00
2023-09-02 07:22:44 +02:00
$tabs [] = [
2023-09-03 10:53:44 +02:00
'label' => $this -> l10n -> t ( 'What\'s Hot' ),
2023-09-02 07:22:44 +02:00
'url' => 'channel/' . self :: WHATSHOT ,
'sel' => self :: $content == self :: WHATSHOT ? 'active' : '' ,
2023-09-02 23:37:02 +02:00
'title' => $this -> l10n -> t ( 'Posts with a lot of interactions' ),
2023-09-02 07:22:44 +02:00
'id' => 'channel-whatshot-tab' ,
'accesskey' => 'h'
];
2023-09-01 23:56:59 +02:00
2023-09-02 17:52:53 +02:00
$tabs [] = [
2023-09-02 23:37:02 +02:00
'label' => $this -> l10n -> t ( 'Images' ),
2023-09-02 17:52:53 +02:00
'url' => 'channel/' . self :: IMAGE ,
'sel' => self :: $content == self :: IMAGE ? 'active' : '' ,
2023-09-02 23:37:02 +02:00
'title' => $this -> l10n -> t ( 'Posts with images' ),
2023-09-02 17:52:53 +02:00
'id' => 'channel-image-tab' ,
'accesskey' => 'i'
];
$tabs [] = [
2023-09-02 23:37:02 +02:00
'label' => $this -> l10n -> t ( 'Videos' ),
2023-09-02 17:52:53 +02:00
'url' => 'channel/' . self :: VIDEO ,
'sel' => self :: $content == self :: VIDEO ? 'active' : '' ,
2023-09-02 23:37:02 +02:00
'title' => $this -> l10n -> t ( 'Posts with videos' ),
2023-09-02 17:52:53 +02:00
'id' => 'channel-video-tab' ,
'accesskey' => 'v'
];
$tabs [] = [
2023-09-02 23:37:02 +02:00
'label' => $this -> l10n -> t ( 'Audio' ),
2023-09-02 17:52:53 +02:00
'url' => 'channel/' . self :: AUDIO ,
'sel' => self :: $content == self :: AUDIO ? 'active' : '' ,
2023-09-02 23:37:02 +02:00
'title' => $this -> l10n -> t ( 'Posts with audio' ),
2023-09-02 17:52:53 +02:00
'id' => 'channel-audio-tab' ,
2023-09-03 05:40:54 +02:00
'accesskey' => 'd'
2023-09-02 17:52:53 +02:00
];
2023-09-03 10:44:17 +02:00
$language = User :: getLanguageCode ( $this -> session -> getLocalUserId (), false );
2023-09-03 07:23:49 +02:00
$languages = $this -> l10n -> getAvailableLanguages ();
2023-09-03 14:54:25 +02:00
2023-09-03 10:44:17 +02:00
$tabs [] = [
'label' => $languages [ $language ],
'url' => 'channel/' . self :: LANGUAGE ,
'sel' => self :: $content == self :: LANGUAGE ? 'active' : '' ,
'title' => $this -> l10n -> t ( 'Posts in %s' , $languages [ $language ]),
'id' => 'channel-language-tab' ,
'accesskey' => 'g'
];
2023-09-01 23:56:59 +02:00
$tab_tpl = Renderer :: getMarkupTemplate ( 'common_tabs.tpl' );
$o .= Renderer :: replaceMacros ( $tab_tpl , [ '$tabs' => $tabs ]);
Nav :: setSelected ( 'channel' );
2023-09-02 23:37:02 +02:00
$this -> page [ 'aside' ] .= Widget :: accountTypes ( 'channel/' . self :: $content , self :: $accountTypeString );
2023-09-01 23:56:59 +02:00
2023-09-02 23:37:02 +02:00
if ( ! in_array ( self :: $content , [ self :: FOLLOWERS , self :: FORYOU ]) && $this -> config -> get ( 'system' , 'community_no_sharer' )) {
2023-09-01 23:56:59 +02:00
$path = self :: $content ;
if ( ! empty ( $this -> parameters [ 'accounttype' ])) {
$path .= '/' . $this -> parameters [ 'accounttype' ];
}
$query_parameters = [];
2023-09-02 21:16:48 +02:00
if ( ! empty ( $request [ 'min_id' ])) {
$query_parameters [ 'min_id' ] = $request [ 'min_id' ];
2023-09-01 23:56:59 +02:00
}
2023-09-02 21:16:48 +02:00
if ( ! empty ( $request [ 'max_id' ])) {
$query_parameters [ 'max_id' ] = $request [ 'max_id' ];
2023-09-01 23:56:59 +02:00
}
2023-09-02 21:16:48 +02:00
if ( ! empty ( $request [ 'last_created' ])) {
$query_parameters [ 'max_id' ] = $request [ 'last_created' ];
2023-09-01 23:56:59 +02:00
}
2023-09-02 00:36:47 +02:00
$path_all = $path . ( ! empty ( $query_parameters ) ? '?' . http_build_query ( $query_parameters ) : '' );
2023-09-01 23:56:59 +02:00
$path_no_sharer = $path . '?' . http_build_query ( array_merge ( $query_parameters , [ 'no_sharer' => true ]));
2023-09-02 23:37:02 +02:00
$this -> page [ 'aside' ] .= Renderer :: replaceMacros ( Renderer :: getMarkupTemplate ( 'widget/community_sharer.tpl' ), [
'$title' => $this -> l10n -> t ( 'Own Contacts' ),
2023-09-01 23:56:59 +02:00
'$path_all' => $path_all ,
'$path_no_sharer' => $path_no_sharer ,
2023-09-02 21:16:48 +02:00
'$no_sharer' => ! empty ( $request [ 'no_sharer' ]),
2023-09-02 23:37:02 +02:00
'$all' => $this -> l10n -> t ( 'Include' ),
'$no_sharer_label' => $this -> l10n -> t ( 'Hide' ),
2023-09-01 23:56:59 +02:00
'$base' => 'channel' ,
]);
}
2023-09-02 23:37:02 +02:00
if ( Feature :: isEnabled ( $this -> session -> getLocalUserId (), 'trending_tags' )) {
$this -> page [ 'aside' ] .= TrendingTags :: getHTML ( self :: $content );
2023-09-01 23:56:59 +02:00
}
// We need the editor here to be able to reshare an item.
2023-09-02 23:37:02 +02:00
$o .= $this -> conversation -> statusEditor ([], 0 , true );
2023-09-01 23:56:59 +02:00
}
2023-09-03 05:35:10 +02:00
$items = $this -> getItems ( $request );
2023-09-01 23:56:59 +02:00
2023-09-02 23:48:55 +02:00
if ( ! $this -> database -> isResult ( $items )) {
2023-09-02 23:37:02 +02:00
$this -> systemMessages -> addNotice ( $this -> l10n -> t ( 'No results.' ));
2023-09-01 23:56:59 +02:00
return $o ;
}
2023-09-02 23:37:02 +02:00
$o .= $this -> conversation -> render ( $items , Conversation :: MODE_CHANNEL , false , false , 'created' , $this -> session -> getLocalUserId ());
2023-09-01 23:56:59 +02:00
$pager = new BoundariesPager (
2023-09-02 23:37:02 +02:00
$this -> l10n ,
$this -> args -> getQueryString (),
2023-09-01 23:56:59 +02:00
$items [ 0 ][ 'created' ],
$items [ count ( $items ) - 1 ][ 'created' ],
self :: $itemsPerPage
);
2023-09-02 23:37:02 +02:00
if ( $this -> pConfig -> get ( $this -> session -> getLocalUserId (), 'system' , 'infinite_scroll' )) {
2023-09-01 23:56:59 +02:00
$o .= HTML :: scrollLoader ();
} else {
$o .= $pager -> renderMinimal ( count ( $items ));
}
return $o ;
}
/**
* Computes module parameters from the request and local configuration
*
* @ throws HTTPException\BadRequestException
* @ throws HTTPException\ForbiddenException
*/
2023-09-02 21:16:48 +02:00
protected function parseRequest ( array $request )
2023-09-01 23:56:59 +02:00
{
2023-09-02 21:16:48 +02:00
self :: $accountTypeString = $request [ 'accounttype' ] ? ? $this -> parameters [ 'accounttype' ] ? ? '' ;
2023-09-02 00:36:47 +02:00
self :: $accountType = User :: getAccountTypeByString ( self :: $accountTypeString );
2023-09-01 23:56:59 +02:00
self :: $content = $this -> parameters [ 'content' ] ? ? '' ;
if ( ! self :: $content ) {
2023-09-02 07:22:44 +02:00
self :: $content = self :: FORYOU ;
2023-09-01 23:56:59 +02:00
}
2023-09-03 14:54:25 +02:00
if ( ! in_array ( self :: $content , [ self :: WHATSHOT , self :: FORYOU , self :: FOLLOWERS , self :: IMAGE , self :: VIDEO , self :: AUDIO , self :: LANGUAGE ])) {
2023-09-02 23:37:02 +02:00
throw new HTTPException\BadRequestException ( $this -> l10n -> t ( 'Channel not available.' ));
2023-09-01 23:56:59 +02:00
}
2023-09-02 23:37:02 +02:00
if ( $this -> mode -> isMobile ()) {
self :: $itemsPerPage = $this -> pConfig -> get (
$this -> session -> getLocalUserId (),
2023-09-01 23:56:59 +02:00
'system' ,
'itemspage_mobile_network' ,
2023-09-02 23:37:02 +02:00
$this -> config -> get ( 'system' , 'itemspage_network_mobile' )
2023-09-01 23:56:59 +02:00
);
} else {
2023-09-02 23:37:02 +02:00
self :: $itemsPerPage = $this -> pConfig -> get (
$this -> session -> getLocalUserId (),
2023-09-01 23:56:59 +02:00
'system' ,
'itemspage_network' ,
2023-09-02 23:37:02 +02:00
$this -> config -> get ( 'system' , 'itemspage_network' )
2023-09-01 23:56:59 +02:00
);
}
2023-09-02 21:16:48 +02:00
if ( ! empty ( $request [ 'item' ])) {
$item = Post :: selectFirst ([ 'parent-uri-id' ], [ 'id' => $request [ 'item' ]]);
2023-09-01 23:56:59 +02:00
self :: $item_id = $item [ 'parent-uri-id' ] ? ? 0 ;
} else {
self :: $item_id = 0 ;
}
2023-09-02 21:16:48 +02:00
self :: $min_id = $request [ 'min_id' ] ? ? null ;
2023-09-03 05:46:19 +02:00
self :: $max_id = $request [ 'last_created' ] ? ? $request [ 'max_id' ] ? ? null ;
2023-09-01 23:56:59 +02:00
}
/**
* Computes the displayed items .
*
* Community pages have a restriction on how many successive posts by the same author can show on any given page ,
* so we may have to retrieve more content beyond the first query
*
* @ return array
* @ throws \Exception
*/
2023-09-03 05:35:10 +02:00
protected function getItems ( array $request )
2023-09-01 23:56:59 +02:00
{
if ( self :: $content == self :: WHATSHOT ) {
if ( ! is_null ( self :: $accountType )) {
2023-09-02 23:37:02 +02:00
$condition = [ " (`comments` >= ? OR `activities` >= ?) AND `contact-type` = ? " , $this -> getMedianComments ( 4 ), $this -> getMedianActivities ( 4 ), self :: $accountType ];
2023-09-01 23:56:59 +02:00
} else {
2023-09-02 23:37:02 +02:00
$condition = [ " (`comments` >= ? OR `activities` >= ?) AND `contact-type` != ? " , $this -> getMedianComments ( 4 ), $this -> getMedianActivities ( 4 ), Contact :: TYPE_COMMUNITY ];
2023-09-01 23:56:59 +02:00
}
2023-09-03 14:54:25 +02:00
$condition = $this -> addLanguageCondition ( $condition );
2023-09-01 23:56:59 +02:00
} elseif ( self :: $content == self :: FORYOU ) {
2023-09-03 05:35:10 +02:00
$cid = Contact :: getPublicIdByUserId ( $this -> session -> getLocalUserId ());
2023-09-02 14:47:48 +02:00
2023-09-02 16:19:52 +02:00
$condition = [ " (`owner-id` IN (SELECT `relation-cid` FROM `contact-relation` WHERE `cid` = ? AND `thread-score` > ?) OR
(( `comments` >= ? OR `activities` >= ? ) AND `owner-id` IN ( SELECT `pid` FROM `account-user-view` WHERE `uid` = ? AND `rel` IN ( ? , ? ))) OR
( `owner-id` IN ( SELECT `pid` FROM `account-user-view` WHERE `uid` = ? AND `rel` IN ( ? , ? ) AND `notify_new_posts` ))) " ,
2023-09-03 05:35:10 +02:00
$cid , $this -> getMedianThreadScore ( $cid , 4 ), $this -> getMedianComments ( 4 ), $this -> getMedianActivities ( 4 ), $this -> session -> getLocalUserId (), Contact :: FRIEND , Contact :: SHARING ,
$this -> session -> getLocalUserId (), Contact :: FRIEND , Contact :: SHARING ];
2023-09-01 23:56:59 +02:00
} elseif ( self :: $content == self :: FOLLOWERS ) {
2023-09-03 05:35:10 +02:00
$condition = [ " `owner-id` IN (SELECT `pid` FROM `account-user-view` WHERE `uid` = ? AND `rel` = ?) " , $this -> session -> getLocalUserId (), Contact :: FOLLOWER ];
2023-09-02 17:52:53 +02:00
} elseif ( self :: $content == self :: IMAGE ) {
$condition = [ " `media-type` & ? " , 1 ];
} elseif ( self :: $content == self :: VIDEO ) {
$condition = [ " `media-type` & ? " , 2 ];
} elseif ( self :: $content == self :: AUDIO ) {
$condition = [ " `media-type` & ? " , 4 ];
2023-09-03 07:23:49 +02:00
} elseif ( self :: $content == self :: LANGUAGE ) {
2023-09-03 10:44:17 +02:00
$condition = [ " JSON_EXTRACT(JSON_KEYS(language), ' $ [0]') = ? " , User :: getLanguageCode ( $this -> session -> getLocalUserId (), true )];
2023-09-02 14:47:48 +02:00
}
2023-09-02 18:16:56 +02:00
$condition [ 0 ] .= " AND NOT EXISTS(SELECT `cid` FROM `user-contact` WHERE `uid` = ? AND `cid` = `post-engagement`.`owner-id` AND (`ignored` OR `blocked` OR `collapsed`)) " ;
2023-09-03 05:35:10 +02:00
$condition [] = $this -> session -> getLocalUserId ();
2023-09-02 18:16:56 +02:00
2023-09-02 14:47:48 +02:00
if (( self :: $content != self :: WHATSHOT ) && ! is_null ( self :: $accountType )) {
$condition [ 0 ] .= " AND `contact-type` = ? " ;
$condition [] = self :: $accountType ;
2023-09-01 23:56:59 +02:00
}
$params = [ 'order' => [ 'created' => true ], 'limit' => self :: $itemsPerPage ];
if ( ! empty ( self :: $item_id )) {
$condition [ 0 ] .= " AND `uri-id` = ? " ;
$condition [] = self :: $item_id ;
} else {
2023-09-02 21:16:48 +02:00
if ( ! empty ( $request [ 'no_sharer' ])) {
2023-09-01 23:56:59 +02:00
$condition [ 0 ] .= " AND NOT `uri-id` IN (SELECT `uri-id` FROM `post-user` WHERE `post-user`.`uid` = ? AND `post-user`.`uri-id` = `post-engagement`.`uri-id`) " ;
2023-09-03 05:35:10 +02:00
$condition [] = $this -> session -> getLocalUserId ();
2023-09-01 23:56:59 +02:00
}
if ( isset ( self :: $max_id )) {
$condition [ 0 ] .= " AND `created` < ? " ;
$condition [] = self :: $max_id ;
}
if ( isset ( self :: $min_id )) {
$condition [ 0 ] .= " AND `created` > ? " ;
$condition [] = self :: $min_id ;
// Previous page case: we want the items closest to min_id but for that we need to reverse the query order
if ( ! isset ( self :: $max_id )) {
$params [ 'order' ][ 'created' ] = false ;
}
}
}
2023-09-02 23:48:55 +02:00
$items = $this -> database -> selectToArray ( 'post-engagement' , [ 'uri-id' , 'created' ], $condition , $params );
2023-09-01 23:56:59 +02:00
if ( empty ( $items )) {
return [];
}
// Previous page case: once we get the relevant items closest to min_id, we need to restore the expected display order
if ( empty ( self :: $item_id ) && isset ( self :: $min_id ) && ! isset ( self :: $max_id )) {
$items = array_reverse ( $items );
}
2023-09-03 14:54:25 +02:00
Item :: update ([ 'unseen' => false ], [ 'unseen' => true , 'uid' => $this -> session -> getLocalUserId (), 'uri-id' => array_column ( $items , 'uri-id' )]);
2023-09-01 23:56:59 +02:00
return $items ;
}
2023-09-02 14:47:48 +02:00
2023-09-03 14:54:25 +02:00
private function addLanguageCondition ( array $condition ) : array
{
$conditions = [];
$languages = $this -> pConfig -> get ( $this -> session -> getLocalUserId (), 'channel' , 'languages' , [ User :: getLanguageCode ( $this -> session -> getLocalUserId (), false )]);
foreach ( $languages as $language ) {
$conditions [] = " JSON_EXTRACT(JSON_KEYS(language), ' $ [0]') = ? " ;
$condition [] = substr ( $language , 0 , 2 );
}
if ( ! empty ( $conditions )) {
$condition [ 0 ] .= " AND (`language` IS NULL OR " . implode ( ' OR ' , $conditions ) . " ) " ;
}
return $condition ;
}
2023-09-02 23:37:02 +02:00
private function getMedianComments ( int $divider ) : int
2023-09-02 14:47:48 +02:00
{
2023-09-02 15:56:54 +02:00
$cache_key = 'Channel:getMedianComments:' . $divider ;
2023-09-02 23:37:02 +02:00
$comments = $this -> cache -> get ( $cache_key );
2023-09-02 14:47:48 +02:00
if ( ! empty ( $comments )) {
return $comments ;
}
2023-09-02 23:48:55 +02:00
$limit = $this -> database -> count ( 'post-engagement' , [ " `contact-type` != ? AND `comments` > ? " , Contact :: TYPE_COMMUNITY , 0 ]) / $divider ;
$post = $this -> database -> selectToArray ( 'post-engagement' , [ 'comments' ], [ " `contact-type` != ? " , Contact :: TYPE_COMMUNITY ], [ 'order' => [ 'comments' => true ], 'limit' => [ $limit , 1 ]]);
2023-09-02 14:47:48 +02:00
$comments = $post [ 0 ][ 'comments' ] ? ? 0 ;
if ( empty ( $comments )) {
return 0 ;
}
2023-09-02 23:37:02 +02:00
$this -> cache -> set ( $cache_key , $comments , Duration :: HOUR );
2023-09-02 14:47:48 +02:00
return $comments ;
}
2023-09-02 23:37:02 +02:00
private function getMedianActivities ( int $divider ) : int
2023-09-02 15:56:54 +02:00
{
$cache_key = 'Channel:getMedianActivities:' . $divider ;
2023-09-02 23:37:02 +02:00
$activities = $this -> cache -> get ( $cache_key );
2023-09-02 15:56:54 +02:00
if ( ! empty ( $activities )) {
return $activities ;
}
2023-09-02 23:48:55 +02:00
$limit = $this -> database -> count ( 'post-engagement' , [ " `contact-type` != ? AND `activities` > ? " , Contact :: TYPE_COMMUNITY , 0 ]) / $divider ;
$post = $this -> database -> selectToArray ( 'post-engagement' , [ 'activities' ], [ " `contact-type` != ? " , Contact :: TYPE_COMMUNITY ], [ 'order' => [ 'activities' => true ], 'limit' => [ $limit , 1 ]]);
2023-09-02 15:56:54 +02:00
$activities = $post [ 0 ][ 'activities' ] ? ? 0 ;
if ( empty ( $activities )) {
return 0 ;
}
2023-09-02 23:37:02 +02:00
$this -> cache -> set ( $cache_key , $activities , Duration :: HOUR );
2023-09-02 15:56:54 +02:00
return $activities ;
}
2023-09-02 23:37:02 +02:00
private function getMedianThreadScore ( int $cid , int $divider ) : int
2023-09-02 14:47:48 +02:00
{
$cache_key = 'Channel:getThreadScore:' . $cid . ':' . $divider ;
2023-09-02 23:37:02 +02:00
$score = $this -> cache -> get ( $cache_key );
2023-09-02 14:47:48 +02:00
if ( ! empty ( $score )) {
return $score ;
}
2023-09-02 23:48:55 +02:00
$limit = $this -> database -> count ( 'contact-relation' , [ " `cid` = ? AND `thread-score` > ? " , $cid , 0 ]) / $divider ;
$relation = $this -> database -> selectToArray ( 'contact-relation' , [ 'thread-score' ], [ 'cid' => $cid ], [ 'order' => [ 'thread-score' => true ], 'limit' => [ $limit , 1 ]]);
2023-09-02 14:47:48 +02:00
$score = $relation [ 0 ][ 'thread-score' ] ? ? 0 ;
if ( empty ( $score )) {
return 0 ;
}
2023-09-02 23:37:02 +02:00
$this -> cache -> set ( $cache_key , $score , Duration :: HOUR );
2023-09-02 14:47:48 +02:00
return $score ;
}
2023-09-01 23:56:59 +02:00
}