aboutsummaryrefslogtreecommitdiff
path: root/p
diff options
context:
space:
mode:
authorGravatar Andy Valencia <ajv-900-660-8060@vsta.org> 2025-12-15 23:36:29 -0800
committerGravatar GitHub <noreply@github.com> 2025-12-16 08:36:29 +0100
commit19666d70ed47df0909b501f51090632e7b2e26cc (patch)
treeb6b708ae62553f3fb454edd3e58dc2a38c65ffe2 /p
parent476e57b04646416e24e24c56133c9fadf9e52b95 (diff)
Bump to API level 4 for Fever; add with_ids so we can mass-change rea… (#8312)
* Bump to API level 4 for Fever; add with_ids so we can mass-change read/unread/saved/unsaved on lists of articles. As discussed in https://github.com/FreshRSS/FreshRSS/issues/8305 A small enhancement to the Fever API to vastly increase efficiency when bulk marking items. - How to test the feature manually: The client at: https://sources.vsta.org:7100/FeedMonkey/file?name=js/Fever.js&ci=tip has code to talk to this API enhancement (when the API level says it's supported). In particular walkArticles(). * Update indentation per PR check on Github * make fix-all * Line length * Fix many typing issues * is_numeric * Update comment --------- Co-authored-by: Andy Valencia <ajv-899-334-8894@vsta.org> Co-authored-by: Alexandre Alapetite <alexandre@alapetite.fr>
Diffstat (limited to 'p')
-rw-r--r--p/api/fever.php46
1 files changed, 29 insertions, 17 deletions
diff --git a/p/api/fever.php b/p/api/fever.php
index 76e3a4ac3..6dc1f233f 100644
--- a/p/api/fever.php
+++ b/p/api/fever.php
@@ -79,8 +79,10 @@ final class FeverDAO extends Minz_ModelPdo
}
/**
- * @param array<string|int> $feed_ids
- * @param array<string> $entry_ids
+ * @param array<numeric-string|int> $feed_ids
+ * @param array<numeric-string> $entry_ids
+ * @param numeric-string|'' $max_id
+ * @param numeric-string|'' $since_id
* @return FreshRSS_Entry[]
*/
public function findEntries(array $feed_ids, array $entry_ids, string $max_id, string $since_id): array {
@@ -138,7 +140,7 @@ final class FeverDAO extends Minz_ModelPdo
*/
final class FeverAPI
{
- public const API_LEVEL = 3;
+ public const API_LEVEL = 4;
public const STATUS_OK = 1;
public const STATUS_ERR = 0;
@@ -227,8 +229,15 @@ final class FeverAPI
$response_arr['saved_item_ids'] = $this->getSavedItemIds();
}
- if (is_string($_REQUEST['mark'] ?? null) && is_string($_REQUEST['as'] ?? null) && is_string($_REQUEST['id'] ?? null) && ctype_digit($_REQUEST['id'])) {
- $id = $_REQUEST['id'];
+ if (is_string($_REQUEST['mark'] ?? null) && is_string($_REQUEST['as'] ?? null)) {
+ if (is_string($_REQUEST['id'] ?? null) && ctype_digit($_REQUEST['id'])) {
+ $id = $_REQUEST['id'];
+ } elseif (is_string($_REQUEST['with_ids'] ?? null)) {
+ $id = array_values(array_filter(explode(',', $_REQUEST['with_ids']), 'ctype_digit'));
+ // N.B.: Not supported by 'feed' and 'group' functions
+ } else {
+ $id = '0';
+ }
$before = is_numeric($_REQUEST['before'] ?? null) ? (int)$_REQUEST['before'] : 0;
switch (strtolower($_REQUEST['mark'])) {
case 'item':
@@ -250,14 +259,14 @@ final class FeverAPI
case 'feed':
switch ($_REQUEST['as']) {
case 'read':
- $this->setFeedAsRead((int)$id, $before);
+ $this->setFeedAsRead(is_numeric($id) ? (int)$id : 0, $before);
break;
}
break;
case 'group':
switch ($_REQUEST['as']) {
case 'read':
- $this->setGroupAsRead((int)$id, $before);
+ $this->setGroupAsRead(is_numeric($id) ? (int)$id : 0, $before);
break;
}
break;
@@ -438,30 +447,30 @@ final class FeverAPI
}
/**
- * @param numeric-string $id
+ * @param list<numeric-string>|numeric-string $id
*/
- private function setItemAsRead(string $id): int|false {
+ private function setItemAsRead(array|string $id): int|false {
return $this->entryDAO->markRead($id, true);
}
/**
- * @param numeric-string $id
+ * @param list<numeric-string>|numeric-string $id
*/
- private function setItemAsUnread(string $id): int|false {
+ private function setItemAsUnread(array|string $id): int|false {
return $this->entryDAO->markRead($id, false);
}
/**
- * @param numeric-string $id
+ * @param list<numeric-string>|numeric-string $id
*/
- private function setItemAsSaved(string $id): int|false {
+ private function setItemAsSaved(array|string $id): int|false {
return $this->entryDAO->markFavorite($id, true);
}
/**
- * @param numeric-string $id
+ * @param list<numeric-string>|numeric-string $id
*/
- private function setItemAsUnsaved(string $id): int|false {
+ private function setItemAsUnsaved(array|string $id): int|false {
return $this->entryDAO->markFavorite($id, false);
}
@@ -473,12 +482,15 @@ final class FeverAPI
$since_id = '';
if (is_string($_REQUEST['feed_ids'] ?? null)) {
- $feed_ids = explode(',', $_REQUEST['feed_ids']);
+ $feed_ids = array_filter(explode(',', $_REQUEST['feed_ids']), 'ctype_digit');
} elseif (is_string($_REQUEST['group_ids'] ?? null)) {
$categoryDAO = FreshRSS_Factory::createCategoryDao();
$group_ids = explode(',', $_REQUEST['group_ids']);
$feeds = [];
foreach ($group_ids as $id) {
+ if (!is_numeric($id)) {
+ continue;
+ }
$category = $categoryDAO->searchById((int)$id); //TODO: Transform to SQL query without loop! Consider FreshRSS_CategoryDAO::listCategories(true)
if ($category === null) {
continue;
@@ -500,7 +512,7 @@ final class FeverAPI
$max_id = '';
}
} elseif (is_string($_REQUEST['with_ids'] ?? null)) {
- $entry_ids = explode(',', $_REQUEST['with_ids']);
+ $entry_ids = array_filter(explode(',', $_REQUEST['with_ids']), 'ctype_digit');
} elseif (is_string($_REQUEST['since_id'] ?? null)) {
// use the since_id argument to request the next $item_limit items
$since_id = $_REQUEST['since_id'];