[CORE][DATABASE] Another approach to semi-join in the inboxnoticestream query

Compared to the solution with INNER JOIN this seems to have better performance
as there is no need to deduplicate the subquery result before use.
This commit is contained in:
Alexei Sorokin 2020-06-10 14:21:47 +03:00 committed by Diogo Peralta Cordeiro
parent ed4cc01b2f
commit a93c38a9af
1 changed files with 14 additions and 11 deletions

View File

@ -93,22 +93,25 @@ class RawInboxNoticeStream extends FullNoticeStream
// Subscription:: is a table of subscriptions (every user is subscribed to themselves)
$notice->_join .= sprintf(
"\n" . <<<'END'
INNER JOIN (
(SELECT id FROM notice
WHERE profile_id
IN (SELECT subscribed FROM subscription WHERE subscriber = %1$d))
UNION
(SELECT notice_id AS id FROM reply WHERE profile_id = %1$d)
UNION
(SELECT notice_id AS id FROM attention WHERE profile_id = %1$d)
UNION
(SELECT notice_id AS id FROM group_inbox INNER JOIN group_member USING (group_id)
WHERE group_member.profile_id = %1$d)
LEFT JOIN (
SELECT notice.id
FROM notice INNER JOIN subscription
ON notice.profile_id = subscription.subscribed
WHERE subscription.subscriber = %1$d
UNION ALL
SELECT notice_id AS id FROM reply WHERE profile_id = %1$d
UNION ALL
SELECT notice_id AS id FROM attention WHERE profile_id = %1$d
UNION ALL
SELECT notice_id AS id FROM group_inbox INNER JOIN group_member USING (group_id)
WHERE group_member.profile_id = %1$d
) AS t1 USING (id)
END,
$this->target->getID()
);
$notice->whereAdd('t1.id IS NOT NULL');
$notice->whereAdd(sprintf(
"notice.created > TIMESTAMP '%s'",
$notice->escape($this->target->created)