From 2c9e1f6591215ed255d3a86e4f0596ebc02b64a4 Mon Sep 17 00:00:00 2001 From: Sean Molenaar Date: Sat, 19 Mar 2022 17:25:09 +0100 Subject: [PATCH] Chore: split user data from feed data Signed-off-by: Sean Molenaar --- AUTHORS.md | 1 + CHANGELOG.md | 1 + lib/Db/FeedMapperV2.php | 20 +-- lib/Db/FolderMapperV2.php | 6 +- lib/Db/ItemMapperV2.php | 26 ++-- lib/Db/NewsMapperV2.php | 5 +- .../Version160100Date20210821130702.php | 141 ++++++++++++++++++ tests/Unit/Db/ItemMapperPaginatedTest.php | 113 ++++++++------ tests/Unit/Db/ItemMapperTest.php | 27 ++-- 9 files changed, 251 insertions(+), 89 deletions(-) create mode 100644 lib/Migration/Version160100Date20210821130702.php diff --git a/AUTHORS.md b/AUTHORS.md index 7ac9408e14..4e305b9edf 100644 --- a/AUTHORS.md +++ b/AUTHORS.md @@ -175,6 +175,7 @@ * [markusj](mailto:markusj@users.noreply.github.com) * [mnassabain](mailto:34754819+mnassabain@users.noreply.github.com) * [mormegil](mailto:mormegil@centrum.cz) +* [nextcloud486153](mailto:78801830+nextcloud486153@users.noreply.github.com) * [nexus-uw](mailto:you@example.com) * [repat](mailto:repat@repat.de) * [ritchiewilson](mailto:rawilson52@gmail.com) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8428e94156..890b503597 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ The format is mostly based on [Keep a Changelog](https://keepachangelog.com/en/1 # Unreleased ## [18.x.x] ### Changed +- Split user data out of feed fields for de-duplication ### Fixed diff --git a/lib/Db/FeedMapperV2.php b/lib/Db/FeedMapperV2.php index bab170f792..688e99f143 100644 --- a/lib/Db/FeedMapperV2.php +++ b/lib/Db/FeedMapperV2.php @@ -29,6 +29,7 @@ class FeedMapperV2 extends NewsMapperV2 { const TABLE_NAME = 'news_feeds'; + const USER_TABLE_NAME = 'news_user_feeds'; /** * FeedMapper constructor. @@ -38,7 +39,7 @@ class FeedMapperV2 extends NewsMapperV2 */ public function __construct(IDBConnection $db, Time $time) { - parent::__construct($db, $time, Feed::class); + parent::__construct($db, $time, Feed::class, self::USER_TABLE_NAME); } /** @@ -53,7 +54,7 @@ public function findAllFromUser(string $userId, array $params = []): array { $builder = $this->db->getQueryBuilder(); $builder->select('feeds.*', $builder->func()->count('items.id', 'unreadCount')) - ->from(static::TABLE_NAME, 'feeds') + ->from(static::USER_TABLE_NAME, 'feeds') ->leftJoin( 'feeds', ItemMapperV2::TABLE_NAME, @@ -84,7 +85,7 @@ public function findFromUser(string $userId, int $id): Entity { $builder = $this->db->getQueryBuilder(); $builder->select('*') - ->from(static::TABLE_NAME) + ->from(static::USER_TABLE_NAME) ->where('user_id = :user_id') ->andWhere('id = :id') ->setParameter('user_id', $userId) @@ -102,7 +103,7 @@ public function findAll(): array { $builder = $this->db->getQueryBuilder(); $builder->select('*') - ->from(static::TABLE_NAME) + ->from(static::USER_TABLE_NAME) ->where('deleted_at = 0'); return $this->findEntities($builder); @@ -123,7 +124,8 @@ public function findByURL(string $userId, string $url): Entity { $builder = $this->db->getQueryBuilder(); $builder->select('*') - ->from(static::TABLE_NAME) + ->from(static::TABLE_NAME, 'feeds') + ->innerJoin('feeds', self::USER_TABLE_NAME, 'users', 'feeds.id = users.feed_id') ->where('user_id = :user_id') ->andWhere('url = :url') ->setParameter('user_id', $userId) @@ -143,7 +145,7 @@ public function findAllFromFolder(?int $id): array { $builder = $this->db->getQueryBuilder(); $builder->select('*') - ->from(static::TABLE_NAME); + ->from(static::USER_TABLE_NAME); if (is_null($id)) { $builder->where('folder_id IS NULL'); @@ -168,8 +170,8 @@ public function read(string $userId, int $id, ?int $maxItemID = null): int { $idBuilder = $this->db->getQueryBuilder(); $idBuilder->select('items.id') - ->from(ItemMapperV2::TABLE_NAME, 'items') - ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') + ->from(ItemMapperV2::USER_TABLE_NAME, 'items') + ->innerJoin('items', FeedMapperV2::USER_TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') ->andWhere('feeds.user_id = :userId') ->andWhere('feeds.id = :feedId') ->setParameter('userId', $userId) @@ -188,7 +190,7 @@ function ($value): int { ); $builder = $this->db->getQueryBuilder(); - $builder->update(ItemMapperV2::TABLE_NAME) + $builder->update(ItemMapperV2::USER_TABLE_NAME) ->set('unread', $builder->createParameter('unread')) ->andWhere('id IN (:idList)') ->andWhere('unread != :unread') diff --git a/lib/Db/FolderMapperV2.php b/lib/Db/FolderMapperV2.php index ea2edee91d..0c30ed7eab 100644 --- a/lib/Db/FolderMapperV2.php +++ b/lib/Db/FolderMapperV2.php @@ -112,8 +112,8 @@ public function read(string $userId, int $id, ?int $maxItemId = null): int { $idBuilder = $this->db->getQueryBuilder(); $idBuilder->select('items.id') - ->from(ItemMapperV2::TABLE_NAME, 'items') - ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') + ->from(ItemMapperV2::USER_TABLE_NAME, 'items') + ->innerJoin('items', FeedMapperV2::USER_TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') ->andWhere('feeds.user_id = :userId') ->andWhere('feeds.folder_id = :folderId') ->setParameter('userId', $userId) @@ -129,7 +129,7 @@ public function read(string $userId, int $id, ?int $maxItemId = null): int }, $this->db->executeQuery($idBuilder->getSQL(), $idBuilder->getParameters())->fetchAll()); $builder = $this->db->getQueryBuilder(); - $builder->update(ItemMapperV2::TABLE_NAME) + $builder->update(ItemMapperV2::USER_TABLE_NAME) ->set('unread', $builder->createParameter('unread')) ->andWhere('id IN (:idList)') ->andWhere('unread != :unread') diff --git a/lib/Db/ItemMapperV2.php b/lib/Db/ItemMapperV2.php index 8a92354d80..08894a1faa 100644 --- a/lib/Db/ItemMapperV2.php +++ b/lib/Db/ItemMapperV2.php @@ -31,6 +31,7 @@ class ItemMapperV2 extends NewsMapperV2 { const TABLE_NAME = 'news_items'; + const USER_TABLE_NAME = 'news_user_items'; /** * ItemMapper constructor. @@ -40,7 +41,7 @@ class ItemMapperV2 extends NewsMapperV2 */ public function __construct(IDBConnection $db, Time $time) { - parent::__construct($db, $time, Item::class); + parent::__construct($db, $time, Item::class, self::USER_TABLE_NAME); } /** @@ -56,9 +57,8 @@ public function findAllFromUser(string $userId, array $params = []): array $builder = $this->db->getQueryBuilder(); $builder->select('items.*') ->from($this->tableName, 'items') - ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') - ->where('feeds.user_id = :user_id') - ->andWhere('feeds.deleted_at = 0') + ->innerJoin('items', self::USER_TABLE_NAME, 'users', 'items.id = users.item_id') + ->where('users.user_id = :user_id') ->setParameter('user_id', $userId, IQueryBuilder::PARAM_STR); foreach ($params as $key => $value) { @@ -92,10 +92,9 @@ public function findFromUser(string $userId, int $id): Entity $builder = $this->db->getQueryBuilder(); $builder->select('items.*') ->from($this->tableName, 'items') - ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') - ->where('feeds.user_id = :user_id') + ->innerJoin('items', self::USER_TABLE_NAME, 'users', 'items.id = users.item_id') + ->where('users.user_id = :user_id') ->andWhere('items.id = :item_id') - ->andWhere('feeds.deleted_at = 0') ->setParameter('user_id', $userId, IQueryBuilder::PARAM_STR) ->setParameter('item_id', $id, IQueryBuilder::PARAM_INT); @@ -444,9 +443,10 @@ public function findAllFeed( ): array { $builder = $this->db->getQueryBuilder(); - $builder->select('items.*') + $builder->select('items.*', 'users.unread', 'users.starred', 'users.shared_by') ->from($this->tableName, 'items') ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') + ->innerJoin('items', self::USER_TABLE_NAME, 'users', 'items.id = users.item_id') ->andWhere('feeds.deleted_at = 0') ->andWhere('feeds.user_id = :userId') ->andWhere('items.feed_id = :feedId') @@ -501,9 +501,10 @@ public function findAllFolder( $folderWhere = $builder->expr()->eq('feeds.folder_id', new Literal($folderId), IQueryBuilder::PARAM_INT); } - $builder->select('items.*') + $builder->select('items.*', 'users.unread', 'users.starred', 'users.shared_by') ->from($this->tableName, 'items') ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') + ->innerJoin('items', self::USER_TABLE_NAME, 'users', 'items.id = users.item_id') ->andWhere('feeds.user_id = :userId') ->andWhere('feeds.deleted_at = 0') ->andWhere($folderWhere) @@ -550,11 +551,10 @@ public function findAllItems( ): array { $builder = $this->db->getQueryBuilder(); - $builder->select('items.*') + $builder->select('items.*', 'users.unread', 'users.starred', 'users.shared_by') ->from($this->tableName, 'items') - ->innerJoin('items', FeedMapperV2::TABLE_NAME, 'feeds', 'items.feed_id = feeds.id') - ->andWhere('feeds.user_id = :userId') - ->andWhere('feeds.deleted_at = 0') + ->innerJoin('items', self::USER_TABLE_NAME, 'users', 'items.id = users.item_id') + ->andWhere('users.user_id = :userId') ->setParameter('userId', $userId) ->addOrderBy('items.id', ($oldestFirst ? 'ASC' : 'DESC')); diff --git a/lib/Db/NewsMapperV2.php b/lib/Db/NewsMapperV2.php index b33266f8b5..9500fec998 100644 --- a/lib/Db/NewsMapperV2.php +++ b/lib/Db/NewsMapperV2.php @@ -56,9 +56,10 @@ abstract class NewsMapperV2 extends QBMapper public function __construct( IDBConnection $db, Time $time, - string $entity + string $entity, + ?string $table = null ) { - parent::__construct($db, static::TABLE_NAME, $entity); + parent::__construct($db, $table ?? static::TABLE_NAME, $entity); $this->time = $time; } diff --git a/lib/Migration/Version160100Date20210821130702.php b/lib/Migration/Version160100Date20210821130702.php new file mode 100644 index 0000000000..6ed600672e --- /dev/null +++ b/lib/Migration/Version160100Date20210821130702.php @@ -0,0 +1,141 @@ +connection = $connection; + } + + /** + * @param IOutput $output + * @param Closure $schemaClosure The `\Closure` returns a `ISchemaWrapper` + * @param array $options + */ + public function preSchemaChange(IOutput $output, Closure $schemaClosure, array $options): void { + } + + /** + * @param IOutput $output + * @param Closure $schemaClosure The `\Closure` returns a `ISchemaWrapper` + * @param array $options + * @return null|ISchemaWrapper + */ + public function changeSchema(IOutput $output, Closure $schemaClosure, array $options): ?ISchemaWrapper { + /** @var ISchemaWrapper $schema */ + $schema = $schemaClosure(); + + if (!$schema->hasTable('news_user_items')) { + $table = $schema->createTable('news_user_items'); + $table->addColumn('item_id', 'bigint', [ + 'notnull' => true, + 'length' => 8, + 'unsigned' => true, + ]); + $table->addColumn('user_id', 'string', [ + 'notnull' => true, + 'length' => 64, + ]); + $table->addColumn('unread', 'boolean', [ + 'notnull' => true, + 'default' => false, + ]); + $table->addColumn('starred', 'boolean', [ + 'notnull' => true, + 'default' => false, + ]); + $table->addColumn('last_modified', 'bigint', [ + 'notnull' => false, + 'length' => 8, + 'default' => 0, + 'unsigned' => true, + ]); + $table->addColumn('shared_by', 'string', [ + 'notnull' => false, + 'length' => 64 + ]); + $table->setPrimaryKey(['item_id', 'user_id']); + } + + if (!$schema->hasTable('news_user_feeds')) { + $table = $schema->createTable('news_user_feeds'); + $table->addColumn('feed_id', 'bigint', [ + 'notnull' => true, + 'length' => 8, + 'unsigned' => true, + ]); + $table->addColumn('user_id', 'string', [ + 'notnull' => true, + 'length' => 64, + ]); + $table->addColumn('folder_id', 'bigint', [ + 'notnull' => false, + 'length' => 8, + ]); + $table->addColumn('deleted_at', 'bigint', [ + 'notnull' => false, + 'length' => 8, + 'default' => 0, + 'unsigned' => true, + ]); + $table->addColumn('added', 'bigint', [ + 'notnull' => false, + 'length' => 8, + 'default' => 0, + 'unsigned' => true, + ]); + $table->addColumn('title', 'text', [ + 'notnull' => true, + ]); + $table->addColumn('last_modified', 'bigint', [ + 'notnull' => false, + 'length' => 8, + 'default' => 0, + 'unsigned' => true, + ]); + $table->setPrimaryKey(['feed_id', 'user_id']); + } + + return $schema; + } + + /** + * @param IOutput $output + * @param Closure $schemaClosure The `\Closure` returns a `ISchemaWrapper` + * @param array $options + */ + public function postSchemaChange(IOutput $output, Closure $schemaClosure, array $options): void { + $qb = $this->connection->getQueryBuilder(); + $user_item_table = $qb->getTableName('news_user_items'); + $user_feed_table = $qb->getTableName('news_user_feeds'); + $item_table = $qb->getTableName('news_items'); + $feed_table = $qb->getTableName('news_feeds'); + + $items_query = "REPLACE INTO $user_item_table SELECT id AS 'item_id', ? AS 'user_id',`unread`,`starred`,`last_modified`,`shared_by` FROM $item_table where feed_id = ?;"; + + $feeds = $this->connection->executeQuery("SELECT `id`,`user_id` FROM $feed_table;")->fetchAll(); + foreach ($feeds as $feed) { + $this->connection->executeUpdate($items_query, [$feed['user_id'], $feed['id']]); + } + + $this->connection->executeUpdate("REPLACE INTO $user_feed_table SELECT id AS 'feed_id',user_id,folder_id,deleted_at,added,title,last_modified FROM $feed_table;"); + } +} diff --git a/tests/Unit/Db/ItemMapperPaginatedTest.php b/tests/Unit/Db/ItemMapperPaginatedTest.php index 9d44e0756e..f25f19b306 100644 --- a/tests/Unit/Db/ItemMapperPaginatedTest.php +++ b/tests/Unit/Db/ItemMapperPaginatedTest.php @@ -64,15 +64,13 @@ public function testFindAllItemsInvalid() $this->builder->expects($this->exactly(1)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive(['items', 'news_user_items', 'users', 'items.id = users.item_id']) ->will($this->returnSelf()); - $this->builder->expects($this->exactly(3)) + $this->builder->expects($this->exactly(2)) ->method('andWhere') ->withConsecutive( - ['feeds.user_id = :userId'], - ['feeds.deleted_at = 0'] - ) + ['users.user_id = :userId']) ->will($this->returnSelf()); $this->builder->expects($this->exactly(2)) @@ -129,14 +127,13 @@ public function testFindAllItemsFullInverted() $this->builder->expects($this->exactly(1)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive(['items', 'news_user_items', 'users', 'items.id = users.item_id']) ->will($this->returnSelf()); - $this->builder->expects($this->exactly(3)) + $this->builder->expects($this->exactly(2)) ->method('andWhere') ->withConsecutive( - ['feeds.user_id = :userId'], - ['feeds.deleted_at = 0'], + ['users.user_id = :userId'], ['items.id > :offset'] ) ->will($this->returnSelf()); @@ -196,14 +193,13 @@ public function testFindAllItemsUnread() $this->builder->expects($this->exactly(1)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive(['items', 'news_user_items', 'users', 'items.id = users.item_id']) ->will($this->returnSelf()); - $this->builder->expects($this->exactly(4)) + $this->builder->expects($this->exactly(3)) ->method('andWhere') ->withConsecutive( - ['feeds.user_id = :userId'], - ['feeds.deleted_at = 0'], + ['users.user_id = :userId'], ['items.id < :offset'], ['items.unread = :unread'] ) @@ -267,14 +263,13 @@ public function testFindAllItemsUnreadNoLimit() $this->builder->expects($this->exactly(1)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive(['items', 'news_user_items', 'users', 'items.id = users.item_id']) ->will($this->returnSelf()); - $this->builder->expects($this->exactly(4)) + $this->builder->expects($this->exactly(3)) ->method('andWhere') ->withConsecutive( - ['feeds.user_id = :userId'], - ['feeds.deleted_at = 0'], + ['users.user_id = :userId'], ['items.id < :offset'], ['items.unread = :unread'] ) @@ -336,14 +331,13 @@ public function testFindAllItemsStarred() $this->builder->expects($this->exactly(1)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive(['items', 'news_user_items', 'users', 'items.id = users.item_id']) ->will($this->returnSelf()); - $this->builder->expects($this->exactly(4)) + $this->builder->expects($this->exactly(3)) ->method('andWhere') ->withConsecutive( - ['feeds.user_id = :userId'], - ['feeds.deleted_at = 0'], + ['users.user_id = :userId'], ['items.id < :offset'], ['items.starred = :starred'] ) @@ -411,14 +405,13 @@ public function testFindAllItemsStarredSearch() $this->builder->expects($this->exactly(1)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive(['items', 'news_user_items', 'users', 'items.id = users.item_id']) ->will($this->returnSelf()); - $this->builder->expects($this->exactly(6)) + $this->builder->expects($this->exactly(5)) ->method('andWhere') ->withConsecutive( - ['feeds.user_id = :userId'], - ['feeds.deleted_at = 0'], + ['users.user_id = :userId'], ['items.id < :offset'], ['items.search_index LIKE :term0'], ['items.search_index LIKE :term1'], @@ -490,9 +483,12 @@ public function testFindAllFeed() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(4)) @@ -563,9 +559,12 @@ public function testFindAllFeedNoLimit() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(4)) @@ -634,9 +633,12 @@ public function testFindAllFeedInverted() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(4)) @@ -705,9 +707,12 @@ public function testFindAllFeedHideRead() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(5)) @@ -782,9 +787,12 @@ public function testFindAllFeedSearch() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(6)) @@ -875,9 +883,12 @@ public function testFindAllFolderIdNull() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(4)) @@ -960,9 +971,12 @@ public function testFindAllFolderIdNullNoLimit() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(4)) @@ -1043,9 +1057,12 @@ public function testFindAllFolderHideRead() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(5)) @@ -1129,9 +1146,12 @@ public function testFindAllFolderHideReadInvertOrder() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(5)) @@ -1218,9 +1238,12 @@ public function testFindAllFolderSearchId() ->with('news_items', 'items') ->will($this->returnSelf()); - $this->builder->expects($this->exactly(1)) + $this->builder->expects($this->exactly(2)) ->method('innerJoin') - ->withConsecutive(['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id']) + ->withConsecutive( + ['items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id'], + ['items', 'news_user_items', 'users', 'items.id = users.item_id'] + ) ->will($this->returnSelf()); $this->builder->expects($this->exactly(6)) diff --git a/tests/Unit/Db/ItemMapperTest.php b/tests/Unit/Db/ItemMapperTest.php index 7fc45018e2..5a9241a5eb 100644 --- a/tests/Unit/Db/ItemMapperTest.php +++ b/tests/Unit/Db/ItemMapperTest.php @@ -88,17 +88,15 @@ public function testFindAllFromUser() $this->builder->expects($this->once()) ->method('innerJoin') - ->with('items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id') + ->withConsecutive( + ['items', 'news_user_items', 'users', 'items.id = users.item_id'], + ['a', 'a', 'a', 'a'] + ) ->will($this->returnSelf()); $this->builder->expects($this->once()) ->method('where') - ->with('feeds.user_id = :user_id') - ->will($this->returnSelf()); - - $this->builder->expects($this->once()) - ->method('andWhere') - ->with('feeds.deleted_at = 0') + ->with('users.user_id = :user_id') ->will($this->returnSelf()); $this->builder->expects($this->exactly(1)) @@ -149,17 +147,12 @@ public function testFindAllFromUserWithParams() $this->builder->expects($this->once()) ->method('innerJoin') - ->with('items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id') + ->with('items', 'news_user_items', 'users', 'items.id = users.item_id') ->will($this->returnSelf()); $this->builder->expects($this->once()) ->method('where') - ->with('feeds.user_id = :user_id') - ->will($this->returnSelf()); - - $this->builder->expects($this->exactly(2)) - ->method('andWhere') - ->withConsecutive(['feeds.deleted_at = 0'], ['key = :val']) + ->with('users.user_id = :user_id') ->will($this->returnSelf()); $this->builder->expects($this->exactly(1)) @@ -291,17 +284,17 @@ public function testFindFromUser() $this->builder->expects($this->once()) ->method('innerJoin') - ->with('items', 'news_feeds', 'feeds', 'items.feed_id = feeds.id') + ->with('items', 'news_user_items', 'users', 'items.id = users.item_id') ->will($this->returnSelf()); $this->builder->expects($this->once()) ->method('where') - ->with('feeds.user_id = :user_id') + ->with('users.user_id = :user_id') ->will($this->returnSelf()); $this->builder->expects($this->exactly(2)) ->method('andWhere') - ->withConsecutive(['items.id = :item_id'], ['feeds.deleted_at = 0']) + ->withConsecutive(['items.id = :item_id'], ['users.deleted_at = 0']) ->will($this->returnSelf()); $this->builder->expects($this->exactly(2))