From f2b74a0ba1e762185b82e92379ce9e7366230c1e Mon Sep 17 00:00:00 2001 From: anoy Date: Mon, 1 Feb 2021 21:15:30 +0100 Subject: fix item purger for PostgreSQL Signed-off-by: anoy --- CHANGELOG.md | 1 + lib/Db/ItemMapperV2.php | 20 +++++++++++++++----- lib/Db/NewsMapperV2.php | 7 +++++++ 3 files changed, 23 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 31bb4e35a..9f3b7a83b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ The format is almost based on [Keep a Changelog](https://keepachangelog.com/en/1 ### Changed ### Fixed +- Item purger does not work with PostgreSQL (#1094) ## [15.2.0-rc1] - 2021-01-31 diff --git a/lib/Db/ItemMapperV2.php b/lib/Db/ItemMapperV2.php index 256621815..9b69cc9f2 100644 --- a/lib/Db/ItemMapperV2.php +++ b/lib/Db/ItemMapperV2.php @@ -149,7 +149,8 @@ class ItemMapperV2 extends NewsMapperV2 public function deleteOverThreshold(int $threshold, bool $removeUnread = false): ?int { $feedQb = $this->db->getQueryBuilder(); - $feedQb->addSelect('feed_id', $feedQb->func()->count('*', 'itemCount'), 'feeds.articles_per_update') + $feedQb->select('feed_id', $feedQb->func()->count('*', 'itemCount')) + ->addSelect($feedQb->func()->max('feeds.articles_per_update', 'articlesPerUpdate')) ->from($this->tableName, 'items') ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') ->groupBy('feed_id'); @@ -165,11 +166,11 @@ class ItemMapperV2 extends NewsMapperV2 $rangeQuery->select('id') ->from($this->tableName) ->where('feed_id = :feedId') - ->andWhere('starred = 0') + ->andWhere('starred = false') ->orderBy('updated_date', 'DESC'); if ($removeUnread === false) { - $rangeQuery->andWhere('unread = 0'); + $rangeQuery->andWhere('unread = false'); } $total_items = []; @@ -178,7 +179,7 @@ class ItemMapperV2 extends NewsMapperV2 continue; } - $rangeQuery->setFirstResult(max($threshold, $feed['articles_per_update'])); + $rangeQuery->setFirstResult(max($threshold, $feed['articlesPerUpdate'])); $items = $this->db->executeQuery($rangeQuery->getSQL(), ['feedId' => $feed['feed_id']]) ->fetchAll(FetchMode::COLUMN); @@ -190,7 +191,16 @@ class ItemMapperV2 extends NewsMapperV2 $deleteQb->delete($this->tableName) ->where('id IN (?)'); - return $this->db->executeUpdate($deleteQb->getSQL(), [$total_items], [IQueryBuilder::PARAM_INT_ARRAY]); + $affected_rows = 0; + // split $total_items into multiple chunks because of the parameter limit + foreach (array_chunk($total_items, NewsMapperV2::PDO_PARAMS_LIMIT) as $items_chunk) { + $affected_rows += $this->db->executeUpdate( + $deleteQb->getSQL(), + [$items_chunk], + [IQueryBuilder::PARAM_INT_ARRAY] + ); + } + return $affected_rows; } /** diff --git a/lib/Db/NewsMapperV2.php b/lib/Db/NewsMapperV2.php index f7179574c..b33266f8b 100644 --- a/lib/Db/NewsMapperV2.php +++ b/lib/Db/NewsMapperV2.php @@ -34,6 +34,13 @@ abstract class NewsMapperV2 extends QBMapper */ const TABLE_NAME = null; + /** + * Maximum number of prepared parameters that PDO can handle + * + * @var int + */ + const PDO_PARAMS_LIMIT = 65535; + /** * @var Time */ -- cgit v1.2.3