2013-02-21 14:58:06 +00:00
< ? php
require_once " colors.php " ;
class Feeds extends Handler_Protected {
2023-03-05 19:14:08 +00:00
/** special feed for archived articles */
const FEED_ARCHIVED = 0 ;
/** special feed for starred articles */
const FEED_STARRED = - 1 ;
/** special feed for published articles */
const FEED_PUBLISHED = - 2 ;
/** special feed for archived articles */
const FEED_FRESH = - 3 ;
/** special feed for all articles */
const FEED_ALL = - 4 ;
/**
* a special case feed used to display auxiliary information when there ' s nothing to load ( e . g . no stuff in fresh feed )
*
* TODO : Remove this and 'Feeds::_generate_dashboard_feed()' ? It only seems to be used if 'Feeds::view()' ( also potentially removable )
* gets passed the ID .
*/
2023-03-07 15:45:07 +00:00
const FEED_DASHBOARD = - 5 ;
2023-03-05 19:14:08 +00:00
/** special feed for recently read articles */
const FEED_RECENTLY_READ = - 6 ;
/** special feed for error scenarios (e.g. feed not found) */
const FEED_ERROR = - 7 ;
/** special "category" for uncategorized articles */
const CATEGORY_UNCATEGORIZED = 0 ;
/** special category for "special" articles (e.g. Starred, Published, Archived, plugin-provided, etc.) */
const CATEGORY_SPECIAL = - 1 ;
/** special category for labels */
const CATEGORY_LABELS = - 2 ;
/** special category for all feeds, excluding virtual feeds (e.g. labels and such) */
const CATEGORY_ALL_EXCEPT_VIRTUAL = - 3 ;
/** special category for all feeds, including virtual feeds (e.g. labels and such) */
const CATEGORY_ALL = - 4 ;
const NEVER_GROUP_FEEDS = [ Feeds :: FEED_RECENTLY_READ , Feeds :: FEED_ARCHIVED ];
const NEVER_GROUP_BY_DATE = [ Feeds :: FEED_PUBLISHED , Feeds :: FEED_STARRED , Feeds :: FEED_FRESH ];
2013-02-21 14:58:06 +00:00
2021-11-12 02:01:31 +00:00
function csrf_ignore ( string $method ) : bool {
2020-09-15 13:28:09 +00:00
$csrf_ignored = array ( " index " );
2013-02-21 14:58:06 +00:00
return array_search ( $method , $csrf_ignored ) !== false ;
}
2021-11-12 04:48:06 +00:00
/**
2021-11-29 07:20:13 +00:00
* @ param string | int $feed
2021-11-12 04:48:06 +00:00
* @ return array { 0 : array < int , int > , 1 : int , 2 : int , 3 : bool , 4 : array < string , mixed > } $topmost_article_ids , $headlines_count , $feed , $disable_cache , $reply
*/
2021-11-29 09:30:33 +00:00
private function _format_headlines_list ( $feed , string $method , string $view_mode , int $limit , bool $cat_view ,
2021-11-13 04:14:18 +00:00
int $offset , string $override_order , bool $include_children , ? int $check_first_id = null ,
2021-11-30 20:50:09 +00:00
? bool $skip_first_id_check = false , ? string $order_by = '' ) : array {
2013-02-21 14:58:06 +00:00
$disable_cache = false ;
2023-10-20 19:39:41 +00:00
$span = Tracer :: start ( __METHOD__ );
$span -> setAttribute ( 'func.args' , json_encode ( func_get_args ()));
2020-12-04 15:55:53 +00:00
2021-02-06 14:19:07 +00:00
$reply = [];
$rgba_cache = [];
$topmost_article_ids = [];
2013-02-21 14:58:06 +00:00
if ( ! $offset ) $offset = 0 ;
if ( $method == " undefined " ) $method = " " ;
$method_split = explode ( " : " , $method );
2016-01-26 08:45:47 +00:00
if ( $method == " ForceUpdate " && $feed > 0 && is_numeric ( $feed )) {
2018-11-03 12:08:43 +00:00
$sth = $this -> pdo -> prepare ( " UPDATE ttrss_feeds
2017-12-31 04:37:49 +00:00
SET last_updated = '1970-01-01' , last_update_started = '1970-01-01'
WHERE id = ? " );
$sth -> execute ([ $feed ]);
2013-02-21 14:58:06 +00:00
}
if ( $method_split [ 0 ] == " MarkAllReadGR " ) {
2021-02-15 12:43:07 +00:00
$this -> _catchup ( $method_split [ 1 ], false );
2013-02-21 14:58:06 +00:00
}
// FIXME: might break tag display?
if ( is_numeric ( $feed ) && $feed > 0 && ! $cat_view ) {
2017-12-01 17:15:25 +00:00
$sth = $this -> pdo -> prepare ( " SELECT id FROM ttrss_feeds WHERE id = ? LIMIT 1 " );
$sth -> execute ([ $feed ]);
2013-02-21 14:58:06 +00:00
2017-12-01 17:15:25 +00:00
if ( ! $sth -> fetch ()) {
2013-02-21 14:58:06 +00:00
$reply [ 'content' ] = " <div align='center'> " . __ ( 'Feed not found.' ) . " </div> " ;
}
}
2021-02-05 20:41:32 +00:00
$search = $_REQUEST [ " query " ] ? ? " " ;
$search_language = $_REQUEST [ " search_language " ] ? ? " " ; // PGSQL only
2013-02-21 14:58:06 +00:00
if ( $search ) {
$disable_cache = true ;
}
2021-02-06 14:19:07 +00:00
$qfh_ret = [];
2013-03-28 19:34:35 +00:00
if ( ! $cat_view && is_numeric ( $feed ) && $feed < PLUGIN_FEED_BASE_INDEX && $feed > LABEL_BASE_INDEX ) {
2021-11-18 08:03:26 +00:00
/** @var IVirtualFeed|false $handler */
2013-04-18 08:27:34 +00:00
$handler = PluginHost :: getInstance () -> get_feed_handler (
2013-03-27 12:14:27 +00:00
PluginHost :: feed_to_pfeed_id ( $feed ));
if ( $handler ) {
$options = array (
" limit " => $limit ,
" view_mode " => $view_mode ,
" cat_view " => $cat_view ,
" search " => $search ,
" override_order " => $override_order ,
" offset " => $offset ,
" owner_uid " => $_SESSION [ " uid " ],
" filter " => false ,
" since_id " => 0 ,
2018-12-09 10:35:37 +00:00
" include_children " => $include_children ,
" order_by " => $order_by );
2013-03-27 12:14:27 +00:00
$qfh_ret = $handler -> get_headlines ( PluginHost :: feed_to_pfeed_id ( $feed ),
$options );
}
} else {
2015-07-11 22:29:36 +00:00
$params = array (
" feed " => $feed ,
" limit " => $limit ,
" view_mode " => $view_mode ,
" cat_view " => $cat_view ,
" search " => $search ,
2015-08-04 10:53:48 +00:00
" search_language " => $search_language ,
2015-07-11 22:29:36 +00:00
" override_order " => $override_order ,
" offset " => $offset ,
" include_children " => $include_children ,
2015-11-21 19:20:00 +00:00
" check_first_id " => $check_first_id ,
2018-12-09 10:35:37 +00:00
" skip_first_id_check " => $skip_first_id_check ,
" order_by " => $order_by
2015-07-11 22:29:36 +00:00
);
2021-02-15 12:43:07 +00:00
$qfh_ret = $this -> _get_headlines ( $params );
2013-03-27 12:14:27 +00:00
}
2013-02-21 14:58:06 +00:00
2021-02-25 11:49:58 +00:00
$vfeed_group_enabled = get_pref ( Prefs :: VFEED_GROUP_BY_FEED ) &&
2020-09-22 11:54:15 +00:00
! ( in_array ( $feed , self :: NEVER_GROUP_FEEDS ) && ! $cat_view );
2014-03-12 21:07:52 +00:00
2017-12-04 07:26:22 +00:00
$result = $qfh_ret [ 0 ]; // this could be either a PDO query result or a -1 if first id changed
2013-02-21 14:58:06 +00:00
$feed_title = $qfh_ret [ 1 ];
$feed_site_url = $qfh_ret [ 2 ];
$last_error = $qfh_ret [ 3 ];
2022-07-13 04:08:31 +00:00
$last_updated = strpos ( $qfh_ret [ 4 ] ? ? " " , '1970-' ) === false ?
2020-09-23 10:04:26 +00:00
TimeHelper :: make_local_datetime ( $qfh_ret [ 4 ], false ) : __ ( " Never " );
2013-07-31 10:53:34 +00:00
$highlight_words = $qfh_ret [ 5 ];
2015-07-12 14:55:35 +00:00
$reply [ 'first_id' ] = $qfh_ret [ 6 ];
2019-01-16 18:33:59 +00:00
$reply [ 'is_vfeed' ] = $qfh_ret [ 7 ];
2019-04-30 11:39:08 +00:00
$query_error_override = $qfh_ret [ 8 ];
2017-03-31 08:21:35 +00:00
$reply [ 'search_query' ] = [ $search , $search_language ];
2018-12-07 18:11:50 +00:00
$reply [ 'vfeed_group_enabled' ] = $vfeed_group_enabled ;
2013-02-21 14:58:06 +00:00
2023-10-20 19:39:41 +00:00
$span -> addEvent ( 'plugin_menu_items' );
2023-04-09 19:15:16 +00:00
2021-02-14 19:17:13 +00:00
$plugin_menu_items = " " ;
2021-12-14 18:53:45 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_HEADLINE_TOOLBAR_SELECT_MENU_ITEM2 ,
2021-02-14 19:17:13 +00:00
function ( $result ) use ( & $plugin_menu_items ) {
$plugin_menu_items .= $result ;
},
$feed , $cat_view );
$plugin_buttons = " " ;
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_HEADLINE_TOOLBAR_BUTTON ,
function ( $result ) use ( & $plugin_buttons ) {
$plugin_buttons .= $result ;
},
$feed , $cat_view );
$reply [ 'toolbar' ] = [
'site_url' => $feed_site_url ,
2021-02-15 04:46:24 +00:00
'title' => strip_tags ( $feed_title ),
2021-02-14 19:17:13 +00:00
'error' => $last_error ,
'last_updated' => $last_updated ,
'plugin_menu_items' => $plugin_menu_items ,
'plugin_buttons' => $plugin_buttons ,
];
2013-02-21 14:58:06 +00:00
2021-02-06 14:19:07 +00:00
$reply [ 'content' ] = [];
2021-02-08 20:10:22 +00:00
if ( $offset == 0 )
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_HEADLINES_BEFORE ,
function ( $result ) use ( & $reply ) {
$reply [ 'content' ] .= $result ;
},
$feed , $cat_view , $qfh_ret );
2014-08-19 10:24:34 +00:00
2023-10-20 19:39:41 +00:00
$span -> addEvent ( 'articles' );
2020-12-04 15:55:53 +00:00
2017-12-01 17:25:13 +00:00
$headlines_count = 0 ;
2021-02-06 14:19:07 +00:00
if ( $result instanceof PDOStatement ) {
2018-12-07 13:00:11 +00:00
while ( $line = $result -> fetch ( PDO :: FETCH_ASSOC )) {
2023-10-20 19:39:41 +00:00
$span -> addEvent ( 'article: ' . $line [ 'id' ]);
2017-12-01 17:25:13 +00:00
2017-12-04 07:26:22 +00:00
++ $headlines_count ;
2013-02-21 14:58:06 +00:00
2021-02-25 11:49:58 +00:00
if ( ! get_pref ( Prefs :: SHOW_CONTENT_PREVIEW )) {
2018-12-09 01:24:48 +00:00
$line [ " content_preview " ] = " " ;
2018-12-07 13:00:11 +00:00
} else {
$line [ " content_preview " ] = " — " . truncate_string ( strip_tags ( $line [ " content " ]), 250 );
2013-02-21 14:58:06 +00:00
2021-02-08 20:10:22 +00:00
$max_excerpt_length = 250 ;
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_QUERY_HEADLINES ,
function ( $result ) use ( & $line ) {
$line = $result ;
},
$line , $max_excerpt_length );
2020-12-04 15:55:53 +00:00
}
2017-12-04 07:26:22 +00:00
$id = $line [ " id " ];
2013-07-10 12:52:03 +00:00
2018-12-08 05:23:18 +00:00
// frontend doesn't expect pdo returning booleans as strings on mysql
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " mysql " ) {
2018-12-08 05:23:18 +00:00
foreach ([ " unread " , " marked " , " published " ] as $k ) {
2022-01-28 07:37:29 +00:00
if ( is_integer ( $line [ $k ])) {
$line [ $k ] = $line [ $k ] === 1 ;
} else {
$line [ $k ] = $line [ $k ] === " 1 " ;
}
2018-12-08 05:23:18 +00:00
}
}
2018-12-06 16:00:11 +00:00
// normalize archived feed
2018-12-07 13:00:11 +00:00
if ( $line [ 'feed_id' ] === null ) {
2023-03-05 19:14:08 +00:00
$line [ 'feed_id' ] = Feeds :: FEED_ARCHIVED ;
2018-12-06 16:00:11 +00:00
$line [ " feed_title " ] = __ ( " Archived articles " );
}
2018-12-07 15:24:56 +00:00
$feed_id = $line [ " feed_id " ];
2018-12-07 13:00:11 +00:00
2021-02-27 07:58:11 +00:00
if ( $line [ " num_labels " ] > 0 ) {
$label_cache = $line [ " label_cache " ];
$labels = false ;
2015-07-12 22:19:52 +00:00
2017-12-04 07:26:22 +00:00
if ( $label_cache ) {
2021-02-27 07:58:11 +00:00
$label_cache = json_decode ( $label_cache , true );
if ( $label_cache ) {
if ( $label_cache [ " no-labels " ] ? ? 0 == 1 )
$labels = [];
else
$labels = $label_cache ;
}
} else {
$labels = Article :: _get_labels ( $id );
2017-12-04 07:26:22 +00:00
}
2021-02-25 18:27:16 +00:00
$line [ " labels " ] = $labels ;
} else {
$line [ " labels " ] = [];
2017-12-04 07:26:22 +00:00
}
2013-07-10 12:52:03 +00:00
2017-12-04 07:26:22 +00:00
if ( count ( $topmost_article_ids ) < 3 ) {
array_push ( $topmost_article_ids , $id );
}
2013-02-21 14:58:06 +00:00
2021-02-05 20:41:32 +00:00
$line [ " feed_title " ] = $line [ " feed_title " ] ? ? " " ;
2013-02-21 14:58:06 +00:00
2021-10-24 17:11:49 +00:00
$button_doc = new DOMDocument ();
2020-12-04 15:55:53 +00:00
$line [ " buttons_left " ] = " " ;
2021-02-08 20:10:22 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_ARTICLE_LEFT_BUTTON ,
2021-10-24 17:11:49 +00:00
function ( $result , $plugin ) use ( & $line , & $button_doc ) {
2021-10-26 12:45:12 +00:00
if ( $result && $button_doc -> loadXML ( $result )) {
2021-10-24 17:11:49 +00:00
2022-07-31 10:55:09 +00:00
/** @var DOMElement|null $child */
2021-10-24 17:11:49 +00:00
$child = $button_doc -> firstChild ;
if ( $child ) {
do {
2022-07-31 10:55:09 +00:00
/** @var DOMElement|null $child */
2021-10-24 17:11:49 +00:00
$child -> setAttribute ( 'data-plugin-name' , get_class ( $plugin ));
} while ( $child = $child -> nextSibling );
$line [ " buttons_left " ] .= $button_doc -> saveXML ( $button_doc -> firstChild );
}
2022-01-06 07:37:03 +00:00
} else if ( $result ) {
user_error ( get_class ( $plugin ) .
" plugin: content provided in HOOK_ARTICLE_LEFT_BUTTON is not valid XML: " .
Errors :: libxml_last_error () . " $result " , E_USER_WARNING );
2021-10-24 17:11:49 +00:00
}
2021-02-08 20:10:22 +00:00
},
$line );
2020-12-04 15:55:53 +00:00
$line [ " buttons " ] = " " ;
2023-04-09 19:15:16 +00:00
2021-02-08 20:10:22 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_ARTICLE_BUTTON ,
2021-10-24 17:11:49 +00:00
function ( $result , $plugin ) use ( & $line , & $button_doc ) {
2021-10-26 12:45:12 +00:00
if ( $result && $button_doc -> loadXML ( $result )) {
2021-10-24 17:11:49 +00:00
2022-07-31 10:55:09 +00:00
/** @var DOMElement|null $child */
2021-10-24 17:11:49 +00:00
$child = $button_doc -> firstChild ;
if ( $child ) {
do {
2022-07-31 10:55:09 +00:00
/** @var DOMElement|null $child */
2021-10-24 17:11:49 +00:00
$child -> setAttribute ( 'data-plugin-name' , get_class ( $plugin ));
} while ( $child = $child -> nextSibling );
$line [ " buttons " ] .= $button_doc -> saveXML ( $button_doc -> firstChild );
}
2022-01-06 07:37:03 +00:00
} else if ( $result ) {
user_error ( get_class ( $plugin ) .
" plugin: content provided in HOOK_ARTICLE_BUTTON is not valid XML: " .
Errors :: libxml_last_error () . " $result " , E_USER_WARNING );
2021-10-24 17:11:49 +00:00
}
2021-02-08 20:10:22 +00:00
},
$line );
2018-12-07 15:24:56 +00:00
2020-12-04 15:55:53 +00:00
$line [ " content " ] = Sanitizer :: sanitize ( $line [ " content " ],
2021-11-11 19:59:25 +00:00
$line [ 'hide_images' ], null , $line [ " site_url " ], $highlight_words , $line [ " id " ]);
2018-12-07 15:24:56 +00:00
2021-02-25 11:49:58 +00:00
if ( ! get_pref ( Prefs :: CDM_EXPANDED )) {
2020-12-04 15:55:53 +00:00
$line [ " cdm_excerpt " ] = " <span class='collapse'>
< i class = 'material-icons' onclick = 'return Article.cdmUnsetActive(event)'
title = \ " " . __ ( " Collapse article " ) . " \" >remove_circle</i></span> " ;
2021-02-25 11:49:58 +00:00
if ( get_pref ( Prefs :: SHOW_CONTENT_PREVIEW )) {
2020-12-04 15:55:53 +00:00
$line [ " cdm_excerpt " ] .= " <span class='excerpt'> " . $line [ " content_preview " ] . " </span> " ;
}
}
2021-02-25 18:27:16 +00:00
if ( $line [ " num_enclosures " ] > 0 ) {
$line [ " enclosures " ] = Article :: _format_enclosures ( $id ,
2021-11-12 01:50:40 +00:00
sql_bool_to_bool ( $line [ " always_display_enclosures " ]),
2021-02-25 18:27:16 +00:00
$line [ " content " ],
2021-11-12 01:50:40 +00:00
sql_bool_to_bool ( $line [ " hide_images " ]));
2021-02-25 18:27:16 +00:00
} else {
$line [ " enclosures " ] = [ 'formatted' => '' , 'entries' => [] ];
}
2020-12-04 15:55:53 +00:00
2020-09-23 10:04:26 +00:00
$line [ " updated_long " ] = TimeHelper :: make_local_datetime ( $line [ " updated " ], true );
2021-11-11 20:12:47 +00:00
$line [ " updated " ] = TimeHelper :: make_local_datetime ( $line [ " updated " ], false , null , false , true );
2018-12-08 06:32:14 +00:00
2018-12-07 13:00:11 +00:00
$line [ 'imported' ] = T_sprintf ( " Imported at %s " ,
2020-12-04 15:55:53 +00:00
TimeHelper :: make_local_datetime ( $line [ " date_entered " ], false ));
2018-12-07 15:24:56 +00:00
if ( $line [ " tag_cache " ])
$tags = explode ( " , " , $line [ " tag_cache " ]);
else
2021-02-25 18:27:16 +00:00
$tags = [];
$line [ " tags " ] = $tags ;
2013-02-21 14:58:06 +00:00
2021-02-25 18:27:16 +00:00
//$line["tags"] = Article::_get_tags($line["id"], false, $line["tag_cache"]);
2013-02-21 14:58:06 +00:00
2021-02-19 14:40:11 +00:00
$line [ 'has_icon' ] = self :: _has_icon ( $feed_id );
2013-02-21 14:58:06 +00:00
2018-12-07 15:24:56 +00:00
//setting feed headline background color, needs to change text color based on dark/light
2021-02-05 20:41:32 +00:00
$fav_color = $line [ 'favicon_avg_color' ] ? ? false ;
2013-02-21 14:58:06 +00:00
2023-10-20 19:39:41 +00:00
$span -> addEvent ( " colors " );
2020-12-04 15:55:53 +00:00
2017-12-04 07:26:22 +00:00
require_once " colors.php " ;
2013-02-21 14:58:06 +00:00
2018-12-12 04:57:37 +00:00
if ( ! isset ( $rgba_cache [ $feed_id ])) {
if ( $fav_color && $fav_color != 'fail' ) {
2021-02-16 14:07:23 +00:00
$rgba_cache [ $feed_id ] = \Colors\_color_unpack ( $fav_color );
2018-12-12 04:57:37 +00:00
} else {
2021-02-16 14:07:23 +00:00
$rgba_cache [ $feed_id ] = \Colors\_color_unpack ( $this -> _color_of ( $line [ 'feed_title' ]));
2017-12-04 07:26:22 +00:00
}
}
2013-02-21 14:58:06 +00:00
2018-12-12 04:57:37 +00:00
if ( isset ( $rgba_cache [ $feed_id ])) {
$line [ 'feed_bg_color' ] = 'rgba(' . implode ( " , " , $rgba_cache [ $feed_id ]) . ',0.3)' ;
2020-12-04 15:55:53 +00:00
}
2023-10-20 19:39:41 +00:00
$span -> addEvent ( " HOOK_RENDER_ARTICLE_CDM " );
2021-03-07 10:22:38 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_RENDER_ARTICLE_CDM ,
function ( $result , $plugin ) use ( & $line ) {
$line = $result ;
},
$line );
$line [ 'content' ] = DiskCache :: rewrite_urls ( $line [ 'content' ]);
2018-12-07 18:52:41 +00:00
/* we don't need those */
2020-12-04 15:55:53 +00:00
foreach ([ " date_entered " , " guid " , " last_published " , " last_marked " , " tag_cache " , " favicon_avg_color " ,
2021-02-25 18:42:05 +00:00
" uuid " , " label_cache " , " yyiw " , " num_enclosures " ] as $k )
2020-12-04 15:55:53 +00:00
unset ( $line [ $k ]);
2018-12-07 18:52:41 +00:00
2018-12-07 13:00:11 +00:00
array_push ( $reply [ 'content' ], $line );
2017-12-04 07:26:22 +00:00
}
2020-12-04 15:55:53 +00:00
}
2017-12-01 17:25:13 +00:00
if ( ! $headlines_count ) {
2013-02-21 14:58:06 +00:00
2021-02-06 14:19:07 +00:00
if ( $result instanceof PDOStatement ) {
2013-02-21 14:58:06 +00:00
2019-04-30 11:39:08 +00:00
if ( $query_error_override ) {
$message = $query_error_override ;
} else {
switch ( $view_mode ) {
case " unread " :
$message = __ ( " No unread articles found to display. " );
break ;
case " updated " :
$message = __ ( " No updated articles found to display. " );
break ;
case " marked " :
$message = __ ( " No starred articles found to display. " );
break ;
default :
if ( $feed < LABEL_BASE_INDEX ) {
$message = __ ( " No articles found to display. You can assign articles to labels manually from article header context menu (applies to all selected articles) or use a filter. " );
} else {
$message = __ ( " No articles found to display. " );
}
}
2017-12-01 17:25:13 +00:00
}
2013-02-21 14:58:06 +00:00
2017-12-01 17:25:13 +00:00
if ( ! $offset && $message ) {
$reply [ 'content' ] = " <div class='whiteBox'> $message " ;
2013-02-21 14:58:06 +00:00
2019-03-08 07:11:57 +00:00
$reply [ 'content' ] .= " <p><span class= \" text-muted \" > " ;
2013-02-21 14:58:06 +00:00
2017-12-01 17:25:13 +00:00
$sth = $this -> pdo -> prepare ( " SELECT " . SUBSTRING_FOR_DATE . " (MAX(last_updated), 1, 19) AS last_updated FROM ttrss_feeds
WHERE owner_uid = ? " );
$sth -> execute ([ $_SESSION [ 'uid' ]]);
$row = $sth -> fetch ();
2013-02-21 14:58:06 +00:00
2020-09-23 10:04:26 +00:00
$last_updated = TimeHelper :: make_local_datetime ( $row [ " last_updated " ], false );
2013-02-21 14:58:06 +00:00
2017-12-01 17:25:13 +00:00
$reply [ 'content' ] .= sprintf ( __ ( " Feeds last updated at %s " ), $last_updated );
2013-02-21 14:58:06 +00:00
2022-12-21 21:03:38 +00:00
$num_errors = ORM :: for_table ( 'ttrss_feeds' )
-> where_not_equal ( 'last_error' , '' )
-> where ( 'owner_uid' , $_SESSION [ 'uid' ])
2022-12-24 21:22:16 +00:00
-> where_gte ( 'update_interval' , 0 )
2022-12-21 21:03:38 +00:00
-> count ( 'id' );
2013-02-21 14:58:06 +00:00
2017-12-01 17:25:13 +00:00
if ( $num_errors > 0 ) {
$reply [ 'content' ] .= " <br/> " ;
2019-03-08 07:11:57 +00:00
$reply [ 'content' ] .= " <a class= \" text-muted \" href= \" # \" onclick= \" CommonDialogs.showFeedsWithErrors() \" > " .
2017-12-01 17:25:13 +00:00
__ ( 'Some feeds have update errors (click for details)' ) . " </a> " ;
}
$reply [ 'content' ] .= " </span></p></div> " ;
2015-07-13 10:29:13 +00:00
2017-12-01 17:25:13 +00:00
}
} else if ( is_numeric ( $result ) && $result == - 1 ) {
$reply [ 'first_id_changed' ] = true ;
2013-02-21 14:58:06 +00:00
}
}
2023-10-20 19:39:41 +00:00
$span -> end ();
2020-12-04 15:55:53 +00:00
2018-12-07 18:11:50 +00:00
return array ( $topmost_article_ids , $headlines_count , $feed , $disable_cache , $reply );
2013-02-21 14:58:06 +00:00
}
2021-11-12 04:48:06 +00:00
function catchupAll () : void {
2017-12-01 16:42:02 +00:00
$sth = $this -> pdo -> prepare ( " UPDATE ttrss_user_entries SET
last_read = NOW (), unread = false WHERE unread = true AND owner_uid = ? " );
$sth -> execute ([ $_SESSION [ 'uid' ]]);
2021-02-24 07:01:39 +00:00
print json_encode ( array ( " message " => " UPDATE_COUNTERS " ));
2013-02-21 14:58:06 +00:00
}
2021-11-12 04:48:06 +00:00
function view () : void {
2013-02-21 14:58:06 +00:00
$reply = array ();
2017-12-01 17:26:51 +00:00
$feed = $_REQUEST [ " feed " ];
2021-02-05 20:41:32 +00:00
$method = $_REQUEST [ " m " ] ? ? " " ;
2021-02-26 07:02:25 +00:00
$view_mode = $_REQUEST [ " view_mode " ] ? ? " " ;
2013-04-02 11:32:47 +00:00
$limit = 30 ;
2021-11-18 18:23:44 +00:00
$cat_view = self :: _param_to_bool ( $_REQUEST [ " cat " ] ? ? false );
2021-02-05 20:41:32 +00:00
$next_unread_feed = $_REQUEST [ " nuf " ] ? ? 0 ;
2021-11-12 04:48:06 +00:00
$offset = ( int ) ( $_REQUEST [ " skip " ] ? ? 0 );
2021-02-16 07:11:58 +00:00
$order_by = $_REQUEST [ " order_by " ] ? ? " " ;
2021-02-05 20:41:32 +00:00
$check_first_id = $_REQUEST [ " fid " ] ? ? 0 ;
2013-02-21 14:58:06 +00:00
if ( is_numeric ( $feed )) $feed = ( int ) $feed ;
2023-03-07 15:45:07 +00:00
if ( $feed == Feeds :: FEED_DASHBOARD ) {
2021-02-15 13:51:35 +00:00
print json_encode ( $this -> _generate_dashboard_feed ());
2013-02-21 14:58:06 +00:00
return ;
}
2017-12-01 16:42:02 +00:00
$sth = false ;
2013-03-27 05:40:07 +00:00
if ( $feed < LABEL_BASE_INDEX ) {
2017-12-01 16:42:02 +00:00
2017-05-04 12:57:40 +00:00
$label_feed = Labels :: feed_to_label_id ( $feed );
2017-12-01 16:42:02 +00:00
$sth = $this -> pdo -> prepare ( " SELECT id FROM ttrss_labels2 WHERE
id = ? AND owner_uid = ? " );
$sth -> execute ([ $label_feed , $_SESSION [ 'uid' ]]);
2013-02-21 14:58:06 +00:00
} else if ( ! $cat_view && is_numeric ( $feed ) && $feed > 0 ) {
2017-12-01 16:42:02 +00:00
$sth = $this -> pdo -> prepare ( " SELECT id FROM ttrss_feeds WHERE
id = ? AND owner_uid = ? " );
$sth -> execute ([ $feed , $_SESSION [ 'uid' ]]);
2013-02-21 14:58:06 +00:00
} else if ( $cat_view && is_numeric ( $feed ) && $feed > 0 ) {
2017-12-01 16:42:02 +00:00
$sth = $this -> pdo -> prepare ( " SELECT id FROM ttrss_feed_categories WHERE
id = ? AND owner_uid = ? " );
$sth -> execute ([ $feed , $_SESSION [ 'uid' ]]);
2013-02-21 14:58:06 +00:00
}
2017-12-01 16:42:02 +00:00
if ( $sth && ! $sth -> fetch ()) {
2021-02-15 13:51:35 +00:00
print json_encode ( $this -> _generate_error_feed ( __ ( " Feed not found. " )));
2013-02-21 14:58:06 +00:00
return ;
}
2021-02-25 11:49:58 +00:00
set_pref ( Prefs :: _DEFAULT_VIEW_MODE , $view_mode );
set_pref ( Prefs :: _DEFAULT_VIEW_ORDER_BY , $order_by );
2013-02-21 14:58:06 +00:00
2013-03-22 08:37:42 +00:00
/* bump login timestamp if needed */
if ( time () - $_SESSION [ " last_login_update " ] > 3600 ) {
2021-03-01 16:32:27 +00:00
$user = ORM :: for_table ( 'ttrss_users' ) -> find_one ( $_SESSION [ " uid " ]);
2021-03-01 20:07:20 +00:00
$user -> last_login = Db :: NOW ();
2021-03-01 16:32:27 +00:00
$user -> save ();
2017-12-01 16:42:02 +00:00
2013-03-22 08:37:42 +00:00
$_SESSION [ " last_login_update " ] = time ();
}
2013-02-21 14:58:06 +00:00
if ( ! $cat_view && is_numeric ( $feed ) && $feed > 0 ) {
2017-12-01 16:42:02 +00:00
$sth = $this -> pdo -> prepare ( " UPDATE ttrss_feeds SET last_viewed = NOW()
WHERE id = ? AND owner_uid = ? " );
$sth -> execute ([ $feed , $_SESSION [ 'uid' ]]);
2013-02-21 14:58:06 +00:00
}
2018-12-07 18:22:51 +00:00
$reply [ 'headlines' ] = [];
2013-02-21 14:58:06 +00:00
2021-02-15 12:43:07 +00:00
list ( $override_order , $skip_first_id_check ) = self :: _order_to_override_query ( $order_by );
2013-02-21 14:58:06 +00:00
2021-02-15 12:43:07 +00:00
$ret = $this -> _format_headlines_list ( $feed , $method ,
2017-04-26 12:29:22 +00:00
$view_mode , $limit , $cat_view , $offset ,
2018-12-09 10:35:37 +00:00
$override_order , true , $check_first_id , $skip_first_id_check , $order_by );
2013-02-21 14:58:06 +00:00
$headlines_count = $ret [ 1 ];
$disable_cache = $ret [ 3 ];
2018-12-07 18:11:50 +00:00
$reply [ 'headlines' ] = $ret [ 4 ];
2015-07-12 09:01:34 +00:00
if ( ! $next_unread_feed )
$reply [ 'headlines' ][ 'id' ] = $feed ;
else
$reply [ 'headlines' ][ 'id' ] = $next_unread_feed ;
2021-02-05 20:41:32 +00:00
$reply [ 'headlines' ][ 'is_cat' ] = $cat_view ;
2013-02-21 14:58:06 +00:00
2018-12-07 18:22:51 +00:00
$reply [ 'headlines-info' ] = [ " count " => ( int ) $headlines_count ,
" disable_cache " => ( bool ) $disable_cache ];
2013-02-21 14:58:06 +00:00
2018-12-07 18:22:51 +00:00
// this is parsed by handleRpcJson() on first viewfeed() to set cdm expanded, etc
2021-02-26 06:21:17 +00:00
$reply [ 'runtime-info' ] = RPC :: _make_runtime_info ();
2013-02-21 14:58:06 +00:00
2021-02-23 19:26:07 +00:00
print json_encode ( $reply );
2013-02-21 14:58:06 +00:00
}
2021-11-12 04:48:06 +00:00
/**
* @ return array < string , array < string , mixed >>
*/
private function _generate_dashboard_feed () : array {
2013-02-21 14:58:06 +00:00
$reply = array ();
2023-03-07 15:45:07 +00:00
$reply [ 'headlines' ][ 'id' ] = Feeds :: FEED_DASHBOARD ;
2013-02-21 14:58:06 +00:00
$reply [ 'headlines' ][ 'is_cat' ] = false ;
$reply [ 'headlines' ][ 'toolbar' ] = '' ;
2015-07-13 19:01:29 +00:00
$reply [ 'headlines' ][ 'content' ] = " <div class='whiteBox'> " . __ ( 'No feed selected.' );
2015-07-13 15:43:54 +00:00
2019-03-08 07:11:57 +00:00
$reply [ 'headlines' ][ 'content' ] .= " <p><span class= \" text-muted \" > " ;
2013-02-21 14:58:06 +00:00
2017-12-01 16:42:02 +00:00
$sth = $this -> pdo -> prepare ( " SELECT " . SUBSTRING_FOR_DATE . " (MAX(last_updated), 1, 19) AS last_updated FROM ttrss_feeds
WHERE owner_uid = ? " );
$sth -> execute ([ $_SESSION [ 'uid' ]]);
$row = $sth -> fetch ();
2013-02-21 14:58:06 +00:00
2020-09-23 10:04:26 +00:00
$last_updated = TimeHelper :: make_local_datetime ( $row [ " last_updated " ], false );
2013-02-21 14:58:06 +00:00
2015-07-13 19:01:29 +00:00
$reply [ 'headlines' ][ 'content' ] .= sprintf ( __ ( " Feeds last updated at %s " ), $last_updated );
2013-02-21 14:58:06 +00:00
2022-12-21 21:03:38 +00:00
$num_errors = ORM :: for_table ( 'ttrss_feeds' )
-> where_not_equal ( 'last_error' , '' )
-> where ( 'owner_uid' , $_SESSION [ 'uid' ])
2022-12-24 21:22:16 +00:00
-> where_gte ( 'update_interval' , 0 )
2022-12-21 21:03:38 +00:00
-> count ( 'id' );
2013-02-21 14:58:06 +00:00
if ( $num_errors > 0 ) {
2015-07-13 19:01:29 +00:00
$reply [ 'headlines' ][ 'content' ] .= " <br/> " ;
2019-03-08 07:11:57 +00:00
$reply [ 'headlines' ][ 'content' ] .= " <a class= \" text-muted \" href= \" # \" onclick= \" CommonDialogs.showFeedsWithErrors() \" > " .
2013-02-21 14:58:06 +00:00
__ ( 'Some feeds have update errors (click for details)' ) . " </a> " ;
}
2015-07-13 19:01:29 +00:00
$reply [ 'headlines' ][ 'content' ] .= " </span></p> " ;
2013-02-21 14:58:06 +00:00
$reply [ 'headlines-info' ] = array ( " count " => 0 ,
" unread " => 0 ,
" disable_cache " => true );
return $reply ;
}
2021-11-12 04:48:06 +00:00
/**
* @ return array < string , mixed >
*/
private function _generate_error_feed ( string $error ) : array {
2013-02-21 14:58:06 +00:00
$reply = array ();
2023-03-05 19:14:08 +00:00
$reply [ 'headlines' ][ 'id' ] = Feeds :: FEED_ERROR ;
2013-02-21 14:58:06 +00:00
$reply [ 'headlines' ][ 'is_cat' ] = false ;
$reply [ 'headlines' ][ 'toolbar' ] = '' ;
$reply [ 'headlines' ][ 'content' ] = " <div class='whiteBox'> " . $error . " </div> " ;
$reply [ 'headlines-info' ] = array ( " count " => 0 ,
" unread " => 0 ,
" disable_cache " => true );
return $reply ;
}
2021-11-12 04:48:06 +00:00
function subscribeToFeed () : void {
2021-02-15 12:21:25 +00:00
print json_encode ([
2021-02-16 11:23:00 +00:00
" cat_select " => \Controls\select_feeds_cats ( " cat " )
2021-02-15 12:21:25 +00:00
]);
2013-04-01 07:14:27 +00:00
}
2021-11-12 04:48:06 +00:00
function search () : void {
2021-02-17 16:34:54 +00:00
print json_encode ([
2021-02-22 18:47:48 +00:00
" show_language " => Config :: get ( Config :: DB_TYPE ) == " pgsql " ,
2021-02-17 16:34:54 +00:00
" show_syntax_help " => count ( PluginHost :: getInstance () -> get_hooks ( PluginHost :: HOOK_SEARCH )) == 0 ,
" all_languages " => Pref_Feeds :: get_ts_languages (),
2021-02-25 11:49:58 +00:00
" default_language " => get_pref ( Prefs :: DEFAULT_SEARCH_LANGUAGE )
2021-02-17 16:34:54 +00:00
]);
2013-04-01 07:14:27 +00:00
}
2021-11-12 04:48:06 +00:00
function opensite () : void {
2021-10-10 19:08:17 +00:00
$feed = ORM :: for_table ( 'ttrss_feeds' )
-> find_one (( int ) $_REQUEST [ 'feed_id' ]);
if ( $feed ) {
$site_url = UrlHelper :: validate ( $feed -> site_url );
if ( $site_url ) {
header ( " Location: $site_url " );
return ;
}
}
header ( $_SERVER [ " SERVER_PROTOCOL " ] . " 404 Not Found " );
print " Feed not found or has an empty site URL. " ;
}
2021-11-12 04:48:06 +00:00
function updatedebugger () : void {
2015-06-12 10:06:36 +00:00
header ( " Content-type: text/html " );
2021-11-12 04:48:06 +00:00
$xdebug = isset ( $_REQUEST [ " xdebug " ]) ? ( int ) $_REQUEST [ " xdebug " ] : Debug :: LOG_VERBOSE ;
if ( ! in_array ( $xdebug , Debug :: ALL_LOG_LEVELS )) {
$xdebug = Debug :: LOG_VERBOSE ;
}
2020-12-12 19:17:23 +00:00
2018-11-30 05:34:29 +00:00
Debug :: set_enabled ( true );
2022-09-29 17:02:59 +00:00
Debug :: set_loglevel (( int ) Debug :: map_loglevel ( $xdebug ));
2018-11-30 05:34:29 +00:00
2015-06-12 10:06:36 +00:00
$feed_id = ( int ) $_REQUEST [ " feed_id " ];
2021-02-06 07:31:06 +00:00
$do_update = ( $_REQUEST [ " action " ] ? ? " " ) == " do_update " ;
2020-09-15 13:12:53 +00:00
$csrf_token = $_POST [ " csrf_token " ];
2015-06-12 10:06:36 +00:00
2017-12-03 10:35:18 +00:00
$sth = $this -> pdo -> prepare ( " SELECT id FROM ttrss_feeds WHERE id = ? AND owner_uid = ? " );
$sth -> execute ([ $feed_id , $_SESSION [ 'uid' ]]);
if ( ! $sth -> fetch ()) {
2021-11-12 04:48:06 +00:00
print " Access denied. " ;
return ;
}
2015-06-12 10:06:36 +00:00
?>
2019-02-23 10:49:40 +00:00
<! DOCTYPE html >
2015-06-12 10:06:36 +00:00
< html >
< head >
< title > Feed Debugger </ title >
2020-01-19 07:56:49 +00:00
< style type = 'text/css' >
@ media ( prefers - color - scheme : dark ) {
body {
background : #222;
}
}
body . css_loading * {
display : none ;
}
2023-08-02 06:04:41 +00:00
. feed - xml {
color : green ;
}
. log - timestamp {
color : gray ;
}
. log - timestamp :: before {
content : " [ "
}
. log - timestamp :: after {
content : " ] "
}
2020-01-19 07:56:49 +00:00
</ style >
2021-02-16 11:23:00 +00:00
< script >
dojoConfig = {
async : true ,
cacheBust : " <?= get_scripts_timestamp(); ?> " ,
packages : [
{ name : " fox " , location : " ../../js " },
]
};
</ script >
2021-02-19 16:29:43 +00:00
< ? = javascript_tag ( " js/utility.js " ) ?>
< ? = javascript_tag ( " js/common.js " ) ?>
< ? = javascript_tag ( " lib/dojo/dojo.js " ) ?>
< ? = javascript_tag ( " lib/dojo/tt-rss-layer.js " ) ?>
2023-02-23 23:46:40 +00:00
< ? = Config :: get_override_links () ?>
2015-06-12 10:06:36 +00:00
</ head >
2020-01-19 07:56:49 +00:00
< body class = " flat ttrss_utility feed_debugger css_loading " >
2019-02-19 18:00:15 +00:00
< script type = " text/javascript " >
2021-02-16 11:23:00 +00:00
require ([ 'dojo/parser' , " dojo/ready " , 'dijit/form/Button' , 'dijit/form/CheckBox' , 'fox/form/Select' , 'dijit/form/Form' ,
2019-02-19 18:00:15 +00:00
'dijit/form/Select' , 'dijit/form/TextBox' , 'dijit/form/ValidationTextBox' ], function ( parser , ready ){
ready ( function () {
parser . parse ();
});
});
</ script >
2019-02-19 16:46:09 +00:00
< div class = " container " >
2021-02-15 12:43:07 +00:00
< h1 > Feed Debugger : < ? = " $feed_id : " . $this -> _get_title ( $feed_id ) ?> </h1>
2019-02-19 16:46:09 +00:00
< div class = " content " >
2021-02-16 11:42:27 +00:00
< form method = " post " action = " " dojoType = " dijit.form.Form " >
2023-10-26 15:01:43 +00:00
< ? = \Controls\hidden_tag ( " op " , " Feeds " ) ?>
2021-02-16 11:42:27 +00:00
< ? = \Controls\hidden_tag ( " method " , " updatedebugger " ) ?>
< ? = \Controls\hidden_tag ( " csrf_token " , $csrf_token ) ?>
< ? = \Controls\hidden_tag ( " action " , " do_update " ) ?>
< ? = \Controls\hidden_tag ( " feed_id " , ( string ) $feed_id ) ?>
2019-02-19 16:46:09 +00:00
2020-12-12 19:17:23 +00:00
< fieldset >
< label >
2021-02-16 11:23:00 +00:00
< ? = \Controls\select_hash ( " xdebug " , $xdebug ,
2021-12-23 14:32:27 +00:00
[ Debug :: LOG_VERBOSE => " LOG_VERBOSE " , Debug :: LOG_EXTENDED => " LOG_EXTENDED " ]);
2020-12-12 19:17:23 +00:00
?> </label>
</ fieldset >
< fieldset >
2021-02-16 12:19:42 +00:00
< label class = " checkbox " >< ? = \Controls\checkbox_tag ( " force_refetch " , isset ( $_REQUEST [ " force_refetch " ])) ?> Force refetch</label>
2019-02-19 18:00:15 +00:00
</ fieldset >
2019-02-19 18:24:00 +00:00
< fieldset class = " narrow " >
2021-02-16 12:19:42 +00:00
< label class = " checkbox " >< ? = \Controls\checkbox_tag ( " force_rehash " , isset ( $_REQUEST [ " force_rehash " ])) ?> Force rehash</label>
2019-02-19 18:00:15 +00:00
</ fieldset >
2023-08-02 06:04:41 +00:00
< fieldset class = " narrow " >
< label class = " checkbox " >< ? = \Controls\checkbox_tag ( " dump_feed_xml " , isset ( $_REQUEST [ " dump_feed_xml " ])) ?> Dump feed XML</label>
</ fieldset >
2021-02-16 11:42:27 +00:00
< ? = \Controls\submit_tag ( " Continue " ) ?>
2019-02-19 16:46:09 +00:00
</ form >
< hr >
< pre >< ? php
if ( $do_update ) {
2023-08-02 06:04:41 +00:00
RSSUtils :: update_rss_feed ( $feed_id , true , true );
2019-02-19 16:46:09 +00:00
}
2013-04-01 07:14:27 +00:00
2019-02-19 16:46:09 +00:00
?> </pre>
</ div >
</ div >
2015-06-12 10:06:36 +00:00
</ body >
</ html >
< ? php
}
2017-05-04 11:26:44 +00:00
2021-11-12 04:48:06 +00:00
/**
* @ param array < int , string > $search
*/
static function _catchup ( string $feed_id_or_tag_name , bool $cat_view , ? int $owner_uid = null , string $mode = 'all' , ? array $search = null ) : void {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( ! $owner_uid ) $owner_uid = $_SESSION [ 'uid' ];
2017-12-01 16:42:02 +00:00
$pdo = Db :: pdo ();
2019-05-07 03:57:28 +00:00
if ( is_array ( $search ) && $search [ 0 ]) {
$search_qpart = " " ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-02-08 19:46:01 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_SEARCH ,
function ( $result ) use ( & $search_qpart , & $search_words ) {
if ( ! empty ( $result )) {
list ( $search_qpart , $search_words ) = $result ;
return true ;
}
},
$search [ 0 ]);
2019-05-07 03:57:28 +00:00
// fall back in case of no plugins
2021-02-08 19:46:01 +00:00
if ( empty ( $search_qpart )) {
2021-02-15 12:43:07 +00:00
list ( $search_qpart , $search_words ) = self :: _search_to_sql ( $search [ 0 ], $search [ 1 ], $owner_uid );
2019-05-07 03:57:28 +00:00
}
} else {
$search_qpart = " true " ;
}
// TODO: all this interval stuff needs some generic generator function
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
switch ( $mode ) {
case " 1day " :
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$date_qpart = " date_entered < NOW() - INTERVAL '1 day' " ;
} else {
$date_qpart = " date_entered < DATE_SUB(NOW(), INTERVAL 1 DAY) " ;
}
break ;
case " 1week " :
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$date_qpart = " date_entered < NOW() - INTERVAL '1 week' " ;
} else {
$date_qpart = " date_entered < DATE_SUB(NOW(), INTERVAL 1 WEEK) " ;
}
break ;
case " 2week " :
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$date_qpart = " date_entered < NOW() - INTERVAL '2 week' " ;
} else {
$date_qpart = " date_entered < DATE_SUB(NOW(), INTERVAL 2 WEEK) " ;
}
break ;
default :
$date_qpart = " true " ;
}
2021-11-12 04:48:06 +00:00
if ( is_numeric ( $feed_id_or_tag_name )) {
$feed_id = ( int ) $feed_id_or_tag_name ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( $cat_view ) {
2021-11-12 04:48:06 +00:00
if ( $feed_id >= 0 ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-03-05 19:14:08 +00:00
if ( $feed_id == Feeds :: CATEGORY_UNCATEGORIZED ) {
$cat_qpart = " cat_id IS NULL " ;
} else {
2021-11-12 04:48:06 +00:00
$children = self :: _get_child_cats ( $feed_id , $owner_uid );
array_push ( $children , $feed_id );
2017-12-17 13:24:13 +00:00
$children = array_map ( " intval " , $children );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$children = join ( " , " , $children );
$cat_qpart = " cat_id IN ( $children ) " ;
}
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT id FROM ttrss_entries , ttrss_user_entries WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND owner_uid = ? AND unread = true AND feed_id IN
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
( SELECT id FROM ttrss_feeds WHERE $cat_qpart ) AND $date_qpart AND $search_qpart ) as tmp ) " );
2017-12-01 16:42:02 +00:00
$sth -> execute ([ $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-03-05 19:14:08 +00:00
} else if ( $feed_id == Feeds :: CATEGORY_LABELS ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ( SELECT COUNT ( * )
FROM ttrss_user_labels2 , ttrss_entries WHERE article_id = ref_id AND id = ref_id AND $date_qpart AND $search_qpart ) > 0
2017-12-01 16:42:02 +00:00
AND unread = true AND owner_uid = ? " );
$sth -> execute ([ $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-11-12 04:48:06 +00:00
} else if ( $feed_id > 0 ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT id FROM ttrss_entries , ttrss_user_entries WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND owner_uid = ? AND unread = true AND feed_id = ? AND $date_qpart AND $search_qpart ) as tmp ) " );
2021-11-12 04:48:06 +00:00
$sth -> execute ([ $owner_uid , $feed_id ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-11-12 04:48:06 +00:00
} else if ( $feed_id < 0 && $feed_id > LABEL_BASE_INDEX ) { // special, like starred
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-03-05 19:14:08 +00:00
if ( $feed_id == Feeds :: FEED_STARRED ) {
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT id FROM ttrss_entries , ttrss_user_entries WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND owner_uid = ? AND unread = true AND marked = true AND $date_qpart AND $search_qpart ) as tmp ) " );
$sth -> execute ([ $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2023-03-05 19:14:08 +00:00
if ( $feed_id == Feeds :: FEED_PUBLISHED ) {
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT id FROM ttrss_entries , ttrss_user_entries WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND owner_uid = ? AND unread = true AND published = true AND $date_qpart AND $search_qpart ) as tmp ) " );
$sth -> execute ([ $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2023-03-05 19:14:08 +00:00
if ( $feed_id == Feeds :: FEED_FRESH ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-02-25 11:49:58 +00:00
$intl = ( int ) get_pref ( Prefs :: FRESH_ARTICLE_MAX_AGE );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$match_part = " date_entered > NOW() - INTERVAL ' $intl hour' " ;
} else {
$match_part = " date_entered > DATE_SUB(NOW(),
INTERVAL $intl HOUR ) " ;
}
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT id FROM ttrss_entries , ttrss_user_entries WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND owner_uid = ? AND score >= 0 AND unread = true AND $date_qpart AND $match_part AND $search_qpart ) as tmp ) " );
$sth -> execute ([ $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2023-03-05 19:14:08 +00:00
if ( $feed_id == Feeds :: FEED_ALL ) {
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT id FROM ttrss_entries , ttrss_user_entries WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND owner_uid = ? AND unread = true AND $date_qpart AND $search_qpart ) as tmp ) " );
$sth -> execute ([ $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-11-12 04:48:06 +00:00
} else if ( $feed_id < LABEL_BASE_INDEX ) { // label
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-11-12 04:48:06 +00:00
$label_id = Labels :: feed_to_label_id ( $feed_id );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT ttrss_entries . id FROM ttrss_entries , ttrss_user_entries , ttrss_user_labels2 WHERE ref_id = id
2017-12-01 16:42:02 +00:00
AND label_id = ? AND ref_id = article_id
AND owner_uid = ? AND unread = true AND $date_qpart AND $search_qpart ) as tmp ) " );
$sth -> execute ([ $label_id , $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
} else { // tag
2021-11-12 04:48:06 +00:00
$tag_name = $feed_id_or_tag_name ;
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " UPDATE ttrss_user_entries
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
SET unread = false , last_read = NOW () WHERE ref_id IN
( SELECT id FROM
( SELECT DISTINCT ttrss_entries . id FROM ttrss_entries , ttrss_user_entries , ttrss_tags WHERE ref_id = ttrss_entries . id
2017-12-01 16:42:02 +00:00
AND post_int_id = int_id AND tag_name = ?
AND ttrss_user_entries . owner_uid = ? AND unread = true AND $date_qpart AND $search_qpart ) as tmp ) " );
2021-11-12 04:48:06 +00:00
$sth -> execute ([ $tag_name , $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
}
2022-02-20 08:04:15 +00:00
/**
* @ param int | string $feed feed id or tag name
* @ param bool $is_cat
* @ param bool $unread_only
* @ param null | int $owner_uid
* @ return int
* @ throws PDOException
*/
static function _get_counters ( $feed , bool $is_cat = false , bool $unread_only = false , ? int $owner_uid = null ) : int {
2023-10-20 19:39:41 +00:00
$span = OpenTelemetry\API\Trace\Span :: getCurrent ();
2023-10-20 14:12:29 +00:00
2023-10-20 19:39:41 +00:00
$span -> addEvent ( __METHOD__ . " : $feed ( $is_cat ) " );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$n_feed = ( int ) $feed ;
$need_entries = false ;
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( ! $owner_uid ) $owner_uid = $_SESSION [ " uid " ];
if ( $unread_only ) {
$unread_qpart = " unread = true " ;
} else {
$unread_qpart = " true " ;
}
2017-12-01 17:15:25 +00:00
$match_part = " " ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( $is_cat ) {
2021-02-15 12:43:07 +00:00
return self :: _get_cat_unread ( $n_feed , $owner_uid );
2022-09-28 20:06:22 +00:00
} else if ( is_numeric ( $feed ) && $feed < PLUGIN_FEED_BASE_INDEX && $feed > LABEL_BASE_INDEX ) { // virtual Feed
$feed_id = PluginHost :: feed_to_pfeed_id ( $feed );
$handler = PluginHost :: getInstance () -> get_feed_handler ( $feed_id );
if ( implements_interface ( $handler , 'IVirtualFeed' )) {
2022-09-29 17:02:59 +00:00
/** @var IVirtualFeed $handler */
2023-10-20 19:39:41 +00:00
//$span->end();
2022-09-28 20:06:22 +00:00
return $handler -> get_unread ( $feed_id );
} else {
2023-10-20 19:39:41 +00:00
//$span->end();
2022-09-28 20:06:22 +00:00
return 0 ;
}
2023-03-05 19:14:08 +00:00
} else if ( $n_feed == Feeds :: FEED_RECENTLY_READ ) {
2023-10-20 19:39:41 +00:00
//$span->end();
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return 0 ;
2022-02-20 08:04:15 +00:00
// tags
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else if ( $feed != " 0 " && $n_feed == 0 ) {
2017-12-01 17:15:25 +00:00
$sth = $pdo -> prepare ( " SELECT SUM((SELECT COUNT(int_id)
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
FROM ttrss_user_entries , ttrss_entries WHERE int_id = post_int_id
AND ref_id = id AND $unread_qpart )) AS count FROM ttrss_tags
2017-12-01 17:15:25 +00:00
WHERE owner_uid = ? AND tag_name = ? " );
$sth -> execute ([ $owner_uid , $feed ]);
$row = $sth -> fetch ();
2021-12-14 12:50:53 +00:00
// Handle 'SUM()' returning null if there are no results
2023-10-20 19:39:41 +00:00
//$span->end();
2021-12-14 12:50:53 +00:00
return $row [ " count " ] ? ? 0 ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-03-05 19:14:08 +00:00
} else if ( $n_feed == Feeds :: FEED_STARRED ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$match_part = " marked = true " ;
2023-03-05 19:14:08 +00:00
} else if ( $n_feed == Feeds :: FEED_PUBLISHED ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$match_part = " published = true " ;
2023-03-05 19:14:08 +00:00
} else if ( $n_feed == Feeds :: FEED_FRESH ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$match_part = " unread = true AND score >= 0 " ;
2021-02-25 11:49:58 +00:00
$intl = ( int ) get_pref ( Prefs :: FRESH_ARTICLE_MAX_AGE , $owner_uid );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$match_part .= " AND date_entered > NOW() - INTERVAL ' $intl hour' " ;
} else {
$match_part .= " AND date_entered > DATE_SUB(NOW(), INTERVAL $intl HOUR) " ;
}
$need_entries = true ;
2023-03-05 19:14:08 +00:00
} else if ( $n_feed == Feeds :: FEED_ALL ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$match_part = " true " ;
} else if ( $n_feed >= 0 ) {
2023-03-05 19:14:08 +00:00
if ( $n_feed != Feeds :: FEED_ARCHIVED ) {
2021-02-06 14:19:07 +00:00
$match_part = sprintf ( " feed_id = %d " , $n_feed );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else {
$match_part = " feed_id IS NULL " ;
}
} else if ( $feed < LABEL_BASE_INDEX ) {
2017-05-04 12:57:40 +00:00
$label_id = Labels :: feed_to_label_id ( $feed );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-10-20 19:39:41 +00:00
//$span->end();
2021-02-15 12:43:07 +00:00
return self :: _get_label_unread ( $label_id , $owner_uid );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
if ( $match_part ) {
if ( $need_entries ) {
$from_qpart = " ttrss_user_entries,ttrss_entries " ;
$from_where = " ttrss_entries.id = ttrss_user_entries.ref_id AND " ;
} else {
$from_qpart = " ttrss_user_entries " ;
$from_where = " " ;
}
2017-12-01 17:15:25 +00:00
$sth = $pdo -> prepare ( " SELECT count(int_id) AS unread
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
FROM $from_qpart WHERE
2017-12-01 17:15:25 +00:00
$unread_qpart AND $from_where ( $match_part ) AND ttrss_user_entries . owner_uid = ? " );
$sth -> execute ([ $owner_uid ]);
$row = $sth -> fetch ();
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-10-20 19:39:41 +00:00
//$span->end();
2017-12-01 17:15:25 +00:00
return $row [ " unread " ];
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else {
2017-12-01 17:15:25 +00:00
$sth = $pdo -> prepare ( " SELECT COUNT(post_int_id) AS unread
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
FROM ttrss_tags , ttrss_user_entries , ttrss_entries
2017-12-01 17:15:25 +00:00
WHERE tag_name = ? AND post_int_id = int_id AND ref_id = ttrss_entries . id
AND $unread_qpart AND ttrss_tags . owner_uid = , " );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2017-12-01 17:15:25 +00:00
$sth -> execute ([ $feed , $owner_uid ]);
$row = $sth -> fetch ();
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2023-10-20 19:39:41 +00:00
//$span->end();
2017-12-01 17:15:25 +00:00
return $row [ " unread " ];
}
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-11-12 04:48:06 +00:00
function add () : void {
2021-02-15 12:21:25 +00:00
$feed = clean ( $_REQUEST [ 'feed' ]);
2021-11-19 14:02:25 +00:00
$cat = ( int ) clean ( $_REQUEST [ 'cat' ] ? ? '' );
2021-02-15 12:21:25 +00:00
$need_auth = isset ( $_REQUEST [ 'need_auth' ]);
$login = $need_auth ? clean ( $_REQUEST [ 'login' ]) : '' ;
$pass = $need_auth ? clean ( $_REQUEST [ 'pass' ]) : '' ;
2021-02-15 12:43:07 +00:00
$rc = Feeds :: _subscribe ( $feed , $cat , $login , $pass );
2021-02-15 12:21:25 +00:00
print json_encode ( array ( " result " => $rc ));
}
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
/**
2021-11-12 04:48:06 +00:00
* @ return array < string , mixed > ( code => Status code , message => error message if available )
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
*
* 0 - OK , Feed already exists
* 1 - OK , Feed added
* 2 - Invalid URL
* 3 - URL content is HTML , no feeds available
* 4 - URL content is HTML which contains multiple feeds .
* Here you should call extractfeedurls in rpc - backend
* to get all possible feeds .
* 5 - Couldn ' t download the URL content .
* 6 - Content is an invalid XML .
2021-03-02 07:11:42 +00:00
* 7 - Error while creating feed database entry .
2021-11-10 17:44:51 +00:00
* 8 - Permission denied ( ACCESS_LEVEL_READONLY ) .
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
*/
2021-11-12 04:48:06 +00:00
static function _subscribe ( string $url , int $cat_id = 0 , string $auth_login = '' , string $auth_pass = '' ) : array {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-11-10 17:44:51 +00:00
$user = ORM :: for_table ( " ttrss_users " ) -> find_one ( $_SESSION [ 'uid' ]);
if ( $user && $user -> access_level == UserHelper :: ACCESS_LEVEL_READONLY ) {
return [ " code " => 8 ];
}
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
2020-09-22 06:04:33 +00:00
$url = UrlHelper :: validate ( $url );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-03-02 07:11:42 +00:00
if ( ! $url ) return [ " code " => 2 ];
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-10-22 10:24:10 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_PRE_SUBSCRIBE ,
/** @phpstan-ignore-next-line */
function ( $result ) use ( & $url , & $auth_login , & $auth_pass ) {
// arguments are updated inside the hook (if needed)
},
$url , $auth_login , $auth_pass );
2023-12-30 15:38:41 +00:00
$contents = UrlHelper :: fetch ([ 'url' => $url , 'login' => $auth_login , 'pass' => $auth_pass ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-02-08 19:46:01 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_SUBSCRIBE_FEED ,
function ( $result ) use ( & $contents ) {
$contents = $result ;
},
$contents , $url , $auth_login , $auth_pass );
2018-11-03 12:08:43 +00:00
2021-02-08 19:46:01 +00:00
if ( empty ( $contents )) {
2021-02-28 07:12:57 +00:00
if ( preg_match ( " /cloudflare \ .com/ " , UrlHelper :: $fetch_last_error_content )) {
UrlHelper :: $fetch_last_error .= " (feed behind Cloudflare) " ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-02-28 07:12:57 +00:00
return array ( " code " => 5 , " message " => UrlHelper :: $fetch_last_error );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-02-28 07:12:57 +00:00
if ( mb_strpos ( UrlHelper :: $fetch_last_content_type , " html " ) !== false && self :: _is_html ( $contents )) {
2021-02-15 12:43:07 +00:00
$feedUrls = self :: _get_feeds_from_html ( $url , $contents );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( count ( $feedUrls ) == 0 ) {
return array ( " code " => 3 );
} else if ( count ( $feedUrls ) > 1 ) {
return array ( " code " => 4 , " feeds " => $feedUrls );
}
//use feed url as new URL
$url = key ( $feedUrls );
}
2021-03-02 07:11:42 +00:00
$feed = ORM :: for_table ( 'ttrss_feeds' )
-> where ( 'feed_url' , $url )
-> where ( 'owner_uid' , $_SESSION [ 'uid' ])
-> find_one ();
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-03-02 07:11:42 +00:00
if ( $feed ) {
return [ " code " => 0 , " feed_id " => $feed -> id ];
2017-12-01 17:15:25 +00:00
} else {
2021-03-02 07:11:42 +00:00
$feed = ORM :: for_table ( 'ttrss_feeds' ) -> create ();
$feed -> set ([
'owner_uid' => $_SESSION [ 'uid' ],
'feed_url' => $url ,
'title' => " [Unknown] " ,
'cat_id' => $cat_id ? $cat_id : null ,
'auth_login' => ( string ) $auth_login ,
'auth_pass' => ( string ) $auth_pass ,
'update_method' => 0 ,
'auth_pass_encrypted' => false ,
]);
if ( $feed -> save ()) {
2021-03-06 12:19:31 +00:00
RSSUtils :: update_basic_info ( $feed -> id );
2021-03-02 07:11:42 +00:00
return [ " code " => 1 , " feed_id " => ( int ) $feed -> id ];
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-03-02 07:11:42 +00:00
return [ " code " => 7 ];
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
}
2021-11-12 04:48:06 +00:00
static function _get_icon_file ( int $feed_id ) : string {
2022-12-19 18:36:50 +00:00
$favicon_cache = DiskCache :: instance ( 'feed-icons' );
2022-11-24 20:31:33 +00:00
return $favicon_cache -> get_full_path (( string ) $feed_id );
}
static function _get_icon_url ( int $feed_id , string $fallback_url = " " ) : string {
if ( self :: _has_icon ( $feed_id )) {
$icon_url = Config :: get_self_url () . " /public.php? " . http_build_query ([
'op' => 'feed_icon' ,
'id' => $feed_id ,
]);
return $icon_url ;
}
return $fallback_url ;
2017-12-03 19:35:12 +00:00
}
2022-11-24 20:31:33 +00:00
static function _has_icon ( int $feed_id ) : bool {
2022-12-19 18:36:50 +00:00
$favicon_cache = DiskCache :: instance ( 'feed-icons' );
2022-11-24 20:31:33 +00:00
return $favicon_cache -> exists (( string ) $feed_id );
2017-12-03 19:49:57 +00:00
}
2021-11-12 04:48:06 +00:00
/**
* @ return false | string false if the icon ID was unrecognized , otherwise , the icon identifier string
*/
static function _get_icon ( int $id ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
switch ( $id ) {
2023-03-05 19:14:08 +00:00
case Feeds :: FEED_ARCHIVED :
2018-12-05 17:26:27 +00:00
return " archive " ;
2023-03-05 19:14:08 +00:00
case Feeds :: FEED_STARRED :
2018-12-05 17:26:27 +00:00
return " star " ;
2023-03-05 19:14:08 +00:00
case Feeds :: FEED_PUBLISHED :
2018-12-05 17:26:27 +00:00
return " rss_feed " ;
2023-03-05 19:14:08 +00:00
case Feeds :: FEED_FRESH :
2018-12-06 10:18:14 +00:00
return " whatshot " ;
2023-03-05 19:14:08 +00:00
case Feeds :: FEED_ALL :
2018-12-05 17:26:27 +00:00
return " inbox " ;
2023-03-05 19:14:08 +00:00
case Feeds :: FEED_RECENTLY_READ :
2018-12-05 19:48:14 +00:00
return " restore " ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
default :
if ( $id < LABEL_BASE_INDEX ) {
2018-12-06 12:22:52 +00:00
return " label " ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else {
2022-11-24 20:31:33 +00:00
return self :: _get_icon_url ( $id );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
}
}
2021-11-12 04:48:06 +00:00
/**
* @ return false | int false if the feed couldn ' t be found by URL + owner , otherwise the feed ID
*/
2021-03-06 12:23:54 +00:00
static function _find_by_url ( string $feed_url , int $owner_uid ) {
$feed = ORM :: for_table ( 'ttrss_feeds' )
-> where ( 'owner_uid' , $owner_uid )
-> where ( 'feed_url' , $feed_url )
-> find_one ();
2021-02-20 05:49:40 +00:00
2021-03-06 12:23:54 +00:00
if ( $feed ) {
return $feed -> id ;
} else {
return false ;
2021-02-20 05:49:40 +00:00
}
}
2021-11-12 04:48:06 +00:00
/**
* $owner_uid defaults to $_SESSION [ 'uid' ]
*
* @ return false | int false if the category / feed couldn ' t be found by title , otherwise its ID
*/
2021-09-08 06:04:15 +00:00
static function _find_by_title ( string $title , bool $cat = false , int $owner_uid = 0 ) {
$res = false ;
if ( $cat ) {
$res = ORM :: for_table ( 'ttrss_feed_categories' )
-> where ( 'owner_uid' , $owner_uid ? $owner_uid : $_SESSION [ 'uid' ])
-> where ( 'title' , $title )
-> find_one ();
} else {
$res = ORM :: for_table ( 'ttrss_feeds' )
-> where ( 'owner_uid' , $owner_uid ? $owner_uid : $_SESSION [ 'uid' ])
-> where ( 'title' , $title )
-> find_one ();
}
if ( $res ) {
return $res -> id ;
} else {
return false ;
}
}
2021-11-29 07:20:13 +00:00
/**
* @ param string | int $id
*/
2021-11-29 09:30:33 +00:00
static function _get_title ( $id , bool $cat = false ) : string {
2021-11-12 04:48:06 +00:00
$pdo = Db :: pdo ();
2017-12-01 16:42:02 +00:00
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( $cat ) {
2021-02-15 12:43:07 +00:00
return self :: _get_cat_title ( $id );
2023-03-05 19:14:08 +00:00
} else if ( $id == Feeds :: FEED_STARRED ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return __ ( " Starred articles " );
2023-03-05 19:14:08 +00:00
} else if ( $id == Feeds :: FEED_PUBLISHED ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return __ ( " Published articles " );
2023-03-05 19:14:08 +00:00
} else if ( $id == Feeds :: FEED_FRESH ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return __ ( " Fresh articles " );
2023-03-05 19:14:08 +00:00
} else if ( $id == Feeds :: FEED_ALL ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return __ ( " All articles " );
2023-03-05 19:14:08 +00:00
} else if ( $id === Feeds :: FEED_ARCHIVED ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return __ ( " Archived articles " );
2023-03-05 19:14:08 +00:00
} else if ( $id == Feeds :: FEED_RECENTLY_READ ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
return __ ( " Recently read " );
} else if ( $id < LABEL_BASE_INDEX ) {
2017-12-01 16:42:02 +00:00
2017-05-04 12:57:40 +00:00
$label_id = Labels :: feed_to_label_id ( $id );
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " SELECT caption FROM ttrss_labels2 WHERE id = ? " );
$sth -> execute ([ $label_id ]);
if ( $row = $sth -> fetch ()) {
return $row [ " caption " ];
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else {
return " Unknown label ( $label_id ) " ;
}
} else if ( is_numeric ( $id ) && $id > 0 ) {
2017-12-01 16:42:02 +00:00
$sth = $pdo -> prepare ( " SELECT title FROM ttrss_feeds WHERE id = ? " );
$sth -> execute ([ $id ]);
if ( $row = $sth -> fetch ()) {
return $row [ " title " ];
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else {
return " Unknown feed ( $id ) " ;
}
2017-12-01 16:42:02 +00:00
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
} else {
2021-11-12 04:48:06 +00:00
return " $id " ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
}
2020-02-20 12:54:40 +00:00
// only real cats
2021-11-12 04:48:06 +00:00
static function _get_cat_marked ( int $cat , int $owner_uid = 0 ) : int {
2020-02-20 12:54:40 +00:00
if ( ! $owner_uid ) $owner_uid = $_SESSION [ " uid " ];
$pdo = Db :: pdo ();
if ( $cat >= 0 ) {
$sth = $pdo -> prepare ( " SELECT SUM(CASE WHEN marked THEN 1 ELSE 0 END) AS marked
FROM ttrss_user_entries
WHERE feed_id IN ( SELECT id FROM ttrss_feeds
WHERE ( cat_id = : cat OR ( : cat IS NULL AND cat_id IS NULL ))
AND owner_uid = : uid )
AND owner_uid = : uid " );
2021-11-12 04:48:06 +00:00
2020-02-20 12:54:40 +00:00
$sth -> execute ([ " cat " => $cat ? $cat : null , " uid " => $owner_uid ]);
2021-11-12 04:48:06 +00:00
if ( $row = $sth -> fetch ()) {
return ( int ) $row [ " marked " ];
}
2020-02-20 12:54:40 +00:00
}
2021-11-12 04:48:06 +00:00
return 0 ;
2020-02-20 12:54:40 +00:00
}
2021-11-12 04:48:06 +00:00
static function _get_cat_unread ( int $cat , int $owner_uid = 0 ) : int {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( ! $owner_uid ) $owner_uid = $_SESSION [ " uid " ];
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( $cat >= 0 ) {
2020-01-25 06:57:28 +00:00
$sth = $pdo -> prepare ( " SELECT SUM(CASE WHEN unread THEN 1 ELSE 0 END) AS unread
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
FROM ttrss_user_entries
2020-01-25 06:57:28 +00:00
WHERE feed_id IN ( SELECT id FROM ttrss_feeds
2021-11-12 04:48:06 +00:00
WHERE ( cat_id = : cat OR ( : cat IS NULL AND cat_id IS NULL ))
2020-01-25 06:57:28 +00:00
AND owner_uid = : uid )
AND owner_uid = : uid " );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-11-12 04:48:06 +00:00
$sth -> execute ([ " cat " => $cat ? $cat : null , " uid " => $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-11-12 04:48:06 +00:00
if ( $row = $sth -> fetch ()) {
return ( int ) $row [ " unread " ];
}
2023-03-05 19:14:08 +00:00
} else if ( $cat == Feeds :: CATEGORY_SPECIAL ) {
2020-01-24 12:54:01 +00:00
return 0 ;
2023-03-05 19:14:08 +00:00
} else if ( $cat == Feeds :: CATEGORY_LABELS ) {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2020-06-05 04:44:57 +00:00
$sth = $pdo -> prepare ( " SELECT COUNT(DISTINCT article_id) AS unread
2020-01-25 09:53:10 +00:00
FROM ttrss_user_entries ue , ttrss_user_labels2 l
WHERE article_id = ref_id AND unread IS true AND ue . owner_uid = : uid " );
2021-11-12 04:48:06 +00:00
2020-01-25 06:57:28 +00:00
$sth -> execute ([ " uid " => $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
2021-11-12 04:48:06 +00:00
if ( $row = $sth -> fetch ()) {
return ( int ) $row [ " unread " ];
}
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
2021-11-12 04:48:06 +00:00
return 0 ;
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
// only accepts real cats (>= 0)
2021-11-12 04:48:06 +00:00
static function _get_cat_children_unread ( int $cat , int $owner_uid = 0 ) : int {
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
if ( ! $owner_uid ) $owner_uid = $_SESSION [ " uid " ];
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
$sth = $pdo -> prepare ( " SELECT id FROM ttrss_feed_categories WHERE parent_cat = ?
AND owner_uid = ? " );
$sth -> execute ([ $cat , $owner_uid ]);
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
$unread = 0 ;
2017-12-01 17:15:25 +00:00
while ( $line = $sth -> fetch ()) {
2021-02-15 12:43:07 +00:00
$unread += self :: _get_cat_unread ( $line [ " id " ], $owner_uid );
$unread += self :: _get_cat_children_unread ( $line [ " id " ], $owner_uid );
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00
}
return $unread ;
}
2017-05-04 11:26:44 +00:00
2021-11-12 04:48:06 +00:00
static function _get_global_unread ( int $user_id = 0 ) : int {
2017-05-04 12:00:21 +00:00
2017-12-01 17:15:25 +00:00
if ( ! $user_id ) $user_id = $_SESSION [ " uid " ];
2017-05-04 12:00:21 +00:00
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
2017-05-04 12:00:21 +00:00
2020-06-05 04:44:57 +00:00
$sth = $pdo -> prepare ( " SELECT SUM(CASE WHEN unread THEN 1 ELSE 0 END) AS count
FROM ttrss_user_entries ue
2020-01-24 11:25:31 +00:00
WHERE ue . owner_uid = ? " );
2017-12-01 17:15:25 +00:00
$sth -> execute ([ $user_id ]);
$row = $sth -> fetch ();
2017-05-04 12:00:21 +00:00
2021-12-14 12:47:25 +00:00
// Handle 'SUM()' returning null if there are no articles/results (e.g. admin user with no feeds)
2021-12-14 12:06:32 +00:00
return $row [ " count " ] ? ? 0 ;
2017-05-04 12:00:21 +00:00
}
2021-11-12 04:48:06 +00:00
static function _get_cat_title ( int $cat_id ) : string {
2021-03-02 17:07:31 +00:00
switch ( $cat_id ) {
2023-03-05 19:14:08 +00:00
case Feeds :: CATEGORY_UNCATEGORIZED :
2017-05-04 12:00:21 +00:00
return __ ( " Uncategorized " );
2023-03-05 19:14:08 +00:00
case Feeds :: CATEGORY_SPECIAL :
2021-03-02 17:07:31 +00:00
return __ ( " Special " );
2023-03-05 19:14:08 +00:00
case Feeds :: CATEGORY_LABELS :
2021-03-02 17:07:31 +00:00
return __ ( " Labels " );
default :
$cat = ORM :: for_table ( 'ttrss_feed_categories' )
-> find_one ( $cat_id );
if ( $cat ) {
return $cat -> title ;
} else {
return " UNKNOWN " ;
}
2017-05-04 12:00:21 +00:00
}
}
2021-11-12 04:48:06 +00:00
private static function _get_label_unread ( int $label_id , ? int $owner_uid = null ) : int {
2017-05-04 12:00:21 +00:00
if ( ! $owner_uid ) $owner_uid = $_SESSION [ " uid " ];
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
$sth = $pdo -> prepare ( " SELECT COUNT(ref_id) AS unread FROM ttrss_user_entries, ttrss_user_labels2
WHERE owner_uid = ? AND unread = true AND label_id = ? AND article_id = ref_id " );
$sth -> execute ([ $owner_uid , $label_id ]);
2017-05-04 12:00:21 +00:00
2017-12-01 17:15:25 +00:00
if ( $row = $sth -> fetch ()) {
return $row [ " unread " ];
2017-05-04 12:00:21 +00:00
} else {
return 0 ;
}
}
2021-11-12 04:48:06 +00:00
/**
* @ param array < string , mixed > $params
* @ return array < int , mixed > $result , $feed_title , $feed_site_url , $last_error , $last_updated , $highlight_words , $first_id , $is_vfeed , $query_error_override
*/
static function _get_headlines ( $params ) : array {
2017-05-04 12:13:02 +00:00
2023-10-20 19:39:41 +00:00
$span = Tracer :: start ( __METHOD__ );
$span -> setAttribute ( 'func.args' , json_encode ( func_get_args ()));
2023-04-09 19:15:16 +00:00
2017-12-01 17:15:25 +00:00
$pdo = Db :: pdo ();
// WARNING: due to highly dynamic nature of this query its going to quote parameters
2020-12-03 11:42:01 +00:00
// right before adding them to SQL part
2017-12-01 17:15:25 +00:00
2017-05-04 12:13:02 +00:00
$feed = $params [ " feed " ];
$limit = isset ( $params [ " limit " ]) ? $params [ " limit " ] : 30 ;
$view_mode = $params [ " view_mode " ];
$cat_view = isset ( $params [ " cat_view " ]) ? $params [ " cat_view " ] : false ;
$search = isset ( $params [ " search " ]) ? $params [ " search " ] : false ;
$search_language = isset ( $params [ " search_language " ]) ? $params [ " search_language " ] : " " ;
$override_order = isset ( $params [ " override_order " ]) ? $params [ " override_order " ] : false ;
$offset = isset ( $params [ " offset " ]) ? $params [ " offset " ] : 0 ;
$owner_uid = isset ( $params [ " owner_uid " ]) ? $params [ " owner_uid " ] : $_SESSION [ " uid " ];
$since_id = isset ( $params [ " since_id " ]) ? $params [ " since_id " ] : 0 ;
$include_children = isset ( $params [ " include_children " ]) ? $params [ " include_children " ] : false ;
$ignore_vfeed_group = isset ( $params [ " ignore_vfeed_group " ]) ? $params [ " ignore_vfeed_group " ] : false ;
$override_strategy = isset ( $params [ " override_strategy " ]) ? $params [ " override_strategy " ] : false ;
$override_vfeed = isset ( $params [ " override_vfeed " ]) ? $params [ " override_vfeed " ] : false ;
$start_ts = isset ( $params [ " start_ts " ]) ? $params [ " start_ts " ] : false ;
$check_first_id = isset ( $params [ " check_first_id " ]) ? $params [ " check_first_id " ] : false ;
$skip_first_id_check = isset ( $params [ " skip_first_id_check " ]) ? $params [ " skip_first_id_check " ] : false ;
2019-08-30 07:16:38 +00:00
//$order_by = isset($params["order_by"]) ? $params["order_by"] : false;
2017-05-04 12:13:02 +00:00
$ext_tables_part = " " ;
2017-12-01 17:15:25 +00:00
$limit_query_part = " " ;
2019-04-30 11:39:08 +00:00
$query_error_override = " " ;
2017-05-04 12:13:02 +00:00
2019-04-30 11:39:08 +00:00
$search_words = [];
2017-05-04 12:13:02 +00:00
if ( $search ) {
2019-04-30 11:39:08 +00:00
$search_query_part = " " ;
2021-02-08 19:46:01 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_SEARCH ,
function ( $result ) use ( & $search_query_part , & $search_words ) {
if ( ! empty ( $result )) {
list ( $search_query_part , $search_words ) = $result ;
return true ;
}
},
$search );
2017-05-04 12:13:02 +00:00
// fall back in case of no plugins
if ( ! $search_query_part ) {
2021-02-15 12:43:07 +00:00
list ( $search_query_part , $search_words ) = self :: _search_to_sql ( $search , $search_language , $owner_uid );
2017-05-04 12:13:02 +00:00
}
2019-04-29 18:15:49 +00:00
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2020-06-05 04:44:57 +00:00
$test_sth = $pdo -> prepare ( " select $search_query_part
2019-05-20 04:12:43 +00:00
FROM ttrss_entries , ttrss_user_entries WHERE id = ref_id limit 1 " );
2019-04-29 18:15:49 +00:00
try {
$test_sth -> execute ();
} catch ( PDOException $e ) {
// looks like tsquery syntax is invalid
$search_query_part = " false " ;
2019-04-30 11:39:08 +00:00
$query_error_override = T_sprintf ( " Incorrect search syntax: %s. " , implode ( " " , $search_words ));
2019-04-29 18:15:49 +00:00
}
}
2017-05-04 12:13:02 +00:00
$search_query_part .= " AND " ;
} else {
$search_query_part = " " ;
}
if ( $since_id ) {
2017-12-01 17:52:30 +00:00
$since_id_part = " ttrss_entries.id > " . $pdo -> quote ( $since_id ) . " AND " ;
2017-05-04 12:13:02 +00:00
} else {
$since_id_part = " " ;
}
$view_query_part = " " ;
if ( $view_mode == " adaptive " ) {
if ( $search ) {
$view_query_part = " " ;
} else if ( $feed != - 1 ) {
2023-03-05 19:14:08 +00:00
// not Feeds::FEED_STARRED or Feeds::CATEGORY_SPECIAL
2017-05-04 12:13:02 +00:00
2022-02-20 09:48:38 +00:00
$unread = Feeds :: _get_counters ( $feed , $cat_view , true );
2017-05-04 12:13:02 +00:00
if ( $cat_view && $feed > 0 && $include_children )
2021-02-15 12:43:07 +00:00
$unread += self :: _get_cat_children_unread ( $feed );
2017-05-04 12:13:02 +00:00
if ( $unread > 0 ) {
$view_query_part = " unread = true AND " ;
}
}
}
if ( $view_mode == " marked " ) {
$view_query_part = " marked = true AND " ;
}
if ( $view_mode == " has_note " ) {
$view_query_part = " (note IS NOT NULL AND note != '') AND " ;
}
if ( $view_mode == " published " ) {
$view_query_part = " published = true AND " ;
}
2023-03-05 19:14:08 +00:00
if ( $view_mode == " unread " && $feed != Feeds :: FEED_RECENTLY_READ ) {
2017-05-04 12:13:02 +00:00
$view_query_part = " unread = true AND " ;
}
if ( $limit > 0 ) {
2017-12-01 18:07:55 +00:00
$limit_query_part = " LIMIT " . ( int ) $limit ;
2017-05-04 12:13:02 +00:00
}
$allow_archived = false ;
$vfeed_query_part = " " ;
/* tags */
if ( ! is_numeric ( $feed )) {
$query_strategy_part = " true " ;
$vfeed_query_part = " (SELECT title FROM ttrss_feeds WHERE
id = feed_id ) as feed_title , " ;
} else if ( $feed > 0 ) {
if ( $cat_view ) {
if ( $feed > 0 ) {
if ( $include_children ) {
# sub-cats
2021-02-15 12:43:07 +00:00
$subcats = self :: _get_child_cats ( $feed , $owner_uid );
2017-05-04 12:13:02 +00:00
array_push ( $subcats , $feed );
2017-12-17 13:24:13 +00:00
$subcats = array_map ( " intval " , $subcats );
2017-05-04 12:13:02 +00:00
$query_strategy_part = " cat_id IN ( " .
implode ( " , " , $subcats ) . " ) " ;
} else {
2021-02-08 20:10:22 +00:00
$query_strategy_part = " cat_id = " . $pdo -> quote (( string ) $feed );
2017-05-04 12:13:02 +00:00
}
} else {
$query_strategy_part = " cat_id IS NULL " ;
}
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
} else {
2021-02-08 20:10:22 +00:00
$query_strategy_part = " feed_id = " . $pdo -> quote (( string ) $feed );
2017-05-04 12:13:02 +00:00
}
2023-03-05 19:14:08 +00:00
} else if ( $feed == Feeds :: FEED_ARCHIVED && ! $cat_view ) { // archive virtual feed
2017-05-04 12:13:02 +00:00
$query_strategy_part = " feed_id IS NULL " ;
$allow_archived = true ;
2023-03-05 19:14:08 +00:00
} else if ( $feed == Feeds :: CATEGORY_UNCATEGORIZED && $cat_view ) { // uncategorized
2017-05-04 12:13:02 +00:00
$query_strategy_part = " cat_id IS NULL AND feed_id IS NOT NULL " ;
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
2023-03-05 19:14:08 +00:00
} else if ( $feed == - 1 ) { // starred virtual feed, Feeds::FEED_STARRED or Feeds::CATEGORY_SPECIAL
2017-05-04 12:13:02 +00:00
$query_strategy_part = " marked = true " ;
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
$allow_archived = true ;
if ( ! $override_order ) {
$override_order = " last_marked DESC, date_entered DESC, updated DESC " ;
}
2023-03-05 19:14:08 +00:00
} else if ( $feed == - 2 ) { // published virtual feed (Feeds::FEED_PUBLISHED) OR labels category (Feeds::CATEGORY_LABELS)
2017-05-04 12:13:02 +00:00
if ( ! $cat_view ) {
$query_strategy_part = " published = true " ;
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
$allow_archived = true ;
if ( ! $override_order ) {
$override_order = " last_published DESC, date_entered DESC, updated DESC " ;
}
} else {
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
$ext_tables_part = " ttrss_labels2,ttrss_user_labels2, " ;
$query_strategy_part = " ttrss_labels2.id = ttrss_user_labels2.label_id AND
ttrss_user_labels2 . article_id = ref_id " ;
}
2023-03-05 19:14:08 +00:00
} else if ( $feed == Feeds :: FEED_RECENTLY_READ ) { // recently read
2017-05-04 12:13:02 +00:00
$query_strategy_part = " unread = false AND last_read IS NOT NULL " ;
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2017-05-04 12:13:02 +00:00
$query_strategy_part .= " AND last_read > NOW() - INTERVAL '1 DAY' " ;
} else {
$query_strategy_part .= " AND last_read > DATE_SUB(NOW(), INTERVAL 1 DAY) " ;
}
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
$allow_archived = true ;
$ignore_vfeed_group = true ;
if ( ! $override_order ) $override_order = " last_read DESC " ;
2023-03-05 19:14:08 +00:00
} else if ( $feed == Feeds :: FEED_FRESH ) { // fresh virtual feed
2017-05-04 12:13:02 +00:00
$query_strategy_part = " unread = true AND score >= 0 " ;
2021-02-25 11:49:58 +00:00
$intl = ( int ) get_pref ( Prefs :: FRESH_ARTICLE_MAX_AGE , $owner_uid );
2017-05-04 12:13:02 +00:00
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2017-05-04 12:13:02 +00:00
$query_strategy_part .= " AND date_entered > NOW() - INTERVAL ' $intl hour' " ;
} else {
$query_strategy_part .= " AND date_entered > DATE_SUB(NOW(), INTERVAL $intl HOUR) " ;
}
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
2023-03-05 19:14:08 +00:00
} else if ( $feed == Feeds :: FEED_ALL ) { // all articles virtual feed
2017-05-04 12:13:02 +00:00
$allow_archived = true ;
$query_strategy_part = " true " ;
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
} else if ( $feed <= LABEL_BASE_INDEX ) { // labels
2017-05-04 12:57:40 +00:00
$label_id = Labels :: feed_to_label_id ( $feed );
2017-05-04 12:13:02 +00:00
2021-11-12 04:48:06 +00:00
$query_strategy_part = " label_id = $label_id AND
2017-05-04 12:13:02 +00:00
ttrss_labels2 . id = ttrss_user_labels2 . label_id AND
ttrss_user_labels2 . article_id = ref_id " ;
$vfeed_query_part = " ttrss_feeds.title AS feed_title, " ;
$ext_tables_part = " ttrss_labels2,ttrss_user_labels2, " ;
$allow_archived = true ;
} else {
$query_strategy_part = " true " ;
}
$order_by = " score DESC, date_entered DESC, updated DESC " ;
if ( $override_order ) {
$order_by = $override_order ;
}
if ( $override_strategy ) {
$query_strategy_part = $override_strategy ;
}
if ( $override_vfeed ) {
$vfeed_query_part = $override_vfeed ;
}
2020-12-04 05:59:37 +00:00
$feed_title = " " ;
$feed_site_url = " " ;
$last_error = " " ;
$last_updated = " " ;
2017-05-04 12:13:02 +00:00
if ( $search ) {
$feed_title = T_sprintf ( " Search results: %s " , $search );
} else {
if ( $cat_view ) {
2021-02-15 12:43:07 +00:00
$feed_title = self :: _get_cat_title ( $feed );
2017-05-04 12:13:02 +00:00
} else {
if ( is_numeric ( $feed ) && $feed > 0 ) {
2017-12-01 17:15:25 +00:00
$ssth = $pdo -> prepare ( " SELECT title,site_url,last_error,last_updated
FROM ttrss_feeds WHERE id = ? AND owner_uid = ? " );
$ssth -> execute ([ $feed , $owner_uid ]);
$row = $ssth -> fetch ();
$feed_title = $row [ " title " ];
$feed_site_url = $row [ " site_url " ];
$last_error = $row [ " last_error " ];
$last_updated = $row [ " last_updated " ];
2017-05-04 12:13:02 +00:00
} else {
2021-02-15 12:43:07 +00:00
$feed_title = self :: _get_title ( $feed );
2017-05-04 12:13:02 +00:00
}
}
}
$content_query_part = " content, " ;
if ( $limit_query_part ) {
2017-12-01 18:07:55 +00:00
$offset_query_part = " OFFSET " . ( int ) $offset ;
2017-05-04 12:13:02 +00:00
} else {
$offset_query_part = " " ;
}
2019-06-18 10:10:32 +00:00
if ( $start_ts ) {
$start_ts_formatted = date ( " Y/m/d H:i:s " , strtotime ( $start_ts ));
$start_ts_query_part = " date_entered >= ' $start_ts_formatted ' AND " ;
} else {
$start_ts_query_part = " " ;
}
2020-12-04 05:59:37 +00:00
$first_id = 0 ;
2021-02-26 12:45:30 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
$yyiw_qpart = " to_char(date_entered, 'IYYY-IW') AS yyiw " ;
} else {
$yyiw_qpart = " date_format(date_entered, '%Y-%u') AS yyiw " ;
}
2017-05-04 12:13:02 +00:00
if ( is_numeric ( $feed )) {
// proper override_order applied above
2021-02-25 11:49:58 +00:00
if ( $vfeed_query_part && ! $ignore_vfeed_group && get_pref ( Prefs :: VFEED_GROUP_BY_FEED , $owner_uid )) {
2019-08-30 07:16:38 +00:00
2020-09-22 11:54:15 +00:00
if ( ! ( in_array ( $feed , self :: NEVER_GROUP_BY_DATE ) && ! $cat_view )) {
2019-08-30 07:16:38 +00:00
$yyiw_desc = $order_by == " date_reverse " ? " " : " desc " ;
$yyiw_order_qpart = " yyiw $yyiw_desc , " ;
} else {
$yyiw_order_qpart = " " ;
}
2018-12-09 10:35:37 +00:00
2017-05-04 12:13:02 +00:00
if ( ! $override_order ) {
2019-08-30 07:16:38 +00:00
$order_by = " $yyiw_order_qpart ttrss_feeds.title, $order_by " ;
2017-05-04 12:13:02 +00:00
} else {
2019-08-30 07:16:38 +00:00
$order_by = " $yyiw_order_qpart ttrss_feeds.title, $override_order " ;
2017-05-04 12:13:02 +00:00
}
}
if ( ! $allow_archived ) {
2022-11-12 16:20:59 +00:00
$from_qpart = " { $ext_tables_part } ttrss_entries LEFT JOIN ttrss_user_entries ON (ref_id = ttrss_entries.id), ttrss_feeds " ;
2017-05-04 12:13:02 +00:00
$feed_check_qpart = " ttrss_user_entries.feed_id = ttrss_feeds.id AND " ;
} else {
2022-11-12 16:20:59 +00:00
$from_qpart = " { $ext_tables_part } ttrss_entries LEFT JOIN ttrss_user_entries ON (ref_id = ttrss_entries.id)
2017-05-04 12:13:02 +00:00
LEFT JOIN ttrss_feeds ON ( feed_id = ttrss_feeds . id ) " ;
2020-12-04 05:59:37 +00:00
$feed_check_qpart = " " ;
2017-05-04 12:13:02 +00:00
}
if ( $vfeed_query_part ) $vfeed_query_part .= " favicon_avg_color, " ;
$first_id_query_strategy_part = $query_strategy_part ;
2023-03-05 19:14:08 +00:00
if ( $feed == Feeds :: FEED_FRESH )
2017-05-04 12:13:02 +00:00
$first_id_query_strategy_part = " true " ;
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2017-05-04 12:13:02 +00:00
$sanity_interval_qpart = " date_entered >= NOW() - INTERVAL '1 hour' AND " ;
2020-12-07 13:59:48 +00:00
$distinct_columns = str_replace ( " desc " , " " , strtolower ( $order_by ));
$distinct_qpart = " DISTINCT ON (id, $distinct_columns ) " ;
2017-05-04 12:13:02 +00:00
} else {
$sanity_interval_qpart = " date_entered >= DATE_SUB(NOW(), INTERVAL 1 hour) AND " ;
2020-12-07 13:59:48 +00:00
$distinct_qpart = " DISTINCT " ; //fallback
2017-05-04 12:13:02 +00:00
}
2021-02-26 06:57:34 +00:00
// except for Labels category
2023-03-05 19:14:08 +00:00
if ( get_pref ( Prefs :: HEADLINES_NO_DISTINCT , $owner_uid ) && ! ( $feed == Feeds :: CATEGORY_LABELS && $cat_view )) {
2021-02-26 06:57:34 +00:00
$distinct_qpart = " " ;
}
2017-05-04 12:13:02 +00:00
if ( ! $search && ! $skip_first_id_check ) {
// if previous topmost article id changed that means our current pagination is no longer valid
2020-12-08 13:59:58 +00:00
$query = " SELECT
2020-12-07 13:59:48 +00:00
ttrss_entries . id ,
2017-05-04 12:13:02 +00:00
date_entered ,
2020-12-07 13:59:48 +00:00
$yyiw_qpart ,
2017-05-04 12:13:02 +00:00
guid ,
ttrss_entries . title ,
2020-12-07 13:59:48 +00:00
ttrss_feeds . title ,
2017-05-04 12:13:02 +00:00
updated ,
score ,
marked ,
published ,
last_marked ,
last_published ,
last_read
FROM
$from_qpart
WHERE
$feed_check_qpart
2017-12-01 17:52:30 +00:00
ttrss_user_entries . owner_uid = " . $pdo->quote ( $owner_uid ). " AND
2017-05-04 12:13:02 +00:00
$search_query_part
$start_ts_query_part
$since_id_part
$sanity_interval_qpart
$first_id_query_strategy_part ORDER BY $order_by LIMIT 1 " ;
2021-02-05 20:41:32 +00:00
if ( ! empty ( $_REQUEST [ " debug " ])) {
2020-12-07 13:59:48 +00:00
print " \n *** FIRST ID QUERY *** \n $query\n " ;
}
2017-05-04 12:13:02 +00:00
2017-12-01 17:25:13 +00:00
$res = $pdo -> query ( $query );
2017-12-01 17:15:25 +00:00
2021-02-08 20:10:22 +00:00
if ( ! empty ( $res ) && $row = $res -> fetch ()) {
2017-12-01 17:25:13 +00:00
$first_id = ( int ) $row [ " id " ];
2017-05-04 12:13:02 +00:00
if ( $offset > 0 && $first_id && $check_first_id && $first_id != $check_first_id ) {
2019-04-30 11:39:08 +00:00
return array ( - 1 , $feed_title , $feed_site_url , $last_error , $last_updated , $search_words , $first_id , $vfeed_query_part != " " , $query_error_override );
2017-05-04 12:13:02 +00:00
}
}
}
2020-12-07 13:59:48 +00:00
$query = " SELECT $distinct_qpart
ttrss_entries . id AS id ,
2017-05-04 12:13:02 +00:00
date_entered ,
2020-12-04 05:44:43 +00:00
$yyiw_qpart ,
2017-05-04 12:13:02 +00:00
guid ,
2020-12-07 13:59:48 +00:00
ttrss_entries . title ,
2017-05-04 12:13:02 +00:00
updated ,
label_cache ,
tag_cache ,
always_display_enclosures ,
site_url ,
note ,
num_comments ,
comments ,
int_id ,
uuid ,
lang ,
hide_images ,
2021-01-17 11:55:11 +00:00
unread , feed_id , marked , published , link , last_read ,
2017-05-04 12:13:02 +00:00
last_marked , last_published ,
$vfeed_query_part
$content_query_part
2021-02-25 18:27:16 +00:00
author , score ,
2021-02-27 07:58:11 +00:00
( SELECT count ( label_id ) FROM ttrss_user_labels2 WHERE article_id = ttrss_entries . id ) AS num_labels ,
2021-02-25 18:27:16 +00:00
( SELECT count ( id ) FROM ttrss_enclosures WHERE post_id = ttrss_entries . id ) AS num_enclosures
2017-05-04 12:13:02 +00:00
FROM
$from_qpart
WHERE
$feed_check_qpart
2017-12-01 17:52:30 +00:00
ttrss_user_entries . owner_uid = " . $pdo->quote ( $owner_uid ). " AND
2017-05-04 12:13:02 +00:00
$search_query_part
$start_ts_query_part
$view_query_part
$since_id_part
$query_strategy_part ORDER BY $order_by
$limit_query_part $offset_query_part " ;
2017-12-17 13:24:13 +00:00
//if ($_REQUEST["debug"]) print $query;
2017-05-04 12:13:02 +00:00
2021-02-05 20:41:32 +00:00
if ( ! empty ( $_REQUEST [ " debug " ])) {
2020-12-07 13:59:48 +00:00
print " \n *** HEADLINES QUERY *** \n $query\n " ;
}
2017-12-01 17:25:13 +00:00
$res = $pdo -> query ( $query );
2017-05-04 12:13:02 +00:00
} else {
// browsing by tag
2021-02-26 12:45:30 +00:00
if ( get_pref ( Prefs :: HEADLINES_NO_DISTINCT , $owner_uid )) {
$distinct_qpart = " " ;
2020-12-08 13:59:58 +00:00
} else {
2021-02-26 12:45:30 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
$distinct_columns = str_replace ( " desc " , " " , strtolower ( $order_by ));
$distinct_qpart = " DISTINCT ON (id, $distinct_columns ) " ;
} else {
$distinct_qpart = " DISTINCT " ; //fallback
}
2020-12-08 13:59:58 +00:00
}
2020-12-07 13:59:48 +00:00
$query = " SELECT $distinct_qpart
2021-02-26 12:45:30 +00:00
ttrss_entries . id AS id ,
2017-05-04 12:13:02 +00:00
date_entered ,
2021-02-26 12:45:30 +00:00
$yyiw_qpart ,
2017-05-04 12:13:02 +00:00
guid ,
2021-02-26 12:45:30 +00:00
ttrss_entries . title ,
2017-05-04 12:13:02 +00:00
updated ,
2021-02-26 12:45:30 +00:00
label_cache ,
tag_cache ,
always_display_enclosures ,
site_url ,
note ,
2017-05-04 12:13:02 +00:00
num_comments ,
comments ,
int_id ,
uuid ,
2021-02-26 12:45:30 +00:00
lang ,
hide_images ,
unread , feed_id , marked , published , link , last_read ,
2017-05-04 12:13:02 +00:00
last_marked , last_published ,
$since_id_part
$vfeed_query_part
$content_query_part
2021-02-26 12:45:30 +00:00
author , score ,
2021-02-27 07:58:11 +00:00
( SELECT count ( label_id ) FROM ttrss_user_labels2 WHERE article_id = ttrss_entries . id ) AS num_labels ,
2021-02-26 12:45:30 +00:00
( SELECT count ( id ) FROM ttrss_enclosures WHERE post_id = ttrss_entries . id ) AS num_enclosures
2021-05-07 16:15:10 +00:00
FROM ttrss_entries ,
ttrss_user_entries LEFT JOIN ttrss_feeds ON ( ttrss_feeds . id = ttrss_user_entries . feed_id ),
ttrss_tags
2017-05-04 12:13:02 +00:00
WHERE
ref_id = ttrss_entries . id AND
2017-12-01 17:52:30 +00:00
ttrss_user_entries . owner_uid = " . $pdo->quote ( $owner_uid ). " AND
2017-05-04 12:13:02 +00:00
post_int_id = int_id AND
2017-12-01 17:52:30 +00:00
tag_name = " . $pdo->quote ( $feed ). " AND
2017-05-04 12:13:02 +00:00
$view_query_part
$search_query_part
2019-06-18 10:10:32 +00:00
$start_ts_query_part
2017-05-04 12:13:02 +00:00
$query_strategy_part ORDER BY $order_by
$limit_query_part $offset_query_part " ;
2020-12-04 15:55:53 +00:00
//if ($_REQUEST["debug"]) print $query;
2017-05-04 12:13:02 +00:00
2021-02-05 20:41:32 +00:00
if ( ! empty ( $_REQUEST [ " debug " ])) {
2020-12-08 13:59:58 +00:00
print " \n *** TAGS QUERY *** \n $query\n " ;
}
2017-12-01 17:25:13 +00:00
$res = $pdo -> query ( $query );
2017-05-04 12:13:02 +00:00
}
2023-10-20 19:39:41 +00:00
$span -> end ();
2017-05-04 12:13:02 +00:00
2023-04-09 19:15:16 +00:00
return array ( $res , $feed_title , $feed_site_url , $last_error , $last_updated , $search_words , $first_id , $vfeed_query_part != " " , $query_error_override );
2017-05-04 12:13:02 +00:00
}
2021-11-12 04:48:06 +00:00
/**
* @ return array < int , int >
*/
static function _get_parent_cats ( int $cat , int $owner_uid ) : array {
2017-05-04 12:13:02 +00:00
$rv = array ();
2017-12-01 17:25:13 +00:00
$pdo = Db :: pdo ();
$sth = $pdo -> prepare ( " SELECT parent_cat FROM ttrss_feed_categories
WHERE id = ? AND parent_cat IS NOT NULL AND owner_uid = ? " );
$sth -> execute ([ $cat , $owner_uid ]);
2017-05-04 12:13:02 +00:00
2017-12-01 17:25:13 +00:00
while ( $line = $sth -> fetch ()) {
2022-08-12 15:31:19 +00:00
$cat = ( int ) $line [ " parent_cat " ];
array_push ( $rv , $cat , ... self :: _get_parent_cats ( $cat , $owner_uid ));
2017-05-04 12:13:02 +00:00
}
return $rv ;
}
2021-11-12 04:48:06 +00:00
/**
* @ return array < int , int >
*/
static function _get_child_cats ( int $cat , int $owner_uid ) : array {
2017-05-04 12:13:02 +00:00
$rv = array ();
2017-12-01 17:25:13 +00:00
$pdo = Db :: pdo ();
$sth = $pdo -> prepare ( " SELECT id FROM ttrss_feed_categories
WHERE parent_cat = ? AND owner_uid = ? " );
$sth -> execute ([ $cat , $owner_uid ]);
2017-05-04 12:13:02 +00:00
2017-12-01 17:25:13 +00:00
while ( $line = $sth -> fetch ()) {
2022-08-12 15:31:19 +00:00
array_push ( $rv , $line [ " id " ], ... self :: _get_child_cats ( $line [ " id " ], $owner_uid ));
2017-05-04 12:13:02 +00:00
}
return $rv ;
}
2021-11-12 04:48:06 +00:00
/**
* @ param array < int , int > $feeds
* @ return array < int , int >
*/
static function _cats_of ( array $feeds , int $owner_uid , bool $with_parents = false ) : array {
2021-02-24 12:07:31 +00:00
if ( count ( $feeds ) == 0 )
return [];
2021-02-24 06:47:26 +00:00
$pdo = Db :: pdo ();
$feeds_qmarks = arr_qmarks ( $feeds );
2021-02-24 06:56:59 +00:00
$sth = $pdo -> prepare ( " SELECT DISTINCT cat_id, fc.parent_cat FROM ttrss_feeds f LEFT JOIN ttrss_feed_categories fc
ON ( fc . id = f . cat_id )
2021-02-24 07:09:08 +00:00
WHERE f . owner_uid = ? AND f . id IN ( $feeds_qmarks ) " );
2022-08-12 15:31:19 +00:00
$sth -> execute ([ $owner_uid , ... $feeds ]);
2021-02-24 06:47:26 +00:00
$rv = [];
if ( $row = $sth -> fetch ()) {
2022-08-12 15:31:19 +00:00
$cat_id = ( int ) $row [ " cat_id " ];
$rv [] = $cat_id ;
2021-02-24 06:47:26 +00:00
array_push ( $rv , ( int ) $row [ " cat_id " ]);
2022-08-12 15:31:19 +00:00
if ( $with_parents && $row [ " parent_cat " ]) {
array_push ( $rv , ... self :: _get_parent_cats ( $cat_id , $owner_uid ));
}
2021-02-24 06:47:26 +00:00
}
$rv = array_unique ( $rv );
return $rv ;
}
2021-03-02 06:36:44 +00:00
// returns Uncategorized as 0
2021-03-06 12:23:54 +00:00
static function _cat_of ( int $feed ) : int {
2021-03-01 17:25:53 +00:00
$feed = ORM :: for_table ( 'ttrss_feeds' ) -> find_one ( $feed );
2017-12-01 17:25:13 +00:00
2021-03-01 17:25:53 +00:00
if ( $feed ) {
2021-03-02 06:36:44 +00:00
return ( int ) $feed -> cat_id ;
2017-05-04 12:36:36 +00:00
} else {
2021-03-02 06:36:44 +00:00
return - 1 ;
2017-05-04 12:36:36 +00:00
}
}
2021-11-12 04:48:06 +00:00
private function _color_of ( string $name ) : string {
$colormap = [ " #1cd7d7 " , " #d91111 " , " #1212d7 " , " #8e16e5 " , " #7b7b7b " ,
" #39f110 " , " #0bbea6 " , " #ec0e0e " , " #1534f2 " , " #b9e416 " ,
" #479af2 " , " #f36b14 " , " #10c7e9 " , " #1e8fe7 " , " #e22727 " ];
2018-12-12 04:57:37 +00:00
2021-11-12 04:48:06 +00:00
$sum = 0 ;
2018-12-12 04:57:37 +00:00
2021-11-12 04:48:06 +00:00
for ( $i = 0 ; $i < strlen ( $name ); $i ++ ) {
$sum += ord ( $name [ $i ]);
}
2018-12-12 04:57:37 +00:00
2021-11-12 04:48:06 +00:00
$sum %= count ( $colormap );
2018-12-12 04:57:37 +00:00
2021-11-12 04:48:06 +00:00
return $colormap [ $sum ];
2018-12-12 04:57:37 +00:00
}
2017-05-04 12:36:36 +00:00
2021-11-12 04:48:06 +00:00
/**
* @ return array < string , string > array of feed URL -> feed title
*/
private static function _get_feeds_from_html ( string $url , string $content ) : array {
$url = UrlHelper :: validate ( $url );
2019-06-20 04:51:48 +00:00
$baseUrl = substr ( $url , 0 , strrpos ( $url , '/' ) + 1 );
$feedUrls = [];
$doc = new DOMDocument ();
2020-10-01 10:20:07 +00:00
if ( @ $doc -> loadHTML ( $content )) {
2019-06-20 04:51:48 +00:00
$xpath = new DOMXPath ( $doc );
$entries = $xpath -> query ( '/html/head/link[@rel="alternate" and ' .
'(contains(@type,"rss") or contains(@type,"atom"))]|/html/head/link[@rel="feed"]' );
foreach ( $entries as $entry ) {
if ( $entry -> hasAttribute ( 'href' )) {
$title = $entry -> getAttribute ( 'title' );
if ( $title == '' ) {
$title = $entry -> getAttribute ( 'type' );
}
2021-11-12 04:48:06 +00:00
$feedUrl = UrlHelper :: rewrite_relative ( $baseUrl , $entry -> getAttribute ( 'href' ));
2019-06-20 04:51:48 +00:00
$feedUrls [ $feedUrl ] = $title ;
}
}
}
return $feedUrls ;
}
2021-11-12 04:48:06 +00:00
static function _is_html ( string $content ) : bool {
2019-06-20 04:51:48 +00:00
return preg_match ( " /<html|DOCTYPE html/i " , substr ( $content , 0 , 8192 )) !== 0 ;
}
2021-11-12 04:48:06 +00:00
static function _remove_cat ( int $id , int $owner_uid ) : void {
2021-03-01 17:25:53 +00:00
$cat = ORM :: for_table ( 'ttrss_feed_categories' )
-> where ( 'owner_uid' , $owner_uid )
-> find_one ( $id );
if ( $cat )
$cat -> delete ();
}
2021-11-12 04:48:06 +00:00
static function _add_cat ( string $title , int $owner_uid , int $parent_cat = null , int $order_id = 0 ) : bool {
2019-06-20 05:14:06 +00:00
2021-03-02 07:24:15 +00:00
$cat = ORM :: for_table ( 'ttrss_feed_categories' )
-> where ( 'owner_uid' , $owner_uid )
-> where ( 'parent_cat' , $parent_cat )
-> where ( 'title' , $title )
-> find_one ();
2019-06-20 05:14:06 +00:00
2021-03-02 07:24:15 +00:00
if ( ! $cat ) {
$cat = ORM :: for_table ( 'ttrss_feed_categories' ) -> create ();
2019-06-20 05:14:06 +00:00
2021-03-02 07:24:15 +00:00
$cat -> set ([
'owner_uid' => $owner_uid ,
'parent_cat' => $parent_cat ,
'order_id' => $order_id ,
'title' => $title ,
]);
2019-06-20 05:14:06 +00:00
2021-03-02 07:24:15 +00:00
return $cat -> save ();
2019-06-20 05:14:06 +00:00
}
return false ;
}
2021-11-12 04:48:06 +00:00
static function _clear_access_keys ( int $owner_uid ) : void {
2021-03-02 05:26:37 +00:00
$key = ORM :: for_table ( 'ttrss_access_keys' )
-> where ( 'owner_uid' , $owner_uid )
-> delete_many ();
}
2021-11-13 14:05:43 +00:00
/**
* @ param string $feed_id may be a feed ID or tag
*
* @ see Handler_Public #generate_syndicated_feed()
*/
static function _update_access_key ( string $feed_id , bool $is_cat , int $owner_uid ) : ? string {
2021-03-02 05:26:37 +00:00
$key = ORM :: for_table ( 'ttrss_access_keys' )
-> where ( 'owner_uid' , $owner_uid )
-> where ( 'feed_id' , $feed_id )
-> where ( 'is_cat' , $is_cat )
-> delete_many ();
return self :: _get_access_key ( $feed_id , $is_cat , $owner_uid );
}
2019-06-20 05:14:06 +00:00
2021-11-13 14:05:43 +00:00
/**
* @ param string $feed_id may be a feed ID or tag
*
* @ see Handler_Public #generate_syndicated_feed()
*/
static function _get_access_key ( string $feed_id , bool $is_cat , int $owner_uid ) : ? string {
2021-03-01 17:25:53 +00:00
$key = ORM :: for_table ( 'ttrss_access_keys' )
-> where ( 'owner_uid' , $owner_uid )
-> where ( 'feed_id' , $feed_id )
-> where ( 'is_cat' , $is_cat )
-> find_one ();
2019-06-20 05:14:06 +00:00
2021-03-01 17:25:53 +00:00
if ( $key ) {
return $key -> access_key ;
2021-11-12 04:48:06 +00:00
}
2019-06-20 05:14:06 +00:00
2021-11-12 04:48:06 +00:00
$key = ORM :: for_table ( 'ttrss_access_keys' ) -> create ();
2019-06-20 05:14:06 +00:00
2021-11-12 04:48:06 +00:00
$key -> owner_uid = $owner_uid ;
$key -> feed_id = $feed_id ;
$key -> is_cat = $is_cat ;
$key -> access_key = uniqid_short ();
if ( $key -> save ()) {
return $key -> access_key ;
2019-06-20 05:14:06 +00:00
}
2021-11-12 04:48:06 +00:00
return null ;
2019-06-20 05:14:06 +00:00
}
2019-06-20 05:40:02 +00:00
2021-11-12 04:48:06 +00:00
static function _purge ( int $feed_id , int $purge_interval ) : ? int {
2019-06-20 05:40:02 +00:00
2021-02-15 12:43:07 +00:00
if ( ! $purge_interval ) $purge_interval = self :: _get_purge_interval ( $feed_id );
2019-06-20 05:40:02 +00:00
$pdo = Db :: pdo ();
2020-12-15 05:50:01 +00:00
$owner_uid = false ;
$rows_deleted = 0 ;
2019-06-20 05:40:02 +00:00
$sth = $pdo -> prepare ( " SELECT owner_uid FROM ttrss_feeds WHERE id = ? " );
$sth -> execute ([ $feed_id ]);
if ( $row = $sth -> fetch ()) {
$owner_uid = $row [ " owner_uid " ];
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: FORCE_ARTICLE_PURGE ) != 0 ) {
2021-12-23 14:32:27 +00:00
Debug :: log ( " purge_feed: FORCE_ARTICLE_PURGE is set, overriding interval to " . Config :: get ( Config :: FORCE_ARTICLE_PURGE ), Debug :: LOG_VERBOSE );
2020-12-15 05:50:01 +00:00
$purge_unread = true ;
2021-02-22 18:47:48 +00:00
$purge_interval = Config :: get ( Config :: FORCE_ARTICLE_PURGE );
2020-12-15 05:50:01 +00:00
} else {
2021-02-25 11:45:11 +00:00
$purge_unread = get_pref ( Prefs :: PURGE_UNREAD_ARTICLES , $owner_uid );
2020-12-15 05:50:01 +00:00
}
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
$purge_interval = ( int ) $purge_interval ;
2019-06-20 05:40:02 +00:00
2021-12-23 14:32:27 +00:00
Debug :: log ( " purge_feed: interval $purge_interval days for feed $feed_id , owner: $owner_uid , purge unread: $purge_unread " , Debug :: LOG_VERBOSE );
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
if ( $purge_interval <= 0 ) {
2021-12-23 14:32:27 +00:00
Debug :: log ( " purge_feed: purging disabled for this feed, nothing to do. " , Debug :: LOG_VERBOSE );
2021-11-12 04:48:06 +00:00
return null ;
2020-12-15 05:50:01 +00:00
}
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
if ( ! $purge_unread )
$query_limit = " unread = false AND " ;
else
$query_limit = " " ;
2019-06-20 05:40:02 +00:00
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2020-12-15 05:50:01 +00:00
$sth = $pdo -> prepare ( " DELETE FROM ttrss_user_entries
USING ttrss_entries
WHERE ttrss_entries . id = ref_id AND
marked = false AND
feed_id = ? AND
$query_limit
ttrss_entries . date_updated < NOW () - INTERVAL '$purge_interval days' " );
$sth -> execute ([ $feed_id ]);
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
} else {
$sth = $pdo -> prepare ( " DELETE FROM ttrss_user_entries
USING ttrss_user_entries , ttrss_entries
WHERE ttrss_entries . id = ref_id AND
marked = false AND
feed_id = ? AND
$query_limit
ttrss_entries . date_updated < DATE_SUB ( NOW (), INTERVAL $purge_interval DAY ) " );
$sth -> execute ([ $feed_id ]);
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
}
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
$rows_deleted = $sth -> rowCount ();
2019-06-20 05:40:02 +00:00
2021-12-23 14:32:27 +00:00
Debug :: log ( " purge_feed: deleted $rows_deleted articles. " , Debug :: LOG_VERBOSE );
2019-06-20 05:40:02 +00:00
2020-12-15 05:50:01 +00:00
} else {
2021-12-23 14:32:27 +00:00
Debug :: log ( " purge_feed: owner of $feed_id not found " , Debug :: LOG_VERBOSE );
2020-12-15 05:50:01 +00:00
}
return $rows_deleted ;
2019-06-20 05:40:02 +00:00
}
2021-11-12 04:48:06 +00:00
private static function _get_purge_interval ( int $feed_id ) : int {
2021-03-01 17:25:53 +00:00
$feed = ORM :: for_table ( 'ttrss_feeds' ) -> find_one ( $feed_id );
2019-06-20 05:40:02 +00:00
2021-03-01 17:25:53 +00:00
if ( $feed ) {
if ( $feed -> purge_interval != 0 )
return $feed -> purge_interval ;
else
return get_pref ( Prefs :: PURGE_OLD_DAYS , $feed -> owner_uid );
2019-06-20 05:40:02 +00:00
} else {
return - 1 ;
}
}
2021-11-12 04:48:06 +00:00
/**
* @ return array { 0 : string , 1 : array < int , string > } [ $search_query_part , $search_words ]
*/
private static function _search_to_sql ( string $search , string $search_language , int $owner_uid ) : array {
2022-11-12 16:20:59 +00:00
$keywords = str_getcsv ( preg_replace ( '/(-?\w+)\:"(\w+)/' , '"{$1}:{$2}' , trim ( $search )), ' ' );
2019-06-20 05:40:02 +00:00
$query_keywords = array ();
$search_words = array ();
$search_query_leftover = array ();
$pdo = Db :: pdo ();
if ( $search_language )
$search_language = $pdo -> quote ( mb_strtolower ( $search_language ));
else
2021-02-25 11:49:58 +00:00
$search_language = $pdo -> quote ( mb_strtolower ( get_pref ( Prefs :: DEFAULT_SEARCH_LANGUAGE , $owner_uid )));
2019-06-20 05:40:02 +00:00
foreach ( $keywords as $k ) {
if ( strpos ( $k , " - " ) === 0 ) {
$k = substr ( $k , 1 );
$not = " NOT " ;
} else {
$not = " " ;
}
$commandpair = explode ( " : " , mb_strtolower ( $k ), 2 );
switch ( $commandpair [ 0 ]) {
case " title " :
if ( $commandpair [ 1 ]) {
array_push ( $query_keywords , " ( $not (LOWER(ttrss_entries.title) LIKE " .
$pdo -> quote ( '%' . mb_strtolower ( $commandpair [ 1 ]) . '%' ) . " )) " );
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER('% $k %')
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
array_push ( $search_words , $k );
}
break ;
case " author " :
if ( $commandpair [ 1 ]) {
array_push ( $query_keywords , " ( $not (LOWER(author) LIKE " .
$pdo -> quote ( '%' . mb_strtolower ( $commandpair [ 1 ]) . '%' ) . " )) " );
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER('% $k %')
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
array_push ( $search_words , $k );
}
break ;
case " note " :
if ( $commandpair [ 1 ]) {
if ( $commandpair [ 1 ] == " true " )
array_push ( $query_keywords , " ( $not (note IS NOT NULL AND note != '')) " );
else if ( $commandpair [ 1 ] == " false " )
array_push ( $query_keywords , " ( $not (note IS NULL OR note = '')) " );
else
array_push ( $query_keywords , " ( $not (LOWER(note) LIKE " .
$pdo -> quote ( '%' . mb_strtolower ( $commandpair [ 1 ]) . '%' ) . " )) " );
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER( " . $pdo -> quote ( " % $k % " ) . " )
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
if ( ! $not ) array_push ( $search_words , $k );
}
break ;
case " star " :
if ( $commandpair [ 1 ]) {
if ( $commandpair [ 1 ] == " true " )
array_push ( $query_keywords , " ( $not (marked = true)) " );
else
array_push ( $query_keywords , " ( $not (marked = false)) " );
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER( " . $pdo -> quote ( " % $k % " ) . " )
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
if ( ! $not ) array_push ( $search_words , $k );
}
break ;
case " pub " :
if ( $commandpair [ 1 ]) {
if ( $commandpair [ 1 ] == " true " )
array_push ( $query_keywords , " ( $not (published = true)) " );
else
array_push ( $query_keywords , " ( $not (published = false)) " );
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER('% $k %')
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
if ( ! $not ) array_push ( $search_words , $k );
}
break ;
2020-04-04 11:34:08 +00:00
case " label " :
if ( $commandpair [ 1 ]) {
$label_id = Labels :: find_id ( $commandpair [ 1 ], $_SESSION [ " uid " ]);
if ( $label_id ) {
2020-06-05 04:44:57 +00:00
array_push ( $query_keywords , " ( $not
2020-04-04 11:34:08 +00:00
( ttrss_entries . id IN (
2020-06-05 04:44:57 +00:00
SELECT article_id FROM ttrss_user_labels2 WHERE
2021-11-12 04:48:06 +00:00
label_id = $label_id ))) " );
2020-04-04 11:34:08 +00:00
} else {
array_push ( $query_keywords , " (false) " );
}
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER( " . $pdo -> quote ( " % $k % " ) . " )
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
if ( ! $not ) array_push ( $search_words , $k );
}
break ;
2019-06-20 05:40:02 +00:00
case " unread " :
if ( $commandpair [ 1 ]) {
if ( $commandpair [ 1 ] == " true " )
array_push ( $query_keywords , " ( $not (unread = true)) " );
else
array_push ( $query_keywords , " ( $not (unread = false)) " );
} else {
array_push ( $query_keywords , " (UPPER(ttrss_entries.title) $not LIKE UPPER( " . $pdo -> quote ( " % $k % " ) . " )
OR UPPER ( ttrss_entries . content ) $not LIKE UPPER ( " . $pdo->quote ( " % $k % " ). " )) " );
if ( ! $not ) array_push ( $search_words , $k );
}
break ;
default :
if ( strpos ( $k , " @ " ) === 0 ) {
2021-02-25 11:49:58 +00:00
$user_tz_string = get_pref ( Prefs :: USER_TIMEZONE , $_SESSION [ 'uid' ]);
2019-06-20 05:40:02 +00:00
$orig_ts = strtotime ( substr ( $k , 1 ));
2020-09-23 10:04:26 +00:00
$k = date ( " Y-m-d " , TimeHelper :: convert_timestamp ( $orig_ts , $user_tz_string , 'UTC' ));
2019-06-20 05:40:02 +00:00
//$k = date("Y-m-d", strtotime(substr($k, 1)));
array_push ( $query_keywords , " ( " . SUBSTRING_FOR_DATE . " (updated,1,LENGTH(' $k ')) $not = ' $k ') " );
} else {
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2019-06-20 05:40:02 +00:00
$k = mb_strtolower ( $k );
array_push ( $search_query_leftover , $not ? " ! $k " : $k );
} else {
2022-06-19 19:21:54 +00:00
$k = mb_strtolower ( $k );
array_push ( $search_query_leftover , $not ? " - $k " : $k );
//array_push($query_keywords, "(UPPER(ttrss_entries.title) $not LIKE UPPER(".$pdo->quote("%$k%").")
// OR UPPER(ttrss_entries.content) $not LIKE UPPER(".$pdo->quote("%$k%")."))");
2019-06-20 05:40:02 +00:00
}
if ( ! $not ) array_push ( $search_words , $k );
}
}
}
if ( count ( $search_query_leftover ) > 0 ) {
2021-02-22 18:47:48 +00:00
if ( Config :: get ( Config :: DB_TYPE ) == " pgsql " ) {
2019-06-20 05:40:02 +00:00
// if there's no joiners consider this a "simple" search and
// concatenate everything with &, otherwise don't try to mess with tsquery syntax
if ( preg_match ( " /[&|]/ " , implode ( " " , $search_query_leftover ))) {
$tsquery = $pdo -> quote ( implode ( " " , $search_query_leftover ));
} else {
$tsquery = $pdo -> quote ( implode ( " & " , $search_query_leftover ));
}
array_push ( $query_keywords ,
" (tsvector_combined @@ to_tsquery( $search_language , $tsquery )) " );
2022-06-19 19:21:54 +00:00
} else {
$ft_query = $pdo -> quote ( implode ( " " , $search_query_leftover ));
2019-06-20 05:40:02 +00:00
2022-06-19 19:21:54 +00:00
array_push ( $query_keywords ,
" MATCH (ttrss_entries.title, ttrss_entries.content) AGAINST ( $ft_query IN BOOLEAN MODE) " );
}
2019-06-20 05:40:02 +00:00
}
2020-04-04 11:34:08 +00:00
if ( count ( $query_keywords ) > 0 )
2022-07-03 21:17:01 +00:00
$search_query_part = implode ( " AND " , $query_keywords );
2020-04-04 11:34:08 +00:00
else
$search_query_part = " false " ;
2019-06-20 05:40:02 +00:00
return array ( $search_query_part , $search_words );
}
2020-08-13 08:52:32 +00:00
2021-11-12 04:48:06 +00:00
/**
* @ return array { 0 : string , 1 : bool }
*/
static function _order_to_override_query ( string $order ) : array {
2020-08-13 08:52:32 +00:00
$query = " " ;
$skip_first_id = false ;
2021-02-08 19:46:01 +00:00
PluginHost :: getInstance () -> chain_hooks_callback ( PluginHost :: HOOK_HEADLINES_CUSTOM_SORT_OVERRIDE ,
function ( $result ) use ( & $query , & $skip_first_id ) {
list ( $query , $skip_first_id ) = $result ;
2023-05-06 11:07:10 +00:00
// run until first hard match
return ! empty ( $query );
2021-02-08 19:46:01 +00:00
},
$order );
2020-09-11 04:48:22 +00:00
2021-11-12 04:48:06 +00:00
if ( is_string ( $query ) && $query !== " " ) {
return [ $query , $skip_first_id ];
}
2020-09-11 04:48:22 +00:00
2020-08-13 08:52:32 +00:00
switch ( $order ) {
case " title " :
$query = " ttrss_entries.title, date_entered, updated " ;
break ;
case " date_reverse " :
$query = " updated " ;
$skip_first_id = true ;
break ;
case " feed_dates " :
$query = " updated DESC " ;
break ;
}
return [ $query , $skip_first_id ];
}
2020-12-04 15:55:53 +00:00
2013-02-21 14:58:06 +00:00
}
move the following to Feeds:
+ static function catchup_feed($feed, $cat_view, $owner_uid = false, $mode = 'all', $search = false) {
+ static function getFeedArticles($feed, $is_cat = false, $unread_only = false,
+ static function subscribe_to_feed($url, $cat_id = 0,
+ static function getFeedIcon($id) {
+ static function getFeedTitle($id, $cat = false) {
+ static function getCategoryUnread($cat, $owner_uid = false) {
+ static function getCategoryChildrenUnread($cat, $owner_uid = false) {
2017-05-04 11:50:56 +00:00